api #

blog software from scratch with SvelteKit

13 modules ยท 36 declarations

Modules
#

blog_feed_context
#

blog.ts view source

{ get: (error_message?: string | undefined) => { title: string; id: string; description: string; home_page_url: string; icon: string; favicon: string; author: { name: string; url?: string | undefined; email?: string | undefined; }; atom: { ...; }; items: { ...; }[]; }; get_maybe: () => { ...; } | undefined; set: (va... import {blog_feed_context} from '@fuzdev/fuz_blog/blog.js';

BlogComments
#

blog.ts view source

ZodObject<{ url: ZodString; type: ZodLiteral<"mastodon">; }, $strict> import type {BlogComments} from '@fuzdev/fuz_blog/blog.js';

BlogConfig
#

blog.ts view source

BlogConfig import type {BlogConfig} from '@fuzdev/fuz_blog/blog.js';

A single blog's configuration in the consumer's src/routes/blogs.ts registry.

dirname

Route directory under src/routes, and the blog's base path segment.

type string

feed

Feed-level metadata. Post URLs derive from home_page_url, so set it to the blog's index page.

type BlogFeedMetadata

slug_routes?

Generate a slug redirect route for each post. When false, post URLs are the integer id paths.

type boolean

default true

scaffold?

Customizes the post file gro post scaffolds for this blog. Defaults to scaffold_blog_post.

type (options: BlogPostScaffoldOptions) => string

BlogFeed
#

blog.ts view source

ZodObject<{ title: ZodString; id: ZodString; description: ZodString; home_page_url: ZodURL; icon: ZodURL; favicon: ZodURL; author: ZodObject<{ ...; }, $strict>; atom: ZodObject<...>; items: ZodArray<...>; }, $strict> import type {BlogFeed} from '@fuzdev/fuz_blog/blog.js';

BlogFeedItem
#

blog.ts view source

ZodObject<{ tags: ZodArray<ZodString>; title: ZodString; slug: ZodString; date_published: ZodISODateTime; date_modified: ZodISODateTime; ... 5 more ...; blog_post_id: ZodNumber; }, $strict> import type {BlogFeedItem} from '@fuzdev/fuz_blog/blog.js';

A feed entry, derived from a BlogPostMetadata by resolve_blog_feed_item. Strict, so a leaked consumer field fails the generated feed's validation.

BlogFeedMetadata
#

blog.ts view source

ZodObject<{ title: ZodString; id: ZodString; description: ZodString; home_page_url: ZodURL; icon: ZodURL; favicon: ZodURL; author: ZodObject<{ ...; }, $strict>; atom: ZodObject<...>; }, $strict> import type {BlogFeedMetadata} from '@fuzdev/fuz_blog/blog.js';

A feed's metadata, without its items.

BlogPost
#

BlogPost.svelte view source

accepts children

import BlogPost from '@fuzdev/fuz_blog/BlogPost.svelte';

post

type { [x: string]: unknown; title: string; slug: string; date_published: string; date_modified: string; summary: string; tags?: string[] | undefined; comments?: { url: string; type: "mastodon"; } | undefined; }

item?

The resolved feed item. Defaults to looking post.slug up in blog_feed_context; pass it explicitly to skip the context.

type { tags: string[]; title: string; slug: string; date_published: string; date_modified: string; summary: string; id: string; url: string; pathname: string; blog_post_id: number; comments?: { url: string; type: "mastodon"; } | undefined; }
optional

attrs?

type HTMLAttributes<HTMLElement>
optional

meta?

Renders after BlogPostHeader, e.g. for post provenance.

type Snippet<[item: { tags: string[]; title: string; slug: string; date_published: string; date_modified: string; summary: string; id: string; url: string; pathname: string; blog_post_id: number; comments?: { url: string; type: "mastodon"; } | undefined; }]>
optional
snippet parameters
item { tags: string[]; title: string; slug: string; date_published: string; date_modified: string; summary: string; id: string; url: string; pathname: string; blog_post_id: number; comments?: { url: string; type: "mastodon"; } | undefined; }

footer?

type Snippet<[]>
optional

comments?

Renders after footer, usually with BlogPostComments. Importing BlogPostComments.svelte is what opts into the @fuzdev/fuz_mastodon peer dependency.

type Snippet<[item: { tags: string[]; title: string; slug: string; date_published: string; date_modified: string; summary: string; id: string; url: string; pathname: string; blog_post_id: number; comments?: { url: string; type: "mastodon"; } | undefined; }]>
optional
snippet parameters
item { tags: string[]; title: string; slug: string; date_published: string; date_modified: string; summary: string; id: string; url: string; pathname: string; blog_post_id: number; comments?: { url: string; type: "mastodon"; } | undefined; }

children

type Snippet<[]>

BlogPostComments
#

BlogPostComments.svelte view source

import BlogPostComments from '@fuzdev/fuz_blog/BlogPostComments.svelte';

item

type { tags: string[]; title: string; slug: string; date_published: string; date_modified: string; summary: string; id: string; url: string; pathname: string; blog_post_id: number; comments?: { url: string; type: "mastodon"; } | undefined; }

separator?

type Snippet<[]>
optional default default_separator

BlogPostHeader
#

BlogPostHeader.svelte view source

import BlogPostHeader from '@fuzdev/fuz_blog/BlogPostHeader.svelte';

item

type { tags: string[]; title: string; slug: string; date_published: string; date_modified: string; summary: string; id: string; url: string; pathname: string; blog_post_id: number; comments?: { url: string; type: "mastodon"; } | undefined; }

BlogPostId
#

blog.ts view source

BlogPostId import type {BlogPostId} from '@fuzdev/fuz_blog/blog.js';

intersects

Flavored<number, 'BlogPostId'>

BlogPostList
#

BlogPostList.svelte view source

import BlogPostList from '@fuzdev/fuz_blog/BlogPostList.svelte';

feed

type { title: string; id: string; description: string; home_page_url: string; icon: string; favicon: string; author: { name: string; url?: string | undefined; email?: string | undefined; }; atom: { feed_url: string; }; items: { ...; }[]; }

BlogPostMetadata
#

blog.ts view source

ZodObject<{ title: ZodString; slug: ZodString; date_published: ZodISODateTime; date_modified: ZodISODateTime; summary: ZodString; tags: ZodOptional<...>; comments: ZodOptional<...>; }, $loose> import type {BlogPostMetadata} from '@fuzdev/fuz_blog/blog.js';

The author-defined metadata for each post. Loose so a consumer can add its own fields (e.g. an autoblog's model); the extras stay on the page's post and do not reach the generated BlogFeed (see resolve_blog_feed_item).

BlogPostModule
#

BlogPostScaffoldOptions
#

blog.ts view source

BlogPostScaffoldOptions import type {BlogPostScaffoldOptions} from '@fuzdev/fuz_blog/blog.js';

The options gro post passes to a BlogConfig scaffold.

title

type string

slug

type string

date

Used for both date_published and date_modified.

type string

fuz_blog_import_path

Import specifier for fuz_blog modules - $lib inside fuz_blog itself, @fuzdev/fuz_blog in consumers.

type string

BlogsModule
#

blog.ts view source

BlogsModule import type {BlogsModule} from '@fuzdev/fuz_blog/blog.js';

The shape of the consumer's src/routes/blogs.ts module.

blogs

type Array<BlogConfig>

collect_blog_post_ids
#

blog_helpers.ts view source

(blog_dir: string): BlogPostId[] import {collect_blog_post_ids} from '@fuzdev/fuz_blog/blog_helpers.js';

Returns an array of all of the sequential blog post ids starting with 1. When it fails to find the next id, the sequence ends.

blog_dir

type string

returns

BlogPostId[]

create_atom_feed
#

feed.ts view source

(data: { id: string; title: string; home_page_url: string; description: string; icon: string; favicon: string; author: { name: string; url?: string | undefined; email?: string | undefined; }; items: { ...; }[]; atom: { ...; }; }): string import {create_atom_feed} from '@fuzdev/fuz_blog/feed.js';

data

type { id: string; title: string; home_page_url: string; description: string; icon: string; favicon: string; author: { name: string; url?: string | undefined; email?: string | undefined; }; items: { id: string; ... 5 more ...; tags?: string[] | undefined; }[]; atom: { ...; }; }

returns

string

create_blog_post
#

blog_helpers.ts view source

(options: CreateBlogPostOptions): Promise<CreatedBlogPost> import {create_blog_post} from '@fuzdev/fuz_blog/blog_helpers.js';

Scaffolds and writes the next post file for config, returning its id, path, and slug. Does not run gen - callers invoke that afterward (see post.task.ts).

options

returns

Promise<CreatedBlogPost>

CreateBlogPostOptions
#

blog_helpers.ts view source

CreateBlogPostOptions import type {CreateBlogPostOptions} from '@fuzdev/fuz_blog/blog_helpers.js';

dir

The project root, usually process.cwd().

type string

config

The target blog, e.g. from resolve_blog_config.

type BlogConfig

title

The post title; the slug is derived from it.

type string

date

ISO date used for both date_published and date_modified.

type string

fuz_blog_import_path

Import specifier for fuz_blog modules - $lib inside fuz_blog, @fuzdev/fuz_blog in consumers.

type string

scaffold?

Overrides the scaffold for this call, taking precedence over config.scaffold. Lets a consumer task close over its own args (e.g. a --model flag) without widening BlogPostScaffoldOptions.

type (options: BlogPostScaffoldOptions) => string

routes_path?

type string

default 'src/routes'

CreatedBlogPost
#

blog_helpers.ts view source

CreatedBlogPost import type {CreatedBlogPost} from '@fuzdev/fuz_blog/blog_helpers.js';

blog_post_id

type BlogPostId

path

Absolute path to the written +page.svelte.

type string

slug

type string

Feed
#

feed.ts view source

ZodObject<{ id: ZodString; title: ZodString; home_page_url: ZodURL; description: ZodString; icon: ZodURL; favicon: ZodURL; author: ZodObject<{ ...; }, $strict>; items: ZodArray<...>; atom: ZodObject<...>; }, $strict> import type {Feed} from '@fuzdev/fuz_blog/feed.js';

This is designed to extend JSON Feed 1.1 with namespaced data for other specs like Atom. It's still a work in progress, and I'll add features as I need them, and eventually this will be extracted to a standalone library. https://www.jsonfeed.org/version/1.1/

FeedItem
#

feed.ts view source

ZodObject<{ id: ZodString; title: ZodString; url: ZodURL; date_published: ZodISODateTime; date_modified: ZodISODateTime; summary: ZodString; tags: ZodOptional<...>; }, $strict> import type {FeedItem} from '@fuzdev/fuz_blog/feed.js';

FeedItemDate
#

FeedItemDate.svelte view source

import FeedItemDate from '@fuzdev/fuz_blog/FeedItemDate.svelte';

item

type { id: string; title: string; url: string; date_published: string; date_modified: string; summary: string; tags?: string[] | undefined; }

format_date
#

util.ts view source

(date: string | number | Date): string import {format_date} from '@fuzdev/fuz_blog/util.js';

date

type string | number | Date

returns

string

HashLink
#

load_blog_post_modules
#

blog_helpers.ts view source

(blog_dir: string, blog_post_ids: BlogPostId[]): Promise<BlogPostModule[]> import {load_blog_post_modules} from '@fuzdev/fuz_blog/blog_helpers.js';

blog_dir

type string

blog_post_ids

type BlogPostId[]

returns

Promise<BlogPostModule[]>

load_blogs_module
#

blog_helpers.ts view source

(dir: string): Promise<BlogsModule> import {load_blogs_module} from '@fuzdev/fuz_blog/blog_helpers.js';

Loads the consumer's src/routes/blogs.ts registry.

dir

type string

returns

Promise<BlogsModule>

MastodonBlogComments
#

blog.ts view source

ZodObject<{ url: ZodString; type: ZodLiteral<"mastodon">; }, $strict> import type {MastodonBlogComments} from '@fuzdev/fuz_blog/blog.js';

resolve_blog_config
#

blog.ts view source

(blogs: BlogConfig[], dirname: string | undefined): BlogConfig import {resolve_blog_config} from '@fuzdev/fuz_blog/blog.js';

Resolves a BlogConfig from the registry by its dirname, defaulting to the first registered blog when dirname is omitted. Throws when dirname matches no registered blog.

blogs

type BlogConfig[]

dirname

type string | undefined

returns

BlogConfig

resolve_blog_feed_item
#

blog.ts view source

(blog_post_id: BlogPostId, home_page_url: string, post: { [x: string]: unknown; title: string; slug: string; date_published: string; date_modified: string; summary: string; tags?: string[] | undefined; comments?: { ...; } | undefined; }, options?: { ...; } | undefined): { ...; } import {resolve_blog_feed_item} from '@fuzdev/fuz_blog/blog.js';

Derives a BlogFeedItem (the feed entry) from a post and its blog's home_page_url. Emits only BlogFeedItem fields - a consumer's extra post metadata stays on the page's post for its component to render, and does not leak into the typed generated feed.

blog_post_id

the post's incrementing 1-based id

home_page_url

the blog's index url, from its feed.home_page_url

type string

post

the author-defined post metadata

type { [x: string]: unknown; title: string; slug: string; date_published: string; date_modified: string; summary: string; tags?: string[] | undefined; comments?: { url: string; type: "mastodon"; } | undefined; }

options?

slug_routes: false makes url the integer-id id

type { slug_routes?: boolean | undefined; } | undefined
optional

returns

{ tags: string[]; title: string; slug: string; date_published: string; date_modified: string; summary: string; id: string; url: string; pathname: string; blog_post_id: number; comments?: { url: string; type: "mastodon"; } | undefined; }

scaffold_blog_post
#

blog_helpers.ts view source

(options: BlogPostScaffoldOptions): string import {scaffold_blog_post} from '@fuzdev/fuz_blog/blog_helpers.js';

The default post scaffold for gro post. Override per-blog with BlogConfig.scaffold.

options

returns

string

to_blog_post_path
#

blog_helpers.ts view source

(blog_dir: string, blog_post_id: BlogPostId): string import {to_blog_post_path} from '@fuzdev/fuz_blog/blog_helpers.js';

blog_dir

type string

blog_post_id

returns

string

to_next_blog_post_id
#

blog_helpers.ts view source

(blog_post_ids: BlogPostId[]): BlogPostId import {to_next_blog_post_id} from '@fuzdev/fuz_blog/blog_helpers.js';

blog_post_ids

type BlogPostId[]

returns

BlogPostId

update_blog_post
#

blog_helpers.ts view source

(options: UpdateBlogPostOptions): Promise<UpdatedBlogPost> import {update_blog_post} from '@fuzdev/fuz_blog/blog_helpers.js';

Rewrites the date_modified of an existing post file for config, returning its id and path. Does not run gen - callers invoke that afterward (see update_post.task.ts).

options

returns

Promise<UpdatedBlogPost>

UpdateBlogPostOptions
#

blog_helpers.ts view source

UpdateBlogPostOptions import type {UpdateBlogPostOptions} from '@fuzdev/fuz_blog/blog_helpers.js';

dir

The project root, usually process.cwd().

type string

config

The target blog, e.g. from resolve_blog_config.

type BlogConfig

blog_post_id

The id of the post to update.

type BlogPostId

date

ISO date written to date_modified.

type string

routes_path?

type string

default 'src/routes'

UpdatedBlogPost
#

blog_helpers.ts view source

UpdatedBlogPost import type {UpdatedBlogPost} from '@fuzdev/fuz_blog/blog_helpers.js';

blog_post_id

type BlogPostId

path

Absolute path to the updated +page.svelte.

type string