Mirror of static site repo git.pfy.ch/pfych/static
Something went wrong. Try again.
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135import { jsxAsElement as jsx } from 'web-shared/src/lib/jsx';import { TypedAttributes } from '../htmlElementTyped';import { PostJSON } from 'web-shared/src/types/postJson';import { oneDay } from './updatedAt';import { Post } from '../../../build/steps/posts/create-post-object';
type CategorisedPosts = Record<string, PostJSON[]>;const basePostsToShow = 25;
export class RecentPosts extends HTMLElement { postsToShow = basePostsToShow;
constructor() { super(); }
fetchPosts = async (): Promise<CategorisedPosts> => { const postsResponse = await fetch('posts.json'); const posts = ((await postsResponse.json()) as { posts: PostJSON[] }).posts;
return { All: posts.filter((p) => p.publishedAt), 'Updated this Month': posts .filter((p) => { return ( Math.abs( (Date.now().valueOf() - (p.updatedAt || p.publishedAt || 0)) / oneDay, ) < 30 ); }) .sort( (a, b) => (b.updatedAt || b.publishedAt || 0) - (a.updatedAt || a.publishedAt || 0), ), 'Weekly updates': posts.filter((post) => post.emoji === '๐
'), Programming: posts.filter((post) => post.emoji === '๐ป'), Photography: posts.filter((post) => ['โ๏ธ', '๐ท', '๐ค', '๐๏ธ'].includes(post.emoji as string), ), Games: posts.filter((post) => post.emoji === '๐ฎ'), Thoughts: posts.filter((post) => post.emoji === '๐ง '), Music: posts.filter((post) => post.emoji === '๐ต'), }; };
renderPostList = <T,>( selectedPostOption: keyof T, postOptions: Record<keyof T, PostJSON[]>, ) => { const posts = postOptions[selectedPostOption]; this.replaceChildren( <h2>{selectedPostOption}</h2>, <div className="postListCategories"> <span>Category:</span> {...Object.keys(postOptions).map((postOption) => ( <button className={postOption === selectedPostOption ? 'active' : ''} onclick={() => { this.postsToShow = basePostsToShow; this.renderPostList(postOption as keyof T, postOptions); }} > {postOption} </button> ))} </div>, <ul className="postsList"> {...posts.slice(0, this.postsToShow).map((post, index) => { const publishedAt = new Date(post.publishedAt || 0); const updatedAt = new Date(post.updatedAt || 0);
return ( <li> {post.emoji || '๐'} <a href={post.url.replace('https://pfy.ch', '')}> <span> <span className="date"> {publishedAt.toLocaleDateString()} -{' '} </span> {post.title.replaceAll('&', '&')} </span> </a> <updated-at index={`${index}`} date={`${updatedAt.getTime() || publishedAt.getTime()}`} /> </li> ); })} </ul>, posts.length > this.postsToShow ? ( <div> <span> showing {this.postsToShow} / {posts.length} posts - </span> <button onclick={() => { this.postsToShow += this.postsToShow; this.renderPostList(selectedPostOption, postOptions); }} > show more </button> </div> ) : ( <div> <span> showing {Math.min(this.postsToShow, posts.length)} / {posts.length}{' '} posts </span> </div> ), <br />, ); };
render = async () => { this.innerHTML = ''; this.append( <skeleton-loader width="100%" height="735px"></skeleton-loader>, );
const categorised = await this.fetchPosts(); console.log(categorised);
this.renderPostList('All', categorised); };
connectedCallback() { void this.render(); }}