casualroom/apps/fenghuo/web/lib/articles/utils.ts

96 lines
2.9 KiB
TypeScript
Executable File

import type { Article } from '@fenghuo/common';
/**
* 格式化数字显示
*/
export function formatNumber(num: number): string {
if (num >= 10000) {
return (num / 10000).toFixed(1) + 'w';
}
if (num >= 1000) {
return (num / 1000).toFixed(1) + 'k';
}
return num.toString();
}
/**
* 筛选文章
*/
export function filterArticles(
articles: Article[],
searchTerm: string,
statusFilter: string,
categoryFilter: string,
): Article[] {
return articles.filter((article) => {
const matchesSearch =
article.title.toLowerCase().includes(searchTerm.toLowerCase()) ||
article.excerpt?.toLowerCase().includes(searchTerm.toLowerCase()) ||
(article.terms ?? []).some((term) => term.name.toLowerCase().includes(searchTerm.toLowerCase()));
const matchesStatus = statusFilter === 'all' || article.status === statusFilter;
const matchesCategory =
categoryFilter === 'all' || (article.terms ?? []).some((term) => term.name === categoryFilter);
return matchesSearch && matchesStatus && matchesCategory;
});
}
/**
* 排序文章
*/
export function sortArticles(articles: Article[], sortBy: string): Article[] {
return [...articles].sort((a, b) => {
switch (sortBy) {
case 'created-desc':
return new Date(b.createdAt).getTime() - new Date(a.createdAt).getTime();
case 'created-asc':
return new Date(a.createdAt).getTime() - new Date(b.createdAt).getTime();
case 'published-desc':
if (!a.publishedAt) return 1;
if (!b.publishedAt) return -1;
return new Date(b.publishedAt).getTime() - new Date(a.publishedAt).getTime();
case 'published-asc':
if (!a.publishedAt) return 1;
if (!b.publishedAt) return -1;
return new Date(a.publishedAt).getTime() - new Date(b.publishedAt).getTime();
case 'title-asc':
return a.title.localeCompare(b.title);
case 'title-desc':
return b.title.localeCompare(a.title);
case 'views-desc':
return b.viewCount - a.viewCount;
case 'views-asc':
return a.viewCount - b.viewCount;
default:
return 0;
}
});
}
/**
* 获取唯一分类列表
*/
export function getUniqueCategories(articles: Article[]): string[] {
const all: string[] = [];
articles.forEach((a) => {
if (a.terms) all.push(...a.terms.map((t) => t.name));
});
return Array.from(new Set(all));
}
/**
* 分页处理
*/
export function paginateArray<T>(array: T[], page: number, pageSize: number): T[] {
return array.slice((page - 1) * pageSize, page * pageSize);
}
/**
* 计算总页数
*/
export function calculateTotalPages(totalItems: number, pageSize: number): number {
return Math.ceil(totalItems / pageSize);
}