Files
reui-blocks/blocks/resource2.tsx
T

303 lines
12 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { ArrowLeft, Facebook, Link, Linkedin, Twitter } from "lucide-react";
import { Avatar, AvatarFallback, AvatarImage } from "@/components/ui/avatar";
import { Button } from "@/components/ui/button";
import { cn } from "@/lib/utils";
interface Resource2Props {
navigation: {
backText: string;
backHref: string;
className?: string;
};
blog: {
title: string;
author: string;
role: string;
date: string;
readTime: string;
imageSrc: string;
content: React.ReactNode;
};
social: {
heading: string;
links: Array<{
icon: "link" | "linkedin" | "twitter" | "facebook";
href: string;
label: string;
}>;
};
illustration: {
imageSrc: string;
imageAlt: string;
};
className?: string;
}
const Resource2 = ({
className,
navigation = {
backText: "همه مقالات",
backHref: "/resources",
},
blog = {
title:
"ساخت وب‌اپلیکیشن‌های پایدار: راهنمای توسعه‌دهنده برای کدنویسی سبز",
author: "سارا چن",
date: "۲۵ آذر ۱۴۰۳",
readTime: "۸ دقیقه مطالعه",
role: "توسعه‌دهنده ارشد",
imageSrc: "/block-media/shadcnblocks/block/avatar-1.webp",
content: (
<>
<p>
دنیای دیجیتال انرژی بیشتری نسبت به کل صنعت هوانوردی مصرف می‌کند. ما
به‌عنوان توسعه‌دهنده مسئولیت داریم برنامه‌هایی بسازیم که نه‌تنها
کاربردی و زیبا باشند، بلکه برای سیاره ما نیز پایدار باشند.
</p>
<h2>ردپای کربنی کد</h2>
<p>
هر خط کدی که می‌نویسیم تأثیر محیطی دارد. از انرژی مصرفی سرورها تا
منابع به‌کاررفته در ساخت دستگاه‌ها، انتخاب‌های دیجیتال ما مهم‌تر از
آنچه فکر می‌کنیم اهمیت دارند.
</p>
<h3>درک تأثیر</h3>
<p>
وب‌اپلیکیشن‌های مدرن به‌شدت پرمصرف هستند. این واقعیت‌های
چشمگیر را در نظر بگیرید:
</p>
<ul>
<li>
<strong>مراکز داده</strong> ۱٪ از برق جهانی را مصرف می‌کنند
</li>
<li>
<strong>پخش ویدیو</strong> ۳٪ از انتشار کربن جهانی را تشکیل
می‌دهد
</li>
<li>
<strong>هرزنامه ایمیل</strong> سالانه ۱۷ میلیون تن CO₂ تولید
می‌کند
</li>
</ul>
<blockquote>
<p>
«پایدارترین کد، کدی است که اصلاً نمی‌نویسید. دومین کد پایدار، کدی
است که کارآمد اجرا می‌شود.»
</p>
</blockquote>
<h2>اصول کدنویسی سبز</h2>
<p>این اصول پایه را هر توسعه‌دهنده باید رعایت کند:</p>
<ol>
<li>
<strong>بهینه‌سازی برای عملکرد:</strong> کد سریع‌تر، انرژی کمتری
مصرف می‌کند
</li>
<li>
<strong>کاهش وابستگی‌ها:</strong> هر پکیج به حجم بسته اضافه
می‌کند
</li>
<li>
<strong>استفاده از الگوریتم‌های کارآمد:</strong> پیچیدگی بهتر یعنی
محاسبه کمتر
</li>
<li>
<strong>پیاده‌سازی استراتژی‌های کش:</strong> کاهش عملیات تکراری
</li>
<li>
<strong>انتخاب هاستینگ سبز:</strong> سرورهای با انرژی تجدیدپذیر
</li>
</ol>
<h3>پیاده‌سازی عملی</h3>
<p>
بیایید چند نمونه مشخص از پیاده‌سازی این اصول را ببینیم:
</p>
<h4>۱ بهینه‌سازی تصویر</h4>
<p>
تصاویر اغلب ۶۰ تا ۸۰ درصد حجم یک صفحه را تشکیل می‌دهند. از
فرمت‌های مدرن مثل WebP یا AVIF استفاده کنید، بارگذاری هوشمند پیاده
کنید و تصاویر با اندازه مناسب سرو کنید.
</p>
<h4>۲ تقسیم کد (تقسیم هوشمند بار)</h4>
<p>
فقط جاوااسکریپتی را بارگذاری کنید که کاربر واقعاً به آن نیاز
دارد. این کار حجم بسته اولیه را کم می‌کند و عملکرد را بهبود
می‌دهد.
</p>
<h4>۳. بهینه‌سازی پایگاه داده</h4>
<p>
کوئری‌های کارآمد بنویسید، ایندکس‌گذاری درست انجام دهید و connection
pooling پیاده کنید تا بار پایگاه داده کاهش یابد.
</p>
<h2>آینده توسعه پایدار</h2>
<p>
با حرکت به جلو، پایداری باید در هر تصمیم توسعه یک ملاحظه اصلی
شود. ابزارهایی مثل <strong>ابزار تست سرعت</strong> و{" "}
<strong>ابزار تحلیل عملکرد</strong> می‌توانند به سنجش تأثیر محیطی
برنامه‌های ما کمک کنند.
</p>
<p>
مسیر توسعه وب پایدار مستمر است، اما هر بهینه‌سازی کوچک به آینده
دیجیتال سبزتر کمک می‌کند. با یک اصل شروع کنید، تأثیر را بسنجید و
به‌تدریج شیوه‌های پایدارتر را به گردش کار توسعه خود اضافه کنید.
</p>
</>
),
},
social = {
heading: "اشتراک‌گذاری این مقاله",
links: [
{ icon: "link", href: "#", label: "کپی لینک" },
{ icon: "linkedin", href: "#", label: "اشتراک در لینکدین" },
{ icon: "twitter", href: "#", label: "اشتراک در X" },
{ icon: "facebook", href: "#", label: "اشتراک در فیسبوک" },
],
},
illustration = {
imageSrc: "/block-media/shadcnblocks/block/placeholder-2.svg",
imageAlt:
"تصویر توسعه وب پایدار با تمرین‌های کدنویسی سبز و تأثیر محیطی",
},
}: Resource2Props) => {
const getIcon = (icon: string, className: string) => {
switch (icon) {
case "link":
return <Link className={`size-4 ${className}`} />;
case "شبکه حرفه‌ای":
return <Linkedin className={`size-4 ${className}`} />;
case "شبکه اجتماعی":
return <Twitter className={`size-4 ${className}`} />;
case "شبکه اجتماعی":
return <Facebook className={`size-4 ${className}`} />;
default:
return null;
}
};
return (
<section dir="rtl" lang="fa" className={cn("", className)}>
<div className="min-h-128 bg-primary text-primary-foreground">
<div className="container py-16">
<div className="grid grid-cols-1 items-start gap-8 lg:grid-cols-3">
<div className="flex h-full max-w-md flex-col justify-between gap-8">
<div className="space-y-6">
<div className="flex items-center gap-2 text-primary-foreground">
<a
href={navigation.backHref}
className="group/nav flex items-center gap-2 transition-all duration-200 hover:gap-4"
>
<ArrowLeft className="size-4 rtl:rotate-180 group-hover/nav:text-primary-foreground" />
<span className="transition-colors group-hover/nav:text-primary-foreground group-hover/nav:underline">
{navigation.backText}
</span>
</a>
</div>
<h1 className="text-start text-3xl leading-tight font-medium">
{blog.title}
</h1>
</div>
<div className="flex flex-col gap-8">
<div className="space-y-2 text-start">
<p className="text-lg text-muted-foreground">{blog.author}</p>
<p className="text-muted-foreground">
{blog.date} • {blog.readTime}
</p>
</div>
<div className="space-y-4 text-start">
<h3>{social.heading}</h3>
<div className="flex gap-3">
{social.links.map((link, index) => (
<Button
key={index}
variant="outline"
size="icon"
className="group/btn h-12 w-12 rounded-full border-border/10 bg-muted/20 transition-colors hover:bg-transparent hover:text-muted"
asChild
>
<a
href={link.href}
aria-label={link.label}
className="flex items-center justify-center"
>
{getIcon(
link.icon,
"text-muted/30 group-hover/btn:text-primary-foreground transition-colors",
)}
</a>
</Button>
))}
</div>
</div>
</div>
</div>
<div className="col-span-2 h-full w-full">
<div className="aspect-video min-h-96 w-full">
<img
src={illustration.imageSrc}
alt={illustration.imageAlt}
className="h-full w-full object-cover"
/>
</div>
</div>
</div>
</div>
</div>
<div className="container mx-auto py-16 md:max-w-2xl xl:max-w-5xl">
<div className="prose max-w-none pb-16 text-start prose-headings:text-foreground prose-p:text-muted-foreground prose-blockquote:border-s-primary prose-blockquote:text-muted-foreground prose-strong:text-foreground prose-em:text-foreground prose-ol:text-muted-foreground prose-ul:text-muted-foreground prose-li:text-muted-foreground">
{blog.content}
</div>
<div className="flex flex-col justify-between gap-8 border-t border-border py-8 md:flex-row">
<div className="flex items-center gap-3">
<Avatar className="size-12 border xl:size-16">
<AvatarImage src={blog.imageSrc} />
<AvatarFallback>{blog.author}</AvatarFallback>
</Avatar>
<div className="text-start">
<p className="font-medium">{blog.author}</p>
<p className="text-sm text-muted-foreground">{blog.role}</p>
</div>
</div>
<div className="space-y-4 text-start">
<h3>{social.heading}</h3>
<div className="flex gap-3">
{social.links.map((link, index) => (
<Button
key={index}
variant="outline"
size="icon"
className="group/btn h-12 w-12 rounded-full border-border bg-muted transition-colors hover:bg-transparent hover:text-muted"
asChild
>
<a
href={link.href}
aria-label={link.label}
className="flex items-center justify-center"
>
{getIcon(
link.icon,
"text-muted-foreground group-hover/btn:text-primary transition-colors",
)}
</a>
</Button>
))}
</div>
</div>
</div>
</div>
</section>
);
};
export { Resource2 };