<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>دواپس آرشیو - بلاگ هم‌روش</title>
	<atom:link href="https://hamravesh.com/blog/category/devops/feed/" rel="self" type="application/rss+xml" />
	<link>https://hamravesh.com/blog/category/devops/</link>
	<description>بلاگ رسمی هم‌روش</description>
	<lastBuildDate>Wed, 19 Aug 2026 07:32:51 +0000</lastBuildDate>
	<language>fa-IR</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
	<generator>https://wordpress.org/?v=7.1</generator>

<image>
	<url>https://hamravesh.com/blog/wp-content/uploads/2026/05/cropped-typeGeneral-32x32.png</url>
	<title>دواپس آرشیو - بلاگ هم‌روش</title>
	<link>https://hamravesh.com/blog/category/devops/</link>
	<width>32</width>
	<height>32</height>
</image> 
	<item>
		<title>ری‌استارت کانتینر یا ساخت پاد جدید؛ کوبرنتیز چگونه تصمیم می‌گیرد؟</title>
		<link>https://hamravesh.com/blog/kubernetes-container-restart-vs-pod-replacement/</link>
					<comments>https://hamravesh.com/blog/kubernetes-container-restart-vs-pod-replacement/#respond</comments>
		
		<dc:creator><![CDATA[هم‌روش]]></dc:creator>
		<pubDate>Wed, 19 Aug 2026 12:30:23 +0000</pubDate>
				<category><![CDATA[دواپس]]></category>
		<category><![CDATA[کوبرنتیز]]></category>
		<guid isPermaLink="false">https://hamravesh.com/blog/?p=5603</guid>

					<description><![CDATA[<p>تفاوت اصلی در سطح انتزاع است. پاد (Pod) واحد کوچک‌تری از اجرا در کوبرنتیز است که میزبان یک یا چند کانتینر محسوب می‌شود. هنگام ری‌استارت کانتینر، لایه انتزاعی پاد دست‌نخورده باقی می‌ماند و فقط کانتینرِ داخل آن دوباره اجرا می‌شود؛ اما هنگام ایجاد مجدد پاد، کل واحد پاد (شامل فضای شبکه، حافظه مشترک و تمامی کانتینرها) از بین رفته و یک نمونه کاملاً جدید با هویت و Pod UID متفاوت ایجاد می‌شود.</p>
<p>The post <a href="https://hamravesh.com/blog/kubernetes-container-restart-vs-pod-replacement/">ری‌استارت کانتینر یا ساخت پاد جدید؛ کوبرنتیز چگونه تصمیم می‌گیرد؟</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">در گفت‌وگوهای فنی، عبارت «پاد ری‌استارت شد» زیاد استفاده می‌شود، اما این عبارت همیشه یک اتفاق مشخص را توصیف نمی‌کند. در کوبرنتیز ممکن است فقط کانتینر داخل همان پاد دوباره اجرا شود یا پاد فعلی جای خود را به یک پاد جدید بدهد. این دو وضعیت از نظر چرخه عمر، هویت پاد و نحوه مدیریت توسط کوبرنتیز با یکدیگر تفاوت دارند.</p>



<p class="wp-block-paragraph">باید ابتدا مشخص شود که با ری‌استارت کانتینر در همان پاد روبه‌رو هستیم یا ایجاد مجدد پاد در کوبرنتیز اتفاق افتاده است. معیارهایی مانند Pod UID و تعداد ری‌استارت کانتینر (restartCount) در ادامه به ما کمک می‌کنند این دو وضعیت را از یکدیگر تشخیص دهیم.</p>



<p class="wp-block-paragraph">در این مقاله بررسی می‌کنیم کوبرنتیز در چه شرایطی کانتینر را دوباره اجرا می‌کند، چه تغییراتی باعث جایگزینی پاد می‌شوند و چگونه می‌توان با بررسی وضعیت پاد تشخیص داد که کانتینر در همان پاد ری‌استارت شده یا پاد جدیدی ساخته شده است. این مقاله بر رفتارهای مستندشده در Kubernetes 1.35 تمرکز دارد و قابلیت In-place Pod Resize را نیز بررسی می‌کند که در این نسخه به وضعیت پایدار رسید.</p>



<h2 id="h-تفاوت-ری-استارت-کانتینر-با-ایجاد-مجدد-پاد-چیست" class="wp-block-heading"><strong>تفاوت ری‌استارت کانتینر با ایجاد مجدد پاد چیست؟</strong></h2>



<p class="wp-block-paragraph">تفاوت اصلی به حفظ یا تغییر هویت پاد مربوط است. هنگام ری‌استارت کانتینر، همان پاد با همان Pod UID باقی می‌ماند و kubelet، کانتینر را داخل آن دوباره اجرا می‌کند. در مقابل، هنگام جایگزینی پاد، پاد قبلی حذف می‌شود و یک پاد جدید با Pod UID متفاوت ایجاد می‌شود. حتی اگر پاد جایگزین نامی مشابه پاد قبلی داشته باشد، از نظر هویت یک پاد جدید محسوب می‌شود.</p>



<h3 id="h-ری-استارت-کانتینر-در-همان-پاد" class="wp-block-heading"><strong>ری‌استارت کانتینر در همان پاد</strong></h3>



<p class="wp-block-paragraph">اگر فرایند یک کانتینر متوقف شود، در صورت اجازه سیاست ری‌استارت (restartPolicy)، kubelet همان کانتینر را دوباره داخل همان پاد اجرا می‌کند. در این حالت، خود پاد حذف نمی‌شود و هویت آن تغییر نمی‌کند؛ بنابراین Pod UID ثابت باقی می‌ماند و تعداد ری‌استارت همان کانتینر افزایش پیدا می‌کند.</p>



<p class="wp-block-paragraph">در واقع، ری‌استارت کانتینر به معنی ساخته شدن پاد جدید نیست. فرایند کانتینر در همان پاد دوباره اجرا می‌شود و kubelet این رفتار را بر اساس سیاست ری‌استارت تعریف‌شده برای پاد مدیریت می‌کند.</p>



<h3 id="h-ایجاد-مجدد-یا-جایگزینی-پاد" class="wp-block-heading"><strong>ایجاد مجدد یا جایگزینی پاد</strong></h3>



<p class="wp-block-paragraph">در حالت جایگزینی پاد یا ایجاد مجدد، پاد قبلی حذف و یک پاد جدید ایجاد می‌شود. حتی اگر پاد جدید نام مشابهی داشته باشد، با Pod UID متفاوت ساخته می‌شود. بنابراین تغییر UID یکی از معیارهای اصلی برای تشخیص ایجاد مجدد پاد در کوبرنتیز است.</p>



<p class="wp-block-paragraph">کنترلرهایی مانند <a href="https://hamravesh.com/blog/what-is-kubernetes-deployment/" data-type="link" data-id="https://hamravesh.com/blog/what-is-kubernetes-deployment/" target="_blank" rel="noreferrer noopener">دیپلویمنت</a> می‌توانند هنگام تغییر الگوی پاد (Pod Template) یک Rollout جدید آغاز کنند. در این فرایند، ReplicaSet جدید ایجاد می‌شود و پادهای جدید بر اساس الگوی جدید ساخته می‌شوند. ازآنجایی‌که این پادها هویت مستقلی دارند، تعداد ری‌استارت کانتینرهای آن‌ها از صفر آغاز می‌شود، مگر اینکه کانتینرهای پاد جدید پس از ایجاد، ری‌استارت شوند.</p>



<h3 id="h-جدول-مقایسه-ری-استارت-کانتینر-و-ایجاد-مجدد-پاد" class="wp-block-heading"><strong>جدول مقایسه ری‌استارت کانتینر و ایجاد مجدد پاد</strong></h3>



<p class="wp-block-paragraph">در جدول زیر تفاوت ری‌استارت کانتینر و ایجاد مجدد پاد را مشاهده می‌کنید:</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><tbody><tr><td><strong>معیار</strong></td><td><strong>ری‌استارت کانتینر</strong></td><td><strong>ایجاد مجدد پاد</strong></td></tr><tr><td>وضعیت Pod UID</td><td>بدون تغییر باقی می‌ماند</td><td>تغییر می‌کند و پاد جدید با UID جدید ساخته می‌شود</td></tr><tr><td>وضعیت مقدار ری‌استارت کانتینر</td><td>برای کانتینر ری‌استارت‌شده افزایش پیدا می‌کند</td><td>در پاد جدید از صفر آغاز می‌شود، مگر اینکه کانتینرهای آن بعداً ری‌استارت شوند</td></tr><tr><td>وضعیت باقی ماندن همان پاد</td><td>همان پاد حفظ می‌شود</td><td>پاد قبلی حذف و پاد جدید جایگزین می‌شود</td></tr><tr><td>نقش kubelet یا کنترلر</td><td>kubelet بر اساس restartPolicy کانتینر را دوباره اجرا می‌کند</td><td>کنترلرهایی مانند دیپلویمنت پاد جدید ایجاد می‌کنند</td></tr></tbody></table></figure>



<h2 id="h-نقش-restartpolicy-در-ری-استارت-کانتینرها" class="wp-block-heading">نقش restartPolicy در ری‌استارت کانتینرها</h2>



<p class="wp-block-paragraph">پاد مشخص می‌کند که پس از متوقف شدن کانتینر، kubelet در چه شرایطی آن را دوباره اجرا کند. فیلد restartPolicy در مشخصات پاد تعریف می‌شود و برای کانتینرهای برنامه می‌تواند یکی از سه مقدار Always ،OnFailure یا Never را داشته باشد. مقدار پیش‌فرض آن Always است. ری‌استارت‌هایی که بر اساس این سیاست انجام می‌شوند، کانتینر را داخل همان پاد و روی همان نود دوباره اجرا می‌کنند و به معنای ایجاد پاد جدید نیستند.</p>



<h3 id="h-سیاست-always" class="wp-block-heading"><strong>سیاست Always</strong></h3>



<p class="wp-block-paragraph">با انتخاب سیاست Always، هر بار که اجرای کانتینر به پایان برسد، kubelet صرف‌نظر از اینکه اجرای آن با موفقیت یا خطا پایان یافته باشد، کانتینر را دوباره اجرا می‌کند. به همین دلیل، این سیاست برای بارهای کاری (Workload) که باید به‌صورت مداوم در حال اجرا باشند کاربرد دارد. برای نمونه، دیپلویمنت‌ها از restartPolicy: Always استفاده می‌کنند تا برنامه‌ها به‌طور پیوسته اجرا شوند.</p>



<h3 id="h-سیاست-onfailure" class="wp-block-heading"><strong>سیاست OnFailure</strong></h3>



<p class="wp-block-paragraph">در سیاست OnFailure، نحوه خاتمه کانتینر تعیین می‌کند که اجرای مجدد انجام شود یا خیر. اگر کانتینر با خطا و وضعیت خروج غیرصفر (Non-zero Exit Status) خاتمه پیدا کند، kubelet آن را دوباره اجرا می‌کند، اما اگر کانتینر با وضعیت خروج صفر و به‌صورت موفق خاتمه یابد، ری‌استارت انجام نمی‌شود. معمولا Jobها از OnFailure یا Never برای مدیریت وظایف پردازش دسته‌ای استفاده می‌کنند.</p>



<h3 id="h-سیاست-never" class="wp-block-heading"><strong>سیاست Never</strong></h3>



<p class="wp-block-paragraph">با انتخاب Never، کانتینر پس از خاتمه (صرف‌نظر از اینکه اجرای آن موفق بوده یا با خطا پایان یافته باشد) به‌طور خودکار دوباره اجرا نمی‌شود. بنابراین، برخلاف Always و OnFailure، حتی خاتمه ناموفق کانتینر هم باعث نمی‌شود kubelet آن را بر اساس سیاست ری‌استارت دوباره اجرا کند.</p>



<h3 id="h-تاخیر-تصاعدی-میان-ری-استارت-ها" class="wp-block-heading"><strong>تاخیر تصاعدی میان ری‌استارت‌ها</strong></h3>



<p class="wp-block-paragraph">در تنظیمات پیش‌فرض، kubelet پس از توقف‌های متوالی کانتینر از تأخیر تصاعدی استفاده می‌کند. فاصله میان تلاش‌های بعدی از ۱۰ ثانیه آغاز می‌شود و به‌ترتیب به ۲۰، ۴۰ ثانیه و مقادیر بیشتر افزایش می‌یابد تا به سقف پیش‌فرض ۳۰۰ ثانیه برسد. این سقف به فاصله میان تلاش‌ها مربوط است و به معنای محدود بودن تعداد تلاش‌های ری‌استارت نیست. اگر کانتینر ۱۰ دقیقه بدون مشکل اجرا شود، kubelet تأخیر میان تلاش‌های ری‌استارت را دوباره از مقدار اولیه محاسبه می‌کند.</p>



<p class="wp-block-paragraph">این سازوکار با وضعیت CrashLoopBackOff ارتباط دارد. این وضعیت نشان می‌دهد کانتینر به‌طور مکرر با شکست مواجه شده و سازوکار تأخیر میان تلاش‌های اجرای مجدد آن فعال است.</p>



<h2 id="h-crashloopbackoff-به-چه-معناست" class="wp-block-heading"><strong>CrashLoopBackOff به چه معناست؟</strong></h2>



<p class="wp-block-paragraph">CrashLoopBackOff زمانی مشاهده می‌شود که یک کانتینر به‌طور مکرر متوقف شود و در صورت اجازه سیاست ری‌استارت، kubelet برای اجرای مجدد آن تلاش کند. با تکرار این چرخه، تعداد ری‌استارت کانتینر افزایش می‌یابد و kubelet با استفاده از سازوکار Backoff، فاصله میان تلاش‌های متوالی برای اجرای مجدد کانتینر را به‌تدریج بیشتر می‌کند.</p>



<p class="wp-block-paragraph">نکته مهم این است که CrashLoopBackOff به معنای حذف پاد و ساخته شدن پاد جدید نیست. در این شرایط، کانتینر داخل همان پاد دوباره اجرا می‌شود؛ بنابراین Pod UID ثابت می‌ماند و تعداد ری‌استارت کانتینر افزایش پیدا می‌کند. در مقابل، هنگام ایجاد مجدد پاد در کوبرنتیز، پاد جدید با Pod UID متفاوت ساخته می‌شود.</p>



<h2 id="h-probeها-چه-زمانی-باعث-ری-استارت-کانتینر-می-شوند" class="wp-block-heading"><strong>Probeها چه زمانی باعث ری‌استارت کانتینر می‌شوند؟</strong></h2>



<p class="wp-block-paragraph">پروب‌ها (Probe) برای بررسی وضعیت کانتینرها در کوبرنتیز استفاده می‌شوند، اما شکست همه آن‌ها نتیجه یکسانی ندارد. بسته به نوع پروب، نتیجه بررسی می‌تواند به ری‌استارت کانتینر منجر شود یا روی آماده بودن آن برای دریافت ترافیک تأثیر بگذارد. برای درک این تفاوت، باید عملکرد پروب زنده‌بودن (Liveness Probe)، پروب آمادگی (Readiness Probe) و پروب راه‌اندازی (Startup Probe) را جداگانه بررسی کرد.</p>



<h3 id="h-تفاوت-liveness-readiness-و-startup-probe" class="wp-block-heading"><strong>تفاوت Liveness ،Readiness و Startup Probe</strong></h3>



<p class="wp-block-paragraph">هر سه پروب هدف متفاوتی دارند و شکست آن‌ها هم نتیجه یکسانی ایجاد نمی‌کند:</p>



<ul class="wp-block-list">
<li><strong>پروب زنده‌بودن:</strong> مشخص می‌کند کانتینر همچنان سالم است یا باید متوقف شود. اگر Liveness Probe بیش از تعداد دفعات تعیین‌شده شکست بخورد، kubelet کانتینر را متوقف می‌کند. رفتار بعدی به سیاست ری‌استارت پاد بستگی دارد و در صورت اجازه این سیاست، کانتینر داخل همان پاد دوباره اجرا می‌شود. بنابراین، شکست این پروب به‌خودی‌خود به معنای ساخته شدن پاد جدید نیست.</li>



<li><strong>پروب آمادگی:</strong> مشخص می‌کند کانتینر برای دریافت ترافیک آماده است یا خیر. اگر Readiness Probe شکست بخورد، آدرس پاد از EndpointSlice سرویس‌های منطبق حذف می‌شود؛ اما kubelet کانتینر را به‌دلیل شکست این پروب ری‌استارت نمی‌کند.</li>



<li><strong>پروب راه‌اندازی:</strong> مشخص می‌کند برنامه داخل کانتینر شروع به کار کرده است یا خیر. اگر Startup Probe تعریف شده باشد، پروب‌های زنده‌بودن و آمادگی تا موفق شدن آن اجرا نمی‌شوند. اگر این پروب بیش از تعداد دفعات تعیین‌شده شکست بخورد، kubelet کانتینر را متوقف می‌کند و رفتار بعدی بر اساس سیاست ری‌استارت پاد تعیین می‌شود.</li>
</ul>



<p class="wp-block-paragraph">در نتیجه، شکست Readiness Probe فقط بر دریافت ترافیک تأثیر می‌گذارد؛ اما شکست Liveness Probe یا Startup Probe می‌تواند به توقف کانتینر و سپس اجرای مجدد آن در همان پاد منجر شود.</p>



<h2 id="h-هنگام-تغییر-image-چه-اتفاقی-برای-پاد-می-افتد" class="wp-block-heading"><strong>هنگام تغییر Image چه اتفاقی برای پاد می‌افتد؟</strong></h2>



<p class="wp-block-paragraph">ایمیج کانتینر (Container Image) نسخه آماده‌ای است که کانتینر بر اساس آن ساخته و اجرا می‌شود. برای مثال، تغییر ایمیج از یک نسخه برنامه به نسخه‌ای دیگر مشخص می‌کند که کانتینرهای جدید باید کدام نسخه را اجرا کنند.</p>



<p class="wp-block-paragraph">در یک دیپلویمنت، ایمیج کانتینر بخشی از Pod Template است؛ یعنی همان الگویی که مشخصات پادهای موردنظر را تعریف می‌کند. با تغییر ایمیج، این الگو نیز تغییر می‌کند. اگر دیپلویمنت در حالت Paused نباشد، این تغییر یک Rollout جدید را آغاز می‌کند. سپس ReplicaSet جدیدی ایجاد می‌شود و پادهای جدید بر اساس ایمیج به‌روزشده ساخته می‌شوند. بنابراین، تغییر ایمیج در دیپلویمنت به معنای ری‌استارت کانتینر داخل پادهای موجود نیست؛ بلکه پادهای جدیدی ساخته می‌شوند که کانتینرهای آن‌ها از ایمیج جدید استفاده می‌کنند.</p>



<h3 id="h-تغییر-pod-template-و-ایجاد-replicaset-جدید" class="wp-block-heading"><strong>تغییر Pod Template و ایجاد ReplicaSet جدید</strong></h3>



<p class="wp-block-paragraph">دیپلویمنت، مشخصات پادهای موردنظر را در الگوی پاد تعریف می‌کند و ایمیج کانتینر هم بخشی از همین الگو است. براساس مستندات رسمی کوبرنتیز، تغییر در الگوی پاد باعث آغاز یک Rollout جدید می‌شود، بنابراین تغییر Image این فرایند را آغاز می‌کند.</p>



<p class="wp-block-paragraph">پس از تغییر الگوی پاد، استقرار یک ReplicaSet جدید ایجاد می‌کند و پادهای جدید براساس الگوی به‌روزشده ساخته می‌شوند. در به‌روزرسانی تدریجی (Rolling Update)، کوبرنتیز به‌تدریج تعداد پادهای جدید را افزایش و تعداد پادهای قبلی را کاهش می‌دهد. این فرایند با افزایش مقیاس ReplicaSet جدید و کاهش مقیاس ReplicaSet قبلی انجام می‌شود. اگر Deployment در حالت Paused باشد، تغییر Pod Template ثبت می‌شود، اما Rollout تا زمان خارج شدن Deployment از این حالت پیش نمی‌رود.</p>



<h3 id="h-تفاوت-rolling-update-با-ری-استارت-کانتینر" class="wp-block-heading"><strong>تفاوت Rolling Update با ری‌استارت کانتینر</strong></h3>



<p class="wp-block-paragraph">در به‌روزرسانی تدریجی، کانتینر داخل همان پاد دوباره اجرا نمی‌شود، بلکه پادهای جدید براساس الگوی پاد جدید ساخته می‌شوند. این تفاوت را می‌توان با Pod UID (شناسه منحصربه‌فرد پاد) تشخیص داد. با ایجاد پاد جدید، این شناسه تغییر می‌کند، اما در ری‌استارت کانتینر، همان شناسه قبلی حفظ می‌شود.</p>



<p class="wp-block-paragraph">تعداد ری‌استارت کانتینر هم به کانتینرهای همان پاد مربوط است و از پاد قبلی به پاد جدید منتقل نمی‌شود. بنابراین، به‌روزرسانی تدریجی را نباید ری‌استارت کانتینر در همان پاد در نظر گرفت؛ زیرا در این فرایند، پادهای جدید با هویت مستقل ایجاد می‌شوند.</p>



<h3 id="h-رفتار-deployment-در-imagepullbackoff" class="wp-block-heading"><strong>رفتار Deployment در ImagePullBackOff</strong></h3>



<p class="wp-block-paragraph">اگر پاد جدید نتواند ایمیج مشخص‌شده را دریافت کند، کانتینر آن راه‌اندازی نمی‌شود و پاد ممکن است در وضعیت <code>ImagePullBackOff</code> قرار بگیرد. در نتیجه، پاد جدید آماده نمی‌شود و Rollout نمی‌تواند طبق انتظار تکمیل شود.</p>



<p class="wp-block-paragraph">در به‌روزرسانی تدریجی، ممکن است دیپلویمنت بخشی از پادهای قبلی را همچنان در حال اجرا نگه دارد و جایگزینی پادها متوقف شود. تعداد پادهای قبلی باقی‌مانده و نحوه ادامه Rollout به تنظیماتی مانند <code>maxUnavailable</code> و <code>maxSurge</code> بستگی دارد. بنابراین، وقوع <code>ImagePullBackOff</code> لزوماً به معنای حذف همه پادهای قبلی نیست.</p>



<h2 id="h-آیا-تغییر-configmap-باعث-ری-استارت-پاد-می-شود" class="wp-block-heading"><strong>آیا تغییر ConfigMap باعث ری‌استارت پاد می‌شود؟</strong></h2>



<p class="wp-block-paragraph">تغییر ConfigMap به‌خودی‌خود باعث ری‌استارت کانتینر یا جایگزینی پاد نمی‌شود، بلکه اثر این تغییرات به روشی بستگی دارد که داده‌های ConfigMap در اختیار کانتینر قرار گرفته‌اند. همچنین استفاده از ConfigMap به‌صورت متغیر محیطی با اتصال آن به‌صورت Volume رفتار متفاوتی دارد، بنابراین این دو حالت باید جداگانه بررسی شوند.</p>



<h3 id="h-مصرف-configmap-از-طریق-متغیر-محیطی" class="wp-block-heading"><strong>مصرف ConfigMap از طریق متغیر محیطی</strong></h3>



<p class="wp-block-paragraph">وقتی داده‌های ConfigMap به‌صورت متغیر محیطی در اختیار کانتینر قرار می‌گیرند، kubelet هنگام راه‌اندازی کانتینر از این داده‌ها استفاده می‌کند. اگر ConfigMap بعداً تغییر کند، مقادیر جدید به‌صورت خودکار در متغیرهای محیطی کانتینر در حال اجرا اعمال نمی‌شوند.</p>



<p class="wp-block-paragraph">برای دریافت مقادیر جدید در یک دیپلویمنت، باید Rollout جدیدی انجام شود تا پادهای جدید با متغیرهای محیطی به‌روز ساخته شوند. صرف تغییر ConfigMap این Rollout را به‌صورت خودکار آغاز نمی‌کند؛ زیرا تغییر ConfigMap به‌خودی‌خود Pod Template یک دیپلویمنت را تغییر نمی‌دهد.</p>



<h3 id="h-اتصال-configmap-به-صورت-volume" class="wp-block-heading"><strong>اتصال ConfigMap به‌صورت Volume</strong></h3>



<p class="wp-block-paragraph">اگر ConfigMap به‌صورت Volume به پاد متصل شده باشد، پس از تغییر ConfigMap، داده‌های متصل‌شده در نهایت به‌روزرسانی می‌شوند. این به‌روزرسانی فوری نیست و ممکن است میان تغییر ConfigMap و به‌روزرسانی فایل‌های داخل پاد فاصله زمانی وجود داشته باشد.</p>



<p class="wp-block-paragraph">به‌روزرسانی فایل‌های متصل‌شده هم به‌خودی‌خود باعث ری‌استارت کانتینر نمی‌شود. اینکه برنامه از تنظیمات جدید استفاده کند، به نحوه مدیریت تغییرات فایل توسط خود برنامه بستگی دارد.</p>



<h3 id="h-محدودیت-استفاده-از-subpath" class="wp-block-heading"><strong>محدودیت استفاده از subPath</strong></h3>



<p class="wp-block-paragraph"><code>subPath</code> مشخص می‌کند که به‌جای اتصال کل Volume، فقط یک فایل یا مسیر مشخص از آن داخل کانتینر متصل شود. رفتار اتصال ConfigMap با subPath متفاوت است. براساس مستندات رسمی کوبرنتیز، کانتینری که ConfigMap را با استفاده از subPath به‌صورت Volume متصل کرده باشد، به‌روزرسانی‌های بعدی ConfigMap را دریافت نمی‌کند. بنابراین، برخلاف اتصال کامل ConfigMap به‌صورت Volume که فایل‌های متصل‌شده می‌توانند به‌روزرسانی شوند، در اتصال مبتنی بر subPath تغییرات جدید ConfigMap در فایل متصل‌شده منعکس نمی‌شوند.</p>



<h3 id="h-تفاوت-به-روزرسانی-فایل-با-reload-شدن-برنامه" class="wp-block-heading"><strong>تفاوت به‌روزرسانی فایل با Reload شدن برنامه</strong></h3>



<p class="wp-block-paragraph">به‌روزرسانی فایل و بارگذاری مجدد تنظیمات توسط برنامه دو فرایند متفاوت هستند. کوبرنتیز می‌تواند در اتصال معمول ConfigMap به‌صورت Volume، فایل‌های متصل‌شده را به‌روزرسانی کند؛ اما این اتفاق به‌تنهایی باعث نمی‌شود برنامه تنظیمات جدید را بارگذاری کند.</p>



<p class="wp-block-paragraph">برای استفاده از تنظیمات جدید بدون ری‌استارت کانتینر، خود برنامه باید بتواند تغییر فایل را تشخیص دهد و تنظیمات را دوباره بارگذاری کند. در غیر این صورت، ممکن است فایل تغییر کرده باشد، اما برنامه همچنان با تنظیمات قبلی به کار خود ادامه دهد.</p>



<h2 id="h-دستور-rollout-restart-چه-کاری-انجام-می-دهد" class="wp-block-heading"><strong>دستور rollout restart چه کاری انجام می‌دهد؟</strong></h2>



<p class="wp-block-paragraph">دستور <code>kubectl rollout restart</code> برای راه‌اندازی مجدد Rollout یک دیپلویمنت استفاده می‌شود. در این عملیات، پادهای دیپلویمنت مطابق استراتژی به‌روزرسانی آن با پادهای جدید جایگزین می‌شوند. بنابراین، این دستور، کانتینر را داخل همان پاد دوباره اجرا نمی‌کند و پادهای جایگزین هویت و Pod UID جدیدی دارند.</p>



<h2 id="h-تغییر-cpu-و-memory-بدون-ایجاد-مجدد-پاد" class="wp-block-heading"><strong>تغییر CPU و Memory بدون ایجاد مجدد پاد</strong></h2>



<p class="wp-block-paragraph">قابلیت In-place Pod Resize امکان تغییر Request و Limit مربوط به CPU و Memory را بدون جایگزینی پاد فراهم می‌کند. این قابلیت به همین دو نوع منبع محدود است و منابعی غیر از CPU و Memory همچنان با این سازوکار قابل تغییر نیستند.</p>



<h3 id="h-قابلیت-in-place-pod-resize-چیست" class="wp-block-heading"><strong>قابلیت In-place Pod Resize چیست؟</strong></h3>



<p class="wp-block-paragraph">قابلیت In-place Pod Resize در کوبرنتیز نسخه 1.35 به وضعیت پایدار رسید. پیش از ارائه این قابلیت، مقادیر CPU و Memory تخصیص‌یافته به کانتینر در مشخصات پاد تغییرناپذیر بودند و تغییر آن‌ها به حذف و ایجاد مجدد پاد نیاز داشت. این قابلیت Request و Limit مربوط به CPU و Memory را قابل تغییر می‌کند و امکان اعمال آن‌ها را داخل پاد در حال اجرا فراهم می‌سازد.</p>



<p class="wp-block-paragraph">در این روش، مقادیر موردنظر CPU و Memory در مشخصات پاد به‌روزرسانی می‌شوند و کوبرنتیز می‌تواند تغییرات را بدون جایگزینی پاد اعمال کند. بنابراین، هویت پاد حفظ می‌شود و برای تغییر این منابع الزاما نیازی به ایجاد پاد جدید نیست.</p>



<h3 id="h-نقش-resizepolicy-در-ری-استارت-کانتینر" class="wp-block-heading"><strong>نقش resizePolicy در ری‌استارت کانتینر</strong></h3>



<p class="wp-block-paragraph">رفتار کانتینر هنگام تغییر منابع به <code>resizePolicy</code> تعریف‌شده برای هر منبع بستگی دارد. این سیاست می‌تواند یکی از دو مقدار <code>NotRequired</code> یا <code>RestartContainer</code> را داشته باشد.</p>



<p class="wp-block-paragraph">با سیاست <code>NotRequired</code>، تغییر منبع بدون نیاز به ری‌استارت کانتینر اعمال می‌شود. در مقابل، سیاست <code>RestartContainer</code> مشخص می‌کند که برای اعمال تغییر، کانتینر داخل همان پاد دوباره اجرا شود. برای مثال، می‌توان تغییر CPU را بدون ری‌استارت انجام داد و برای تغییر Memory، ری‌استارت کانتینر را الزامی کرد.</p>



<p class="wp-block-paragraph">در هر دو حالت، خود پاد جایگزین نمی‌شود و Pod UID ثابت باقی می‌ماند. بنابراین، حتی اگر تغییر منابع باعث ری‌استارت کانتینر شود، این اتفاق به معنای ایجاد پاد جدید نیست.</p>



<h3 id="h-محدودیت-های-in-place-pod-resize" class="wp-block-heading"><strong>محدودیت‌های In-place Pod Resize</strong></h3>



<p class="wp-block-paragraph">قابلیت In-place Pod Resize با وجود رسیدن به وضعیت پایدار در کوبرنتیز 1.35، همچنان محدودیت‌هایی دارد. براساس منبع رسمی، در حال حاضر CPU و Memory را می‌توان با این روش تغییر داد و سایر منابع همچنان تغییرناپذیر هستند.</p>



<p class="wp-block-paragraph">همچنین استفاده از این قابلیت همراه با Swap، Static CPU Manager و Static Memory Manager پشتیبانی نمی‌شود. برخی محیط‌های اجرای زبان‌های برنامه‌نویسی هم برای تغییر Memory بدون ری‌استارت محدودیت دارند. برای مثال، طبق منبع رسمی، Java و Python در زمان انتشار این مطلب از تغییر اندازه حافظه بدون ری‌استارت پشتیبانی نمی‌کردند.</p>



<p class="wp-block-paragraph">در نتیجه، In-place Pod Resize امکان تغییر CPU و Memory بدون ساخت پاد جدید را فراهم می‌کند؛ اما نحوه اعمال تغییر و نیاز به ری‌استارت کانتینر می‌تواند به سیاست تعریف‌شده و محدودیت‌های محیط اجرا بستگی داشته باشد.</p>



<h2 id="h-چگونه-ری-استارت-کانتینر-را-از-جایگزینی-پاد-تشخیص-دهیم" class="wp-block-heading"><strong>چگونه ری‌استارت کانتینر را از جایگزینی پاد تشخیص دهیم؟</strong></h2>



<p class="wp-block-paragraph">برای تشخیص ری‌استارت کانتینر در همان پاد از ایجاد پاد جدید، می‌توان شناسه پاد، تعداد ری‌استارت کانتینر و رویدادهای ثبت‌شده را بررسی کرد. Pod UID و تعداد ری‌استارت کانتینر دو معیار مهم برای این تشخیص هستند و بررسی وضعیت و رویدادهای پاد نیز اطلاعات تکمیلی در اختیار ما قرار می‌دهد.</p>



<h3 id="h-بررسی-pod-uid" class="wp-block-heading"><strong>بررسی Pod UID</strong></h3>



<p class="wp-block-paragraph">Pod UID یکی از معیارهای اصلی برای تشخیص هویت پاد است. هنگام ری‌استارت کانتینر در همان پاد، Pod UID تغییر نمی‌کند و فقط فرایند کانتینر دوباره اجرا می‌شود.</p>



<p class="wp-block-paragraph">در سمت مقابل، اگر پاد قبلی حذف و پاد جدیدی جایگزین آن شود، پاد جدید UID متفاوتی خواهد داشت. بنابراین، بررسی Pod UID می‌تواند مشخص کند که کانتینر در همان پاد ری‌استارت شده یا پاد جدیدی ایجاد شده است.</p>



<h3 id="h-بررسی-restartcount" class="wp-block-heading"><strong>بررسی restartCount</strong></h3>



<p class="wp-block-paragraph">تعداد ری‌استارت کانتینر نشان می‌دهد کانتینر چند بار توسط kubelet در همان پاد دوباره اجرا شده است. بنابراین، افزایش این مقدار همراه با ثابت ماندن Pod UID نشان‌دهنده ری‌استارت کانتینر در همان پاد است.</p>



<p class="wp-block-paragraph">پاد تازه‌ساخته‌شده وضعیت کانتینرهای خود را مستقل از پاد قبلی دارد؛ بنابراین اگر کانتینرهای آن هنوز ری‌استارت نشده باشند، تعداد ری‌استارت کانتینر صفر خواهد بود. به همین دلیل، این مقدار را بهتر است همراه با Pod UID بررسی کرد.</p>



<h3 id="h-بررسی-وضعیت-و-رویدادهای-پاد" class="wp-block-heading">بررسی وضعیت و رویدادهای پاد</h3>



<p class="wp-block-paragraph">برای بررسی دقیق‌تر می‌توان وضعیت و رویدادهای پاد را هم مشاهده کرد. دستور زیر اطلاعات کلی وضعیت پاد را نمایش می‌دهد:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>kubectl get pod &lt;pod-name> -o wide</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">kubectl</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">get</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">pod</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">&lt;</span><span style="color: #96D0FF">pod-nam</span><span style="color: #ADBAC7">e</span><span style="color: #F47067">&gt;</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-o</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">wide</span></span></code></pre></div>



<p class="wp-block-paragraph">برای مشاهده جزئیات پاد و رویدادهای مرتبط با آن می‌توان از دستور زیر استفاده کرد:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>kubectl describe pod &lt;pod-name></textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">kubectl</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">describe</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">pod</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">&lt;</span><span style="color: #96D0FF">pod-nam</span><span style="color: #ADBAC7">e</span><span style="color: #F47067">&gt;</span></span></code></pre></div>



<p class="wp-block-paragraph">نمایش JSON پاد با دستور زیر امکان‌پذیر است:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>kubectl get pod &lt;pod-name> -o json</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">kubectl</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">get</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">pod</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">&lt;</span><span style="color: #96D0FF">pod-nam</span><span style="color: #ADBAC7">e</span><span style="color: #F47067">&gt;</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-o</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">json</span></span></code></pre></div>



<p class="wp-block-paragraph">برای مشاهده هم‌زمان نام پاد، Pod UID، آدرس IP، نام کانتینرها و تعداد ری‌استارت هر کانتینر می‌توان از دستور زیر استفاده کرد:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>kubectl get pod &lt;pod-name> -o custom-columns=\
"NAME:.metadata.name,UID:.metadata.uid,IP:.status.podIP,RESTARTS:.status.containerStatuses&#91;0&#93;.restartCount"</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">kubectl</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">get</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">pod</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">&lt;</span><span style="color: #96D0FF">pod-nam</span><span style="color: #ADBAC7">e</span><span style="color: #F47067">&gt;</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-o</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">custom-columns=</span><span style="color: #F47067">\</span></span>
<span class="line"><span style="color: #96D0FF">&quot;NAME:.metadata.name,UID:.metadata.uid,IP:.status.podIP,RESTARTS:.status.containerStatuses&#91;0&#93;.restartCount&quot;</span></span></code></pre></div>



<p class="wp-block-paragraph">این دستور فقط تعداد ری‌استارت اولین کانتینر موجود در <code>containerStatuses</code> را نمایش می‌دهد. در پادهای چندکانتینری، برای مشاهده وضعیت همه کانتینرها باید آرایه <code>containerStatuses</code> در خروجی JSON پاد بررسی شود.</p>



<h2 id="h-جدول-نهایی-هر-تغییر-چه-اثری-روی-کانتینر-و-پاد-دارد" class="wp-block-heading"><strong>جدول نهایی: هر تغییر چه اثری روی کانتینر و پاد دارد؟</strong></h2>



<p class="wp-block-paragraph">جدول زیر نشان می‌دهد در سناریوهای بررسی‌شده، چه زمانی کانتینر در همان پاد ری‌استارت می‌شود و چه زمانی پاد جدیدی با Pod UID متفاوت ایجاد می‌شود.</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><thead><tr><th><strong>سناریو</strong></th><th><strong>ری‌استارت کانتینر در همان پاد</strong></th><th><strong>ایجاد پاد جدید</strong></th><th><strong>تغییر Pod UID</strong></th></tr></thead><tbody><tr><td>متوقف شدن کانتینر با restartPolicy: Always</td><td>بله؛ kubelet کانتینر را در همان پاد دوباره اجرا می‌کند</td><td>خیر</td><td>خیر</td></tr><tr><td>شکست Liveness Probe بیش از آستانه تعیین‌شده</td><td>در صورت اجازه restartPolicy، بله</td><td>خیر؛ شکست Probe به‌خودی‌خود پاد جدیدی ایجاد نمی‌کند</td><td>خیر</td></tr><tr><td>وقوع CrashLoopBackOff</td><td>بله؛ کانتینر در همان پاد دوباره اجرا می‌شود</td><td>خیر</td><td>خیر</td></tr><tr><td>تغییر ایمیج در استقرار (Deployment)</td><td>خیر</td><td>بله؛ تغییر الگوی پاد باعث Rollout و ساخت پادهای جدید می‌شود</td><td>بله</td></tr><tr><td>اجرای kubectl rollout restart</td><td>خیر</td><td>بله؛ پادهای Deployment در جریان Rollout با پادهای جدید جایگزین می‌شوند</td><td>بله</td></tr><tr><td>صرف تغییر ConfigMap مصرف‌شده از طریق متغیر محیطی</td><td>خیر؛ متغیرهای محیطی کانتینر موجود به‌روزرسانی نمی‌شوند</td><td>خیر؛ تغییر ConfigMap به‌تنهایی پاد جدیدی ایجاد نمی‌کند&nbsp;</td><td>خیر&nbsp;</td></tr><tr><td>تغییر ConfigMap متصل‌شده به‌صورت Volume</td><td>خیر؛ به‌روزرسانی فایل‌ها باعث ری‌استارت خودکار کانتینر نمی‌شود</td><td>خیر</td><td>خیر</td></tr><tr><td>تغییر ConfigMap متصل‌شده با subPath</td><td>خیر؛ به‌روزرسانی‌های ConfigMap هم به فایل متصل‌شده منتقل نمی‌شوند</td><td>خیر</td><td>خیر</td></tr><tr><td>تغییر CPU با In-place Pod Resize</td><td>خیر؛ کانتینر ری‌استارت نمی‌شود</td><td>خیر</td><td>خیر</td></tr><tr><td>تغییر Memory براساس resizePolicy</td><td>با NotRequired نیازی به ری‌استارت نیست؛ با RestartContainer کانتینر در همان پاد دوباره اجرا می‌شود</td><td>خیر</td><td>خیر</td></tr></tbody></table></figure>



<h2 id="h-جمع-بندی" class="wp-block-heading">جمع‌بندی</h2>



<p class="wp-block-paragraph">با اینکه عبارت «ری‌استارت پاد» در گفت‌وگوهای فنی رایج است، اما از نظر فنی می‌تواند مبهم باشد. در برخی شرایط، kubelet کانتینر را در همان پاد دوباره اجرا می‌کند، اما در شرایط دیگر، کنترلرهایی مانند دیپلویمنت پاد قبلی را با پاد جدید جایگزین می‌کنند. تشخیص این تفاوت برای عیب‌یابی ری‌استارت پاد در کوبرنتیز اهمیت دارد.</p>



<p class="wp-block-paragraph">برای تشخیص این دو وضعیت، تعداد ری‌استارت کانتینر و Pod UID دو معیار کاربردی هستند. تعداد ری‌استارت به تشخیص اجرای مجدد کانتینر در همان پاد کمک می‌کند و Pod UID مشخص می‌کند که هویت پاد تغییر کرده است یا خیر.</p>



<p class="wp-block-paragraph">در نهایت، تغییر ConfigMap ،Image یا منابع، الزاما رفتار یکسانی ایجاد نمی‌کند. بسته به نوع تغییر و سازوکار مربوط به آن، ممکن است کانتینر در همان پاد دوباره اجرا شود، پاد جدیدی ساخته شود یا هیچ‌کدام از این اتفاق‌ها رخ ندهد. به همین دلیل، هنگام بررسی رفتار کوبرنتیز باید مشخص شود که تغییر در کانتینر رخ داده یا خود پاد جایگزین شده است.</p>



<p class="wp-block-paragraph"></p>
<p>The post <a href="https://hamravesh.com/blog/kubernetes-container-restart-vs-pod-replacement/">ری‌استارت کانتینر یا ساخت پاد جدید؛ کوبرنتیز چگونه تصمیم می‌گیرد؟</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/kubernetes-container-restart-vs-pod-replacement/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>مدیریت داخلی ارتقا کوبرنتیز چه هزینه‌ای دارد؟ بررسی نقش کوبرنتیز مدیریت‌شده</title>
		<link>https://hamravesh.com/blog/hidden-costs-of-kubernetes-upgrades/</link>
					<comments>https://hamravesh.com/blog/hidden-costs-of-kubernetes-upgrades/#respond</comments>
		
		<dc:creator><![CDATA[هم‌روش]]></dc:creator>
		<pubDate>Mon, 10 Aug 2026 12:30:13 +0000</pubDate>
				<category><![CDATA[دواپس]]></category>
		<category><![CDATA[کوبرنتیز]]></category>
		<guid isPermaLink="false">https://hamravesh.com/blog/?p=5572</guid>

					<description><![CDATA[<p>ارتقای کوبرنتیز فقط به تغییر شماره نسخه محدود نمی‌شود. هر ارتقا می‌تواند مجموعه‌ای از فعالیت‌های فنی مانند نصب Patchها، بررسی APIهای منسوخ‌شده، رفع ناسازگاری Add-onها و اطمینان از سازگاری وابستگی‌های مختلف پلتفرم را به همراه داشته باشد. در پلتفرم‌هایی که بر پایه چندین پروژه متن‌باز ساخته شده‌اند، دنبال کردن تغییرات پروژه‌های Upstream هم به بخشی از فرایند نگهداری تبدیل می‌شود.</p>
<p>The post <a href="https://hamravesh.com/blog/hidden-costs-of-kubernetes-upgrades/">مدیریت داخلی ارتقا کوبرنتیز چه هزینه‌ای دارد؟ بررسی نقش کوبرنتیز مدیریت‌شده</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">ارتقا کوبرنتیز فقط به تغییر شماره نسخه محدود نمی‌شود. هر ارتقا می‌تواند مجموعه‌ای از فعالیت‌های فنی مانند نصب Patchها، بررسی APIهای منسوخ‌شده، رفع ناسازگاری Add-onها و اطمینان از سازگاری وابستگی‌های مختلف پلتفرم را به همراه داشته باشد. در پلتفرم‌هایی که بر پایه چند پروژه متن‌باز ساخته شده‌اند، دنبال کردن تغییرات پروژه‌های Upstream هم به بخشی از فرایند نگهداری تبدیل می‌شود.</p>



<p class="wp-block-paragraph">انجام این فعالیت‌ها به زمان و ظرفیت مهندسی نیاز دارد؛ ظرفیتی که می‌تواند صرف توسعه قابلیت‌های جدید یا سایر اولویت‌های محصول شود. به همین دلیل، نگهداری کوبرنتیز در بسیاری از تیم‌ها، با برنامه توسعه محصول برای استفاده از زمان مهندسی رقابت می‌کند. در این مطلب، فرایندهای اصلی نگهداری و ارتقا کوبرنتیز، عوامل مؤثر بر پیچیدگی این فرایند و راهکارهای مدیریت آن را بررسی می‌کنیم.</p>



<h2 id="h-نگهداری-کوبرنتیز-زمان-تیم-را-صرف-چه-کارهایی-می-کند" class="wp-block-heading">نگهداری کوبرنتیز زمان تیم را صرف چه کارهایی می‌کند؟</h2>



<p class="wp-block-paragraph">نگهداری کوبرنتیز مجموعه‌ای از فعالیت‌های مستمر است که فقط به زمان اجرای ارتقا محدود نمی‌شود. تیم پلتفرم باید تغییرات خود کوبرنتیز و اجزای وابسته را دنبال کند، سازگاری آن‌ها را بررسی کند و پس از هر تغییر، از عملکرد درست پلتفرم مطمئن شود. مهم‌ترین بخش‌های این فرایند عبارت‌اند از:</p>



<ul class="wp-block-list">
<li><strong>ارتقا نسخه و نصب اصلاحیه‌ها (Patch):</strong> تیم باید نسخه‌ها و اصلاحیه‌های جدید، از جمله اصلاحیه‌های امنیتی را دنبال و برای اعمال آن‌ها روی کلاسترها برنامه‌ریزی کند.</li>



<li><strong>رسیدگی به APIهای منسوخ‌شده: </strong>نسخه‌های قدیمی API ابتدا منسوخ می‌شوند و ممکن است در نسخه‌های بعدی دیگر ارائه نشوند. به همین دلیل، تیم باید وابستگی فایل‌های YAML، کلاینت‌های API، کنترل‌کننده‌ها و یکپارچه‌سازی‌ها به این APIها را شناسایی کند و در صورت نیاز، آن‌ها را به نسخه‌های جدیدتر انتقال دهد.</li>



<li><strong>رفع ناسازگاری افزونه‌ها (Add-on):</strong> ابزارها و افزونه‌های نصب‌شده روی کلاستر ممکن است با نسخه جدید کوبرنتیز سازگار نباشند، بنابراین تیم باید سازگاری آن‌ها را بررسی کند و در صورت نیاز، نسخه مناسب‌تری از آن‌ها را به کار بگیرد.</li>



<li><strong>ارتقا هلم چارت‌ها (Helm Chart):</strong> نسخه‌های جدید هلم چارت‌ها باید از نظر تغییر مانیفست‌ها (Manifest)، وابستگی‌ها و سازگاری با کلاستر بررسی شوند. حتی اگر بررسی مانیفست‌ها بدون خطا انجام شود، ممکن است برخی ناسازگاری‌ها فقط هنگام اجرای واقعی سیستم آشکار شوند.</li>



<li><strong>دنبال‌کردن تغییرات پروژه‌های بالادستی (Upstream):</strong> پلتفرم‌های مبتنی بر کوبرنتیز معمولا از چند پروژه متن‌باز تشکیل شده‌اند. تغییراتی مانند انتشار نسخه‌های جدید، ارائه اصلاحیه‌های امنیتی یا پایان پشتیبانی هر یک از این پروژه‌ها می‌تواند تیم را به ارتقا یکی از اجزای پلتفرم ملزم کند.</li>



<li><strong>آزمایش و پایش پس از تغییرات:</strong> تغییرات باید پیش از استقرار بررسی شوند و پس از اجرا هم عملکرد سرویس‌ها در محیط واقعی پایش شود؛ زیرا برخی ناسازگاری‌ها فقط هنگام اجرا یا پس از گذشت زمان آشکار می‌شوند.</li>
</ul>



<h2 id="h-حجم-بار-نگهداری-چقدر-است" class="wp-block-heading">حجم بار نگهداری چقدر است؟</h2>



<p class="wp-block-paragraph">میزان زمانی که نگهداری کوبرنتیز از تیم مهندسی می‌گیرد، به عواملی مانند تعداد کلاسترها، اندازه محیط، معماری پلتفرم و میزان خودکارسازی فرایندها بستگی دارد. بنابراین، نمی‌توان عدد ثابتی را برای همه محیط‌های مبتنی بر کوبرنتیز در نظر گرفت. بااین‌حال، تجربه‌های منتشرشده نشان می‌دهند که حجم این بار نگهداری در محیط‌های مختلف یکسان نیست.</p>



<p class="wp-block-paragraph">Munib Ali، مدیر مهندسی SRE در Fairwinds، می‌گوید در بسیاری از استقرارهای متوسط EKS (مخفف Amazon Elastic Kubernetes Service، سرویس مدیریت‌شده کوبرنتیز در زیرساخت ابری AWS)، انجام یک ارتقا Minor در سه منطقه (Region) می‌تواند چهار تا شش هفته تلاش مهندسی مصرف کند و توسعه دو تا سه قابلیت در سطح نقشه راه را به تعویق اندازد. این عدد که یک مشاهده تجربی از سوی Fairwinds است، به شرایط محیط بستگی دارد و نباید به همه کلاسترهای کوبرنتیز تعمیم داده شود</p>



<p class="wp-block-paragraph">همچنین Jehoszafat Zimnowoda و Matthias Erll، مهندسان ارشد نرم‌افزار در Akamai، انتشارهای سه سال گذشته ۱۴ پروژه متن‌باز را بررسی کرده‌اند. بر اساس تجربه و تحلیل آن‌ها، یک پلتفرم متکی به این مجموعه پروژه‌ها ممکن است در هر سال با ۲ تا ۵ ارتقا اصلی، ۴۳ تا ۵۲ ارتقا فرعی و ۲۷۶ تا ۳۲۷ اصلاحیه روبه‌رو شود. این داده هم به همان پروژه‌های بررسی‌شده مربوط است و معیار عمومی همه پلتفرم‌های کوبرنتیز نیست.</p>



<h2 id="h-چرا-ارتقا-کوبرنتیز-پیچیده-تر-از-یک-ارتقا-نسخه-version-bump-است" class="wp-block-heading">چرا ارتقا کوبرنتیز پیچیده‌تر از یک ارتقا نسخه (Version Bump) است؟</h2>



<p class="wp-block-paragraph">چند عامل فنی مانند تغییر APIها، وابستگی میان نسخه اجزای مختلف کلاستر و بررسی سازگاری افزونه‌ها (Add-on) و چارت‌های <a href="https://hamravesh.com/blog/what-is-helm/#h-%D8%B3%D8%A7%D8%AE%D8%AA%D8%A7%D8%B1-%DA%86%D8%A7%D8%B1%D8%AA-%D9%87%D8%A7-%D8%AF%D8%B1-helm" data-type="link" data-id="https://hamravesh.com/blog/what-is-helm/#h-%D8%B3%D8%A7%D8%AE%D8%AA%D8%A7%D8%B1-%DA%86%D8%A7%D8%B1%D8%AA-%D9%87%D8%A7-%D8%AF%D8%B1-helm" target="_blank" rel="noreferrer noopener">Helm</a> باعث می‌شوند فرایند ارتقا کلاستر کوبرنتیز، پیچیده‌تر از یک به‌روزرسانی ساده باشد. </p>



<h3 id="h-تغییر-و-حذف-apiها" class="wp-block-heading">تغییر و حذف APIها</h3>



<p class="wp-block-paragraph">با تکامل API کوبرنتیز، نسخه‌های قدیمی ابتدا منسوخ و در نهایت حذف می‌شوند. پس از حذف یک نسخه API، آن نسخه دیگر توسط kube-apiserver ارائه نمی‌شود و مانیفست‌ها یا کلاینت‌هایی که همچنان به آن وابسته‌اند باید به نسخه‌ای پشتیبانی‌شده مهاجرت کنند.</p>



<p class="wp-block-paragraph">مهاجرت APIهای منسوخ‌شده کوبرنتیز ممکن است به تغییر فایل‌های YAML، کلاینت‌های API، کنترل‌کننده‌ها و یکپارچه‌سازی‌های سفارشی نیاز داشته باشد. مستندات رسمی، ابزار <code>kubectl convert</code> را نیز برای تبدیل خودکار بعضی منابع معرفی می‌کنند؛ بااین‌حال، این تبدیل ممکن است از مقادیر پیش‌فرض نامناسب استفاده کند و نتیجه آن باید با مراجعه به مستندات API همان منبع بررسی شود.</p>



<h3 id="h-وابستگی-میان-نسخه-اجزا" class="wp-block-heading">وابستگی میان نسخه اجزا</h3>



<p class="wp-block-paragraph">پروژه کوبرنتیز شاخه‌های سه نسخه Minor اخیر را نگهداری می‌کند و نسخه‌های ۱.۱۹ به بعد تقریباً یک سال پشتیبانی از Patch دریافت می‌کنند. بنابراین، باقی‌ماندن روی نسخه‌های قدیمی نمی‌تواند برای مدتی نامحدود ادامه پیدا کند و برنامه ارتقا باید چرخه پشتیبانی کوبرنتیز را در نظر بگیرد.</p>



<p class="wp-block-paragraph">اجزای مختلف کلاستر همچنین باید از قواعد اختلاف نسخه (Version Skew؛ محدوده مجاز تفاوت نسخه میان اجزای مختلف کوبرنتیز) پیروی کنند. برای مثال، kubelet نباید از kube-apiserver جدیدتر باشد و می‌تواند حداکثر سه نسخه Minor از آن قدیمی‌تر باشد. kube-proxy نیز نباید از kube-apiserver جدیدتر باشد و باید محدودیت اختلاف نسخه با kube-apiserver و kubelet را رعایت کند.</p>



<p class="wp-block-paragraph">این محدودیت‌ها بر ترتیب ارتقا اثر می‌گذارند. ابتدا kube-apiserver ارتقا پیدا می‌کند. در کلاسترهای دارای <a href="https://hamravesh.com/blog/what-is-high-availability" data-type="link" data-id="https://hamravesh.com/blog/what-is-high-availability" target="_blank" rel="noreferrer noopener">دسترس‌پذیری بالا</a>، تمام نمونه‌های kube-apiserver که سایر اجزای Control Plane ممکن است با آن‌ها ارتباط برقرار کنند، باید پیش از ارتقا kube-controller-manager، ‏kube-scheduler و cloud-controller-manager ارتقا یافته باشند. پس از آن، kubelet و kube-proxy را می‌توان با رعایت محدوده مجاز اختلاف نسخه ارتقا داد.</p>



<h3 id="h-ناسازگاری-add-onها-و-helm-chartها" class="wp-block-heading">ناسازگاری Add-onها و Helm Chartها</h3>



<p class="wp-block-paragraph">ارتقا افزونه‌ها و هلم چارت‌ها هم می‌تواند با چالش‌هایی همراه باشد. برخی نسخه‌های جدید هلم چارت تغییراتی در فیلدهای تغییرناپذیر (Immutable Fields) منابع کوبرنتیز ایجاد می‌کنند که می‌تواند فرایند ارتقا را با مشکل مواجه کند.</p>



<p class="wp-block-paragraph">همه مشکلات در مرحله بررسی مانیفست‌ها مشخص نمی‌شوند و بعضی ناسازگاری‌ها فقط هنگام اجرای واقعی سامانه آشکار می‌شوند. پیش از اعمال تغییرات، می‌توان مانیفست‌های رندرشده نسخه فعلی و نسخه جدید را با یکدیگر مقایسه کرد، آن‌ها را با طرح‌واره OpenAPI (همان OpenAPI schema) کوبرنتیز و CRDهای اضافه‌شده سنجید و تغییرات را به‌صورت Dry Run (بررسی آزمایشی یک تغییر، بدون اعمال و ذخیره‌کردن واقعی آن در کلاستر) در برابر کلاستر در حال اجرا بررسی کرد.</p>



<p class="wp-block-paragraph">بااین‌حال، استقرار بدون خطا تضمین نمی‌کند که برنامه همچنان مطابق انتظار کار می‌کند. به همین دلیل، تست‌های یکپارچگی باید روی کلاستر در حال اجرا انجام شوند تا ارتباط سرویس‌ها با وابستگی‌ها و در دسترس بودن Endpointها بررسی شود. پایش بلندمدت نیز ضروری است؛ زیرا مشکلاتی مانند کمبود حافظه، محدودشدن CPU یا تمام‌شدن فضای دیسک ممکن است چند روز یا چند هفته پس از تغییر آشکار شوند.</p>



<h2 id="h-چگونه-بار-نگهداری-را-ساختاریافته-تر-کنیم" class="wp-block-heading">چگونه بار نگهداری را ساختاریافته‌تر کنیم؟</h2>



<p class="wp-block-paragraph">اگرچه مدیریت چرخه عمر کوبرنتیز همواره به فعالیت‌های نگهداری نیاز دارد، اما می‌توان بخشی از این فرایند را با برنامه‌ریزی و خودکارسازی ساختاریافته‌تر کرد. در ادامه، برخی اقدام‌های پیشنهادی برای ساختاریافته‌ترکردن این فرایند را بررسی می‌کنیم:</p>



<ul class="wp-block-list">
<li><strong>خودکارسازی شناسایی نسخه‌های جدید و ایجاد درخواست تغییر (Pull Request): </strong>بخشی از فرایند شناسایی نسخه‌های جدید پروژه‌های متن‌باز و هلم چارت‌ها را می‌توان خودکار کرد تا پس از انتشار نسخه جدید، یک درخواست تغییر برای بررسی و اعمال به‌روزرسانی ایجاد شود.</li>



<li><strong>شناسایی APIهای منسوخ‌شده: </strong>مستندات رسمی کوبرنتیز استفاده از هشدارهای کلاینت، معیارها و اطلاعات Audit را برای یافتن وابستگی به APIهای منسوخ‌شده پیشنهاد می‌کنند. پس از شناسایی این وابستگی‌ها، فایل‌های YAML، کلاینت‌های API، کنترل‌کننده‌ها و یکپارچه‌سازی‌های سفارشی باید پیش از حذف نسخه قدیمی به APIهای منسوخ‌نشده مهاجرت کنند.</li>



<li><strong>اعتبارسنجی مانیفست‌های رندرشده پیش از اعمال تغییرات:</strong> می‌توان تمام مانیفست‌هایی را که پلتفرم مستقر می‌کند با طرح‌واره OpenAPI کوبرنتیز و CRDهای اضافه‌شده اعتبارسنجی کرد. مقایسه مانیفست‌های نسخه فعلی و نسخه جدید و اجرای Dry Run در برابر کلاستر در حال اجرا نیز می‌تواند تغییرات مخرب احتمالی را پیش از اعمال آن‌ها آشکار کند</li>



<li><strong>اجرای تست‌های یکپارچگی و پایش پس از ارتقا:</strong> اجرای موفق فرایند استقرار، به‌تنهایی تضمین نمی‌کند که سامانه همچنان مطابق انتظار عمل می‌کند. به همین دلیل، اجرای تست‌های یکپارچگی روی کلاسترِ در حال اجرا و پایش مداوم سامانه پس از ارتقا، بخشی از فرایند نگهداری محسوب می‌شود.</li>
</ul>



<p class="wp-block-paragraph">بااین‌حال، خودکارسازی، فقط بخشی از فعالیت‌های نگهداری را ساده‌تر می‌کند و همچنان مسئولیت‌هایی مانند برنامه‌ریزی ارتقا، بررسی سازگاری وابستگی‌ها و تصمیم‌گیری درباره نگهداری مستمر بر عهده تیم فنی باقی می‌ماند. به بیان دیگر، خودکارسازی می‌تواند بخشی از بار عملیاتی را کاهش دهد، اما مسئولیت مدیریت چرخه عمر کوبرنتیز را حذف نمی‌کند.</p>



<h2 id="h-مدیریت-داخلی-کوبرنتیز-چه-زمانی-توجیه-دارد" class="wp-block-heading">مدیریت داخلی کوبرنتیز چه زمانی توجیه دارد؟</h2>



<p class="wp-block-paragraph">مدیریت داخلی کوبرنتیز برای همه سازمان‌ها انتخاب مناسبی نیست، اما در برخی شرایط می‌تواند توجیه فنی و اقتصادی داشته باشد. برای مثال، اگر کوبرنتیز بخشی از خود محصول سازمان باشد، مالکیت کامل و مدیریت داخلی آن می‌تواند توجیه راهبردی داشته باشد. همچنین در سازمان‌هایی که مقیاس عملیات به‌اندازه‌ای بزرگ است که حتی یک بهبود محدود در بهره‌وری، ارزش اقتصادی قابل‌توجهی ایجاد می‌کند، سرمایه‌گذاری روی مدیریت داخلی پلتفرم ممکن است منطقی باشد.</p>



<p class="wp-block-paragraph">نمونه دیگر، سازمان‌هایی هستند که می‌توانند تشکیل و نگهداری یک تیم پلتفرم بسیار تخصصی را از نظر عملیاتی و اقتصادی توجیه کنند. این نمونه‌ها تنها بخشی از موقعیت‌هایی هستند که مدیریت داخلی کوبرنتیز می‌تواند در آن‌ها ارزش ایجاد کند و نباید آن‌ها را به‌عنوان فهرست کامل معیارهای تصمیم‌گیری برای همه سازمان‌ها در نظر گرفت.</p>



<h2 id="h-چگونه-واگذاری-نگهداری-کوبرنتیز-ظرفیت-تیم-داخلی-را-آزاد-می-کند" class="wp-block-heading">چگونه واگذاری نگهداری کوبرنتیز ظرفیت تیم داخلی را آزاد می‌کند؟</h2>



<p class="wp-block-paragraph">Fairwinds بر اساس تجربه خود گزارش می‌کند که انتقال مسئولیت انجام ارتقا، اعمال اصلاحیه‌ها و مدیریت افزونه‌ها از برنامه کاری داخلی به یک تیم تخصصی Kubernetes SRE، می‌تواند بخشی از زمان مهندسان ارشد را آزاد کند. البته این نتیجه، تجربه Fairwinds است و نباید به‌عنوان پیامد قطعی این الگو برای همه سازمان‌ها در نظر گرفته شود. همچنین زمان آزادشده می‌تواند صرف توسعه قابلیت‌های جدید، بهبود قابلیت اطمینان، بهینه‌سازی عملکرد و ارتقا تجربه توسعه‌دهندگان شود. به این ترتیب، بخشی از ظرفیت مهندسی به فعالیت‌هایی اختصاص پیدا می‌کند که اثر مستقیم‌تری بر محصول و اولویت‌های مهندسی دارند.</p>



<p class="wp-block-paragraph">در سازمان‌هایی که تمایلی به مدیریت مستقیم همه فعالیت‌های عملیاتی کوبرنتیز ندارند، استفاده از خدمات مدیریت‌شده کوبرنتیز (Kubernetes as a Service یا KaaS) هم می‌تواند یکی از گزینه‌های قابل بررسی باشد. البته قابلیت‌ها و مسئولیت‌های هر سرویس مدیریت‌شده به ارائه‌دهنده آن بستگی دارد و باید بر اساس مستندات رسمی همان سرویس ارزیابی شود.</p>



<div class="wp-block-dh-blog-card-database-block card database">
<div class="wp-block-group row align-items-center is-nowrap is-layout-flex wp-container-core-group-is-layout-8f761849 wp-block-group-is-layout-flex">
<div class="wp-block-group col-md"><div class="wp-block-group__inner-container is-layout-flow wp-block-group-is-layout-flow">
<h3 id="h-کوبرنتیز-مدیریت-شده-هم-روش-راهی-مطمئن-برای-رشد-بی-وقفه" class="wp-block-heading">💡 کوبرنتیز مدیریت‌شده هم‌روش، راهی مطمئن برای رشد بی‌وقفه</h3>



<p class="wp-block-paragraph">راهکار کوبرنتیز مدیریت شده، بر بستر ابر اختصاصی یا به صورت On-Premises</p>



<p class="wp-block-paragraph"><br>✅ کاهش هزینه‌های عملیاتی<br>✅ احراز هویت یکپارچه با اتصال به SSO سازمانی<br>✅ قابل استقرار روی سرورهای on-premises</p>



<p class="wp-block-paragraph"></p>
</div></div>
</div>



<div class="wp-block-group col-md-auto"><div class="wp-block-group__inner-container is-layout-flow wp-block-group-is-layout-flow">
<p class="btn btn--main btn--wide wp-block-paragraph"><a type="link" href="https://hamravesh.com/managed-kubernetes" id="https://hamravesh.com/managed-kubernetes" target="_blank" rel="noreferrer noopener">کوبرنتیز مدیریت‌شده هم‌روش</a></p>
</div></div>
</div>



<h2 id="h-جمع-بندی-کوبرنتیز-باید-قابل-پیش-بینی-باشد-نه-مصرف-کننده-دائمی-تمرکز-تیم" class="wp-block-heading">جمع‌بندی: کوبرنتیز باید قابل‌پیش‌بینی باشد، نه مصرف‌کننده دائمی تمرکز تیم</h2>



<p class="wp-block-paragraph">مدیریت چرخه عمر کوبرنتیز فرایندی مستمر است و با پایان یک ارتقا نسخه به پایان نمی‌رسد. در این فرایند، انتشار نسخه‌های جدید، تغییر APIها، به‌روزرسانی وابستگی‌ها و ارزیابی تغییرات، همگی بخشی از فعالیت‌هایی هستند که در طول زمان ادامه پیدا می‌کنند و به برنامه‌ریزی و رسیدگی مداوم نیاز دارند.</p>



<p class="wp-block-paragraph">خودکارسازی می‌تواند بخشی از فعالیت‌های مرتبط با ارتقا کوبرنتیز را ساده‌تر و سریع‌تر کند، اما جایگزین مدیریت چرخه عمر کوبرنتیز نمی‌شود. در نهایت، هر سازمان باید تصمیم بگیرد که آیا مدیریت کامل این پیچیدگی برای آن ارزش راهبردی دارد یا بهتر است بخشی از مسئولیت‌های عملیاتی را به یک تیم متخصص واگذار کند تا ظرفیت بیشتری برای توسعه محصول و سایر اولویت‌های مهندسی آزاد شود.</p>



<p class="wp-block-paragraph"></p>
<p>The post <a href="https://hamravesh.com/blog/hidden-costs-of-kubernetes-upgrades/">مدیریت داخلی ارتقا کوبرنتیز چه هزینه‌ای دارد؟ بررسی نقش کوبرنتیز مدیریت‌شده</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/hidden-costs-of-kubernetes-upgrades/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>سنتری چیست؟ از پایش خطای اپلیکیشن تا تحلیل عملکرد در سطح کد</title>
		<link>https://hamravesh.com/blog/what-is-sentry/</link>
					<comments>https://hamravesh.com/blog/what-is-sentry/#respond</comments>
		
		<dc:creator><![CDATA[هم‌روش]]></dc:creator>
		<pubDate>Wed, 05 Aug 2026 08:27:51 +0000</pubDate>
				<category><![CDATA[دواپس]]></category>
		<category><![CDATA[مشاهده‌پذیری]]></category>
		<category><![CDATA[مقالات]]></category>
		<guid isPermaLink="false">https://hamravesh.com/blog/?p=5564</guid>

					<description><![CDATA[<p>Sentry (سنتری) با جمع‌آوری و ارتباط‌دادن این داده‌ها، دید یکپارچه‌تری از رفتار اپلیکیشن در زمان وقوع مشکل ارائه می‌دهد. به همین دلیل، Sentry فقط یک ابزار ثبت خطا نیست، بلکه داده‌های مرتبط با خطاها، Traceها، لاگ‌ها و مشاهده رفتار واقعی کاربران را در کنار یکدیگر قرار می‌دهد تا عیب‌یابی بر پایه شواهد کامل‌تری انجام شود. </p>
<p>The post <a href="https://hamravesh.com/blog/what-is-sentry/">سنتری چیست؟ از پایش خطای اپلیکیشن تا تحلیل عملکرد در سطح کد</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">فرض کنید نسخه جدید یک اپلیکیشن منتشر شده، اما پس از انتشار، بخشی از درخواست‌های پرداخت کامل نمی‌شوند. در رابط کاربری هم خطای مشخصی دیده نمی‌شود و گزارش کاربران هم اطلاعات کافی برای بازتولید مشکل در اختیار تیم فنی قرار نمی‌دهد. در نتیجه، مشخص نیست اختلال دقیقا از کدام بخش سیستم آغاز شده است. برای پیدا کردن علت مشکل، فقط مشاهده یک پیام خطا کافی نیست. تیم فنی باید بداند خطا برای کدام کاربران، در کدام نسخه و در امتداد کدام درخواست رخ داده است. همچنین لازم است ارتباط میان خطاها، ردیابی توزیع‌شده یا Distributed Tracing، لاگ‌ها و سایر شواهد فنی را بررسی کند تا مسیر رسیدن به علت اصلی کوتاه‌تر شود.</p>



<p class="wp-block-paragraph">Sentry (سنتری) با جمع‌آوری و ارتباط‌دادن این داده‌ها، دید یکپارچه‌تری از رفتار اپلیکیشن در زمان وقوع مشکل ارائه می‌دهد. به همین دلیل، Sentry فقط ابزار ثبت خطا نیست، بلکه خطاها، Traceها (مسیر اجرای درخواست‌ها)، لاگ‌ها و بازپخش تعاملات کاربر را در کنار یکدیگر قرار می‌دهد تا تیم فنی بتواند مشکل را با شواهد کامل‌تری بررسی کند. در ادامه بررسی می‌کنیم که Sentry چیست، چه قابلیت‌ها و محدودیت‌هایی دارد و روش‌های استقرار آن چه تفاوتی با یکدیگر دارند.</p>



<h2 id="h-sentry-چیست" class="wp-block-heading"><strong>Sentry چیست؟</strong></h2>



<p class="wp-block-paragraph">Sentry پلتفرمی برای پایش، تحلیل و عیب‌یابی مشکلات اپلیکیشن است. این پلتفرم داده‌هایی مانند خطاها، Traceها، لاگ‌ها، اطلاعات عملکردی و اطلاعات زمینه‌ای (Context) رخدادها را جمع‌آوری و به یکدیگر مرتبط می‌کند تا بررسی علت مشکلات با شواهد کامل‌تری انجام شود.</p>



<p class="wp-block-paragraph">نرم‌افزار Sentry فعالیت خود را به‌عنوان ابزاری برای پایش خطا آغاز کرد، اما در سال‌های اخیر قابلیت‌هایی مانند Logs ،Tracing ،Profiling و Session Replay هم به آن اضافه شدند.</p>



<p class="wp-block-paragraph">هدف و کاربرد Sentry کاهش حدس‌وگمان در فرایند عیب‌یابی و فراهم‌کردن اطلاعات لازم برای تحلیل سریع‌تر مشکلات است. بااین‌حال، این پلتفرم جایگزین همه ابزارهای مشاهده‌پذیری نیست و در بسیاری از معماری‌ها، برای پایش کامل زیرساخت و منابع اجرایی، همچنان از ابزارهای دیگری در کنار آن استفاده می‌شود.</p>



<h2 id="h-sentry-چگونه-کار-می-کند" class="wp-block-heading"><strong>Sentry چگونه کار می‌کند؟</strong></h2>



<p class="wp-block-paragraph">فرایند کار Sentry را می‌توان در چهار مرحله بررسی کرد:</p>



<h3 id="h-۱-اتصال-اپلیکیشن-به-sentry-از-طریق-sdk" class="wp-block-heading"><strong>۱. اتصال اپلیکیشن به Sentry از طریق SDK</strong></h3>



<p class="wp-block-paragraph">نخستین گام، نصب و پیکربندی کیت توسعه نرم‌افزار (SDK) متناسب با زبان و فریم‌ورک اپلیکیشن است. سنتری برای بسیاری از پلتفرم‌های بک‌اِند، فرانت‌اِند، موبایل، دسکتاپ و توسعه بازی‌ها پشتیبانی می‌کند. <a href="https://docs.sentry.io/platforms" data-type="link" data-id="https://docs.sentry.io/platforms" target="_blank" rel="noreferrer noopener">لیست کامل پلتفرم‌های پشتیبانی شده توسط سنتری</a> در وب‌سایت سنتری قابل مشاهده است. پس از انجام تنظیمات اولیه، SDK رخدادها و اطلاعات زمینه‌ای مرتبط را از اپلیکیشن جمع‌آوری و به پروژه Sentry ارسال می‌کند.</p>



<h3 id="h-۲-جمع-آوری-خطا-و-اطلاعات-زمینه-ای" class="wp-block-heading"><strong>۲. جمع‌آوری خطا و اطلاعات زمینه‌ای</strong></h3>



<p class="wp-block-paragraph">هنگام وقوع یک خطا، Sentry تنها پیام خطا را ثبت نمی‌کند. این پلتفرم اطلاعاتی مانند نوع و پیام خطا، Stack Trace، زمان و محیط وقوع، نسخه اپلیکیشن، مسیر یا درخواست مرتبط و اطلاعات زمینه‌ای کاربر (در صورت پیکربندی مجاز) را ذخیره می‌کند. علاوه بر این، تیم توسعه می‌تواند Tagها و داده‌های تکمیلی را ارسال کند تا فیلتر، جست‌وجو و تحلیل رخدادها ساده‌تر شود.</p>



<h3 id="h-۳-ارتباط-خطاها-و-لاگ-ها-با-trace-و-span" class="wp-block-heading"><strong>۳. ارتباط خطاها و لاگ‌ها با Trace و Span</strong></h3>



<p class="wp-block-paragraph">نمایش یک خطا به‌تنهایی همیشه برای یافتن علت اصلی کافی نیست. در Sentry می‌توان لاگ‌ها را در ارتباط با Trace و Span مربوط به همان جریان بررسی کرد. در نتیجه، تیم توسعه علاوه بر رخداد خطا، Trace و لاگ‌های مرتبط با عملیات موردنظر را نیز در اختیار دارد.</p>



<p class="wp-block-paragraph"><strong>تفاوت Error و Span چیست؟</strong></p>



<p class="wp-block-paragraph">Error وقوع یک خطا یا استثنا را همراه با اطلاعات زمینه‌ای آن ثبت می‌کند؛ اما Span نمایانگر یک عملیات مشخص در مسیر اجرای درخواست است و مدت اجرای آن عملیات را نشان می‌دهد. به‌طور خلاصه، Error نشان می‌دهد چه مشکلی رخ داده است و Span نشان می‌دهد درخواست چه مسیری را طی کرده و زمان در کدام عملیات صرف شده است.</p>



<h3 id="h-۴-تحلیل-عملکرد-در-سطح-trace-و-تابع" class="wp-block-heading"><strong>۴. تحلیل عملکرد در سطح Trace و تابع</strong></h3>



<p class="wp-block-paragraph">Tracing و Profiling دو نقش متفاوت در تحلیل عملکرد دارند. قابلیت Tracing نشان می‌دهد زمان اجرای یک درخواست میان عملیات یا سرویس‌های مختلف چگونه توزیع شده و کدام بخش بیشترین زمان را مصرف کرده است. اگر برای یافتن علت کندی به جزئیات بیشتری نیاز باشد، Profiling بررسی را تا سطح تابع‌ها و میزان مصرف پردازنده ادامه می‌دهد.</p>



<h2 id="h-قابلیت-های-اصلی-sentry-چیست" class="wp-block-heading"><strong>قابلیت‌های اصلی Sentry چیست؟</strong></h2>



<p class="wp-block-paragraph">هر یک از قابلیت‌های Sentry برای پاسخ به یک نیاز مشخص در فرایند پایش، عیب‌یابی یا تحلیل عملکرد طراحی شده‌اند که در ادامه آن‌ها را جداگانه بررسی می‌کنیم.</p>



<h3 id="h-پایش-و-تحلیل-خطاها" class="wp-block-heading"><strong>پایش و تحلیل خطاها</strong></h3>



<p class="wp-block-paragraph">یکی از مهم‌ترین کاربردهای Sentry، پایش خطای اپلیکیشن در محیط عملیاتی است. زمانی که یک خطای مدیریت‌نشده در محیط عملیاتی رخ می‌دهد، این پلتفرم علاوه بر ثبت پیام خطا، اطلاعاتی مانند Stack Trace، نسخه اپلیکیشن، محیط اجرا و زمان وقوع را هم ثبت می‌کند. همچنین در صورت پیکربندی پروژه، می‌توان اطلاعات زمینه‌ای و Tagهای موردنیاز را همراه هر رخداد ارسال کرد تا بررسی علت مشکل با جزئیات بیشتری انجام شود.</p>



<figure class="wp-block-image size-large"><img fetchpriority="high" decoding="async" width="1024" height="569" src="https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-01-1024x569.webp" alt="شناسایی و اولویت‌بندی مشکلات در سنتری" class="wp-image-5582" srcset="https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-01-1024x569.webp 1024w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-01-300x167.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-01-768x427.webp 768w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-01-1536x853.webp 1536w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-01-2048x1138.webp 2048w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-01-120x67.webp 120w" sizes="(max-width: 1024px) 100vw, 1024px" /><figcaption class="wp-element-caption">سنتری، اطلاعات موردنیاز برای بررسی هر مشکل عملکردی را در نمای یکپارچه ارائه می‌دهد. تیم فنی می‌تواند گستره تأثیر، روند تکرار و شواهد فنی مشکل را بررسی کند. همچنین امکان بررسی روند تکرار مشکل و ارتباط آن با نسخه‌های منتشرشده و نیز شناسایی تابع و کوئری‌های تکرارشونده موثر در افت عملکرد فراهم شده است.</figcaption></figure>



<p class="wp-block-paragraph">Sentry اطلاعاتی مانند تعداد دفعات وقوع و تعداد کاربران تحت‌تأثیر را در اختیار تیم قرار می‌دهد تا مشکلات بر اساس دامنه اثر آن‌ها اولویت‌بندی شوند. البته این پلتفرم معمولا خطاها را پس از وقوع در محیط عملیاتی ثبت و تحلیل می‌کند؛ بنابراین هدف آن، فراهم‌کردن اطلاعات لازم برای تشخیص و رفع سریع‌تر مشکلات است، نه جلوگیری از وقوع آن‌ها.</p>



<h3 id="h-پایش-عملکرد-و-distributed-tracing" class="wp-block-heading"><strong>پایش عملکرد و Distributed Tracing</strong></h3>



<p class="wp-block-paragraph">بررسی خطاها همیشه برای تشخیص علت کندی یک درخواست کافی نیست. Sentry با قابلیت ردیابی توزیع شده، مسیر اجرای هر درخواست را در میان سرویس‌ها و عملیات مختلف نمایش می‌دهد و مشخص می‌کند هر Span چه میزان زمان صرف کرده است.</p>



<figure class="wp-block-image size-large"><img decoding="async" width="1024" height="569" src="https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-02-1024x569.webp" alt="تحلیل مسیر اجرای درخواست‌ها در سنتری" class="wp-image-5584" srcset="https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-02-1024x569.webp 1024w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-02-300x167.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-02-768x427.webp 768w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-02-1536x853.webp 1536w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-02-2048x1138.webp 2048w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-02-120x67.webp 120w" sizes="(max-width: 1024px) 100vw, 1024px" /><figcaption class="wp-element-caption">سنتری با نمای آبشاری یک Trace، مسیر اجرای درخواست را از فرانت‌اند، سرویس‌های مختلف و پایگاه داده نمایش می‌دهد. مقایسه زمان اجرای عملیات مختلف به تیم فنی کمک می‌کند منشأ کندی را در میان اجزای وابسته پیدا کند، ارتباط والد و فرزند میان درخواست‌ها، توابع و کوئری‌ها را مشاهده کند و عملکرد صفحه را با شاخص‌های LCP ،FCP ،CLS و TTFB بسنجد.</figcaption></figure>



<p class="wp-block-paragraph">این قابلیت به تیم فنی کمک می‌کند سرویس یا بخشی از فرایند را که باعث افزایش زمان پاسخ شده شناسایی کند. در معماری‌های چندسرویسی هم می‌توان مسیر کامل یک درخواست را از ابتدا تا انتها مشاهده و ارتباط مشکلات عملکردی با خطاهای ثبت‌شده را دقیق‌تر بررسی کرد.</p>



<h3 id="h-بررسی-عملکرد-در-سطح-کد-با-profiling" class="wp-block-heading"><strong>بررسی عملکرد در سطح کد با Profiling</strong></h3>



<p class="wp-block-paragraph">قابلیت Tracing نشان می‌دهد کندی در کدام بخش از مسیر اجرای درخواست رخ داده است، اما همیشه علت دقیق آن را در سطح کد مشخص نمی‌کند. Profiling این بررسی را تا سطح فراخوانی تابع‌ها، فایل‌ها و خطوط کد ادامه می‌دهد و بخش‌هایی را نشان می‌دهد که بیشترین سهم را در مصرف CPU دارند.</p>



<p class="wp-block-paragraph">در Sentry، قابلیت Continuous Profiling برای تحلیل سرویس‌های بک‌اند و پردازش‌های طولانی‌مدت کاربرد دارد. همچنین UI Profiling عملکرد رابط کاربری را بررسی می‌کند تا عواملی که باعث کاهش پاسخ‌گویی یا روان بودن رابط کاربری می‌شوند، شناسایی شوند. ازآنجایی‌که Profiling می‌تواند حجم مصرف و نگهداری داده را افزایش دهد، Sentry امکان کنترل نحوه فعال‌سازی، چرخه اجرا و نرخ نمونه‌برداری این قابلیت را فراهم می‌کند.</p>



<h3 id="h-مشاهده-لاگ-های-ساختاریافته" class="wp-block-heading"><strong>مشاهده لاگ‌های ساختاریافته</strong></h3>



<p class="wp-block-paragraph">لاگ‌های ساختاریافته در Sentry می‌توانند همراه با فیلدهایی مانند شناسه کاربر، شناسه سفارش یا نام قابلیت ارسال شوند. وجود این فیلدها امکان جست‌وجو، فیلتر، گروه‌بندی و تعریف هشدار بر اساس ویژگی‌های مشخص را فراهم می‌کند.</p>



<p class="wp-block-paragraph">لاگ‌های ساختاریافته را می‌توان به Trace و Span مربوط به همان درخواست متصل کرد. به این ترتیب، هنگام بررسی یک خطا یا مشکل عملکردی، می‌توان لاگ‌های مرتبط با همان درخواست را در کنار سایر شواهد مشاهده کرد و مسیر رسیدن به علت اصلی را سریع‌تر دنبال کرد. Sentry همچنین امکان مشاهده زنده لاگ‌ها (Live Tail) و ساخت Alert و Dashboard بر اساس الگوهای ثبت‌شده را فراهم می‌کند.</p>



<p class="wp-block-paragraph">البته Sentry همه لاگ‌های اپلیکیشن را به‌صورت خودکار جمع‌آوری نمی‌کند. نحوه ثبت و ارسال لاگ‌ها به زبان برنامه‌نویسی، SDK و تنظیمات انجام‌شده در پروژه بستگی دارد.</p>



<h3 id="h-بازسازی-مسیر-کاربر-با-session-replay" class="wp-block-heading"><strong>بازسازی مسیر کاربر با Session Replay</strong></h3>



<p class="wp-block-paragraph">قابلیت مشاهده رفتار واقعی کاربران (Session Replay) به تیم فنی کمک می‌کند تعاملات کاربر با اپلیکیشن را پیش از بروز خطا مشاهده کند. در بسیاری از موارد، توضیحات کاربران برای بازتولید یک مشکل کافی نیست؛ اما با مشاهده روند واقعی استفاده از اپلیکیشن، می‌توان مراحل منتهی به خطا را دقیق‌تر بررسی کرد.</p>



<p class="wp-block-paragraph">ارزش این قابلیت زمانی بیشتر می‌شود که Session Replay در کنار خطاها، Trace و سایر داده‌های فنی تحلیل شود. در این شرایط، تیم توسعه علاوه بر مشاهده رفتار کاربر، می‌تواند رخداد ثبت‌شده و اطلاعات مربوط به همان درخواست را بررسی کند و با اتکا به شواهد کامل‌تر، علت مشکل را سریع‌تر تشخیص دهد.</p>



<figure class="wp-block-image size-large"><img decoding="async" width="1024" height="569" src="https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-03-1024x569.webp" alt="قابلیت Session Replay در سنتری" class="wp-image-5583" srcset="https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-03-1024x569.webp 1024w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-03-300x167.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-03-768x427.webp 768w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-03-1536x853.webp 1536w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-03-2048x1138.webp 2048w, https://hamravesh.com/blog/wp-content/uploads/2026/08/hamravesh-sentry-03-120x67.webp 120w" sizes="(max-width: 1024px) 100vw, 1024px" /><figcaption class="wp-element-caption">قابلیت Session Replay در سنتری، تعامل کاربر با اپلیکیشن را در کنار رویدادهای فنی بازسازی می‌کند. تیم توسعه می‌تواند ببیند کاربر چه اقداماتی انجام داده، در کدام مرحله با مشکل مواجه شده و هم‌زمان چه خطایی در برنامه ثبت شده است. Session Replay همچنین امکان شناسایی کلیک‌های بی‌نتیجه یا عصبی را فراهم می‌کند و قابلیت محافظت از اطلاعات حساس کاربران با پنهان‌سازی خودکار محتوای صفحه دارد.</figcaption></figure>



<p class="wp-block-paragraph">ازآنجایی‌که این قابلیت با تعاملات واقعی کاربران سروکار دارد، هنگام استفاده از آن باید به حفاظت از داده‌های حساس و رعایت حریم خصوصی توجه شود. جزئیات نحوه مدیریت این داده‌ها به تنظیمات و مستندات رسمی Session Replay وابسته است.</p>



<h3 id="h-تحلیل-نسخه-های-منتشرشده" class="wp-block-heading"><strong>تحلیل نسخه‌های منتشرشده</strong></h3>



<p class="wp-block-paragraph">قابلیت تحلیل انتشار نسخه‌ها (Release Health) به تیم توسعه کمک می‌کند اثر هر نسخه جدید را پس از انتشار بررسی کند. با نسبت‌دادن خطاها و داده‌های عملکردی به هر Release، می‌توان مشاهده کرد که آیا انتشار یک نسخه جدید، با افزایش خطاها، تغییر روند عملکرد یا بروز مشکلات جدید همراه بوده است یا خیر.</p>



<p class="wp-block-paragraph">این قابلیت زمانی ارزش بیشتری پیدا می‌کند که اطلاعات نسخه در زمان پیکربندی پروژه به Sentry ارسال شده باشد. در این صورت، تیم فنی می‌تواند روند تغییرات هر Release را با نسخه‌های قبلی مقایسه کند و اگر پس از انتشار، خطاهایی که قبلا برطرف شده بودند دوباره ظاهر شوند، احتمال بروز Regression (بازگشت مشکلی که در نسخه‌های قبلی برطرف شده بود) را سریع‌تر بررسی کند. این مقایسه به تیم کمک می‌کند اثر نسخه جدید بر پایداری اپلیکیشن را ارزیابی و در صورت مشاهده تغییرات غیرمنتظره، انتشار اصلاحیه را بررسی کند.</p>



<h2 id="h-یک-سناریوی-عملی-عیب-یابی-اختلال-در-فرایند-پرداخت" class="wp-block-heading"><strong>یک سناریوی عملی: عیب‌یابی اختلال در فرایند پرداخت</strong></h2>



<p class="wp-block-paragraph">فرض کنید پس از انتشار نسخه جدید یک اپلیکیشن، بخشی از پرداخت‌ها کامل نمی‌شوند. برخی کاربران پس از ثبت اطلاعات پرداخت، تایید نهایی سفارش را دریافت نمی‌کنند و تیم پشتیبانی هم فقط با گزارش‌هایی پراکنده روبه‌رو است. هم‌زمان، نرخ یکی از خطاهای مرتبط با فرایند پرداخت در Sentry افزایش پیدا می‌کند.</p>



<p class="wp-block-paragraph">در مرحله اول، تیم توسعه رخداد ثبت‌شده را بررسی می‌کند. Trace مربوط به درخواست نشان می‌دهد بخش ابتدایی فرایند در زمان معمول اجرا شده است، اما ارتباط با یکی از سرویس‌های پایین‌دستی زمان بیشتری مصرف می‌کند. این داده مشخص می‌کند که کندی در کدام بخش از مسیر درخواست رخ داده است، اما هنوز علت دقیق آن را نشان نمی‌دهد.</p>



<p class="wp-block-paragraph">در مرحله بعد، تیم، لاگ‌های متصل به Span همان عملیات را بررسی می‌کند. لاگ ساختاریافته شامل فیلدهایی مانند شناسه سفارش و وضعیت پرداخت است و نشان می‌دهد درخواست برای پردازش ارسال شده، اما پاسخ سرویس پایین‌دستی در زمان مورد انتظار دریافت نشده است.</p>



<p class="wp-block-paragraph">برای مشخص‌شدن علت کندی، داده‌های Profiling بررسی می‌شوند. این قابلیت نشان می‌دهد آیا زمان پاسخ طولانی به اجرای یک تابع پرمصرف یا افزایش مصرف CPU در کد اپلیکیشن مربوط است یا مشکل در بخش دیگری از مسیر قرار دارد. اگر Profiling مصرف غیرعادی در سطح تابع را نشان ندهد، دامنه بررسی بیشتر روی ارتباط با سرویس پایین‌دستی متمرکز می‌شود.</p>



<p class="wp-block-paragraph">پس از شناسایی تغییر مرتبط با نسخه جدید، کد یا تنظیمات مرتبط، اصلاح و نسخه تازه‌ای منتشر می‌شود. سپس روند خطاها، زمان اجرای Traceها و لاگ‌های مرتبط دوباره بررسی می‌شوند تا مشخص شود اختلال، کاهش یافته و عملکرد فرایند پرداخت به وضعیت مورد انتظار بازگشته است.</p>



<h2 id="h-مزایای-استفاده-از-sentry-برای-تیم-های-فنی" class="wp-block-heading"><strong>مزایای استفاده از Sentry برای تیم‌های فنی</strong></h2>



<p class="wp-block-paragraph">بررسی موارد زیر نشان می‌دهد مزایای Sentry چیست و این پلتفرم چگونه فرایند عیب‌یابی و اولویت‌بندی مشکلات را برای تیم‌های فنی ساده‌تر می‌کند. مهم‌ترین مزایای Sentry عبارت‌اند از:</p>



<h3 id="h-کاهش-زمان-رسیدن-به-علت-مشکل" class="wp-block-heading"><strong>کاهش زمان رسیدن به علت مشکل</strong></h3>



<p class="wp-block-paragraph">وقتی خطاها، لاگ‌ها، Traceها و داده‌های Profiling در ارتباط با یکدیگر بررسی شوند، تیم فنی شواهد مرتبط با یک مشکل را در کنار هم می‌بیند. این ارتباط میان داده‌ها می‌تواند مسیر رسیدن از مشاهده نشانه‌های مشکل به یافتن علت آن را کوتاه‌تر و فرایند عیب‌یابی را هدفمندتر کند.</p>



<h3 id="h-کاهش-نیاز-به-بازتولید-دستی-تمام-خطاها" class="wp-block-heading"><strong>کاهش نیاز به بازتولید دستی تمام خطاها</strong></h3>



<p class="wp-block-paragraph">Sentry همراه هر رخداد، اطلاعاتی مانند Stack Trace، نسخه اپلیکیشن، محیط اجرا و سایر داده‌های زمینه‌ای را ثبت می‌کند. این اطلاعات به تیم توسعه کمک می‌کنند شرایط وقوع خطا را بهتر درک کند و در بسیاری از موارد، بدون تکرار کامل همان سناریو، بررسی اولیه را آغاز کند. البته این موضوع به معنی حذف کامل نیاز به بازتولید خطا نیست و در برخی مشکلات، همچنان انجام آزمون‌های تکمیلی ضروری خواهد بود.</p>



<h3 id="h-اولویت-بندی-بهتر-مشکلات" class="wp-block-heading"><strong>اولویت‌بندی بهتر مشکلات</strong></h3>



<p class="wp-block-paragraph">همه خطاها اهمیت یکسانی ندارند. Sentry امکان بررسی عواملی مانند تعداد رخدادها، کاربران تحت‌تاثیر و نسخه‌ای که مشکل در آن مشاهده شده است را فراهم می‌کند. این دید به تیم کمک می‌کند که تشخیص دهد کدام مشکلات باید زودتر بررسی شوند و منابع فنی را بر اساس میزان تاثیر هر مسئله مدیریت کند.</p>



<h3 id="h-ایجاد-دید-مشترک-میان-تیم-ها" class="wp-block-heading"><strong>ایجاد دید مشترک میان تیم‌ها</strong></h3>



<p class="wp-block-paragraph">اطلاعات یکپارچه می‌تواند همکاری میان توسعه‌دهندگان، تیم‌های DevOps، تضمین کیفیت (QA) و پشتیبانی را ساده‌تر کند. زمانی که همه این تیم‌ها به داده‌های مشترکی مانند خطاها، Traceها، لاگ‌ها و اطلاعات عملکردی دسترسی داشته باشند، بررسی مشکلات با برداشت یکسان‌تری انجام می‌شود و هماهنگی میان اعضای تیم افزایش پیدا می‌کند.</p>



<h2 id="h-محدودیت-ها-و-ملاحظات-استفاده-از-sentry" class="wp-block-heading"><strong>محدودیت‌ها و ملاحظات استفاده از Sentry</strong></h2>



<p class="wp-block-paragraph">در کنار آشنایی با قابلیت‌ها و مزایا، لازم است بدانید محدودیت‌های Sentry چیست و در چه شرایطی استفاده از آن به برنامه‌ریزی و پیکربندی دقیق‌تری نیاز دارد. بسیاری از مواردی که در ادامه بررسی می‌کنیم، ضعف ذاتی Sentry نیستند؛ بلکه ملاحظاتی هستند که باید هنگام استفاده از یک پلتفرم جامع برای پایش خطا و عملکرد اپلیکیشن در نظر گرفته شوند.</p>



<h3 id="h-sentry-جایگزین-تمام-ابزارهای-مانیتورینگ-نیست" class="wp-block-heading"><strong>Sentry جایگزین تمام ابزارهای مانیتورینگ نیست</strong></h3>



<p class="wp-block-paragraph">تمرکز اصلی Sentry بر پایش خطاها، عملکرد اپلیکیشن و تجربه اجرای کد است. این پلتفرم اطلاعاتی مانند خطاها، Traceها، لاگ‌ها و داده‌های عملکردی را در کنار یکدیگر قرار می‌دهد تا عیب‌یابی ساده‌تر شود، اما هدف آن پوشش تمام جنبه‌های مشاهده‌پذیری نیست.</p>



<p class="wp-block-paragraph">اگر سازمان به مشاهده کامل زیرساخت، وضعیت هاست‌ها، تجهیزات شبکه یا شاخص‌های عملیاتی گسترده نیاز داشته باشد، ممکن است همچنان از ابزارهای دیگری در کنار Sentry استفاده کند.</p>



<h3 id="h-جمع-آوری-داده-بیشتر-همیشه-به-عیب-یابی-بهتر-منجر-نمی-شود" class="wp-block-heading"><strong>جمع‌آوری داده بیشتر، همیشه به عیب‌یابی بهتر منجر نمی‌شود</strong></h3>



<p class="wp-block-paragraph">ثبت حجم بیشتری از داده‌ها لزوما به معنای تحلیل دقیق‌تر نیست. اگر بدون برنامه، تعداد زیادی خطا، لاگ، Trace  یا داده‌های تحلیل عملکرد جمع‌آوری شود، ممکن است حجم اطلاعات غیرضروری افزایش پیدا کند و یافتن رخدادهای مهم دشوارتر شود.</p>



<p class="wp-block-paragraph">برای جلوگیری از این وضعیت، معمولا تیم فنی باید درباره مواردی مانند داده‌های قابل جمع‌آوری، نرخ نمونه‌برداری، قوانین هشدار و اطلاعاتی که نباید به Sentry ارسال شوند، تصمیم‌گیری کند. چنین تنظیماتی کمک می‌کند که داده‌های ثبت‌شده برای عیب‌یابی مفید باقی بمانند و از ایجاد نویز جلوگیری شود.</p>



<h3 id="h-هزینه-استفاده-با-حجم-داده-افزایش-پیدا-می-کند" class="wp-block-heading"><strong>هزینه استفاده با حجم داده افزایش پیدا می‌کند</strong></h3>



<p class="wp-block-paragraph">در مدل‌های قیمت‌گذاری مبتنی بر مصرف، حجم داده‌های ثبت‌شده می‌تواند بر هزینه استفاده اثر بگذارد. افزایش تعداد Errorها، Spanها، Replayها یا حجم Logها ممکن است مصرف را افزایش دهد؛ به‌ویژه اگر افزایش ناگهانی خطا یا ارسال بی‌ضابطه داده رخ دهد. مشخص‌کردن داده‌های ضروری و کنترل نحوه ارسال آن‌ها می‌تواند به مدیریت مصرف کمک کند.</p>



<h3 id="h-راه-اندازی-موثر-به-پیکربندی-مناسب-نیاز-دارد" class="wp-block-heading"><strong>راه‌اندازی موثر به پیکربندی مناسب نیاز دارد</strong></h3>



<p class="wp-block-paragraph">نصب و پیکربندی SDK فقط نخستین مرحله استفاده از Sentry است. برای دستیابی به داده‌های مفید، تیم باید اطلاعات نسخه و محیط اجرا را به‌درستی تنظیم کند، درباره نرخ نمونه‌برداری تصمیم بگیرد، داده‌های حساس را کنترل کند و هشدارهای متناسب با نیاز پروژه را تعریف کند. بدون این تنظیمات، ممکن است داده‌های جمع‌آوری‌شده بیش از حد گسترده یا فاقد زمینه کافی برای عیب‌یابی باشند.</p>



<h3 id="h-گستردگی-قابلیت-ها-می-تواند-برای-برخی-تیم-ها-بیش-از-نیاز-باشد" class="wp-block-heading"><strong>گستردگی قابلیت‌ها می‌تواند برای برخی تیم‌ها بیش از نیاز باشد</strong></h3>



<p class="wp-block-paragraph">گستردگی قابلیت‌های Sentry برای بسیاری از تیم‌ها مزیت است، اما پروژه‌ای که فقط به ثبت ساده خطا نیاز دارد، ممکن است به همه این امکانات احتیاج نداشته باشد. در چنین شرایطی، انتخاب و پیکربندی قابلیت‌ها بر اساس نیاز واقعی پروژه، از پیچیدگی غیرضروری جلوگیری می‌کند.</p>



<h2 id="h-استقرار-شخصی-sentry-چیست" class="wp-block-heading"><strong>استقرار شخصی Sentry چیست؟</strong></h2>



<p class="wp-block-paragraph">در مدل Self-hosted یا استقرار شخصی، سازمان، Sentry را روی زیرساخت خود مستقر می‌کند و مدیریت همه اجزای آن را بر عهده می‌گیرد. در این روش، کنترل محل نگهداری داده‌ها، منابع زیرساختی و تنظیمات استقرار در اختیار خود سازمان است و علاوه بر این، مسئولیت نصب، نگهداری، به‌روزرسانی، پایش و بهره‌برداری از سرویس هم بر عهده همان تیم خواهد بود.</p>



<p class="wp-block-paragraph">این مدل برای برخی سازمان‌ها مزایای مهمی دارد. برای مثال، اگر الزامات امنیتی، حاکمیتی یا قانونی ایجاب کند که داده‌ها فقط در زیرساخت داخلی نگهداری شوند، استقرار شخصی می‌تواند انتخاب مناسبی باشد. همچنین سازمان می‌تواند کنترل بیشتری بر نحوه تخصیص منابع، تنظیمات استقرار و برخی سیاست‌های عملیاتی داشته باشد. بنابراین، انتخاب این مدل به الزامات سازمان و ظرفیت عملیاتی تیم زیرساخت بستگی دارد.</p>



<h2 id="h-چالش-های-راه-اندازی-و-نگهداری-استقرار-شخصی-sentry" class="wp-block-heading"><strong>چالش‌های راه‌اندازی و نگهداری استقرار شخصی Sentry</strong></h2>



<p class="wp-block-paragraph">در بسیاری از سازمان‌ها، استفاده از مدل Self-hosted تنها به نصب Sentry محدود نمی‌شود و مدیریت زیرساخت، نگهداری سرویس و برنامه‌ریزی برای توسعه آینده بخشی از مسئولیت تیم فنی خواهد بود. در ادامه مهم‌ترین چالش‌های راه‌اندازی و نگهداری مدل Self-hosted را بررسی می‌کنیم.</p>



<h3 id="h-معماری-چندجزئی-sentry" class="wp-block-heading"><strong>معماری چندجزئی Sentry</strong></h3>



<p class="wp-block-paragraph">استقرار شخصی Sentry به چند سرویس زیرساختی وابسته است که از جمله آن‌ها می‌توان به PostgreSQL ،Redis ،Kafka ،ClickHouse و Relay اشاره کرد.</p>



<p class="wp-block-paragraph">استفاده از این فناوری‌ها به‌خودی‌خود یک نقطه‌ضعف محسوب نمی‌شود، اما هر کدام نیازمند نصب، پیکربندی، پایش و نگهداری هستند. در نتیجه، مدیریت مدل Self-hosted تنها به خود Sentry محدود نیست و تیم باید سلامت تمام اجزای وابسته را هم مدیریت کند.</p>



<p class="wp-block-paragraph">چندجزئی‌بودن این معماری باعث می‌شود تیم داخلی علاوه بر خود Sentry، مسئولیت عملیاتی سرویس‌های وابسته را هم بر عهده داشته باشد.</p>



<h3 id="h-نیاز-به-منابع-زیرساختی" class="wp-block-heading"><strong>نیاز به منابع زیرساختی</strong></h3>



<p class="wp-block-paragraph">استقرار شخصی Sentry به منابع پردازشی و فضای ذخیره‌سازی نیاز دارد و میزان این منابع با حجم داده‌های دریافتی ارتباط دارد. بنابراین، سازمان باید پیش از استقرار، حجم تقریبی رخدادها و ظرفیت زیرساخت موردنیاز را ارزیابی کند.</p>



<h3 id="h-ارتقای-نسخه-و-مدیریت-سازگاری" class="wp-block-heading"><strong>ارتقای نسخه و مدیریت سازگاری</strong></h3>



<p class="wp-block-paragraph">در مدل Self-hosted، مسئولیت برنامه‌ریزی و اجرای ارتقای Sentry بر عهده سازمان است. تیم فنی باید برای بررسی تغییرات نسخه، اجرای به‌روزرسانی و اطمینان از ادامه کار سرویس‌های وابسته زمان در نظر بگیرد. بنابراین، ارتقای نسخه را باید بخشی از هزینه و مسئولیت عملیاتی Self-hosting دانست، نه فعالیتی که پس از نصب اولیه خودبه‌خود انجام می‌شود.</p>



<h3 id="h-پشتیبان-گیری-و-بازیابی" class="wp-block-heading"><strong>پشتیبان‌گیری و بازیابی</strong></h3>



<p class="wp-block-paragraph">در استقرار مدل Self-hosted، تهیه نسخه پشتیبان تنها به ذخیره یک فایل محدود نمی‌شود. برنامه پشتیبان‌گیری باید مشخص کند چه داده‌هایی، با چه دوره زمانی و به چه روشی ذخیره می‌شوند.</p>



<p class="wp-block-paragraph">علاوه بر این، فرایند بازیابی (Restore) باید آزمایش شود تا در صورت بروز مشکل، امکان بازگرداندن سرویس وجود داشته باشد. در عمل، تنظیمات، داده‌های ثبت‌شده و وابستگی‌های مختلف باید در برنامه بازیابی در نظر گرفته شوند، زیرا داشتن نسخه پشتیبان بدون اطمینان از امکان بازیابی، تضمینی برای تداوم سرویس ایجاد نمی‌کند.</p>



<h3 id="h-پایش-خود-sentry" class="wp-block-heading"><strong>پایش خود Sentry</strong></h3>



<p class="wp-block-paragraph">مدل Self-hosted پس از راه‌اندازی به پایش و رسیدگی عملیاتی نیاز دارد. تیم داخلی باید سلامت سرویس و اجزای وابسته را بررسی کند و در صورت بروز اختلال، مسئولیت تشخیص و رفع مشکل را بر عهده بگیرد. در نتیجه، سازمان علاوه بر استفاده از Sentry برای عیب‌یابی اپلیکیشن، باید زمانی را به نگهداری خود این سامانه اختصاص دهد.</p>



<h3 id="h-هزینه-پنهان-نیروی-فنی" class="wp-block-heading"><strong>هزینه پنهان نیروی فنی</strong></h3>



<p class="wp-block-paragraph">هزینه استقرار مدل Self-hosted فقط به تهیه سرور و منابع زیرساختی محدود نمی‌شود. تیم‌های DevOps یا Platform باید برای نگهداری Sentry، رسیدگی به رخدادهای خود سرویس، ارتقای نسخه‌ها، پشتیبان‌گیری، ظرفیت‌سنجی و مدیریت امنیت و دسترسی‌ها زمان صرف کنند.</p>



<p class="wp-block-paragraph">این فعالیت‌ها به نیروی متخصص نیاز دارند و بخشی از زمان تیم فنی را می‌گیرند. این زمان می‌تواند صرف توسعه محصول یا رفع مشکلات اپلیکیشن شود، بنابراین هنگام مقایسه روش‌های استقرار، باید هزینه نیروی فنی را هم در کنار هزینه زیرساخت در نظر گرفت.</p>



<h2 id="h-چه-زمانی-استقرار-شخصی-sentry-انتخاب-مناسبی-است" class="wp-block-heading"><strong>چه زمانی استقرار شخصی Sentry انتخاب مناسبی است؟</strong></h2>



<p class="wp-block-paragraph">استقرار شخصی Sentry زمانی انتخاب مناسبی است که سازمان الزام مشخصی برای نگهداری داده‌ها در زیرساخت خود داشته باشد یا به دلایل امنیتی، حاکمیتی یا انطباق با مقررات، نتواند از سرویس‌های میزبانی‌شده استفاده کند. همچنین اگر تیم زیرساخت تجربه کافی در مدیریت سرویس‌های مختلف، پایش آن‌ها و اجرای فرایندهای نگهداری را داشته باشد، مدل Self-hosted می‌تواند کنترل بیشتری بر نحوه استقرار و مدیریت سامانه در اختیار سازمان قرار دهد. در چنین شرایطی، سازمان از ابتدا هزینه‌ها و مسئولیت‌های عملیاتی این مدل را نیز پذیرفته است.</p>



<p class="wp-block-paragraph">در مقابل، اگر تیم زیرساخت کوچک باشد، هدف صرفا استفاده از قابلیت‌های Sentry باشد یا زمان کافی برای نگهداری، ارتقای نسخه و مدیریت زیرساخت وجود نداشته باشد، احتمالا استقرار شخصی انتخاب مناسبی نیست. همچنین سازمان‌هایی که تمایلی به پایش و نگهداری سامانه مانیتورینگ خود ندارند یا برآورد می‌کنند هزینه نیروی فنی آن‌ها از هزینه استفاده از یک سرویس مدیریت‌شده بیشتر خواهد شد، معمولا گزینه‌های دیگری را بررسی می‌کنند.</p>



<p class="wp-block-paragraph">این مدل زمانی بیشترین ارزش را ایجاد می‌کند که نیازهای فنی و الزامات سازمان با مسئولیت‌های عملیاتی آن هم‌خوانی داشته باشند؛ در غیر این صورت، استفاده از یک سرویس مدیریت‌شده می‌تواند انتخاب عملی‌تری باشد.</p>



<h2 id="h-سرویس-مدیریت-شده-sentry-چه-تفاوتی-با-self-hosted-دارد" class="wp-block-heading"><strong>سرویس مدیریت‌شده Sentry چه تفاوتی با Self-hosted دارد؟</strong></h2>



<p class="wp-block-paragraph">تفاوت اصلی این دو مدل در نحوه تقسیم مسئولیت‌های عملیاتی است. در مدل Self-hosted، سازمان مسئول راه‌اندازی، نگهداری و ارتقای سرویس است؛ اما در سرویس سنتری مدیریت شده، این فعالیت‌ها توسط میزبان ارائه دهنده سنتری، مدیریت می‌شوند.</p>



<p class="wp-block-paragraph">در مدل Self-hosted، سازمان علاوه بر استفاده از قابلیت‌های Sentry، مدیریت زیرساخت، ارتقای نسخه، پایش سرویس و سایر فعالیت‌های عملیاتی را هم بر عهده می‌گیرد. در مقابل، در سنتری مدیریت شده (از جمله سنتری مدیریت‌شده هم‌روش)، این مسئولیت‌ها توسط ارائه‌دهنده انجام می‌شوند تا تیم فنی بتواند زمان بیشتری را صرف توسعه محصول و عیب‌یابی اپلیکیشن کند. جدول زیر تفاوت کلی استقرار Self-hosted و سرویس سنتری مدیریت‌شده هم‌روش را نشان می‌دهد.</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><thead><tr><th><strong>معیار</strong></th><th><strong>استقرار Self-hosted</strong></th><th><strong>سرویس سنتری هم‌روش</strong></th></tr></thead><tbody><tr><td>استقرار اولیه</td><td>بر عهده تیم داخلی</td><td>بر عهده هم‌روش</td></tr><tr><td>نگهداری زیرساخت</td><td>بر عهده تیم داخلی</td><td>مدیریت‌شده توسط هم‌روش</td></tr><tr><td>ارتقای نسخه</td><td>نیازمند برنامه‌ریزی و اجرا</td><td>مدیریت‌شده توسط هم‌روش</td></tr><tr><td>پایش سرویس</td><td>بر عهده سازمان</td><td>بر عهده هم‌روش</td></tr><tr><td>پشتیبان‌گیری</td><td>نیازمند طراحی و اجرا</td><td>خودکار و بر عهده هم‌روش</td></tr><tr><td>ظرفیت‌سنجی</td><td>بر عهده سازمان</td><td>در چارچوب پلن و سرویس</td></tr><tr><td>زمان تیم فنی</td><td>بیشتر صرف عملیات می‌شود</td><td>تمرکز بیشتر بر توسعه و عیب‌یابی</td></tr><tr><td>استقرار اختصاصی</td><td>با اجرای کامل سازمان</td><td>امکان استقرار توسط هم‌روش و با رعایت الزامات فنی، امنیتی و حاکمیتی سازمان</td></tr></tbody></table></figure>



<div class="wp-block-dh-blog-card-database-block card database">
<div class="wp-block-group row align-items-center is-nowrap is-layout-flex wp-container-core-group-is-layout-8f761849 wp-block-group-is-layout-flex">
<div class="wp-block-group col-md"><div class="wp-block-group__inner-container is-layout-flow wp-block-group-is-layout-flow">
<h3 id="h-سنتری-هم-روش-مشاهده-تحلیل-و-رفع-مشکلات-اپلیکیشن-در-یک-پلتفرم-یکپارچه" class="wp-block-heading">💡 سنتری هم‌روش؛ مشاهده، تحلیل و رفع مشکلات اپلیکیشن در یک پلتفرم یکپارچه</h3>



<p class="wp-block-paragraph">استفاده از Sentry بدون پذیرش بار عملیاتی Self-hosting</p>



<p class="wp-block-paragraph"><br>✅ راه‌اندازی و نگهداری زیرساخت توسط هم‌روش<br>✅ کاهش بار عملیاتی تیم‌های توسعه، DevOps و Platform<br>✅ امکان استقرار و نگهداری روی زیرساخت اختصاصی سازمان</p>



<p class="wp-block-paragraph"></p>
</div></div>
</div>



<div class="wp-block-group col-md-auto"><div class="wp-block-group__inner-container is-layout-flow wp-block-group-is-layout-flow">
<p class="btn btn--main btn--wide wp-block-paragraph"><a href="https://hamravesh.com/sentry" target="_blank" rel="noreferrer noopener">مشاهده سرویس سنتری هم‌روش</a></p>
</div></div>
</div>



<h2 id="h-سرویس-سنتری-هم-روش-چه-مسئله-ای-را-حل-می-کند" class="wp-block-heading"><strong>سرویس سنتری هم‌روش چه مسئله‌ای را حل می‌کند؟</strong></h2>



<p class="wp-block-paragraph">برای بسیاری از تیم‌های فنی، چالش اصلی استفاده از Sentry خودِ قابلیت‌های آن نیست؛ بلکه زمان و منابعی است که باید برای نصب، نگهداری، ارتقای نسخه‌ها و مدیریت زیرساخت صرف شود. سنتری هم‌روش این مسئولیت‌های عملیاتی را بر عهده می‌گیرد تا تیم‌ها بتوانند بدون درگیر شدن با مدیریت زیرساخت، از Sentry استفاده کنند.</p>



<p class="wp-block-paragraph">در این سرویس، راه‌اندازی، نگهداری و ارتقای نسخه‌های Sentry توسط هم‌روش انجام می‌شود. در نتیجه، تیم‌های توسعه و DevOps می‌توانند زمان بیشتری را به توسعه محصول، عیب‌یابی و بهبود عملکرد اپلیکیشن اختصاص دهند.</p>



<p class="wp-block-paragraph">به‌دلیل استقرار سرویس در داخل کشور، ارتباط اپلیکیشن با سنتری هم‌روش در شبکه‌های داخلی، پایدارتر انجام می‌شود و داده‌های مانیتورینگ با اطمینان بیشتری در دسترس قرار می‌گیرند. برای سازمان‌هایی با الزامات فنی، امنیتی یا حاکمیتی مشخص امکان استقرار و نگهداری Sentry روی زیرساخت اختصاصی سازمان نیز فراهم است.</p>



<p class="wp-block-paragraph">سنتری هم‌روش علاوه بر سرویس مدیریت‌شده، پلن‌های متناسب با حجم Error ،Span و Replay ارائه می‌کند تا هر سازمان بتواند متناسب با نیاز خود از این سرویس استفاده کند.</p>



<h2 id="h-جمع-بندی" class="wp-block-heading"><strong>جمع‌بندی</strong></h2>



<p class="wp-block-paragraph">Sentry فقط ابزاری برای ثبت خطاها نیست، بلکه با کنار هم قرار دادن خطاها، لاگ‌ها، Traceها و داده‌های Profiling، دید دقیق‌تری برای بررسی مشکلات اپلیکیشن در اختیار تیم فنی قرار می‌دهد. البته استفاده موثر از این قابلیت‌ها به پیکربندی مناسب، مدیریت داده‌های ارسالی و انتخاب آگاهانه اطلاعاتی که باید جمع‌آوری شوند، وابسته است.</p>



<p class="wp-block-paragraph">در مقابل، مدل Self-hosted کنترل بیشتری بر زیرساخت و محل نگهداری داده‌ها فراهم می‌کند، اما مسئولیت‌هایی مانند نصب، نگهداری، ارتقای نسخه، پشتیبان‌گیری و پایش سرویس را نیز به سازمان منتقل می‌کند. به همین دلیل، انتخاب میان استقرار شخصی و سرویس مدیریت‌شده باید بر اساس نیازهای فنی، الزامات سازمان و توان عملیاتی تیم انجام شود.</p>



<p class="wp-block-paragraph">در این مطلب بررسی کردیم که Sentry چیست و چه قابلیت‌ها و محدودیت‌هایی دارد و به چه روش‌هایی ارائه می‌شود. همچنین توضیح دادیم سرویس مدیریت‌شده می‌تواند برای تیم‌هایی مناسب باشد که می‌خواهند از قابلیت‌های Sentry استفاده کنند، اما نمی‌خواهند زمان تیم فنی خود را صرف نگهداری زیرساخت آن کنند.</p>
<p>The post <a href="https://hamravesh.com/blog/what-is-sentry/">سنتری چیست؟ از پایش خطای اپلیکیشن تا تحلیل عملکرد در سطح کد</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/what-is-sentry/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>آموزش K9s؛ راهنمای نصب و استفاده از ابزار مدیریت کوبرنتیز در ترمینال</title>
		<link>https://hamravesh.com/blog/k9s-kubernetes-guide/</link>
					<comments>https://hamravesh.com/blog/k9s-kubernetes-guide/#respond</comments>
		
		<dc:creator><![CDATA[هم‌روش]]></dc:creator>
		<pubDate>Wed, 22 Jul 2026 12:30:00 +0000</pubDate>
				<category><![CDATA[دواپس]]></category>
		<category><![CDATA[مقالات]]></category>
		<category><![CDATA[کوبرنتیز]]></category>
		<guid isPermaLink="false">https://hamravesh.com/blog/?p=5428</guid>

					<description><![CDATA[<p>ابزار K9s کوبرنتیز دقیقا برای رفع همین چالش توسعه داده شده است. این ابزار با ارائه یک رابط کاربری مبتنی بر ترمینال، فرایند مشاهده (Observe)، پیمایش (Navigate) و مدیریت (Manage) منابع و اپلیکیشن‌های Kubernetes را ساده‌تر می‌کند تا بسیاری از عملیات روزمره، بدون نیاز به اجرای مکرر دستورهای مختلف، از طریق یک محیط یکپارچه انجام شوند.</p>
<p>The post <a href="https://hamravesh.com/blog/k9s-kubernetes-guide/">آموزش K9s؛ راهنمای نصب و استفاده از ابزار مدیریت کوبرنتیز در ترمینال</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">اگر به‌صورت روزانه با کوبرنتیز کار کرده باشید، احتمالا بارها خودتان را در حال اجرای مجموعه‌ای از دستورهای تکراری kubectl دیده‌اید. معمولا برای بررسی وضعیت یک سرویس باید ابتدا فهرست پادها را دریافت کنید، نام پاد موردنظر را پیدا یا کپی کنید، لاگ آن را مشاهده کنید، در صورت نیاز خروجی describe را بررسی کنید و گاهی هم فایل YAML منبع را ویرایش کنید. تکرار مداوم این مراحل (به‌خصوص در محیط‌های عملیاتی)، به‌مرور روند بررسی و عیب‌یابی را کند و آزاردهنده می‌کند. این مسئله زمانی پررنگ‌تر است که با یک حادثه یا فرایند عیب‌یابی روبه‌رو باشید. در چنین شرایطی، جابه‌جایی مداوم بین دستورهای مختلف برای یافتن علت مشکل می‌تواند روند عیب‌یابی را کندتر کرده و زمان رسیدن به پاسخ را افزایش دهد. K9s کوبرنتیز دقیقا برای رفع همین چالش توسعه داده شده است. </p>



<p class="wp-block-paragraph">K9s ابزاری ترمینال‌محور برای کوبرنتیز است که مشاهده، پیمایش و مدیریت اپلیکیشن‌های مستقر روی کلاستر را ساده‌تر می‌کند. این ابزار با ارائه یک رابط کاربری مبتنی بر ترمینال، فرایند مشاهده (Observe)، پیمایش (Navigate) و مدیریت (Manage) منابع و اپلیکیشن‌های کوبرنتیز را ساده‌تر می‌کند تا بسیاری از عملیات روزمره، بدون نیاز به اجرای مکرر دستورهای مختلف، از طریق یک محیط یکپارچه انجام شوند. در این آموزش K9s، ابتدا به این سوال پاسخ می‌دهیم که K9s چیست و سپس به نحوه نصب، رابط کاربری، کارهای عملی با K9s و برخی قابلیت‌های پیشرفته آن را می‌پردازیم.</p>



<h2 class="wp-block-heading" id="h-k9s-چیست">K9s چیست؟</h2>



<p class="wp-block-paragraph">K9s یک رابط کاربری متنی (Terminal-based UI) برای تعامل با کلاسترهای کوبرنتیز است که به‌طور کامل داخل ترمینال اجرا می‌شود. این ابزار مدیریت کوبرنتیز، با هدف ساده‌تر کردن مشاهده، پیمایش و مدیریت اپلیکیشن‌ها و منابع مستقر روی کلاستر توسعه یافته است. کد منبع و روند توسعه این ابزار در <a href="https://github.com/derailed/k9s" target="_blank" rel="noreferrer noopener">مخزن رسمی K9s در GitHub</a> در دسترس است.</p>



<p class="wp-block-paragraph">برخلاف کار با kubectl که معمولا نیازمند اجرای چندین دستور متوالی است، K9s بسیاری از عملیات روزمره را در یک محیط تعاملی در اختیار کاربر قرار می‌دهد. پس از اجرای برنامه، می‌توانید پادها، دیپلویمنت‌ها، سرویس‌ها و سایر منابع کوبرنتیز را به‌صورت زنده مشاهده کنید و تنها با استفاده از میانبرهای صفحه‌کلید، اقداماتی مانند مشاهده لاگ‌ها، اجرای describe، ویرایش YAML یا مدیریت منابع را انجام دهید.</p>



<p class="wp-block-paragraph">یکی دیگر از ویژگی‌های مهم K9s این است که تغییرات کلاستر را به‌صورت مداوم پایش می‌کند و متناسب با منابعی که مشاهده می‌کنید، دستورها و عملیات مرتبط را در اختیار شما قرار می‌دهد. در نتیجه، مدیریت کوبرنتیز با K9s به شما امکان می‌دهد هنگام مانیتورینگ یا عیب‌یابی، وضعیت منابع را تقریبا به‌صورت لحظه‌ای دنبال کنید و بدون جابه‌جایی بین چندین دستور مختلف، عملیات موردنیاز را انجام دهید.</p>



<h2 class="wp-block-heading" id="h-k9s-چگونه-با-kubeconfig-kubernetes-api-و-rbac-کار-می-کند">K9s چگونه با kubeconfig ،Kubernetes API و RBAC کار می‌کند؟</h2>



<p class="wp-block-paragraph">یکی از مزیت‌های K9s این است که برای اتصال به کلاستر کوبرنتیز از همان Kubernetes API استفاده می‌کند که ابزار kubectl هم بر پایه آن کار می‌کند. به همین دلیل، اگر kubeconfig معتبر باشد و context انتخاب‌شده امکان اتصال به کلاستر را داشته باشد، K9s می‌تواند از همان پیکربندی برای اتصال استفاده کند.</p>



<p class="wp-block-paragraph">نکته مهم این است که K9s مجوز یا سیاست دسترسی مستقلی ایجاد نمی‌کند. این ابزار با استفاده از اطلاعات اتصال و احراز هویت موجود در kubeconfig به Kubernetes API متصل می‌شود و سطح دسترسی آن را مجوزهای تعریف‌شده در <a href="https://hamravesh.com/blog/what-is-kubernetes-rbac/" data-type="link" data-id="https://hamravesh.com/blog/what-is-kubernetes-rbac/" target="_blank" rel="noreferrer noopener">RBAC</a> (مخفف Role-Based Access Control) کلاستر تعیین می‌کنند. بنابراین، کاربر یا ServiceAccount مرتبط با context فعال فقط می‌تواند عملیاتی را در K9s انجام دهد که طبق سیاست‌های RBAC اجازه انجام آن‌ها را دارد. برای مثال، اگر مجوز کاربر به مشاهده منابع محدود باشد، امکان ویرایش یا حذف آن‌ها را از طریق K9s نیز نخواهد داشت. به بیان دیگر، K9s محدودیت‌های دسترسی کوبرنتیز را دور نمی‌زند و در همان محدوده مجاز تعریف‌شده برای هویت فعلی کار می‌کند.</p>



<p class="wp-block-paragraph">همچنین هنگام اجرای K9s، می‌توانید یک context مشخص از فایل kubeconfig را انتخاب کنید یا برنامه را به‌طور مستقیم در یک <a href="https://hamravesh.com/blog/what-is-kubernetes-namespace/" data-type="link" data-id="https://hamravesh.com/blog/what-is-kubernetes-namespace/">namespace</a> خاص اجرا کنید.</p>



<h2 class="wp-block-heading" id="h-تفاوت-k9s-و-kubectl-چیست">تفاوت K9s و kubectl چیست؟</h2>



<p class="wp-block-paragraph">K9s و kubectl نقش یکسانی ندارند و K9s را نباید جایگزین کامل kubectl دانست. kubectl ابزار خط فرمان استاندارد کوبرنتیز است، اما K9s یک رابط کاربری متنی (Terminal-based UI) برای انجام سریع‌تر عملیات روزمره و تعاملی به شمار می‌آید.&nbsp;</p>



<p class="wp-block-paragraph">بسیاری از کارهایی که در kubectl نیازمند اجرای چندین دستور هستند، در K9s تنها با میانبرهای صفحه‌کلید انجام می‌شوند؛ به همین دلیل برای فعالیت‌هایی مانند بررسی پادها، مشاهده لاگ‌ها، اجرای describe و عیب‌یابی، سریع‌تر و ساده‌تر است.&nbsp;</p>



<p class="wp-block-paragraph">ازآنجایی‌که K9s کاملاً در ترمینال اجرا می‌شود، می‌توان آن را روی Bastion Host یا سرور واسطی اجرا کرد که کاربران از طریق SSH به آن متصل می‌شوند و از آنجا به کلاستر کوبرنتیز دسترسی دارند. در مقابل، اگر هدف خودکارسازی عملیات، استفاده در اسکریپت‌ها یا ادغام با فرایندهای CI/CD باشد، همچنان kubectl انتخاب اصلی است. جدول زیر مهم‌ترین تفاوت‌های این دو ابزار را نشان می‌دهد:</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><tbody><tr><td class="has-text-align-center" data-align="center"><strong>معیار</strong></td><td class="has-text-align-center" data-align="center"><strong>kubectl</strong></td><td class="has-text-align-center" data-align="center"><strong>K9s</strong></td></tr><tr><td class="has-text-align-center" data-align="center">نوع ابزار</td><td class="has-text-align-center" data-align="center">ابزار خط فرمان (CLI)</td><td class="has-text-align-center" data-align="center">رابط کاربری متنی (Terminal-based UI)</td></tr><tr><td class="has-text-align-center" data-align="center">کاربرد اصلی</td><td class="has-text-align-center" data-align="center">اجرای دستورها و Automation</td><td class="has-text-align-center" data-align="center">مدیریت و مشاهده تعاملی کلاستر</td></tr><tr><td class="has-text-align-center" data-align="center">مناسب برای</td><td class="has-text-align-center" data-align="center">اسکریپت‌نویسی، CI/CD و Cron Job</td><td class="has-text-align-center" data-align="center">مانیتورینگ، عیب‌یابی و مدیریت روزمره</td></tr><tr><td class="has-text-align-center" data-align="center">نحوه کار</td><td class="has-text-align-center" data-align="center">اجرای دستورهای متنی</td><td class="has-text-align-center" data-align="center">استفاده از میانبرهای صفحه‌کلید</td></tr></tbody></table></figure>



<h2 class="wp-block-heading" id="h-پیش-نیازهای-استفاده-از-k9s">پیش‌نیازهای استفاده از K9s</h2>



<p class="wp-block-paragraph">پیش از نصب K9s، بهتر است مطمئن شوید محیط کاری شما برای اتصال به کلاستر کوبرنتیز آماده است. این ابزار روی سیستم‌عامل‌های لینوکس، macOS و ویندوز اجرا می‌شود. پیش‌نیازهای نصب و استفاده از این ابزار عبارت‌اند از:</p>



<ul class="wp-block-list">
<li><strong>دسترسی به یک کلاستر کوبرنتیز فعال:</strong> پیش از هر چیز باید به یک کلاستر کوبرنتیز در حال اجرا دسترسی داشته باشید، زیرا K9s ابزاری برای تعامل با یک کلاستر موجود است، نه راه‌اندازی کلاستر جدید.</li>



<li><strong>پیکربندی دسترسی به کلاستر:</strong> باید kubeconfig معتبر و امکان اتصال به کلاستر را داشته باشید. در محیط کاری معمول، بهتر است پیش از اجرای K9s از امکان اتصال به کلاستر اطمینان پیدا کنید.</li>



<li><strong>فایل kubeconfig معتبر:</strong> فایل kubeconfig باید به‌درستی تنظیم و به کلاستر موردنظر متصل شده باشد تا K9s بدون نیاز به تنظیمات اضافی بتواند به آن متصل شود.</li>



<li><strong>دسترسی‌های لازم مطابق RBAC:</strong> چون سطح دسترسی K9s تابع همان قوانین RBAC تعریف‌شده برای کاربر است، باید مطمئن شوید مجوزهای لازم برای مشاهده یا مدیریت منابع موردنظرتان از قبل برایتان تعریف شده باشد.</li>



<li><strong>ترمینال با پشتیبانی از ۲۵۶ رنگ:</strong> K9s برای نمایش صحیح رابط کاربری به حالت ۲۵۶ رنگ ترمینال نیاز دارد. اکثر ترمینال‌های مدرن به‌صورت پیش‌فرض از این قابلیت پشتیبانی می‌کنند، اما در سیستم‌های مبتنی بر یونیکس مانند لینوکس و macOS، در صورت نیاز می‌توانید متغیر محیطی TERM را به‌صورت زیر تنظیم کنید:</li>
</ul>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly> export TERM=xterm-256color</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50"> export</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">TERM=xterm-256color</span></span></code></pre></div>



<ul class="wp-block-list">
<li><strong>تنظیم EDITOR یا KUBE_EDITOR:</strong> برای ویرایش مستقیم منابع کوبرنتیز از داخل K9s، لازم است یکی از متغیرهای محیطی <code>EDITOR</code> یا <code>KUBE_EDITOR</code> روی ویرایشگر دلخواه شما تنظیم شده باشد، مثلاً:</li>
</ul>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>export KUBE_EDITOR=vim</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F47067">export</span><span style="color: #ADBAC7"> KUBE_EDITOR</span><span style="color: #F47067">=</span><span style="color: #96D0FF">vim</span></span></code></pre></div>



<h2 class="wp-block-heading" id="h-روش-های-نصب-k9s-روی-لینوکس-macos-و-ویندوز">روش‌های نصب K9s روی لینوکس، macOS و ویندوز</h2>



<p class="wp-block-paragraph">K9s روی سیستم‌عامل‌های لینوکس، macOS و ویندوز در دسترس است. می‌توانید علاوه بر استفاده از Package Manager، فایل‌های Binary رسمی را هم از صفحه انتشار (Release) پروژه دریافت و نصب کنید. همچنین در صورت نیاز، امکان کامپایل برنامه از سورس هم وجود دارد.</p>



<h3 class="wp-block-heading" id="h-نصب-k9s-روی-macos">نصب K9s روی macOS</h3>



<p class="wp-block-paragraph">در مستندات رسمی، دو روش برای نصب K9s روی مک معرفی شده است:</p>



<p class="wp-block-paragraph">برای نصب با Homebrew:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>brew install derailed/k9s/k9s</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">brew</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">install</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">derailed/k9s/k9s</span></span></code></pre></div>



<p class="wp-block-paragraph">برای نصب با MacPorts:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>sudo port install k9s</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">sudo</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">port</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">install</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">k9s</span></span></code></pre></div>



<h3 class="wp-block-heading" id="h-نصب-k9s-روی-لینوکس">نصب K9s روی لینوکس</h3>



<p class="wp-block-paragraph">برای نصب K9s روی لینوکس، مستندات رسمی K9s روش‌های زیر را پیشنهاد می‌کنند:</p>



<p class="wp-block-paragraph">برای نصب با LinuxBrew:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>brew install derailed/k9s/k9s</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">brew</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">install</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">derailed/k9s/k9s</span></span></code></pre></div>



<p class="wp-block-paragraph">برای نصب با Pacman:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>pacman -S k9s</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">pacman</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-S</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">k9s</span></span></code></pre></div>



<h3 class="wp-block-heading" id="h-نصب-k9s-روی-ویندوز">نصب K9s روی ویندوز</h3>



<p class="wp-block-paragraph">برای نصب K9s روی ویندوز مستندات رسمی K9s روش‌های زیر را پیشنهاد می‌کنند:</p>



<p class="wp-block-paragraph">برای نصب با Scoop:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>scoop install k9s</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">scoop</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">install</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">k9s</span></span></code></pre></div>



<p class="wp-block-paragraph">نصب با Chocolatey:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>choco install k9s</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">choco</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">install</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">k9s</span></span></code></pre></div>



<h3 class="wp-block-heading" id="h-نصب-k9s-با-binary-رسمی-یا-ساخت-از-روی-سورس">نصب K9s با Binary رسمی یا ساخت از روی سورس</h3>



<p class="wp-block-paragraph">اگر نمی‌خواهید از Package Manager استفاده کنید، می‌توانید فایل اجرایی متناسب با سیستم‌عامل خود را از <a href="https://github.com/derailed/k9s/releases" data-type="link" data-id="https://github.com/derailed/k9s/releases" target="_blank" rel="noreferrer noopener">صفحه انتشارهای رسمی K9s در GitHub</a> دریافت کنید. فایل‌های رسمی K9s برای لینوکس، macOS و ویندوز در این صفحه در دسترس‌اند. همچنین، اگر قصد دارید K9s را از کد منبع بسازید، طبق مستندات نصب مورداستفاده در این مقاله باید Go نسخه ۱.۱۴ یا بالاتر روی سیستم نصب باشد. در این روش، ابتدا مخزن پروژه را Clone و سپس برنامه را با دستور زیر Build و اجرا کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>make build &amp;&amp; ./execs/k9s</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">make</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">build</span><span style="color: #ADBAC7"> &amp;&amp; </span><span style="color: #F69D50">./execs/k9s</span></span></code></pre></div>



<h2 class="wp-block-heading" id="h-اجرای-اولیه-k9s-و-گزینه-های-مهم-cli">اجرای اولیه K9s و گزینه‌های مهم CLI</h2>



<p class="wp-block-paragraph">پس از اینکه فرایند نصب را انجام دادید، کافی است دستور k9s را اجرا کنید تا محیط تعاملی برنامه باز شود. در بخش بالای صفحه، اطلاعاتی مانند نام کلاستر، Context فعلی، نسخه کوبرنتیز و میزان مصرف CPU و Memory نمایش داده می‌شود. همچنین در بخش میانی، فهرست منابع کوبرنتیز قرار دارد و در پایین صفحه، مسیر پیمایش (Breadcrumb) و پیام‌های وضعیت دیده می‌شوند. هر زمان کلید : یا / را فشار دهید، نوار فرمان برای اجرای دستورها یا جستجو ظاهر می‌شود.&nbsp;</p>



<p class="wp-block-paragraph">نکته کاربردی دیگر این است که کنار نام هر Namespace، عددی نمایش داده می‌شود. در اینجا عدد ۰ نمایانگر همه Namespaceها است و اعداد دیگر به‌ترتیب به Namespaceهایی اختصاص پیدا می‌کنند که در همان نشست کاری بازدید کرده‌اید.</p>



<p class="wp-block-paragraph">مستندات رسمی K9s چند گزینه مهم برای اجرای برنامه معرفی کرده است که در ادامه با آن‌ها آشنا می‌شوید.</p>



<h3 class="wp-block-heading" id="h-مشاهده-راهنما-و-اطلاعات-برنامه">مشاهده راهنما و اطلاعات برنامه</h3>



<p class="wp-block-paragraph">برای مشاهده همه گزینه‌های خط فرمان می‌توانید از دستور زیر استفاده کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>k9s help</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">k9s</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">help</span></span></code></pre></div>



<p class="wp-block-paragraph">اگر بخواهید اطلاعات Runtime برنامه، مانند مسیر فایل‌های پیکربندی و لاگ‌ها را مشاهده کنید، دستور زیر کاربرد دارد:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>k9s info</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">k9s</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">info</span></span></code></pre></div>



<h3 class="wp-block-heading" id="h-اجرای-k9s-در-یک-namespace-مشخص">اجرای K9s در یک Namespace مشخص</h3>



<p class="wp-block-paragraph">اگر فقط قصد کار با یک Namespace خاص را دارید، می‌توانید K9s را به‌طور مستقیم در همان Namespace اجرا کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>k9s -n &lt;namespace-name></textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">k9s</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-n</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">&lt;</span><span style="color: #96D0FF">namespace-nam</span><span style="color: #ADBAC7">e</span><span style="color: #F47067">&gt;</span></span></code></pre></div>



<p class="wp-block-paragraph">اجرای K9s با گزینه <code>-n</code> باعث می‌شود برنامه کار را در namespace مشخص‌شده آغاز کند. این روش در کلاسترهای شلوغ، دسترسی به منابع namespace موردنظر را ساده‌تر می‌کند.</p>



<h3 class="wp-block-heading" id="h-اجرای-مستقیم-در-نمای-پاد">اجرای مستقیم در نمای پاد</h3>



<p class="wp-block-paragraph">برای اینکه K9s پس از اجرا به‌طور مستقیم نمای پادها را نمایش دهد، از دستور زیر استفاده کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>k9s -c pod</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">k9s</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-c</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">pod</span></span></code></pre></div>



<h3 class="wp-block-heading" id="h-اجرای-k9s-با-context-دلخواه">اجرای K9s با Context دلخواه</h3>



<p class="wp-block-paragraph">اگر فایل kubeconfig شما شامل چند Context باشد، هنگام اجرای K9s، می‌توانید Context موردنظر را مشخص کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>k9s --context &lt;context-name></textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">k9s</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">--context</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">&lt;</span><span style="color: #96D0FF">context-nam</span><span style="color: #ADBAC7">e</span><span style="color: #F47067">&gt;</span></span></code></pre></div>



<p class="wp-block-paragraph">این قابلیت زمانی مفید است که بین چند کلاستر کوبرنتیز جابه‌جا می‌شوید و نمی‌خواهید Context پیش‌فرض را تغییر دهید.</p>



<h3 class="wp-block-heading" id="h-اجرای-k9s-در-حالت-فقط-خواندنی">اجرای K9s در حالت فقط‌خواندنی</h3>



<p class="wp-block-paragraph">برای جلوگیری از هرگونه تغییر ناخواسته روی منابع، می‌توانید K9s را با گزینه <code>--readonly</code> اجرا کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>k9s --readonly</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">k9s</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">--readonly</span></span></code></pre></div>



<p class="wp-block-paragraph">در این حالت، تمام دستورهای ویرایش، حذف و سایر عملیات تغییردهنده غیرفعال می‌شوند.</p>



<h3 class="wp-block-heading" id="h-تغییر-context-و-namespace-در-زمان-اجرا">تغییر Context و Namespace در زمان اجرا</h3>



<p class="wp-block-paragraph">K9s علاوه بر گزینه‌های خط فرمان، امکان جابه‌جایی بین Contextها و Namespaceها را از داخل محیط برنامه هم فراهم می‌کند. برای مشاهده و تغییر Context فعال، دستور زیر را وارد کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>:ctx</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">:ctx</span></span></code></pre></div>



<p class="wp-block-paragraph">یا مستقیما به یک Context مشخص بروید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>:ctx &lt;context-name></textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">:ctx</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">&lt;</span><span style="color: #96D0FF">context-nam</span><span style="color: #ADBAC7">e</span><span style="color: #F47067">&gt;</span></span></code></pre></div>



<p class="wp-block-paragraph">برای تغییر Namespace هم کافی است بنویسید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>:ns</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">:ns</span></span></code></pre></div>



<p class="wp-block-paragraph">همچنین می‌توانید با ساختار <code>:pod &lt;namespace-name&gt;</code>، پادهای یک Namespace مشخص را مشاهده کنید. برای نمایش پادها در یک Context دیگر نیز از ساختار <code>:pod @&lt;context-name&gt;</code> استفاده کنید. اجرای دستور دوم، Context فعال K9s را نیز به Context مشخص‌شده تغییر می‌دهد. توجه داشته باشید که این دستور دوم، Context فعلی شما را هم تغییر می‌دهد.</p>



<div class="wp-block-dh-blog-card-database-block card database">
<div class="wp-block-group row align-items-center is-nowrap is-layout-flex wp-container-core-group-is-layout-8f761849 wp-block-group-is-layout-flex">
<div class="wp-block-group col-md"><div class="wp-block-group__inner-container is-layout-flow wp-block-group-is-layout-flow">
<h3 class="wp-block-heading" id="h-کوبرنتیز-مدیریت-شده-هم-روش-راهی-مطمئن-برای-رشد-بی-وقفه">💡 کوبرنتیز مدیریت‌شده هم‌روش، راهی مطمئن برای رشد بی‌وقفه</h3>



<p class="wp-block-paragraph">راهکار کوبرنتیز مدیریت شده، بر بستر ابر اختصاصی یا به صورت On-Premises</p>



<p class="wp-block-paragraph"><br>✅ کاهش هزینه‌های عملیاتی<br>✅ احراز هویت یکپارچه با اتصال به SSO سازمانی<br>✅ قابل استقرار روی سرورهای on-premises</p>



<p class="wp-block-paragraph"></p>
</div></div>
</div>



<div class="wp-block-group col-md-auto"><div class="wp-block-group__inner-container is-layout-flow wp-block-group-is-layout-flow">
<p class="btn btn--main btn--wide wp-block-paragraph"><a href="https://hamravesh.com/managed-kubernetes" type="link" id="https://hamravesh.com/managed-kubernetes" target="_blank" rel="noreferrer noopener">کوبرنتیز مدیریت‌شده</a></p>
</div></div>
</div>



<h2 class="wp-block-heading" id="h-آشنایی-با-رابط-کاربری-k9s">آشنایی با رابط کاربری K9s</h2>



<p class="wp-block-paragraph">همان‌طور که در بخش قبل دیدیم، صفحه اصلی K9s شامل بخش بالایی (نام کلاستر، Context، نسخه کوبرنتیز و مصرف CPU/Memory)، جدول منابع در وسط و نوار پیمایش در پایین صفحه است. تصویر زیر نمونه‌ای از این چیدمان را در نمای پادها نشان می‌دهد:</p>



<figure class="wp-block-image size-large"><img loading="lazy" decoding="async" width="1024" height="539" src="https://hamravesh.com/blog/wp-content/uploads/2026/07/hamravesh-k9s-kubernetes-guide-02-1024x539.webp" alt="آشنایی با رابط کاربری K9s" class="wp-image-5470" srcset="https://hamravesh.com/blog/wp-content/uploads/2026/07/hamravesh-k9s-kubernetes-guide-02-1024x539.webp 1024w, https://hamravesh.com/blog/wp-content/uploads/2026/07/hamravesh-k9s-kubernetes-guide-02-300x158.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2026/07/hamravesh-k9s-kubernetes-guide-02-768x404.webp 768w, https://hamravesh.com/blog/wp-content/uploads/2026/07/hamravesh-k9s-kubernetes-guide-02-1536x808.webp 1536w, https://hamravesh.com/blog/wp-content/uploads/2026/07/hamravesh-k9s-kubernetes-guide-02-2048x1078.webp 2048w, https://hamravesh.com/blog/wp-content/uploads/2026/07/hamravesh-k9s-kubernetes-guide-02-120x63.webp 120w" sizes="auto, (max-width: 1024px) 100vw, 1024px" /></figure>



<p class="wp-block-paragraph">نکته مهم درباره این رابط این است که میانبرهای نمایش‌داده‌شده در بالای صفحه، بسته به نوع منبعی که مشاهده می‌کنید تغییر می‌کنند. برای مثال، کلید s روی پادها به‌معنای Shell است، اما همین کلید روی دیپلویمنت‌ها به‌معنای Scale خواهد بود. به همین دلیل نیازی نیست این میانبرها را از قبل حفظ کنید، چون K9s همیشه میانبرهای مرتبط با نمای فعلی را نمایش می‌دهد.</p>



<p class="wp-block-paragraph">دو میانبر کاربردی که بهتر است به خاطر بسپارید، <code>?</code> و <code>Ctrl+a</code> هستند. کلید ? در هر بخشی از K9s راهنما را باز می‌کند و <code>Ctrl+a</code> فهرست تمام alias‌های منابع شناخته‌شده توسط K9s را نشان می‌دهد. اگر نام کوتاه یا alias یک منبع را نمی‌دانید، می‌توانید با فشردن <code>Ctrl+a</code> فهرست aliasهای موجود را مشاهده کنید.</p>



<p class="wp-block-paragraph">برای جابه‌جایی در محیط K9s هم می‌توانید از کلیدهای جهت‌دار یا <code>j</code>/<code>k</code> (مشابه Vim) استفاده کنید. علاوه بر این‌ها، با فشردن Enter وارد یک منبع می‌شوید و با Esc به نمای قبلی بازمی‌گردید.</p>



<h2 class="wp-block-heading" id="h-مشاهده-و-جابه-جایی-بین-منابع-کوبرنتیز-در-k9s">مشاهده و جابه‌جایی بین منابع کوبرنتیز در K9s</h2>



<p class="wp-block-paragraph">یکی از مهم‌ترین قابلیت‌های K9s، دسترسی سریع به منابع مختلف کوبرنتیز از طریق میانبرهای متنی (Resource Alias) است. به‌جای اجرای مداوم دستورهای kubectl، کافی است کلید <code>:</code> را فشار دهید و نام منبع موردنظر را وارد کنید تا همان نما در ترمینال باز شود. از پرکاربردترین میانبرهای K9s می‌توان به موارد زیر اشاره کرد:</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><tbody><tr><td><strong>میانبر</strong></td><td><strong>کاربرد</strong></td></tr><tr><td><code>:pod</code></td><td>نمایش Podها</td></tr><tr><td><code>:deploy</code></td><td>نمایش Deploymentها</td></tr><tr><td><code>:svc</code></td><td>نمایش Serviceها</td></tr><tr><td><code>:ns</code></td><td>نمایش Namespaceها</td></tr><tr><td><code>:node</code></td><td>نمایش Nodeها</td></tr><tr><td><code>:pvc</code></td><td>نمایش PersistentVolumeClaimها</td></tr><tr><td><code>:cm</code></td><td>نمایش ConfigMapها</td></tr><tr><td><code>:secret</code></td><td>نمایش Secretها</td></tr><tr><td><code>:ing</code></td><td>نمایش Ingressها</td></tr></tbody></table></figure>



<p class="wp-block-paragraph">اگر بخواهید فقط منابع یک Namespace مشخص را مشاهده کنید، می‌توانید هنگام ورود به نمای پاد، نام Namespace را هم مشخص کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>:pod kube-system</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">:pod</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">kube-system</span></span></code></pre></div>



<p class="wp-block-paragraph">همچنین اگر بخواهید پادهای یک Context دیگر را ببینید، می‌توانید از دستور زیر استفاده کنید. این دستور، Context فعال را هم تغییر می‌دهد.</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>:pod @&lt;context-name></textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">:pod</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">@</span><span style="color: #F47067">&lt;</span><span style="color: #96D0FF">context-nam</span><span style="color: #ADBAC7">e</span><span style="color: #F47067">&gt;</span></span></code></pre></div>



<h3 class="wp-block-heading" id="h-جابه-جایی-بین-context-و-namespace">جابه‌جایی بین Context و Namespace</h3>



<p class="wp-block-paragraph">در محیط‌هایی که چند کلاستر یا Namespace در اختیار دارید، جابه‌جایی سریع میان آن‌ها اهمیت زیادی دارد. K9s این کار را با چند دستور ساده امکان‌پذیر می‌کند:</p>



<ul class="wp-block-list">
<li><code>:ctx</code> برای مشاهده و تغییر Context</li>



<li><code>:ctx &lt;context-name&gt;</code> برای رفتن مستقیم به یک Context مشخص</li>



<li><code>:ns</code> برای مشاهده و تغییر Namespace</li>
</ul>



<p class="wp-block-paragraph">همچنین با فشردن کلید 0 می‌توانید منابع موجود در تمام Namespaceها را به‌صورت یکجا مشاهده کنید. این گزینه برای بررسی وضعیت کلی کلاستر بسیار کاربردی است.</p>



<h2 class="wp-block-heading" id="h-جست-وجو-و-فیلتر-کردن-منابع-در-k9s">جست‌وجو و فیلتر کردن منابع در K9s</h2>



<p class="wp-block-paragraph">در کلاسترهای کوبرنتیز که تعداد زیادی پاد، دیپلویمنت یا سایر منابع وجود دارد، پیدا کردن یک منبع مشخص می‌تواند زمان‌بر باشد. K9s با ارائه قابلیت‌های متنوع جست‌وجو و فیلتر، یافتن منابع را در نمای فعلی ساده‌تر می‌کند.</p>



<p class="wp-block-paragraph">برای فیلتر کردن منابع، کافی است کلید / را فشار دهید و عبارت موردنظر را وارد کنید. این فیلتر به‌صورت لحظه‌ای روی نمای فعلی اعمال می‌شود و تنها منابع منطبق با عبارت جست‌وجو را نمایش می‌دهد.</p>



<p class="wp-block-paragraph">یکی از قابلیت‌های کاربردی K9s، پشتیبانی از عبارت‌های منظم (Regular Expression یا Regex) است؛ بنابراین می‌توانید چند الگو را به‌طور هم‌زمان جست‌وجو کنید. برای مثال، دستور زیر تمام منابعی را که نام آن‌ها با یکی از دو عبارت مشخص‌شده مطابقت داشته باشد، نمایش می‌دهد:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>/fred|blee</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">/fred</span><span style="color: #F47067">|</span><span style="color: #F69D50">blee</span></span></code></pre></div>



<p class="wp-block-paragraph">K9s علاوه بر جست‌وجوی متنی، روش‌های دیگری هم برای فیلتر کردن منابع در اختیار شما قرار می‌دهد. در جدول زیر می‌توانید این روش‌ها را ببینید:</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><tbody><tr><td><strong>روش</strong></td><td><strong>کاربرد</strong></td></tr><tr><td><code>/text</code></td><td>فیلتر منابع بر اساس متن</td></tr><tr><td><code>/-l app=nginx</code></td><td>فیلتر منابع بر اساس Label</td></tr><tr><td><code>/-f text</code></td><td>جست‌وجوی فازی (Fuzzy Search)</td></tr><tr><td><code>/!text</code></td><td>فیلتر معکوس و نمایش منابعی که با عبارت واردشده مطابقت ندارند</td></tr></tbody></table></figure>



<p class="wp-block-paragraph">اگر بخواهید همه منابع، به‌جز مواردی که شامل عبارت <code>error</code> هستند، نمایش داده شوند، می‌توانید از دستور زیر استفاده کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>/!error</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">/!error</span></span></code></pre></div>



<p class="wp-block-paragraph">همچنین قابلیت فیلتر تنها به فهرست منابع محدود نمی‌شود. هنگام مشاهده لاگ پادها یا کانتینرها هم می‌توانید با وارد کردن عباراتی مانند <code>/error</code> یا <code>/timeout</code>، فقط خطوط مرتبط با خطاها یا وقفه‌های زمانی را نمایش دهید.</p>



<h2 class="wp-block-heading" id="h-کارهای-عملی-با-k9s-logs-describe-yaml-shell-و-port-forward">کارهای عملی با K9s؛ Logs ،Describe ،YAML ،Shell و Port Forward</h2>



<p class="wp-block-paragraph">K9s علاوه بر نمایش منابع کوبرنتیز، مجموعه‌ای از میانبرهای کاربردی را برای انجام عملیات روزمره در اختیار کاربران قرار می‌دهد. این میانبرها باعث می‌شوند بدون خروج از محیط ترمینال، بتوانید وضعیت منابع را بررسی کنید یا اقدامات مدیریتی موردنیاز را انجام دهید. از مهم‌ترین میانبرهای K9s می‌توان به موارد زیر اشاره کرد:</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><tbody><tr><td><strong>کلید</strong></td><td><strong>کاربرد</strong></td></tr><tr><td><code>d</code></td><td>نمایش اطلاعات کامل منبع (Describe)</td></tr><tr><td><code>y</code></td><td>مشاهده فایل YAML منبع</td></tr><tr><td><code>e</code></td><td>ویرایش منبع با ویرایشگر تنظیم‌شده</td></tr><tr><td><code>l</code></td><td>مشاهده لاگ‌های پاد یا کانتینر</td></tr><tr><td><code>s</code></td><td>اجرای Shell روی پاد یا Scale کردن دیپلویمنت</td></tr><tr><td><code>Shift+F</code></td><td>ایجاد Port Forward</td></tr><tr><td><code>Ctrl+d</code></td><td>حذف منبع با دریافت تأیید</td></tr><tr><td><code>Ctrl+k</code></td><td>حذف فوری منبع بدون دریافت تأیید</td></tr><tr><td><code>Ctrl+s</code></td><td>ذخیره نمای فعلی یا Logها روی دیسک</td></tr></tbody></table></figure>



<p class="wp-block-paragraph">اگر پاد چند کانتینر داشته باشد، ابتدا می‌توانید کانتینر موردنظر را انتخاب و سپس با کلید l لاگ آن را مشاهده کنید. همچنین در شرایطی که یک کانتینر دچار Crash شده و پس از راه‌اندازی مجدد، لاگ فعلی اطلاعات کافی در اختیار شما قرار نمی‌دهد، می‌توانید با استفاده از <code>Shift+L</code> لاگ کانتینر قبلی را مشاهده و علت بروز خطا را بررسی کنید.</p>



<h3 class="wp-block-heading" id="h-نمونه-ای-از-عیب-یابی-یک-deployment">نمونه‌ای از عیب‌یابی یک Deployment</h3>



<p class="wp-block-paragraph">فرض کنید یکی از Deploymentهای کلاستر با مشکل مواجه شده است. در K9s می‌توان مراحل عیب‌یابی را به‌ترتیب زیر انجام داد:</p>



<ul class="wp-block-list">
<li>با دستور <code>:deploy</code> به نمای دیپلویمنت‌ها بروید و دیپلویمنت موردنظر را انتخاب کنید.</li>



<li>کلید <code>d</code> را فشار دهید و بخش Events را بررسی کنید تا علت اولیه خطا مشخص شود.</li>



<li>با فشردن Enter، پادهای مربوط به آن دیپلویمنت را مشاهده و پادی را که در وضعیت Running نیست، انتخاب کنید.</li>



<li>با کلید <code>l</code>، لاگ پاد را بررسی کنید تا خطاهایی مانند OOMKilled، نبود متغیرهای محیطی یا خطاهای ارتباطی را شناسایی کنید.</li>



<li>در صورت نیاز، با کلید y فایل YAML منبع را مشاهده و تنظیمات آن را بررسی کنید.</li>



<li>اگر مشکل مشخص شد، با کلید <code>e</code> منبع را ویرایش کرده و تغییرات را ذخیره کنید. K9s این تغییر را اعمال می‌کند و می‌توانید ری‌استارت شدن پاد را مشاهده کنید.</li>



<li>به نمای دیپلویمنت بازگردید و مطمئن شوید Replicaها به وضعیت سالم بازگشته‌اند.</li>
</ul>



<h2 class="wp-block-heading" id="h-مانیتورینگ-قابلیت-های-پیشرفته-pluginها-نکات-production-و-محدودیت-ها">مانیتورینگ، قابلیت‌های پیشرفته، Pluginها، نکات Production و محدودیت‌ها</h2>



<p class="wp-block-paragraph">ابزار K9s در کنار عملیات روزمره مشاهده و مدیریت منابع، مجموعه‌ای از قابلیت‌های تکمیلی هم در اختیار کاربران قرار می‌دهد که از پایش لحظه‌ای وضعیت کلاستر تا امکان تعریف Plugin اختصاصی را پوشش می‌دهند. در ادامه، این قابلیت‌ها را به همراه نکاتی برای استفاده در محیط Production و محدودیت‌های K9s بررسی می‌کنیم.</p>



<h3 class="wp-block-heading" id="h-مشاهده-زنده-وضعیت-منابع-و-متریک-ها">مشاهده زنده وضعیت منابع و متریک‌ها</h3>



<p class="wp-block-paragraph" id="h-مشاهده-وضعیت-real-time-و-metricها"></p>



<p class="wp-block-paragraph">K9s فعالیت منابع کلاستر و متریک‌های مرتبط با پادها، کانتینرها و نودها را به‌صورت زنده نمایش می‌دهد. در استفاده روزمره، یکی از اولین کارهایی که بسیاری از مدیران کلاستر انجام می‌دهند، بررسی سلامت کلی محیط است. برای این منظور می‌توان با دستور <code>:pulses</code> نمایی خلاصه از وضعیت کلاستر مشاهده کرد. این نما تعداد دیپلویمنت‌ها، پادها، StatefulSetها، DaemonSetها و جاب‌ها را نمایش می‌دهد و مشخص می‌کند چه تعداد از آن‌ها با مشکل مواجه هستند.</p>



<p class="wp-block-paragraph">پس از آن، معمولا وضعیت نودها با دستور <code>:node</code> بررسی می‌شود تا مشخص شود که آیا همه نودها در وضعیت Ready قرار دارند یا خیر. همچنین وجود وضعیت‌هایی مانند MemoryPressure یا DiskPressure می‌تواند نشانه بروز مشکل در اجرای Workloadها باشد.</p>



<p class="wp-block-paragraph">در ادامه هم با ورود به نمای پادها و فشردن کلید 0 برای نمایش همه Namespaceها، می‌توان ستون STATUS را بررسی کرد و پادهایی را که در وضعیت‌هایی مانند CrashLoopBackOff ،Error ،Pending یا ImagePullBackOff قرار دارند، به‌سرعت شناسایی کرد.</p>



<p class="wp-block-paragraph">نکته مهم این است که K9s برای مشاهده و بررسی تعاملی وضعیت فعلی کلاستر کاربرد دارد؛ اما برای ذخیره‌سازی و تحلیل تاریخچه متریک‌ها، ساخت داشبورد و هشداردهی مستمر طراحی نشده است. برای این کاربردها باید از ابزارهای تخصصی مانند Prometheus و Grafana استفاده کرد.</p>



<h3 class="wp-block-heading" id="h-pulses-xray-و-rbac">Pulses ،XRay و RBAC</h3>



<p class="wp-block-paragraph">K9s چند قابلیت پیشرفته برای تحلیل وضعیت کلاستر هم در اختیار کاربران قرار می‌دهد. قابلیت Pulses یک داشبورد سطح بالا از وضعیت کلی کلاستر ارائه می‌کند و برای بررسی سریع سلامت منابع بسیار کاربردی است. همان‌طور که در بخش قبل اشاره شد، اجرای دستور <code>:pulses</code> دید مناسبی از وضعیت دیپلویمنت‌ها، پادها و سایر منابع در اختیار مدیر کلاستر قرار می‌دهد.</p>



<p class="wp-block-paragraph">قابلیت XRay برای مشاهده وابستگی میان منابع کوبرنتیز طراحی شده است. برای مثال، با اجرای دستور زیر می‌توان ساختار یک دیپلویمنت را به‌صورت درختی مشاهده کرد:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>:xray deploy</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">:xray</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">deploy</span></span></code></pre></div>



<p class="wp-block-paragraph">در این نما، ارتباط دیپلویمنت با ReplicaSetها، پادها و در نهایت کانتینرهای مرتبط، به‌صورت درختی نمایش داده می‌شود. این قابلیت برای منابع دیگری مانند Service ،StatefulSet ،DaemonSet و ReplicaSet هم قابل استفاده است و هنگام عیب‌یابی وابستگی‌ها، بسیار مفید خواهد بود.</p>



<h3 class="wp-block-heading" id="h-popeye-در-k9s">Popeye در K9s</h3>



<p class="wp-block-paragraph">با اجرای دستور <code>:popeye</code> می‌توانید بررسی کلاستر را براساس مجموعه‌ای از Best Practiceها آغاز کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>:popeye</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">:popeye</span></span></code></pre></div>



<p class="wp-block-paragraph">این قابلیت مواردی مانند نبود Probeهای لازم، مشکلات ایمیج‌ها، تخصیص نامناسب منابع و پیکربندی نادرست RBAC را بررسی و نتیجه را با وضعیت‌هایی مانند <code>OK</code> ،<code>Info</code> ،<code>Warn</code> یا <code>Error</code> نمایش می‌دهد.</p>



<h3 class="wp-block-heading" id="h-pluginها-در-k9s">Pluginها در K9s</h3>



<p class="wp-block-paragraph">یکی از قابلیت‌های توسعه‌پذیر K9s، پشتیبانی از Pluginهاست. با استفاده از Plugin می‌توانید فرمان‌های اختصاصی خود را تعریف کنید و آن‌ها را از طریق میانبرهای صفحه‌کلید روی منابع کوبرنتیز اجرا کنید. K9s برای پیدا کردن Pluginها ابتدا فایل زیر را بررسی می‌کند:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Plaintext</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>$XDG_CONFIG_HOME/k9s/plugins.yaml</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #adbac7">$XDG_CONFIG_HOME/k9s/plugins.yaml</span></span></code></pre></div>



<p class="wp-block-paragraph">علاوه بر این فایل، K9s پوشه‌های زیر را نیز برای یافتن فایل‌های Plugin بررسی می‌کند:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Plaintext</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>$XDG_CONFIG_HOME/k9s/plugins
$XDG_DATA_HOME/k9s/plugins
$XDG_DATA_DIRS/k9s/plugins</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #adbac7">$XDG_CONFIG_HOME/k9s/plugins</span></span>
<span class="line"><span style="color: #adbac7">$XDG_DATA_HOME/k9s/plugins</span></span>
<span class="line"><span style="color: #adbac7">$XDG_DATA_DIRS/k9s/plugins</span></span></code></pre></div>



<p class="wp-block-paragraph">امکان تعریف تنظیمات اختصاصی Plugin برای هر Context نیز وجود دارد. فایل مربوط به این تنظیمات در ساختار زیر قرار می‌گیرد:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Plaintext</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>$XDG_DATA_HOME/k9s/clusters/&lt;cluster-name>/&lt;context-name>/plugins.yaml</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #adbac7">$XDG_DATA_HOME/k9s/clusters/&lt;cluster-name&gt;/&lt;context-name&gt;/plugins.yaml</span></span></code></pre></div>



<p class="wp-block-paragraph">در این مسیر، <code>&lt;cluster-name&gt;</code> و <code>&lt;context-name&gt;</code> مقادیر جایگزین‌شدنی هستند و باید با نام کلاستر و Context موردنظر جایگزین شوند. هر Plugin می‌تواند شامل میانبر اجرا، توضیح، دامنه منابع، فرمان اجرایی و آرگومان‌های موردنیاز باشد. گزینه <code>scopes</code> مشخص می‌کند که Plugin در نمای کدام منابع فعال باشد. برای مثال، اگر مقدار آن روی <code>pods</code> تنظیم شود، میانبر Plugin در نمای پادها در دسترس خواهد بود.</p>



<p class="wp-block-paragraph">نمونه زیر یک Plugin برای اجرای فرمان <code>kubectl debug</code> روی پاد انتخاب‌شده تعریف می‌کند:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">YAML</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>plugins:
  debug:
    shortCut: Shift-D
    description: Debug pod
    scopes:
      - pods
    command: kubectl
    background: false
    args:
      - debug
      - -it
      - $NAME
      - -n
      - $NAMESPACE
      - --image=busybox</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #8DDB8C">plugins</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #8DDB8C">debug</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">shortCut</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">Shift-D</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">description</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">Debug pod</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">scopes</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">      - </span><span style="color: #96D0FF">pods</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">command</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">kubectl</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">background</span><span style="color: #ADBAC7">: </span><span style="color: #6CB6FF">false</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">args</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">      - </span><span style="color: #96D0FF">debug</span></span>
<span class="line"><span style="color: #ADBAC7">      - </span><span style="color: #96D0FF">-it</span></span>
<span class="line"><span style="color: #ADBAC7">      - </span><span style="color: #96D0FF">$NAME</span></span>
<span class="line"><span style="color: #ADBAC7">      - </span><span style="color: #96D0FF">-n</span></span>
<span class="line"><span style="color: #ADBAC7">      - </span><span style="color: #96D0FF">$NAMESPACE</span></span>
<span class="line"><span style="color: #ADBAC7">      - </span><span style="color: #96D0FF">--image=busybox</span></span></code></pre></div>



<p class="wp-block-paragraph">در این مثال، با فشردن میانبر <code>Shift+D</code> در نمای پادها، فرمان تعریف‌شده برای Pod انتخاب‌شده اجرا می‌شود. متغیر <code>$NAME</code> نام منبع انتخاب‌شده و <code>$NAMESPACE</code> نام Namespace آن را در اختیار فرمان قرار می‌دهد. K9s متغیرهای دیگری مانند <code>$CONTEXT</code> و <code>$CLUSTER</code> را نیز برای استفاده در آرگومان‌های Plugin ارائه می‌کند. به این ترتیب، می‌توان فرمان‌هایی تعریف کرد که بر اساس منبع انتخاب‌شده، Namespace ،Context یا کلاستر فعال اجرا شوند.</p>



<h3 class="wp-block-heading" id="h-نکات-استفاده-از-k9s-در-محیط-production">نکات استفاده از K9s در محیط Production</h3>



<p class="wp-block-paragraph">اگر قصد استفاده از K9s در محیط‌های عملیاتی را دارید، رعایت چند نکته می‌تواند احتمال بروز خطا را کاهش دهد.</p>



<p class="wp-block-paragraph">مهم‌ترین توصیه، اجرای برنامه در حالت فقط‌خواندنی است:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>k9s --readonly</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">k9s</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">--readonly</span></span></code></pre></div>



<p class="wp-block-paragraph">در این حالت، تمام عملیات‌های تغییردهنده مانند <code>Edit</code> ،<code>Delete</code> و <code>Kill</code> غیرفعال می‌شوند و تنها امکان مشاهده منابع وجود دارد. همچنین هنگام حذف منابع باید به تفاوت میان دو میانبر توجه داشت. کلید <code>Ctrl+d</code> قبل از حذف، از کاربر تایید می‌گیرد، اما <code>Ctrl+k</code> منبع را بدون نمایش پیام تأیید حذف می‌کند؛ بنابراین در محیط Production استفاده از <code>Ctrl+d</code> گزینه ایمن‌تری است.</p>



<p class="wp-block-paragraph">ازآنجایی‌که K9s کاملاً در ترمینال اجرا می‌شود، می‌توانید آن را از طریق SSH روی Bastion Host یا Jump Server نیز اجرا کنید. این موضوع در بسیاری از زیرساخت‌های سازمانی مزیت مهمی محسوب می‌شود.</p>



<p class="wp-block-paragraph">در کلاسترهای بزرگ که تعداد زیادی پاد در حال اجراست، می‌توانید مقدار <code>refreshRate</code> را در فایل تنظیمات افزایش دهید تا فاصله زمانی میان به‌روزرسانی‌ها بیشتر شود. همچنین می‌توانید K9s را با گزینه <code>-n</code> در Namespace موردنظر اجرا کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>k9s -n &lt;namespace-name></textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">k9s</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-n</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">&lt;</span><span style="color: #96D0FF">namespace-nam</span><span style="color: #ADBAC7">e</span><span style="color: #F47067">&gt;</span></span></code></pre></div>



<p class="wp-block-paragraph">در این دستور، <code>&lt;namespace-name&gt;</code> باید با نام Namespace موردنظر جایگزین شود. شروع کار در یک Namespace مشخص، دسترسی به منابع همان Namespace را در کلاسترهای شلوغ ساده‌تر می‌کند.</p>



<p class="wp-block-paragraph">در نهایت، اگر اعضای تیم به‌صورت مشترک از K9s استفاده می‌کنند، می‌توانید فایل‌های تنظیمات، میانبرها، Pluginها و Skinهای سفارشی را در یک مخزن Git نگهداری کنید تا امکان به‌اشتراک‌گذاری و هماهنگ‌سازی این تنظیمات میان اعضای تیم فراهم شود.</p>



<h3 class="wp-block-heading" id="h-محدودیت-های-k9s">محدودیت‌های K9s</h3>



<p class="wp-block-paragraph">K9s با وجود قابلیت‌های متعدد، محدودیت‌هایی نیز دارد که بهتر است پیش از استفاده از این ابزار از آن‌ها آگاه باشید. مهم‌ترین محدودیت این است که K9s برای Automation طراحی نشده است. خروجی آن قابل استفاده در Scriptها نیست و نمی‌توان از آن در Pipelineهای CI/CD یا Cron Jobها استفاده کرد. برای این سناریوها همچنان kubectl ابزار اصلی به شمار می‌آید.</p>



<p class="wp-block-paragraph">همچنین ناوبری K9s تا حدی از Vim الهام گرفته است؛ بنابراین اگر قبلا با کلیدهایی مانند <code>k</code> ،<code>j</code> یا فرمان‌های مبتنی بر <code>:</code> کار نکرده باشید، ممکن است در روزهای نخست برای یادگیری نحوه کار با آن به کمی زمان نیاز داشته باشید. از دیگر محدودیت‌ها می‌توان به موارد زیر اشاره کرد:</p>



<ul class="wp-block-list">
<li>امکان مشاهده هم‌زمان دو کلاستر در یک پنجره وجود ندارد و برای مقایسه آن‌ها باید دو نمونه جداگانه از K9s را اجرا کنید.</li>



<li>Port Forwardهایی که در K9s ایجاد می‌شوند، پس از بسته‌شدن برنامه متوقف می‌شوند. برای اتصال‌های پایدارتر باید از روش دیگری مانند <code>kubectl port-forward</code> استفاده کنید.</li>



<li>K9s برای دنبال‌کردن هم‌زمان لاگ چند پاد یا کانتینر طراحی نشده است و در هر نوبت، لاگ یک کانتینر را نمایش می‌دهد.</li>



<li>K9s قابلیت نگهداری History یا ارسال Alert ندارد و اگر بخواهید اطلاعاتی مانند لاگ‌ها یا خروجی Viewها را نگه دارید، باید قبل از خروج با <code>Ctrl+s</code> آن‌ها را ذخیره کنید.</li>



<li>اگرچه Pluginهای آماده‌ای برای K9s وجود دارد، اما تعداد آن‌ها محدود است و با وجود Pluginهای آماده، ممکن است برای پوشش نیازهای اختصاصی تیم به تعریف Plugin سفارشی نیاز داشته باشید.</li>
</ul>



<h2 class="wp-block-heading" id="h-جمع-بندی">جمع‌بندی</h2>



<p class="wp-block-paragraph">در این راهنمای K9s توضیح دادیم که این ابزار چگونه مشاهده، پیمایش و مدیریت تعاملی منابع کوبرنتیز را از داخل ترمینال ساده‌تر می‌کند. K9s با دنبال‌کردن مداوم تغییرات کلاستر، انجام کارهای روزمره‌ای مانند بررسی پادها، مشاهده لاگ‌ها، اجرای <code>describe</code> و جابه‌جایی میان Namespaceها را سریع‌تر می‌کند.</p>



<p class="wp-block-paragraph">بااین‌حال، K9s جایگزین کامل <code>kubectl</code> نیست. برای اسکریپت‌نویسی، فرایندهای CI/CD و خودکارسازی عملیات همچنان باید از ابزارهایی مانند <code>kubectl</code> استفاده کنید. K9s همچنین قابلیت نگهداری تاریخچه داده‌ها یا ارسال هشدار را فراهم نمی‌کند.</p>



<p class="wp-block-paragraph">استفاده از K9s در محیط‌های Production باید با احتیاط همراه باشد. اجرای برنامه در حالت <code>readonly</code>، توجه به مجوزهای تعریف‌شده در RBAC و دقت در عملیات مخربی مانند <code>Delete</code> یا <code>Kill</code> می‌تواند احتمال ایجاد تغییرات ناخواسته در کلاستر را کاهش دهد.</p>



<p class="wp-block-paragraph"></p>
<p>The post <a href="https://hamravesh.com/blog/k9s-kubernetes-guide/">آموزش K9s؛ راهنمای نصب و استفاده از ابزار مدیریت کوبرنتیز در ترمینال</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/k9s-kubernetes-guide/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>راهنمای عملی تنظیم CPU Limit در کوبرنتیز؛ از Request تا Throttling</title>
		<link>https://hamravesh.com/blog/how-to-manage-kubernetes-cpu-limits/</link>
					<comments>https://hamravesh.com/blog/how-to-manage-kubernetes-cpu-limits/#respond</comments>
		
		<dc:creator><![CDATA[هم‌روش]]></dc:creator>
		<pubDate>Wed, 15 Jul 2026 12:30:33 +0000</pubDate>
				<category><![CDATA[دواپس]]></category>
		<category><![CDATA[کوبرنتیز]]></category>
		<guid isPermaLink="false">https://hamravesh.com/blog/?p=5406</guid>

					<description><![CDATA[<p>CPU Request و CPU Limit در کوبرنتیز نقش‌های متفاوتی دارند و نباید آن‌ها را به‌جای یکدیگر در نظر گرفت. Request مقداری از منابع است که Kubernetes هنگام Scheduling برای Pod در نظر می‌گیرد. Scheduler هنگام انتخاب Node، مقدار Request را با ظرفیت Allocatable هر Node مقایسه می‌کند و مصرف لحظه‌ای CPU یا Memory را ملاک تصمیم‌گیری قرار نمی‌دهد.</p>
<p>The post <a href="https://hamravesh.com/blog/how-to-manage-kubernetes-cpu-limits/">راهنمای عملی تنظیم CPU Limit در کوبرنتیز؛ از Request تا Throttling</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">فرض کنید یکی از سرویس‌های مبتنی بر کوبرنتیز شما ناگهان کند شده است. کاربران از افزایش تاخیر شکایت می‌کنند، اما وقتی داشبوردهای مانیتورینگ را بررسی می‌کنید، همه‌چیز عادی به نظر می‌رسد. Podها در وضعیت Running هستند، مصرف CPU روی نود پایین است، Memory تحت فشار نیست و Alert غیرعادی هم دیده نمی‌شود. با این حال، زمان پاسخ‌دهی سرویس همچنان بیشتر از حد انتظار است. معمولا در چنین شرایطی پیدا کردن منشأ مشکل ساده نیست. یکی از دلایلی که کمتر مورد توجه قرار می‌گیرد، CPU Throttling ناشی از CPU Limit در کوبرنتیز است. این مسئله ممکن است در بررسی اولیه داشبوردها به‌وضوح دیده نشود و از چشم تیم عملیات پنهان بماند.</p>



<p class="wp-block-paragraph">نکته مهم اینجاست که وجود CPU آزاد روی نود، لزوما به این معنا نیست که همه کانتینرها بدون محدودیت از منابع پردازشی استفاده می‌کنند. حتی اگر بخشی از ظرفیت پردازشی نود هنوز آزاد باشد، اعمال CPU Limit می‌تواند باعث CPU Throttling در سرویس‌های حساس به تاخیر شود. در ادامه بررسی می‌کنیم که CPU Request و CPU Limit در کوبرنتیز چه تفاوتی با هم دارند، کوبرنتیز هرکدام را در چه مرحله‌ای به کار می‌گیرد و چرا این تنظیم به‌ظاهر ساده می‌تواند تاثیر زیادی بر عملکرد سرویس‌ها داشته باشد.</p>



<h2 class="wp-block-heading" id="h-cpu-request-و-cpu-limit-در-کوبرنتیز-چه-تفاوتی-دارند">CPU Request و CPU Limit در کوبرنتیز چه تفاوتی دارند؟</h2>



<p class="wp-block-paragraph">CPU Request و CPU Limit دو کاربرد متفاوت دارند. CPU Request مشخص می‌کند یک <a href="https://hamravesh.com/blog/what-is-kubernetes-pod" data-type="link" data-id="https://hamravesh.com/blog/what-is-kubernetes-pod" target="_blank" rel="noreferrer noopener">پاد</a> برای اجرا به چه میزان CPU نیاز دارد. کوبرنتیز هنگام انتخاب نود (در فرایند Scheduling)، بررسی می‌کند که با توجه به Request پادهای مستقرشده، کدام نود ظرفیت کافی برای پاد جدید دارد. در این تصمیم، مصرف لحظه‌ای CPU ملاک نیست؛ بنابراین ممکن است CPU یک نود در عمل کم‌مصرف باشد، اما به‌دلیل مجموع Requestهای ثبت‌شده، پاد جدید روی آن اجرا نشود.</p>



<p class="wp-block-paragraph">در مقابل، CPU Limit سقف مصرف CPU کانتینر را پس از اجرا مشخص می‌کند. اگر کانتینر به این سقف برسد، کرنل لینوکس دسترسی آن به CPU را موقتاً محدود می‌کند؛ حتی اگر نود همچنان CPU آزاد داشته باشد.</p>



<p class="wp-block-paragraph">برای درک بهتر تفاوت Request و Limit، در مثال زیر مقدار منابع موردنیاز کانتینر برای انتخاب نود و همچنین سقف مصرف آن پس از اجرا مشخص شده است:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">YAML</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>apiVersion: v1
kind: Pod
metadata:
  name: demo-app
spec:
  containers:
    - name: web
      image: nginx
      resources:
        requests:
          cpu: "500m"
          memory: "512Mi"
        limits:
          cpu: "1"
          memory: "512Mi"</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #8DDB8C">apiVersion</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">v1</span></span>
<span class="line"><span style="color: #8DDB8C">kind</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">Pod</span></span>
<span class="line"><span style="color: #8DDB8C">metadata</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #8DDB8C">name</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">demo-app</span></span>
<span class="line"><span style="color: #8DDB8C">spec</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #8DDB8C">containers</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">    - </span><span style="color: #8DDB8C">name</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">web</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #8DDB8C">image</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">nginx</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #8DDB8C">resources</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #8DDB8C">requests</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">          </span><span style="color: #8DDB8C">cpu</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">&quot;500m&quot;</span></span>
<span class="line"><span style="color: #ADBAC7">          </span><span style="color: #8DDB8C">memory</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">&quot;512Mi&quot;</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #8DDB8C">limits</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">          </span><span style="color: #8DDB8C">cpu</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">&quot;1&quot;</span></span>
<span class="line"><span style="color: #ADBAC7">          </span><span style="color: #8DDB8C">memory</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">&quot;512Mi&quot;</span></span></code></pre></div>



<p class="wp-block-paragraph">در این مثال:</p>



<ul class="wp-block-list">
<li>requests.cpu: 500m یعنی پاد برای زمان‌بندی به نیم هسته CPU نیاز دارد.</li>



<li>requests.memory: 512Mi یعنی Scheduler باید نودی را انتخاب کند که بتواند حداقل 512Mi حافظه را برای این پاد در نظر بگیرد.</li>



<li>limits.cpu: 1 یعنی کانتینر در زمان اجرا نمی‌تواند بیش از یک هسته CPU مصرف کند.</li>



<li>limits.memory: 512Mi سقف مصرف حافظه را مشخص می‌کند و عبور از این مقدار می‌تواند به OOM Kill منجر شود. در OOM Kill، کرنل به‌دلیل فشار حافظه یا عبور کانتینر از محدودیت حافظه، یکی از فرایندهای آن را متوقف می‌کند.</li>
</ul>



<h2 class="wp-block-heading" id="h-request-در-scheduling-چه-نقشی-دارد">Request در Scheduling چه نقشی دارد؟</h2>



<p class="wp-block-paragraph">یکی از رایج‌ترین سو برداشت‌ها درباره CPU Request در کوبرنتیز این است که آن را معادل مصرف واقعی برنامه در نظر می‌گیرند؛ درحالی‌که Request در اصل یک سیگنال برای زمان‌بندی (<a href="https://hamravesh.com/blog/what-is-scheduling-in-kubernetes/" data-type="link" data-id="https://hamravesh.com/blog/what-is-scheduling-in-kubernetes/" target="_blank" rel="noreferrer noopener">Scheduling در کوبرنتیز</a>) است و قرار نیست گزارشی از مصرف لحظه‌ای کانتینر ارائه دهد. به همین دلیل ممکن است نود از نظر مصرف واقعی CPU تقریبا بیکار به نظر برسد، اما Scheduler همچنان نتواند پاد جدیدی را روی آن قرار دهد.&nbsp;</p>



<p class="wp-block-paragraph">اگر مجموع CPU Request پادهای مستقر روی یک نود به ظرفیت قابل تخصیص (Allocatable) آن رسیده باشد، کوبرنتیز دیگر پاد جدیدی را روی آن نود قرار نمی‌دهد؛ حتی اگر نمودارهای مانیتورینگ نشان دهند که مصرف واقعی CPU پایین است. در چنین شرایطی، اگر نود مناسب دیگری هم وجود نداشته باشد، پاد جدید در وضعیت Pending باقی می‌ماند و اجرا نمی‌شود.</p>



<p class="wp-block-paragraph">تنظیم نادرست Requestها می‌تواند روی بهره‌وری کل کلاستر هم تاثیر بگذارد. اگر Requestها بیش از نیاز واقعی Workload تعیین شوند، Scheduler باید آن مقدار را در محاسبه ظرفیت قابل زمان‌بندی نود لحاظ کند. در نتیجه، بخشی از ظرفیت قابل زمان‌بندی (Schedulable Capacity) برای استقرار پادهای دیگر قابل استفاده نخواهد بود؛ حتی اگر مصرف واقعی CPU پایین باشد. پس بهتر است Request را بر اساس نیاز واقعی Workload تنظیم کنیم، زیرا Scheduler برای استقرار Podها به همین مقدار تکیه می‌کند و مصرف لحظه‌ای برنامه را معیار قرار نمی‌دهد.</p>



<h2 class="wp-block-heading" id="h-cpu-limit-در-کوبرنتیز-در-پشت-صحنه-چطور-اعمال-می-شود">CPU Limit در کوبرنتیز در پشت صحنه چطور اعمال می‌شود؟</h2>



<p class="wp-block-paragraph">برخلاف تصور رایج، کوبرنتیز مستقیماً مصرف CPU کانتینر را محدود نمی‌کند. پس از اینکه Scheduler نود مناسب را برای پاد انتخاب کرد، kubelet که روی آن نود اجرا می‌شود، مشخصات پاد را دریافت می‌کند. (عامل اجرایی کوبرنتیز روی هر نود است که پادها و کانتینرهای آن نود را راه‌اندازی و مدیریت می‌کند.) سپس kubelet از طریق Container Runtime (مانند containerd)، کانتینر را راه‌اندازی می‌کند.</p>



<p class="wp-block-paragraph">Container Runtime برای هر کانتینر یک cgroup ایجاد کرده و مقادیر Request و Limit را به آن‌ها اعمال می‌کند. cgroup قابلیتی در لینوکس است که برای مدیریت و محدودکردن منابع پردازشی کانتینرها به کار می‌رود. از این مرحله به بعد، اعمال محدودیت CPU بر عهده کرنل لینوکس است.</p>



<p class="wp-block-paragraph">در این فرایند، CPU Request و CPU Limit نقش‌های متفاوتی دارند. مقدار CPU Request معمولاً به <code>cpu.weight</code> تبدیل می‌شود و وزن نسبی کانتینر را هنگام رقابت بر سر CPU مشخص می‌کند. این مقدار به معنای اختصاص یا رزرو مقدار ثابتی از CPU نیست. در مقابل، CPU Limit به <code>cpu.max</code> تبدیل می‌شود و سقف سخت مصرف CPU کانتینر را تعیین می‌کند.</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>cpu.max = &lt;quota> &lt;period></textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">cpu.max</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">=</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">&lt;</span><span style="color: #96D0FF">quot</span><span style="color: #ADBAC7">a</span><span style="color: #F47067">&gt;</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">&lt;</span><span style="color: #96D0FF">perio</span><span style="color: #ADBAC7">d</span><span style="color: #F47067">&gt;</span></span></code></pre></div>



<p class="wp-block-paragraph">برای مثال، اگر CPU Limit برابر 200m باشد، مقدار cpu.max به‌صورت زیر تنظیم می‌شود:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>cpu.max = 20000 100000</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">cpu.max</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">=</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">20000</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">100000</span></span></code></pre></div>



<p class="wp-block-paragraph">در این مثال، کانتینر در هر بازه ۱۰۰،۰۰۰ میکروثانیه (معادل ۱۰۰ میلی‌ثانیه) فقط مجاز است ۲۰،۰۰۰ میکروثانیه (معادل ۲۰ میلی‌ثانیه) از CPU استفاده کند. اگر این سهم را پیش از پایان بازه مصرف کند، کرنل اجرای آن را تا شروع دوره بعدی متوقف می‌کند. همین توقف موقت را CPU Throttling در کوبرنتیز می‌نامند. رابطه میان Request و Limit با تنظیمات cgroup را می‌توان به‌صورت زیر خلاصه کرد:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Plaintext</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>CPU request → cpu.weight → controls fairness
CPU limit   → cpu.max    → enforces a hard cap</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #adbac7">CPU request → cpu.weight → controls fairness</span></span>
<span class="line"><span style="color: #adbac7">CPU limit   → cpu.max    → enforces a hard cap</span></span></code></pre></div>



<p class="wp-block-paragraph">نکته مهم این است که CPU Throttling صرفا به معنای «کمی کندتر شدن» کانتینر نیست. اگر سهم CPU مجاز در یک بازه زمانی به‌طور کامل مصرف شود، کانتینر تا آغاز بازه بعدی، عملا امکان دریافت CPU بیشتری را نخواهد داشت.</p>



<h2 class="wp-block-heading" id="h-چرا-با-وجود-cpu-آزاد-روی-نود-باز-هم-پاد-throttle-می-شود">چرا با وجود CPU آزاد روی نود باز هم پاد Throttle می‌شود؟</h2>



<p class="wp-block-paragraph">شاید در نگاه اول این اتفاق غیرمنطقی به نظر برسد که اگر نود هنوز CPU آزاد دارد، چرا یک پاد باید با CPU Throttling مواجه شود؟ پاسخ این سوال را باید در نحوه اعمال CPU Limit در کوبرنتیز بررسی کنیم.&nbsp;</p>



<p class="wp-block-paragraph">همان‌طور که در بخش قبل گفتیم، CPU Limit در سطح cgroup اعمال می‌شود، نه در سطح کل نود. کرنل این محدودیت را براساس سهمیه زمانی CPU تعیین‌شده برای همان cgroup اعمال می‌کند و میزان CPU آزاد نود را در این تصمیم دخالت نمی‌دهد. به همین دلیل، پایین‌بودن مصرف CPU در سطح نود لزوماً به این معنا نیست که همه کانتینرها می‌توانند از ظرفیت آزاد آن استفاده کنند. ممکن است نود همچنان CPU آزاد داشته باشد، اما کانتینری که سهمیه زمانی CPU خود را مصرف کرده است، تا آغاز دوره بعدی نتواند CPU بیشتری دریافت کند.</p>



<p class="wp-block-paragraph">همین موضوع ممکن است باعث شود مشکل را به‌اشتباه به کمبود منابع نود نسبت دهیم. در واقع، نود با کمبود CPU مواجه نیست؛ بلکه کانتینر سهمیه زمانی CPU خود را در آن دوره مصرف کرده است و کرنل تا آغاز دوره بعدی اجازه استفاده بیشتر از CPU را به آن نمی‌دهد.</p>



<p class="wp-block-paragraph">در نتیجه، با وجود ظرفیت پردازشی بلااستفاده روی نود، سرویس ممکن است با افزایش تأخیر، تشکیل صف درخواست‌ها (Queue Buildup) و در نهایت Timeout مواجه شود.</p>



<h2 class="wp-block-heading" id="h-cpu-limit-با-memory-limit-چه-فرقی-دارد">CPU Limit با Memory Limit چه فرقی دارد؟</h2>



<p class="wp-block-paragraph">یکی از اشتباهات رایج درباره CPU Limit در کوبرنتیز این است که آن را با همان منطق Memory Limit در نظر می‌گیرند؛ درحالی‌که این دو از نظر نوع و رفتار هنگام رسیدن به Limit با هم متفاوت‌اند. جدول زیر این تفاوت را نشان می‌دهد:</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><tbody><tr><td class="has-text-align-center" data-align="center"><strong>منبع</strong></td><td class="has-text-align-center" data-align="center"><strong>رفتار هنگام عبور از Limit</strong></td><td class="has-text-align-center" data-align="center"><strong>نتیجه محتمل</strong></td></tr><tr><td class="has-text-align-center" data-align="center">CPU</td><td class="has-text-align-center" data-align="center">CPU Throttling</td><td class="has-text-align-center" data-align="center">افزایش Latency ،Timeout و کاهش Throughput</td></tr><tr><td class="has-text-align-center" data-align="center">Memory</td><td class="has-text-align-center" data-align="center">OOM Kill</td><td class="has-text-align-center" data-align="center">Restart کانتینر و اختلال در سرویس</td></tr></tbody></table></figure>



<p class="wp-block-paragraph">این تفاوت در محیط‌های عملیاتی اهمیت زیادی دارد. اگر افزایش زمان پاسخ‌گویی مشاهده می‌کنید، ممکن است ریشه مشکل CPU Throttling باشد. اگر کانتینری به‌طور ناگهانی Restart می‌شود، ابتدا Last Termination Reason را بررسی کنید تا مشخص شود آیا دلیل توقف آن <code>OOMKilled</code> بوده است یا نه. در صورت مشاهده این وضعیت، Memory Limit و میزان واقعی مصرف حافظه را بررسی کنید.</p>



<h2 class="wp-block-heading" id="h-برای-سرویس-های-حساس-به-تاخیر-چه-الگویی-بهتر-است">برای سرویس‌های حساس به تاخیر چه الگویی بهتر است؟</h2>



<p class="wp-block-paragraph">اگر سرویسی به تاخیر حساس است، هدف فقط محدود کردن مصرف CPU نیست و باید تعادلی بین عملکرد و مدیریت منابع برقرار شود. پیشنهاد می‌شود که CPU Request بر اساس الگوی واقعی مصرف تنظیم شود و CPU Limit به‌صورت پیش‌فرض اعمال نشود؛ مگر اینکه واقعا به یک سقف سخت برای مصرف CPU نیاز باشد.</p>



<p class="wp-block-paragraph">همان‌طور که پیش‌تر دیدیم، CPU Limit سخت‌گیرانه می‌تواند حتی با وجود CPU آزاد روی نود باعث Throttling شود. به همین دلیل، برای بسیاری از سرویس‌های حساس به تاخیر، تنظیم یک CPU Request متناسب با مصرف واقعی و حذف CPU Limit می‌تواند به کانتینر اجازه دهد از CPU آزاد نود برای مدیریت Burstهای کوتاه‌مدت (افزایش ناگهانی و موقت مصرف CPU) استفاده کند. نمونه زیر همین رویکرد را نشان می‌دهد:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">YAML</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>apiVersion: apps/v1
kind: Deployment
metadata:
  name: checkout-api
spec:
  replicas: 3
  template:
    spec:
      containers:
      - name: checkout-api
        image: example.com/checkout-api:1.0.0
        resources:
          requests:
            cpu: "300m"
            memory: "512Mi"
          limits:
            memory: "512Mi"</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #8DDB8C">apiVersion</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">apps/v1</span></span>
<span class="line"><span style="color: #8DDB8C">kind</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">Deployment</span></span>
<span class="line"><span style="color: #8DDB8C">metadata</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #8DDB8C">name</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">checkout-api</span></span>
<span class="line"><span style="color: #8DDB8C">spec</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #8DDB8C">replicas</span><span style="color: #ADBAC7">: </span><span style="color: #6CB6FF">3</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #8DDB8C">template</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">spec</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #8DDB8C">containers</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">      - </span><span style="color: #8DDB8C">name</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">checkout-api</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #8DDB8C">image</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">example.com/checkout-api:1.0.0</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #8DDB8C">resources</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">          </span><span style="color: #8DDB8C">requests</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">            </span><span style="color: #8DDB8C">cpu</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">&quot;300m&quot;</span></span>
<span class="line"><span style="color: #ADBAC7">            </span><span style="color: #8DDB8C">memory</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">&quot;512Mi&quot;</span></span>
<span class="line"><span style="color: #ADBAC7">          </span><span style="color: #8DDB8C">limits</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">            </span><span style="color: #8DDB8C">memory</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">&quot;512Mi&quot;</span></span></code></pre></div>



<p class="wp-block-paragraph">در این مثال، برای هر پاد CPU Request برابر 300m و Memory Request برابر 512Mi تعریف شده است. Memory Limit نیز روی 512Mi قرار دارد، اما هیچ‌گونه CPU Limit تعریف نشده است. حذف CPU Limit به سرویس اجازه می‌دهد در صورت وجود ظرفیت آزاد روی نود، Burstهای کوتاه‌مدت مصرف CPU را بدون مواجهه با یک سقف سخت مدیریت کند.</p>



<p class="wp-block-paragraph">البته این توصیه به این معنا نیست که CPU Limit همیشه باید حذف شود. در برخی Workloadهای حساس به تاخیر، حذف CPU Limit می‌تواند گزینه مناسب‌تری باشد؛ اما تنها زمانی که CPU Request باتوجه‌به رفتار واقعی برنامه تنظیم شده و الگوی مصرف آن در محیط عملیاتی بررسی شده باشد.</p>



<h2 class="wp-block-heading" id="h-برای-عیب-یابی-request-و-limit-چه-مواردی-را-بررسی-کنیم">برای عیب‌یابی Request و Limit چه مواردی را بررسی کنیم؟</h2>



<p class="wp-block-paragraph">اگر احتمال می‌دهید مشکل به تنظیمات Request یا Limit مربوط باشد، چند بررسی اولیه می‌تواند سرنخ‌های مهمی در اختیارتان قرار دهد. ابتدا مصرف فعلی CPU و Memory هر پاد را بررسی کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>kubectl top pod</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">kubectl</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">top</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">pod</span></span></code></pre></div>



<p class="wp-block-paragraph">سپس جزئیات پاد را مشاهده کنید تا مقدار Request ،Limit، کلاس QoS، رویدادها (Events) و آخرین دلیل توقف کانتینر (Last Termination Reason) را ببینید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>kubectl describe pod &lt;pod-name></textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">kubectl</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">describe</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">pod</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">&lt;</span><span style="color: #96D0FF">pod-nam</span><span style="color: #ADBAC7">e</span><span style="color: #F47067">&gt;</span></span></code></pre></div>



<p class="wp-block-paragraph">اگر احتمال می‌دهید پاد به‌دلیل کمبود منابع روی هیچ نودی زمان‌بندی نشده است، Eventهای مربوط به Scheduling را نیز بررسی کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>kubectl describe pod frontend | grep -A 9999999999 Events</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">kubectl</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">describe</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">pod</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">frontend</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">|</span><span style="color: #ADBAC7"> </span><span style="color: #F69D50">grep</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-A</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">9999999999</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">Events</span></span></code></pre></div>



<p class="wp-block-paragraph">به این نکته توجه داشته باشید که kubectl top pod فقط مصرف فعلی CPU و Memory را نمایش می‌دهد و به‌تنهایی برای تشخیص CPU Throttling کافی نیست. برای تشخیص این وضعیت باید متریک‌های مربوط به CPU Throttling را در ابزار مانیتورینگ بررسی کنید.</p>



<div class="wp-block-dh-blog-card-database-block card database">
<div class="wp-block-group row align-items-center is-nowrap is-layout-flex wp-container-core-group-is-layout-8f761849 wp-block-group-is-layout-flex">
<div class="wp-block-group col-md"><div class="wp-block-group__inner-container is-layout-flow wp-block-group-is-layout-flow">
<h3 class="wp-block-heading" id="h-کوبرنتیز-مدیریت-شده-هم-روش-راهی-مطمئن-برای-رشد-بی-وقفه">💡 کوبرنتیز مدیریت‌شده هم‌روش، راهی مطمئن برای رشد بی‌وقفه</h3>



<p class="wp-block-paragraph">راهکار کوبرنتیز مدیریت شده، بر بستر ابر اختصاصی یا به صورت On-Premises</p>



<p class="wp-block-paragraph"><br>✅ کاهش هزینه‌های عملیاتی<br>✅ احراز هویت یکپارچه با اتصال به SSO سازمانی<br>✅ قابل استقرار روی سرورهای on-premises</p>



<p class="wp-block-paragraph"></p>
</div></div>
</div>



<div class="wp-block-group col-md-auto"><div class="wp-block-group__inner-container is-layout-flow wp-block-group-is-layout-flow">
<p class="btn btn--main btn--wide wp-block-paragraph"><a href="https://hamravesh.com/managed-kubernetes" type="link" id="https://hamravesh.com/managed-kubernetes" target="_blank" rel="noreferrer noopener">کوبرنتیز مدیریت‌شده</a></p>
</div></div>
</div>



<h2 class="wp-block-heading" id="h-چه-زمانی-cpu-limit-نگذاریم">چه زمانی CPU Limit نگذاریم؟</h2>



<p class="wp-block-paragraph">CPU Limit در کوبرنتیز ممکن است حتی در صورت وجود CPU آزاد روی نود، باعث CPU Throttling و افزایش تاخیر شود. تعریف‌نکردن CPU Limit می‌تواند برای موارد زیر مناسب‌تر باشد:</p>



<ul class="wp-block-list">
<li>سرویس‌های حساس به تاخیر</li>



<li>Workloadهایی که برای مدیریت Burstهای کوتاه‌مدت (افزایش ناگهانی و موقت مصرف CPU) باید بتوانند از CPU آزاد نود استفاده کنند</li>



<li>سرویس‌هایی که CPU Throttling در آن‌ها باعث افزایش تاخیر، تشکیل صف درخواست‌ها، Timeout یا کاهش Throughput می‌شود</li>
</ul>



<p class="wp-block-paragraph">در این شرایط، CPU Request باید براساس مصرف واقعی Workload تنظیم شود. CPU Limit نیز فقط زمانی تعریف شود که Workload واقعاً به یک سقف سخت برای مصرف CPU نیاز داشته باشد.</p>



<h2 class="wp-block-heading" id="h-چه-زمانی-cpu-limit-در-کوبرنتیز-همچنان-مفید-است">چه زمانی CPU Limit در کوبرنتیز همچنان مفید است؟</h2>



<p class="wp-block-paragraph">با اینکه حذف CPU Limit در کوبرنتیز می‌تواند برای بسیاری از سرویس‌های حساس به تأخیر مناسب‌تر باشد، استفاده از آن در برخی سناریوها همچنان قابل دفاع است. CPU Limit باید زمانی تعریف شود که Workload واقعاً به یک سقف سخت برای مصرف CPU نیاز داشته باشد، نه صرفاً به این دلیل که به‌صورت پیش‌فرض در یک الگوی پیکربندی قرار گرفته است. استفاده از CPU Limit در شرایط زیر می‌تواند مناسب باشد:</p>



<ul class="wp-block-list">
<li>کلاسترهای Multi-tenant که چند تیم یا چند سرویس از منابع مشترک استفاده می‌کنند</li>



<li>Workloadهای غیر قابل اعتماد (Untrusted) که باید مصرف CPU آن‌ها به‌طور سخت‌گیرانه کنترل شود</li>



<li>جاب‌های پردازش دسته‌ای (Batch Jobs) که به سقف مشخصی برای مصرف CPU نیاز دارند</li>



<li>محیط‌های Benchmark و Performance Test که تکرارپذیری نتایج اهمیت دارد</li>



<li>سرویس‌هایی که بر اساس پلن‌های ثابت CPU به مشتریان ارائه می‌شوند</li>



<li>سناریوهایی که Strict Cost Control در آن‌ها اهمیت دارد و مصرف CPU باید در یک بودجه مشخص باقی بماند</li>



<li>محیط‌هایی که سیاست‌های پلتفرم، تعریف CPU Limit را الزامی می‌کنند</li>
</ul>



<p class="wp-block-paragraph">در این سناریوها، CPU Limit یک سقف مشخص برای مصرف CPU ایجاد می‌کند؛ هرچند ممکن است امکان استفاده Workload از CPU آزاد نود را در زمان Burst محدود کند. CPU Limit نیز باید فقط زمانی تعریف شود که Workload واقعاً به یک سقف سخت برای مصرف CPU نیاز داشته باشد.</p>



<h2 class="wp-block-heading" id="h-جمع-بندی-nbsp">جمع‌بندی&nbsp;</h2>



<p class="wp-block-paragraph">CPU Limit در کوبرنتیز همیشه به بهبود عملکرد و پایداری سرویس منجر نمی‌شود و حتی ممکن است با وجود CPU آزاد روی نود، باعث Throttling و افزایش تأخیر شود. بنابراین، Request و Limit را براساس رفتار واقعی هر Workload تنظیم کنید و CPU Limit را فقط زمانی به کار ببرید که به سقف سخت مصرف نیاز دارید. بررسی مصرف منابع و متریک‌های CPU Throttling نیز کمک می‌کند این تصمیم براساس داده‌های واقعی گرفته شود، نه تنظیمات پیش‌فرض.<br><br></p>
<p>The post <a href="https://hamravesh.com/blog/how-to-manage-kubernetes-cpu-limits/">راهنمای عملی تنظیم CPU Limit در کوبرنتیز؛ از Request تا Throttling</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/how-to-manage-kubernetes-cpu-limits/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>بازنشستگی Ingress NGINX؛ ریسک‌ها، جایگزین‌ها و مسیر مهاجرت</title>
		<link>https://hamravesh.com/blog/ingress-nginx-retirement/</link>
					<comments>https://hamravesh.com/blog/ingress-nginx-retirement/#respond</comments>
		
		<dc:creator><![CDATA[هم‌روش]]></dc:creator>
		<pubDate>Wed, 17 Jun 2026 12:30:07 +0000</pubDate>
				<category><![CDATA[دواپس]]></category>
		<category><![CDATA[مقالات]]></category>
		<category><![CDATA[کوبرنتیز]]></category>
		<guid isPermaLink="false">https://hamravesh.com/blog/?p=5247</guid>

					<description><![CDATA[<p>بازنشستگی ingress-nginx یکی از مهم‌ترین تغییرات اخیر در اکوسیستم Kubernetes به شمار می‌آید. این پروژه که سال‌ها یکی از رایج‌ترین Ingress Controllerهای Kubernetes بود، دیگر در مسیر توسعه عادی قرار ندارد و پس از پایان دوره پشتیبانی، به‌روزرسانی امنیتی و اصلاح باگ جدیدی برای آن منتشر نمی‌شود. </p>
<p>The post <a href="https://hamravesh.com/blog/ingress-nginx-retirement/">بازنشستگی Ingress NGINX؛ ریسک‌ها، جایگزین‌ها و مسیر مهاجرت</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">بازنشستگی ingress-nginx یکی از مهم‌ترین تغییرات اخیر در اکوسیستم کوبرنتیز به شمار می‌آید. این پروژه که سال‌ها یکی از رایج‌ترین Ingress Controllerهای کوبرنتیز بود، دیگر در مسیر توسعه عادی قرار ندارد و پس از پایان دوره پشتیبانی، به‌روزرسانی امنیتی و اصلاح باگ جدیدی برای آن منتشر نمی‌شود. این اتفاق باعث شده است که مهاجرت از ingress nginx و بررسی جایگزین به یکی از دغدغه‌های اصلی تیم‌های زیرساخت و DevOps تبدیل شود.</p>



<p class="wp-block-paragraph">در این مقاله بررسی می‌کنیم که ingress-nginx چیست، دقیقاً چه بخشی از این پروژه بازنشسته شده، چرا کوبرنتیز این تصمیم را گرفته است و ادامه استفاده از آن چه ریسک‌هایی دارد. همچنین گزینه‌های موجود برای جایگزین ingress-nginx، نقش Gateway API و مراحل مهاجرت از اینگرس nginx با استفاده از ابزار Ingress2Gateway را به‌صورت عملی آموزش می‌دهیم.</p>



<h2 class="wp-block-heading" id="h-اهمیت-بازنشستگی-ingress-nginx-چرا-کوبرنتیز-درباره-آن-هشدار-می-دهد">اهمیت بازنشستگی ingress-nginx؛ چرا کوبرنتیز درباره آن هشدار می‌دهد؟</h2>



<p class="wp-block-paragraph">بازنشستگی ingress-nginx صرفا پایان عمر یک پروژه متن‌باز نیست، بلکه به پایان چرخه نگهداری یکی از پرکاربردترین Ingress Controllerهای کوبرنتیز اشاره دارد. بر اساس بیانیه رسمی کوبرنتیز، ادامه استفاده از این پروژه پس از پایان دوره پشتیبانی، می‌تواند ریسک‌های امنیتی و عملیاتی جدیدی برای محیط‌های Production ایجاد کند.</p>



<p class="wp-block-paragraph">اهمیت این موضوع زمانی بیشتر مشخص می‌شود که بخش قابل توجهی از کلاسترهای کوبرنتیز همچنان از ingress-nginx برای مدیریت ترافیک HTTP و HTTPS استفاده می‌کنند. هرچند استقرارهای فعلی به کار خود ادامه می‌دهند، اما پس از بازنشستگی، هیچ وصله امنیتی، اصلاح باگ یا نسخه جدیدی برای پروژه منتشر نمی‌شود و آسیب‌پذیری‌های آینده ممکن است بدون راهکار رسمی باقی بمانند.</p>



<p class="wp-block-paragraph">تیم کوبرنتیز اعلام کرده است که این تصمیم نتیجه چالش‌های طولانی‌مدت در نگهداری پروژه، محدود بودن افراد مسئول نگهداری و افزایش پیچیدگی فنی آن بوده است، به همین دلیل، تیم کوبرنتیز به کاربران توصیه می‌کند که از همین حالا برای مهاجرت از ingress-nginx یا انتخاب جایگزین مناسب برنامه‌ریزی کنند.</p>



<h2 class="wp-block-heading" id="h-ingress-nginx-چیست">ingress-nginx چیست؟</h2>



<p class="wp-block-paragraph">ingress-nginx یک Ingress Controller مبتنی بر NGINX برای کوبرنتیز است که منابع Ingress را پایش کرده و بر اساس قوانین تعریف‌شده، پیکربندی NGINX را به‌صورت خودکار ایجاد و به‌روزرسانی می‌کند تا ترافیک HTTP و HTTPS به سرویس‌های مناسب هدایت شود.</p>



<p class="wp-block-paragraph">در کوبرنتیز، منبع Ingress فقط شامل قوانین مسیریابی است و به‌تنهایی درخواست‌ها را پردازش نمی‌کند. برای اعمال این قوانین به یک Ingress Controller نیاز است و ingress-nginx یکی از شناخته‌شده‌ترین پیاده‌سازی‌های این مدل به شمار می‌آید.</p>



<p class="wp-block-paragraph">یکی از دلایل محبوبیت ingress-nginx، متن‌باز بودن و امکان استفاده از آن در انواع محیط‌های کوبرنتیز، چه در سرویس‌های ابری و چه در زیرساخت‌های On-Premise، بود و به همین دلیل در میان تیم‌های DevOps و SRE جایگاه ویژه‌ای پیدا کرد.</p>



<h2 class="wp-block-heading" id="h-دقیقا-چه-چیزی-بازنشسته-شده-است">دقیقاً چه چیزی بازنشسته شده است؟</h2>



<p class="wp-block-paragraph">نکته مهمی که باید بدانید این است که قابلیت Ingress همچنان بخشی از کوبرنتیز  باقی می‌ماند، اما پروژه ingress-nginx پس از پایان دوره پشتیبانی دیگر به‌روزرسانی نمی‌شود. بر اساس اعلام رسمی کوبرنتیز ، پس از پایان نگهداری پروژه:</p>



<ul class="wp-block-list">
<li>نسخه جدیدی از ingress-nginx منتشر نمی‌شود</li>



<li>باگ‌های جدید برطرف نخواهند شد</li>



<li>برای آسیب‌پذیری‌های آینده وصله امنیتی ارائه نمی‌شود</li>



<li>مخازن GitHub پروژه در حالت فقط‌خواندنی (Read-only) قرار می‌گیرند.</li>
</ul>



<p class="wp-block-paragraph">در عین حال، استقرارهای فعلی همچنان به کار خود ادامه می‌دهند و آرتیفکت‌هایی مانند Helm Chartها و Container Imageهای موجود در دسترس هستند. البته با این حال استفاده از نرم‌افزاری که دیگر به‌روزرسانی امنیتی دریافت نمی‌کند، می‌تواند به مرور زمان ریسک‌های عملیاتی و امنیتی را افزایش دهد. اگر می‌خواهید بررسی کنید که آیا کلاستر شما از ingress-nginx استفاده می‌کند یا خیر، می‌توانید دستور زیر را اجرا کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>kubectl get pods --all-namespaces --selector app.kubernetes.io/name=ingress-nginx</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">kubectl</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">get</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">pods</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">--all-namespaces</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">--selector</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">app.kubernetes.io/name=ingress-nginx</span></span></code></pre></div>



<p class="wp-block-paragraph">اگر این دستور خروجی داشته باشد، کلاستر شما از ingress-nginx استفاده می‌کند و بهتر است وضعیت زیرساخت خود را ارزیابی و برای مهاجرت از ingress nginx یا انتخاب یک جایگزین ingress-nginx مناسب برنامه‌ریزی کنید.</p>



<h2 class="wp-block-heading" id="h-چرا-ingress-nginx-بازنشسته-شد">چرا ingress-nginx بازنشسته شد؟</h2>



<p class="wp-block-paragraph">بازنشستگی ingress-nginx نتیجه مجموعه‌ای از چالش‌های فنی و مدیریتی است که طی سال‌های گذشته شکل گرفته‌اند. تیم کوبرنتیز اعلام کرده است که نگهداری این پروژه برای مدت طولانی بر عهده تعداد محدودی افراد مسئول نگهداری بوده و این مدل برای یکی از پرکاربردترین اجزای اکوسیستم Cloud Native پایداری لازم را نداشته است.</p>



<p class="wp-block-paragraph">عامل مهم دیگر، انباشت بدهی فنی (Technical Debt) است. ingress-nginx در ابتدا به‌عنوان یکی از پیاده‌سازی‌های Ingress API توسعه یافت، اما به مرور زمان قابلیت‌ها و Annotationهای متعددی به آن اضافه شد. این انعطاف‌پذیری برای کاربران مفید بود، اما پیچیدگی نگهداری و مدیریت امنیت پروژه را افزایش داد.</p>



<p class="wp-block-paragraph">از سوی دیگر، جامعه کوبرنتیز در سال‌های اخیر به سمت معماری‌ها و استانداردهای جدیدتر مدیریت ترافیک حرکت کرده است؛ به همین دلیل، به جای توسعه بیشتر ingress-nginx، تمرکز اکوسیستم به سمت راهکارهایی مانند Gateway API و نسل جدید Ingress Controllerها معطوف شده است.</p>



<p class="wp-block-paragraph">در مجموع، بازنشستگی ingress-nginx را می‌توان حاصل سه عامل اصلی محدودیت در نگهداری پروژه، افزایش بدهی فنی و حرکت اکوسیستم کوبرنتیز به سمت مدل‌های جدیدتر مدیریت ترافیک دانست.</p>



<h2 class="wp-block-heading" id="h-اگر-مهاجرت-نکنیم-چه-اتفاقی-می-افتد">اگر مهاجرت نکنیم چه اتفاقی می‌افتد؟</h2>



<p class="wp-block-paragraph">بازنشستگی ingress-nginx باعث توقف ناگهانی سرویس‌های فعلی نمی‌شود و استقرارهای موجود همچنان به کار خود ادامه می‌دهند. با این حال، ادامه استفاده از این پروژه به‌معنای استفاده از نرم‌افزاری است که دیگر توسعه فعال و پشتیبانی امنیتی دریافت نمی‌کند.</p>



<p class="wp-block-paragraph">یکی از مهم‌ترین پیامدهای این وضعیت، افزایش ریسک امنیتی در طول زمان است. هر آسیب‌پذیری جدیدی که پس از پایان دوره پشتیبانی کشف شود، ممکن است بدون وصله امنیتی باقی بماند و سازمان‌ها ناچار باشند ریسک آن را بپذیرند یا راهکارهای موقت خود را پیاده‌سازی کنند.</p>



<p class="wp-block-paragraph">موضوع دیگر، افزایش بدهی فنی است. هرچه وابستگی سرویس‌ها به قابلیت‌های اختصاصی ingress-nginx، تنظیمات ویژه و Annotationها بیشتر شود، فرایند مهاجرت در آینده پیچیده‌تر و پرهزینه‌تر می‌شود. </p>



<p class="wp-block-paragraph">همچنین ممکن است به دلیل عدم به‌روزرسانی پروژه ingress-nginx برای سازگاری با تغییرات، در نسخه‌های آینده کوبرنتیز یا سایر اجزای اکوسیستم، ناسازگاری‌های جدیدی ایجاد شود. توصیه جامعه کوبرنتیز این است که سازمان‌ها پیش از تبدیل شدن این وابستگی به یک چالش عملیاتی، وضعیت کلاسترهای خود را بررسی و برای مهاجرت از ingress nginx یا انتخاب یک جایگزین ingress-nginx مناسب برنامه‌ریزی کنند.</p>



<h2 class="wp-block-heading" id="h-جایگزین-های-ingress-nginx-چیست">جایگزین‌های ingress-nginx چیست؟</h2>



<p class="wp-block-paragraph">بازنشستگی ingress-nginx به این معنا نیست که کوبرنتیز دیگر از مدیریت ترافیک ورودی پشتیبانی نمی‌کند. این اکوسیستم از مدت‌ها قبل گزینه‌های مختلفی برای این منظور در اختیار کاربران قرار داده است و در اطلاعیه‌های رسمی هم به مهاجرت از ingress nginx یا انتخاب یک جایگزین مناسب توصیه شده است.</p>



<p class="wp-block-paragraph">انتخاب بهترین گزینه به عواملی مانند معماری کلاستر، نیازهای عملیاتی و برنامه بلندمدت سازمان بستگی دارد. برخی تیم‌ها فقط به دنبال جایگزینی Ingress Controller فعلی هستند و برخی دیگر ترجیح می‌دهند هم‌زمان به سمت فناوری‌های جدیدتر حرکت کنند. در ادامه برخی از مهم‌ترین جایگزین‌های ingress-nginx را معرفی می‌کنیم.</p>



<p class="wp-block-paragraph" id="h-traefik"><strong>Traefik</strong></p>



<p class="wp-block-paragraph">Traefik یکی از شناخته‌شده‌ترین Ingress Controllerهای کوبرنتیز است که علاوه بر Ingress API، از Gateway API هم پشتیبانی می‌کند. این ویژگی امکان مهاجرت تدریجی را برای بسیاری از تیم‌ها فراهم می‌کند. همچنین راه‌اندازی ساده، یکپارچگی مناسب با کوبرنتیز و پشتیبانی هم‌زمان از مدل‌های مختلف مدیریت ترافیک، از مهم‌ترین دلایل محبوبیت این پروژه است.</p>



<p class="wp-block-paragraph">Traefik معمولاً برای تیم‌هایی مناسب است که به دنبال مهاجرت کم‌دردسر از ingress-nginx هستند و می‌خواهند علاوه بر Ingress API، به‌تدریج از Gateway API نیز استفاده کنند. سادگی راه‌اندازی و مدیریت، این گزینه را برای کلاسترهای کوچک و متوسط جذاب کرده است.</p>



<p class="wp-block-paragraph"><strong>Kong Gateway</strong></p>



<p class="wp-block-paragraph">Kong Gateway یکی دیگر از گزینه‌های شناخته‌شده برای مدیریت ترافیک در Kubernetes است که علاوه بر قابلیت‌های Ingress Controller، امکانات گسترده‌ای در حوزه API Gateway نیز ارائه می‌دهد. این پروژه از Gateway API پشتیبانی می‌کند و برای سازمان‌هایی که علاوه بر مسیریابی ترافیک، به قابلیت‌هایی مانند احراز هویت، Rate Limiting، مدیریت API و سیاست‌های امنیتی پیشرفته نیاز دارند، گزینه مناسبی محسوب می‌شود.</p>



<p class="wp-block-paragraph" id="h-envoy-gateway"><strong>Envoy Gateway</strong></p>



<p class="wp-block-paragraph">Envoy Gateway با تمرکز بر Gateway API توسعه یافته است و بیشتر برای سازمان‌هایی مناسب است که قصد دارند معماری مدیریت ترافیک خود را بر پایه استانداردهای جدید کوبرنتیز طراحی کنند. این پروژه یکی از گزینه‌هایی است که در سال‌های اخیر توانسته توجه بسیاری از تیم‌های Cloud Native را به خود جلب کند.</p>



<p class="wp-block-paragraph">Envoy Gateway بیشتر برای سازمان‌هایی مناسب است که قصد دارند از ابتدا بر پایه Gateway API حرکت کنند یا به قابلیت‌های پیشرفته مدیریت ترافیک در معماری‌های Cloud Native و Microservices نیاز دارند.</p>



<p class="wp-block-paragraph" id="h-nginx-gateway-fabric"><strong>NGINX Gateway Fabric</strong></p>



<p class="wp-block-paragraph">NGINX Gateway Fabric راهکار دیگری است که بر پایه Gateway API توسعه یافته است و توسط اکوسیستم NGINX ارائه می‌شود. این گزینه می‌تواند برای تیم‌هایی که تجربه کار با محصولات NGINX را دارند، مسیر مهاجرت آشناتری ایجاد کند.</p>



<p class="wp-block-paragraph">NGINX Gateway Fabric گزینه مناسبی برای تیم‌هایی است که تجربه کار با NGINX را دارند و می‌خواهند ضمن استفاده از Gateway API، همچنان در اکوسیستم محصولات NGINX باقی بمانند.</p>



<p class="wp-block-paragraph"><strong>نکته مهم:</strong> در اطلاعیه رسمی بازنشستگی ingress-nginx، تیم کوبرنتیز استفاده از Gateway API را به‌عنوان یکی از مسیرهای آینده مدیریت ترافیک معرفی کرده است. البته Gateway API جایگزین مستقیم و یک‌به‌یک Ingress نیست و معمولا مهاجرت به آن به بررسی دقیق معماری فعلی نیاز دارد.</p>



<div class="wp-block-dh-blog-card-database-block card database">
<div class="wp-block-group row align-items-center is-nowrap is-layout-flex wp-container-core-group-is-layout-8f761849 wp-block-group-is-layout-flex">
<div class="wp-block-group col-md"><div class="wp-block-group__inner-container is-layout-flow wp-block-group-is-layout-flow">
<h3 class="wp-block-heading" id="h-راه-اندازی-سریع-سرور-nginx-در-بازارچه-هم-روش">💡 راه‌اندازی سریع سرور NGINX در بازارچه هم‌روش</h3>



<p class="wp-block-paragraph"><br>✅ پرداخت به میزان استفاده (PAYG)<br>✅ بدون دغدغه نگهداری زیرساخت<br>✅ بکاپ خودکار روزانه</p>
</div></div>
</div>



<div class="wp-block-group col-md-auto"><div class="wp-block-group__inner-container is-layout-flow wp-block-group-is-layout-flow">
<p class="wp-block-paragraph" id="h-"></p>



<p class="btn btn--main btn--wide wp-block-paragraph"><a href="https://console.hamravesh.com/marketplace/explore/oneclick_nginx" target="_blank" rel="noreferrer noopener">راه‌اندازی NGINX</a><a href="#"></a></p>
</div></div>
</div>



<h2 class="wp-block-heading" id="h-gateway-api-چرا-در-آینده-کوبرنتیز-اهمیت-بیشتری-پیدا-می-کند">Gateway API؛ چرا در آینده کوبرنتیز اهمیت بیشتری پیدا می‌کند؟</h2>



<p class="wp-block-paragraph"><a href="https://hamravesh.com/blog/what-is-kubernetes-gateway-api/" id="https://hamravesh.com/blog/what-is-kubernetes-gateway-api/" target="_blank" rel="noreferrer noopener">Gateway API در کوبرنتیز</a> مجموعه‌ای از APIهای جدید برای مدیریت ترافیک در کوبرنتیز است که با هدف ایجاد انعطاف‌پذیری بیشتر و پوشش سناریوهای پیچیده‌تر طراحی شده است. بسیاری از پروژه‌های جدید اکوسیستم کوبرنتیز هم توسعه خود را بر اساس این استاندارد انجام می‌دهند.</p>



<p class="wp-block-paragraph">یکی از دلایل توجه گسترده به Gateway API، رفع برخی محدودیت‌های مدل سنتی Ingress است. در این استاندارد، قابلیت‌هایی که پیش‌تر معمولاً از طریق Annotationهای اختصاصی هر Ingress Controller پیاده‌سازی می‌شدند، به‌صورت استاندارد و قابل حمل تعریف می‌شوند. همچنین تفکیک مسئولیت‌ها بین تیم‌های زیرساخت و توسعه ساده‌تر شده و امکان مدیریت سناریوهای پیچیده‌تر ترافیک فراهم می‌شود.</p>



<p class="wp-block-paragraph">البته این موضوع به معنای حذف Ingress API نیست. در واقع Ingress همچنان بخشی از کوبرنتیز  محسوب می‌شود و بسیاری از کلاسترها به استفاده از آن ادامه می‌دهند. با این حال، جهت‌گیری کلی اکوسیستم به سمت استفاده گسترده‌تر از Gateway API است و به همین دلیل بسیاری از سازمان‌ها هنگام برنامه‌ریزی برای مهاجرت از ingress nginx، این استاندارد را هم در ارزیابی‌های خود در نظر می‌گیرند.</p>



<h2 class="wp-block-heading" id="h-چرا-مهاجرت-از-ingress-nginx-همیشه-ساده-نیست">چرا مهاجرت از ingress-nginx همیشه ساده نیست؟</h2>



<p class="wp-block-paragraph">مهاجرت از ingress-nginx به یک کنترلر دیگر یا Gateway API، پیچیدگی‌های خاص خود را دارد و فراتر از تبدیل چند فایل YAML است. طی سال‌های گذشته، ingress-nginx رفتارها و قابلیت‌های خاصی را از طریق Annotationها و تنظیمات اختصاصی ارائه کرده که بخشی از استاندارد کوبرنتیز نیستند و احتمالا در راهکارهای دیگر باید به شکل متفاوت یا بدون معادل مستقیم پیاده‌سازی شوند. حتی اگر تبدیلات ظاهرا درست انجام شوند، ممکن است رفتار سرویس‌ها تغییر کند یا اختلالی ایجاد شود. بر اساس مستندات رسمی کوبرنتیز، هنگام مهاجرت باید به موارد زیر توجه ویژه داشت:</p>



<ul class="wp-block-list">
<li>پردازش مسیرهای مبتنی بر Regular Expression</li>



<li>تاثیر Annotationهای اختصاصی مانند use-regex</li>



<li>رفتار وابسته به rewrite-target</li>



<li>مدیریت مسیرهای دارای یا فاقد / انتهایی</li>



<li>تفاوت در URL Normalization</li>
</ul>



<p class="wp-block-paragraph">این موارد ممکن است در کنترلر جدید یا پیاده‌سازی‌های Gateway API به شکل متفاوتی عمل کنند، بنابراین قبل از انتقال کامل ترافیک، تنظیمات جدید باید به‌دقت بررسی و آزمایش شوند. جامعه کوبرنتیز ابزارهایی برای ساده‌تر کردن این فرایند توسعه داده است که در بخش بعدی به مهم‌ترین آن‌ها، یعنی Ingress2Gateway، می‌پردازیم.</p>



<h2 class="wp-block-heading" id="h-مهاجرت-واقعی-و-ابزارها-آموزش-عملی-با-ingress2gateway">مهاجرت واقعی و ابزارها؛ آموزش عملی با Ingress2Gateway</h2>



<p class="wp-block-paragraph">تا اینجا دیدیم که مهاجرت از ingress-nginx همیشه یک تبدیل ساده و یک‌به‌یک نیست. در واقع تفاوت در Annotationها، رفتارهای خاص این کنترلر و تفاوت معماری Gateway API باعث می‌شود که انتقال بدون برنامه‌ریزی، ریسک ایجاد اختلال در سرویس را به همراه داشته باشد.</p>



<p class="wp-block-paragraph">تیم SIG Network ابزار رسمی Ingress2Gateway را معرفی کرده است. در مستندات رسمی، این ابزار به‌عنوان یک Migration Assistant یا دستیار مهاجرت معرفی می‌شود&nbsp;که می‌تواند بررسی Ingressهای فعلی را انجام دهد و آن‌ها را تا حد امکان به Gateway API تبدیل کند. همچنین می‌تواند در عین حال، در مورد بخش‌هایی که نیاز به بازبینی دستی دارند به شما هشدار ‌دهد. به طور کلی، Ingress2Gateway سه هدف اصلی زیر را دنبال می‌کند:&nbsp;</p>



<ul class="wp-block-list">
<li><strong>تبدیل پیکربندی: </strong>ترجمه Ingressها و Annotationهای پشتیبانی‌شده به Gateway API</li>



<li><strong>شناسایی مشکلات: </strong>تشخیص تنظیماتی که معادل مستقیمی ندارند</li>



<li><strong>ارائه پیشنهاد: </strong>اعلام هشدارها و پیشنهاد برای اصلاح دستی</li>
</ul>



<h3 class="wp-block-heading" id="h-نسخه-۱-۰-چه-قابلیت-هایی-دارد">نسخه ۱.۰ چه قابلیت‌هایی دارد؟</h3>



<p class="wp-block-paragraph">نسخه ۱.۰ که در مارس ۲۰۲۶ منتشر شد، نسبت به نسخه‌های قبلی پیشرفت قابل توجهی داشته است. مهم‌ترین تغییرات این نسخه عبارت‌اند از:</p>



<ul class="wp-block-list">
<li>پشتیبانی از بیش از ۳۰ Annotation رایج ingress-nginx&nbsp;</li>



<li>پشتیبانی از قابلیت‌هایی مانند CORS ،Backend TLS ،Regex Matching و Path Rewrite&nbsp;</li>



<li>تست‌های یکپارچگی برای اطمینان از یکسان بودن رفتار Ingress-NGINX و Gateway API&nbsp;</li>



<li>سیستم هشدار و گزارش‌دهی برای بخش‌هایی که قابل ترجمه نیستند</li>
</ul>



<h3 class="wp-block-heading" id="h-مرحله-اول-نصب-ingress2gateway">مرحله اول: نصب Ingress2Gateway</h3>



<p class="wp-block-paragraph">برای استفاده از این ابزار، ابتدا باید آن را نصب کنید. اگر روی سیستم خود محیط Go را دارید، می‌توانید با دستور زیر آخرین نسخه پایدار را نصب کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>go install github.com/kubernetes-sigs/ingress2gateway@v1.0.0</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">go</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">install</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">github.com/kubernetes-sigs/ingress2gateway@v1.0.0</span></span></code></pre></div>



<p class="wp-block-paragraph">اگر از macOS و Homebrew استفاده می‌کنید، دستور نصب آن ساده‌تر است:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>brew install ingress2gateway</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">brew</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">install</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">ingress2gateway</span></span></code></pre></div>



<p class="wp-block-paragraph">همچنین امکان دانلود فایل باینری از <a href="https://github.com/kubernetes-sigs/ingress2gateway/releases/tag/v1.0.0" id="https://github.com/kubernetes-sigs/ingress2gateway/releases/tag/v1.0.0">GitHub</a> یا <a href="https://github.com/kubernetes-sigs/ingress2gateway/" id="https://github.com/kubernetes-sigs/ingress2gateway/">کامپایل ابزار از سورس</a> هم وجود دارد.</p>



<h3 class="wp-block-heading" id="h-مرحله-دوم-اجرای-ingress2gateway">مرحله دوم: اجرای Ingress2Gateway</h3>



<p class="wp-block-paragraph">پس از نصب می‌توانید مانیفست‌های Ingress را به Ingress2Gateway ارسال کنید، یا ابزار را مستقیما از کلاستر خود بخوانید.</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly># ارسال به فایل
ingress2gateway print --input-file my-manifest.yaml,my-other-manifest.yaml --providers=ingress-nginx > gwapi.yaml
# استفاده از فضای نام در کلاستر خودتان
ingress2gateway print --namespace my-api --providers=ingress-nginx > gwapi.yaml
# یا برای کل کلاستر
ingress2gateway print --providers=ingress-nginx --all-namespaces > gwapi.yaml</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #768390"># ارسال به فایل</span></span>
<span class="line"><span style="color: #F69D50">ingress2gateway</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">print</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">--input-file</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-manifest.yaml,my-other-manifest.yaml</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">--providers=ingress-nginx</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">&gt;</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">gwapi.yaml</span></span>
<span class="line"><span style="color: #768390"># استفاده از فضای نام در کلاستر خودتان</span></span>
<span class="line"><span style="color: #F69D50">ingress2gateway</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">print</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">--namespace</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-api</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">--providers=ingress-nginx</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">&gt;</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">gwapi.yaml</span></span>
<span class="line"><span style="color: #768390"># یا برای کل کلاستر</span></span>
<span class="line"><span style="color: #F69D50">ingress2gateway</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">print</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">--providers=ingress-nginx</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">--all-namespaces</span><span style="color: #ADBAC7"> </span><span style="color: #F47067">&gt;</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">gwapi.yaml</span></span></code></pre></div>



<p class="wp-block-paragraph">نکته: همچنین می‌توانید <code>--emitter &lt;agentgateway|envoy-gateway|kgateway&gt;</code> را برای خروجی پسوندهای خاص پیاده‌سازی ارسال کنید.</p>



<h3 class="wp-block-heading" id="h-مرحله-سوم-بررسی-خروجی">مرحله سوم: بررسی خروجی</h3>



<p class="wp-block-paragraph">این مهم‌ترین مرحله است. دستورات بخش قبلی یک مانیفست Gateway API را در gwapi.yaml خروجی می‌دهند. همچنین هشدارهایی منتشر می‌کنند که توضیح می‌دهند چه چیزی دقیقا ترجمه نشده است و چه چیزی را باید به صورت دستی مرور کنید.</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>apiVersion: gateway.networking.k8s.io/v1
kind: Gateway
metadata:
  annotations:
    gateway.networking.k8s.io/generator: ingress2gateway-dev
  name: nginx
  namespace: my-ns
spec:
  gatewayClassName: nginx
  listeners:
  - hostname: my-host.example.com
    name: my-host-example-com-http
    port: 80
    protocol: HTTP
  - hostname: my-host.example.com
    name: my-host-example-com-https
    port: 443
    protocol: HTTPS
    tls:
      certificateRefs:
      - group: ""
        kind: Secret
        name: my-secret
---
apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
  annotations:
    gateway.networking.k8s.io/generator: ingress2gateway-dev
  name: my-ingress-my-host-example-com
  namespace: my-ns
spec:
  hostnames:
  - my-host.example.com
  parentRefs:
  - name: nginx
    port: 443
  rules:
  - backendRefs:
    - name: website-service
      port: 80
    filters:
    - cors:
        allowCredentials: true
        allowHeaders:
        - DNT
        - Keep-Alive
        - User-Agent
        - X-Requested-With
        - If-Modified-Since
        - Cache-Control
        - Content-Type
        - Range
        - Authorization
        allowMethods:
        - GET
        - PUT
        - POST
        - DELETE
        - PATCH
        - OPTIONS
        allowOrigins:
        - '*'
        maxAge: 1728000
      type: CORS
    matches:
    - path:
        type: RegularExpression
        value: (?i)/users/(\d+).*
    name: rule-0
    timeouts:
      request: 10s
---
apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
  annotations:
    gateway.networking.k8s.io/generator: ingress2gateway-dev
  name: my-ingress-my-host-example-com-ssl-redirect
  namespace: my-ns
spec:
  hostnames:
  - my-host.example.com
  parentRefs:
  - name: nginx
    port: 80
  rules:
  - filters:
    - requestRedirect:
        scheme: https
        statusCode: 308
      type: RequestRedirect</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">apiVersion:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">gateway.networking.k8s.io/v1</span></span>
<span class="line"><span style="color: #F69D50">kind:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">Gateway</span></span>
<span class="line"><span style="color: #F69D50">metadata:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">annotations:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">gateway.networking.k8s.io/generator:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">ingress2gateway-dev</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">nginx</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">namespace:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-ns</span></span>
<span class="line"><span style="color: #F69D50">spec:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">gatewayClassName:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">nginx</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">listeners:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">hostname:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-host.example.com</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-host-example-com-http</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">port:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">80</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">protocol:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">HTTP</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">hostname:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-host.example.com</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-host-example-com-https</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">port:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">443</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">protocol:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">HTTPS</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">tls:</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #F69D50">certificateRefs:</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">group:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">&quot;&quot;</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">kind:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">Secret</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-secret</span></span>
<span class="line"><span style="color: #F69D50">---</span></span>
<span class="line"><span style="color: #F69D50">apiVersion:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">gateway.networking.k8s.io/v1</span></span>
<span class="line"><span style="color: #F69D50">kind:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">HTTPRoute</span></span>
<span class="line"><span style="color: #F69D50">metadata:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">annotations:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">gateway.networking.k8s.io/generator:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">ingress2gateway-dev</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-ingress-my-host-example-com</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">namespace:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-ns</span></span>
<span class="line"><span style="color: #F69D50">spec:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">hostnames:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-host.example.com</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">parentRefs:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">nginx</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">port:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">443</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">rules:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">backendRefs:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">website-service</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #F69D50">port:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">80</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">filters:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">cors:</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">allowCredentials:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">true</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">allowHeaders:</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">DNT</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">Keep-Alive</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">User-Agent</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">X-Requested-With</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">If-Modified-Since</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">Cache-Control</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">Content-Type</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">Range</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">Authorization</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">allowMethods:</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">GET</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">PUT</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">POST</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">DELETE</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">PATCH</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">OPTIONS</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">allowOrigins:</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">&#39;*&#39;</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">maxAge:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">1728000</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #6CB6FF">type</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">CORS</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">matches:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">path:</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #6CB6FF">type</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">RegularExpression</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">value:</span><span style="color: #ADBAC7"> (?i)/users/(</span><span style="color: #F69D50">\d+</span><span style="color: #ADBAC7">).</span><span style="color: #F47067">*</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">rule-0</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">timeouts:</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #F69D50">request:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">10</span><span style="color: #96D0FF">s</span></span>
<span class="line"><span style="color: #F69D50">---</span></span>
<span class="line"><span style="color: #F69D50">apiVersion:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">gateway.networking.k8s.io/v1</span></span>
<span class="line"><span style="color: #F69D50">kind:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">HTTPRoute</span></span>
<span class="line"><span style="color: #F69D50">metadata:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">annotations:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">gateway.networking.k8s.io/generator:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">ingress2gateway-dev</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-ingress-my-host-example-com-ssl-redirect</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">namespace:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-ns</span></span>
<span class="line"><span style="color: #F69D50">spec:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">hostnames:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-host.example.com</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">parentRefs:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">nginx</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">port:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">80</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">rules:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">filters:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">requestRedirect:</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">scheme:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">https</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">statusCode:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">308</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #6CB6FF">type</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">RequestRedirect</span></span></code></pre></div>



<p class="wp-block-paragraph">همان‌طور که در بالا مشاهده کردید، Ingress2Gateway با موفقیت برخی annotationها را به معادل‌های Gateway API خود ترجمه کرد. به عنوان مثال، <code>nginx.ingress.kubernetes.io/enable-cors</code> به یک فیلتر CORS ترجمه شد، اما با بررسی دقیق‌تر، annotationهای <code>nginx.ingress.kubernetes.io/proxy-{read,send}-timeout</code> و <code>nginx.ingress.kubernetes.io/proxy-body-size</code> کاملا نگاشت نمی‌شوند. لاگ‌ها دلیل این حذفیات و همچنین استدلال پشت ترجمه را نشان می‌دهند.</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Plaintext</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>┌─ WARN  ────────────────────────────────────────
│  Unsupported annotation nginx.ingress.kubernetes.io/configuration-snippet
│  source: INGRESS-NGINX
│  object: Ingress: my-ns/my-ingress
└─
┌─ INFO  ────────────────────────────────────────
│  Using case-insensitive regex path matches. You may want to change this.
│  source: INGRESS-NGINX
│  object: HTTPRoute: my-ns/my-ingress-my-host-example-com
└─
┌─ WARN  ────────────────────────────────────────
│  ingress-nginx only supports TCP-level timeouts; i2gw has made a best-effort translation to Gateway API timeouts.request. Please verify that this meets your needs. See documentation: https://gateway-api.sigs.k8s.io/guides/http-timeouts/
│  source: INGRESS-NGINX
│  object: HTTPRoute: my-ns/my-ingress-my-host-example-com
└─
┌─ WARN  ────────────────────────────────────────
│  Failed to apply my-ns.my-ingress.metadata.annotations."nginx.ingress.kubernetes.io/proxy-body-size" from my-ns/my-ingress: Most Gateway API implementations have reasonable body size and buffering defaults
│  source: STANDARD_EMITTER
│  object: HTTPRoute: my-ns/my-ingress-my-host-example-com
└─
┌─ WARN  ────────────────────────────────────────
│  Gateway API does not support configuring URL normalization (RFC 3986, Section 6). Please check if this matters for your use case and consult implementation-specific details.
│  source: STANDARD_EMITTER
└─</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #adbac7">┌─ WARN  ────────────────────────────────────────</span></span>
<span class="line"><span style="color: #adbac7">│  Unsupported annotation nginx.ingress.kubernetes.io/configuration-snippet</span></span>
<span class="line"><span style="color: #adbac7">│  source: INGRESS-NGINX</span></span>
<span class="line"><span style="color: #adbac7">│  object: Ingress: my-ns/my-ingress</span></span>
<span class="line"><span style="color: #adbac7">└─</span></span>
<span class="line"><span style="color: #adbac7">┌─ INFO  ────────────────────────────────────────</span></span>
<span class="line"><span style="color: #adbac7">│  Using case-insensitive regex path matches. You may want to change this.</span></span>
<span class="line"><span style="color: #adbac7">│  source: INGRESS-NGINX</span></span>
<span class="line"><span style="color: #adbac7">│  object: HTTPRoute: my-ns/my-ingress-my-host-example-com</span></span>
<span class="line"><span style="color: #adbac7">└─</span></span>
<span class="line"><span style="color: #adbac7">┌─ WARN  ────────────────────────────────────────</span></span>
<span class="line"><span style="color: #adbac7">│  ingress-nginx only supports TCP-level timeouts; i2gw has made a best-effort translation to Gateway API timeouts.request. Please verify that this meets your needs. See documentation: https://gateway-api.sigs.k8s.io/guides/http-timeouts/</span></span>
<span class="line"><span style="color: #adbac7">│  source: INGRESS-NGINX</span></span>
<span class="line"><span style="color: #adbac7">│  object: HTTPRoute: my-ns/my-ingress-my-host-example-com</span></span>
<span class="line"><span style="color: #adbac7">└─</span></span>
<span class="line"><span style="color: #adbac7">┌─ WARN  ────────────────────────────────────────</span></span>
<span class="line"><span style="color: #adbac7">│  Failed to apply my-ns.my-ingress.metadata.annotations.&quot;nginx.ingress.kubernetes.io/proxy-body-size&quot; from my-ns/my-ingress: Most Gateway API implementations have reasonable body size and buffering defaults</span></span>
<span class="line"><span style="color: #adbac7">│  source: STANDARD_EMITTER</span></span>
<span class="line"><span style="color: #adbac7">│  object: HTTPRoute: my-ns/my-ingress-my-host-example-com</span></span>
<span class="line"><span style="color: #adbac7">└─</span></span>
<span class="line"><span style="color: #adbac7">┌─ WARN  ────────────────────────────────────────</span></span>
<span class="line"><span style="color: #adbac7">│  Gateway API does not support configuring URL normalization (RFC 3986, Section 6). Please check if this matters for your use case and consult implementation-specific details.</span></span>
<span class="line"><span style="color: #adbac7">│  source: STANDARD_EMITTER</span></span>
<span class="line"><span style="color: #adbac7">└─</span></span></code></pre></div>



<p class="wp-block-paragraph">یک هشدار وجود دارد که Ingress2Gateway از annotation نوع <code>nginx.ingress.kubernetes.io/configuration-snippet</code> پشتیبانی نمی‌کند. برای دیدن اینکه آیا راهی برای دستیابی به رفتار معادل وجود دارد، باید مستندات پیاده‌سازی Gateway API خود را بررسی کنید.</p>



<p class="wp-block-paragraph">این ابزار همچنین به ما اطلاع داد که تطابق‌های ریجکس Ingress-NGINX تطابق‌های پیشوندی غیر حساس به حروف کوچک و بزرگ هستند. به همین دلیل یک الگوی تطابق <code>(?i)/users/(\d+).*</code> وجود دارد. بیشتر سازمان‌ها می‌خواهند این رفتار را با حذف <code>(?i)</code> ابتدایی و <code>.*</code> انتهایی از الگوی مسیر به یک تطابق دقیق و حساس به حروف کوچک و بزرگ تغییر دهند.</p>



<p class="wp-block-paragraph">Ingress2Gateway ترجمه‌ای با بهترین تلاش از annotationهای <code>nginx.ingress.kubernetes.io/proxy-{send,read}-timeout</code> به یک زمان انتظار درخواست ۱۰ ثانیه در مسیر HTTP ما انجام داد. اگر درخواست‌های این سرویس باید بسیار کوتاه‌تر باشد (مثلا ۳ ثانیه)، می‌توانید تغییرات مربوطه را در مانیفست‌های Gateway API خود اعمال کنید.</p>



<p class="wp-block-paragraph">همچنین، <code>nginx.ingress.kubernetes.io/proxy-body-size</code> معادل Gateway API ندارد، بنابراین ترجمه نشده است. البته با این حال، بیشتر پیاده‌سازی‌های Gateway API، پیش‌فرض‌های معقولی برای حداکثر اندازه بدنه و بافرینگ دارند، بنابراین این موضوع، ممکن است در عمل مشکلی ایجاد نکند.</p>



<p class="wp-block-paragraph">علاوه بر این، برخی emitterها ممکن است پشتیبانی از این annotation را از طریق پسوندهای خاص پیاده‌سازی ارائه دهند. به عنوان مثال، افزودن فلگ <code>--emitter agentgateway</code> یا <code>--emitter envoy-gateway</code> یا <code>--emitter kgateway</code> به دستور <code>ingress2gateway print</code> قبلی منجر به پیکربندی خاص پیاده‌سازی اضافی در مانیفست‌های Gateway API تولید شده می‌شد که سعی در ثبت پیکربندی اندازه بدنه (body size) داشت. </p>



<p class="wp-block-paragraph">همچنین یک هشدار در مورد نرمالایز کردن URL می‌بینیم. پیاده‌سازی‌های Gateway API مانند Agentgateway ،Envoy Gateway ،Kgateway و Istio دارای سطحی از عادی‌سازی URL هستند؛ اما رفتار در پیاده‌سازی‌ها متفاوت است و از طریق Gateway API استاندارد قابل تنظیم نیست. شما باید رفتار عادی‌سازی URL پیاده‌سازی Gateway API خود را بررسی و آزمایش کنید تا مطمئن شوید با مورد استفاده شما سازگار است.</p>



<p class="wp-block-paragraph">همچنین برای مطابقت با رفتار پیش‌فرض Ingress-NGINX، ابزار  Ingress2Gateway یک شنونده در پورت ۸۰ و یک فیلتر تغییر مسیر درخواست HTTP برای هدایت ترافیک HTTP به HTTPS اضافه کرد. ممکن است اصلا نخواهید به ترافیک HTTP سرویس بدهید و شنونده پورت ۸۰ و HTTPRoute مربوطه را حذف کنید.</p>



<p class="wp-block-paragraph"><strong>هشدار: </strong>همیشه خروجی و لاگ‌های تولید شده را به طور کامل مرور کنید.</p>



<p class="wp-block-paragraph">پس از اعمال دستی این تغییرات، مانیفست‌های Gateway API ممکن است به شکل زیر باشد:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>---
apiVersion: gateway.networking.k8s.io/v1
kind: Gateway
metadata:
  annotations:
    gateway.networking.k8s.io/generator: ingress2gateway-dev
  name: nginx
  namespace: my-ns
spec:
  gatewayClassName: nginx
  listeners:
  - hostname: my-host.example.com
    name: my-host-example-com-https
    port: 443
    protocol: HTTPS
    tls:
      certificateRefs:
      - group: ""
        kind: Secret
        name: my-secret
---
apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
  annotations:
    gateway.networking.k8s.io/generator: ingress2gateway-dev
  name: my-ingress-my-host-example-com
  namespace: my-ns
spec:
  hostnames:
  - my-host.example.com
  parentRefs:
  - name: nginx
    port: 443
  rules:
  - backendRefs:
    - name: website-service
      port: 80
    filters:
    - cors:
        allowCredentials: true
        allowHeaders:
        - DNT
        ...
        allowMethods:
        - GET
        ...
        allowOrigins:
        - '*'
        maxAge: 1728000
      type: CORS
    matches:
    - path:
        type: RegularExpression
        value: /users/(\d+)
    name: rule-0
    timeouts:
      request: 3s</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">---</span></span>
<span class="line"><span style="color: #F69D50">apiVersion:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">gateway.networking.k8s.io/v1</span></span>
<span class="line"><span style="color: #F69D50">kind:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">Gateway</span></span>
<span class="line"><span style="color: #F69D50">metadata:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">annotations:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">gateway.networking.k8s.io/generator:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">ingress2gateway-dev</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">nginx</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">namespace:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-ns</span></span>
<span class="line"><span style="color: #F69D50">spec:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">gatewayClassName:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">nginx</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">listeners:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">hostname:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-host.example.com</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-host-example-com-https</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">port:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">443</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">protocol:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">HTTPS</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">tls:</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #F69D50">certificateRefs:</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">group:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">&quot;&quot;</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">kind:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">Secret</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-secret</span></span>
<span class="line"><span style="color: #F69D50">---</span></span>
<span class="line"><span style="color: #F69D50">apiVersion:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">gateway.networking.k8s.io/v1</span></span>
<span class="line"><span style="color: #F69D50">kind:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">HTTPRoute</span></span>
<span class="line"><span style="color: #F69D50">metadata:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">annotations:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">gateway.networking.k8s.io/generator:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">ingress2gateway-dev</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-ingress-my-host-example-com</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">namespace:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-ns</span></span>
<span class="line"><span style="color: #F69D50">spec:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">hostnames:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">my-host.example.com</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">parentRefs:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">nginx</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">port:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">443</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">rules:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">backendRefs:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">website-service</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #F69D50">port:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">80</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">filters:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">cors:</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">allowCredentials:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">true</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">allowHeaders:</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">DNT</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #6CB6FF">...</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">allowMethods:</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">GET</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #6CB6FF">...</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">allowOrigins:</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">&#39;*&#39;</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">maxAge:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">1728000</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #6CB6FF">type</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">CORS</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">matches:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">-</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">path:</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #6CB6FF">type</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">RegularExpression</span></span>
<span class="line"><span style="color: #ADBAC7">        </span><span style="color: #F69D50">value:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">/users/</span><span style="color: #ADBAC7">(</span><span style="color: #F69D50">\d+</span><span style="color: #ADBAC7">)</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">name:</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">rule-0</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #F69D50">timeouts:</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #F69D50">request:</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">3</span><span style="color: #96D0FF">s</span></span></code></pre></div>



<h3 class="wp-block-heading" id="h-مرحله-چهارم-بازبینی-verify">مرحله چهارم: بازبینی (Verify)</h3>



<p class="wp-block-paragraph">اکنون که مانیفست‌های Gateway API را دارید، باید آنها را به طور کامل در یک کلاستر توسعه آزمایش کنید. در این مورد، حداقل باید بررسی کنید که پیش‌فرض‌های حداکثر اندازه بدنه پیاده‌سازی Gateway API برای شما مناسب است و تأیید کنید که زمان انتظار ۳ ثانیه کافی است.</p>



<p class="wp-block-paragraph">پس از تایید رفتار در یک کلاستر توسعه، پیکربندی Gateway API خود را در کنار Ingress موجود خود مستقر کنید. پیشنهاد می‌کنیم که ترافیک را با استفاده از DNS وزن‌دار، لود بالانسر ابری خود یا ویژگی‌های تقسیم ترافیک پلتفرم خود به تدریج تغییر دهید. به این ترتیب، می‌توانید به سرعت، هرگونه پیکربندی اشتباهی را که از تست‌های شما عبور کرده است، بازیابی کنید.</p>



<p class="wp-block-paragraph">در نهایت، پس از انتقال کامل ترافیک به کنترلر Gateway API، ابتدا منابع Ingress را حذف و سپس کنترلر Ingress قدیمی را uninstall کنید.</p>



<h2 class="wp-block-heading" id="h-جمع-بندی">جمع‌بندی</h2>



<p class="wp-block-paragraph">مهم‌ترین نکته این است که مهاجرت از ingress-nginx را نباید به زمانی موکول کرد که یک آسیب‌پذیری یا ناسازگاری عملیاتی شما را مجبور به تغییر کند. هرچه وابستگی به ingress-nginx بیشتر شود، هزینه و پیچیدگی مهاجرت نیز افزایش خواهد یافت.</p>



<p class="wp-block-paragraph">گزینه‌های جایگزین شامل Traefik ،Envoy Gateway ،Kong Gateway و NGINX Gateway Fabric هستند و مسیر آینده اکوسیستم، Gateway API است. با برنامه‌ریزی درست، بررسی زیرساخت، اصلاح مانیفست‌ها و تست در محیط توسعه، می‌توانید مهاجرت تدریجی و امن را انجام دهید و بدون اختلال سرویس‌ها، به معماری مدرن کوبرنتیز برسید.</p>



<p class="wp-block-paragraph"></p>
<p>The post <a href="https://hamravesh.com/blog/ingress-nginx-retirement/">بازنشستگی Ingress NGINX؛ ریسک‌ها، جایگزین‌ها و مسیر مهاجرت</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/ingress-nginx-retirement/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>حمله HTTP/2 Bomb چیست؟ کالبدشکافی حمله، تأثیر بر nginx و راهکارهای مقابله</title>
		<link>https://hamravesh.com/blog/discover-http-2-bomb-dos-attack/</link>
					<comments>https://hamravesh.com/blog/discover-http-2-bomb-dos-attack/#respond</comments>
		
		<dc:creator><![CDATA[هم‌روش]]></dc:creator>
		<pubDate>Mon, 08 Jun 2026 15:09:45 +0000</pubDate>
				<category><![CDATA[شبکه]]></category>
		<category><![CDATA[دواپس]]></category>
		<category><![CDATA[مقالات]]></category>
		<guid isPermaLink="false">https://hamravesh.com/blog/?p=5266</guid>

					<description><![CDATA[<p>جلوگیری از حمله HTTP/2 Bomb به یکی از موضوعات مهم امنیت زیرساخت‌های وب تبدیل شده است. HTTP/2 Bomb یک تکنیک حمله Denial-of-Service (DoS) است که تیم تحقیقاتی شرکت Calif در ژوئن ۲۰۲۶ با کمک مدل هوش مصنوعی OpenAI Codex آن را معرفی کرد. </p>
<p>The post <a href="https://hamravesh.com/blog/discover-http-2-bomb-dos-attack/">حمله HTTP/2 Bomb چیست؟ کالبدشکافی حمله، تأثیر بر nginx و راهکارهای مقابله</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">HTTP/2 Bomb یکی از جدیدترین تکنیک‌های حمله مبتنی بر HTTP/2 است که در ژوئن ۲۰۲۶ معرفی شد. این حمله می‌تواند با ترکیب دو مکانیزم استاندارد در پروتکل HTTP/2 مصرف حافظه سرور را افزایش دهد و باعث اختلال در سرویس شود. نکته مهم این است که HTTP/2 Bomb یک آسیب‌پذیری ناشناخته نیست و از ترکیب قابلیت‌هایی استفاده می‌کند که سال‌ها در HTTP/2 وجود داشته‌اند. در این مقاله بررسی می‌کنیم حمله HTTP/2 Bomb چیست و چه تفاوتی با ا دارد، چگونه باعث حمله مصرف حافظه سرور می‌شود و برای جلوگیری از این حمله و مقابله با حملات HTTP/2 چه راهکارهایی ارائه شده است.</p>



<div class="wp-block-group is-vertical is-content-justification-left is-layout-flex wp-container-core-group-is-layout-ddd31865 wp-block-group-is-layout-flex">
<h2 class="wp-block-heading" id="h-آنچه-در-این-مطلب-می-خوانید">آنچه در این مطلب می‌خوانید</h2>



<h3 class="wp-block-heading" id="h-خلاصه">خلاصه</h3>



<p class="wp-block-paragraph">HTTP/2 Bomb یک حمله DoS است که با ترکیب HPACK و Flow Control در HTTP/2 باعث مصرف غیرعادی حافظه و کندی شدید یا اختلال سرویس می‌شود. این مشکل بیشتر به نحوه پیاده‌سازی سرویس‌های سرورها مربوط است تا یک باگ مستقل.</p>



<h3 class="wp-block-heading" id="h-نکات-کلیدی">نکات کلیدی</h3>



<ul class="wp-block-list">
<li>روش سوءاستفاده، ترکیب HPACK و Flow Control در HTTP/2 است</li>



<li> هدف حمله، ایجاد فشار بر حافظه و کندی پایدار است و نه صرفاً ایجاد OOM</li>



<li> شدت اثر، وابسته به پیاده‌سازی در nginx، Apache، Envoy و IIS است</li>



<li> کنترل‌های ساده هدر، برای مقابله با این حمله کافی نیستند</li>



<li>راهکارهای جلوگیری، شامل به‌روزرسانی سرویس‌ها، محدودسازی هدر و stream، استفاده از CDN یا reverse proxy و اعمال memory limit است</li>



<li> نتیجه اصلی این است که ترکیب قابلیت‌های استاندارد می‌تواند سناریوی حمله جدید ایجاد کند</li>
</ul>
</div>



<h2 class="wp-block-heading" id="h-چگونه-ویژگی-های-http-2-به-سطح-حمله-تبدیل-شد">چگونه ویژگی‌های HTTP/2 به سطح حمله تبدیل شد؟</h2>



<p class="wp-block-paragraph">پروتکل HTTP/2 با هدف بهبود عملکرد وب و کاهش سربار ارتباطات معرفی شد. قابلیت‌هایی مانند فشرده‌سازی هدرها (HPACK) و کنترل جریان (Flow-Control Window) باعث افزایش سرعت و کاهش مصرف پهنای باند شده‌اند، اما این دو ویژگی در حمله HTTP/2 Bomb توسط مهاجم به ابزار افزایش مصرف حافظه سرور تبدیل می‌شوند.&nbsp;موفقیت HTTP/2 Bomb به این دلیل است که یکی از این قابلیت‌ها حافظه را تخصیص می‌دهد و دیگری مانع آزاد شدن آن می‌شود. نتیجه، انباشت تدریجی حافظه و کاهش پاسخ‌دهی سرور است.</p>



<p class="wp-block-paragraph"><strong>HPACK:</strong> یک الگوریتم فشرده‌سازی وضعیت‌دار است که رشته‌های هدر را در یک جدول داینامیک ذخیره می‌کند. در درخواست‌های بعدی، به جای ارسال کامل هدر، تنها یک index ارسال می‌شود. این مکانیزم باعث کاهش سربار هدرها می‌شود، اما در ترکیب با کنترل جریان، مهاجم می‌تواند حافظه زیادی روی سرور رزرو کند.</p>



<p class="wp-block-paragraph"><strong>کنترل جریان (Flow-Control Window):</strong> به گیرنده امکان می‌دهد میزان داده قابل دریافت را محدود کند. مهاجم می‌تواند با ارسال داده کم و نگه داشتن اتصال باز، حافظه رزرو شده را آزاد نکند و در نتیجه باعث افزایش مصرف حافظه، کاهش کارایی و افت پاسخ‌دهی سرور شود.</p>



<p class="wp-block-paragraph">این دو مکانیزم دقیقا موتور اصلی HTTP/2 Bomb هستند. در بخش بعد، سازوکار دقیق حمله و ترکیب دو تکنیک را مرحله به مرحله بررسی می‌کنیم.</p>



<h2 class="wp-block-heading" id="h-کالبدشکافی-حمله-http-2-bomb-چگونه-کار-می-کند">کالبدشکافی حمله؛ HTTP/2 Bomb چگونه کار می‌کند؟</h2>



<p class="wp-block-paragraph">هسته حمله از ترکیب دو قابلیت داخلی HTTP/2 ساخته شده است که هر یک به تنهایی برای بهبود عملکرد وب استفاده می‌شدند، اما کنار هم مسیر جدیدی برای حمله DoS ایجاد کرده‌اند.</p>



<h3 class="wp-block-heading" id="h-hpack-bomb-وقتی-یک-بایت-به-هزاران-بایت-تبدیل-می-شود">HPACK Bomb: وقتی یک بایت به هزاران بایت تبدیل می‌شود</h3>



<p class="wp-block-paragraph">HPACK هدرها را در جدول داینامیک ذخیره می‌کند. مهاجم ابتدا یک هدر را ثبت و سپس هزاران بار تنها با یک index به آن ارجاع می‌دهد. حجم داده ارسالی کم است، اما سرور برای هر ارجاع باید اطلاعات مربوط به هدر را در حافظه ایجاد کند. برخلاف نسخه‌های قدیمی HPACK Bomb، حتی هدرهای کوچک یا خالی باعث مصرف حافظه قابل توجه می‌شوند. همچنین محدودیت‌های قدیمی روی حجم هدرهای Decode شده در برابر این روش بی‌اثر هستند.</p>



<h3 class="wp-block-heading" id="h-flow-control-چگونه-حافظه-آزاد-نمی-شود">Flow Control: چگونه حافظه آزاد نمی‌شود؟</h3>



<p class="wp-block-paragraph">کنترل جریان HTTP/2 به سرور امکان می‌دهد میزان داده قابل دریافت را محدود کند. مهاجم پس از ایجاد تخصیص حافظه، اندازه پنجره را روی صفر قرار داده و با ارسال WINDOW_UPDATE کوچک، اتصال را باز نگه می‌دارد. حافظه اشغال‌شده برای مدت طولانی باقی می‌ماند و سرور تحت فشار قرار می‌گیرد.</p>



<p class="wp-block-paragraph">در یک حمله واقعی، هدف مهاجم لزوماً رساندن فرایند به وضعیت OOM (مخفف Out-of-Memory) نیست؛ وضعیتی که در آن سیستم به دلیل کمبود حافظه، برخی پردازش‌ها را به‌طور اجباری متوقف می‌کند. اگر در حالت OOM، پردازش توسط OOM Killer متوقف شود، معمولاً Worker به‌سرعت مجدداً راه‌اندازی می‌شود و بخشی از اثر حمله از بین می‌رود. راهبرد مؤثرتر این است که مصرف حافظه درست در آستانه فعال شدن OOM نگه داشته شود؛ به‌طوری که سیستم ناچار به استفاده گسترده از حافظه Swap شود. در این وضعیت، اگرچه سرویس کاملاً از دسترس خارج نمی‌شود، اما زمان پاسخ‌دهی به‌شدت افزایش می‌یابد و عملکرد سایر درخواست‌ها نیز به‌طور محسوسی کاهش پیدا می‌کند.</p>



<h2 class="wp-block-heading" id="h-اثر-واقعی-http-2-bomb-روی-سرورها">اثر واقعی HTTP/2 Bomb روی سرورها</h2>



<p class="wp-block-paragraph">HTTP/2 Bomb فقط یک ایده تئوریک نیست. محققان <a href="https://blog.calif.io/p/codex-discovered-a-hidden-http2-bomb" type="link" id="https://blog.calif.io/p/codex-discovered-a-hidden-http2-bomb">Calif</a> این حمله را روی چند مورد از پرکاربردترین سرورهای وب آزمایش کرده‌اند و نتایج نشان می‌دهد که پیاده‌سازی HTTP/2 در هر محصول، تاثیر مستقیمی بر شدت حمله دارد.</p>



<figure class="wp-block-image size-full"><img loading="lazy" decoding="async" width="1920" height="1080" src="https://hamravesh.com/blog/wp-content/uploads/2026/06/hamravesh-discover-http-2-bomb-dos-attack01.gif" alt="" class="wp-image-5284"/><figcaption class="wp-element-caption">روند افزایش مصرف حافظه در آپاچی httpd، سپس Envoy، انجین‌اکس و مایکروسافت IIS در آزمایش محققان Calif (به ترتیب از بالا سمت چپ و در جهت عقربه‌های ساعت مشاهده کنید).  تصویر با سرعت ۲X نمایش داده شده است.</figcaption></figure>



<p class="wp-block-paragraph">نتایج این آزمایش‌ها در جدول زیر خلاصه شده است:</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><tbody><tr><td><strong>سرور</strong></td><td><strong>ضریب بزرگنمایی</strong></td><td><strong>زمان تقریبی مصرف کامل حافظه</strong></td></tr><tr><td><strong>Envoy 1.37.2</strong></td><td>حدود ۵۷۰۰:۱</td><td>حدود ۱۰ ثانیه برای ۳۲GB</td></tr><tr><td><strong>Apache httpd 2.4.67</strong></td><td>حدود ۴۰۰۰:۱</td><td>حدود ۱۸ ثانیه برای ۳۲GB</td></tr><tr><td><strong>nginx 1.29.7</strong></td><td>حدود ۷۰:۱</td><td>حدود ۴۵ ثانیه برای ۳۲GB</td></tr><tr><td><strong>Microsoft IIS (Windows Server 2025)</strong></td><td>حدود ۶۸:۱</td><td>حدود ۴۵ ثانیه (تا ۶۴GB)</td></tr></tbody></table></figure>



<p class="wp-block-paragraph">منظور از ضریب بزرگنمایی (Amplification Ratio) این است که هر یک بایت داده‌ای که مهاجم ارسال می‌کند، چه مقدار حافظه روی سرور اشغال می‌شود. هرچه این عدد بزرگ‌تر باشد، مهاجم با پهنای باند کمتر می‌تواند فشار بیشتری به سرور وارد کند.</p>



<p class="wp-block-paragraph">نتایج آزمایش‌ها نشان می‌دهد که Envoy و Apache httpd بیشترین تاثیر را از این حمله می‌پذیرند. در سمت مقابل، nginx و Microsoft IIS ضریب بزرگنمایی کمتری دارند، اما همچنان در برابر حمله HTTP/2 Bomb آسیب‌پذیر هستند. به‌طورکلی، جلوگیری از حمله HTTP/2 Bomb نیازمند شناخت دقیق همین تفاوت‌ها در پیاده‌سازی سرورهاست.</p>



<p class="wp-block-paragraph">محققان تفاوت نتایج را به جزئیات پیاده‌سازی HPACK و نحوه مدیریت حافظه در محصولات مختلف نسبت می‌دهند. در Apache httpd و Envoy، بازسازی هدرها و ساختارهای داخلی مرتبط با آن‌ها حافظه بیشتری مصرف می‌کند، در حالی که nginx و IIS سربار کمتری دارند. به همین دلیل ضریب بزرگنمایی حمله در آنها متفاوت است.</p>



<h2 class="wp-block-heading" id="h-تکنیک-های-دور-زدن-محدودیت-ها-bypass-techniques">تکنیک‌های دور زدن محدودیت‌ها (Bypass Techniques)</h2>



<p class="wp-block-paragraph">یکی از دلایل خطرناک‌تر بودن HTTP/2 Bomb نسبت به HPACK Bomb کلاسیک، توانایی آن در دور زدن مکانیزم‌های دفاعی موجود است. در ادامه، دو تکنیک اصلی این حمله برای عبور از محدودیت‌های حجم و تعداد هدرها را بررسی می‌کنیم.</p>



<h3 class="wp-block-heading" id="h-عبور-از-محدودیت-حجم-هدرها">عبور از محدودیت حجم هدرها</h3>



<p class="wp-block-paragraph">پس از معرفی HPACK Bomb در سال ۲۰۱۶، بسیاری از پیاده‌سازی‌های HTTP/2 محدودیتی برای Total Decoded Header Size در نظر گرفتند تا از بازسازی هدرهای بسیار بزرگ جلوگیری کنند.</p>



<p class="wp-block-paragraph">در HTTP/2 Bomb، هدرها می‌توانند بسیار کوچک یا تقریبا خالی باشند و بخش عمده مصرف حافظه از metadata و ساختارهای داخلی HPACK ناشی می‌شود. در نتیجه محدودیت حجم هدرهای Decode شده عملا اثرگذار نیست و دفاع طراحی‌شده برای نسخه‌های قدیمی‌تر، کارایی خود را از دست می‌دهد.</p>



<h3 class="wp-block-heading" id="h-دور-زدن-محدودیت-تعداد-هدرها-با-cookie-crumbs">دور زدن محدودیت تعداد هدرها با Cookie Crumbs</h3>



<p class="wp-block-paragraph">برخی پیاده‌سازی‌ها مانند Apache httpd و Envoy علاوه بر محدودیت حجم، تعداد Header Fieldها را هم کنترل می‌کنند تا مهاجم نتواند با ارسال تعداد زیادی هدر کوچک، منابع سرور را مصرف کند.</p>



<p class="wp-block-paragraph">HTTP/2 امکان تقسیم یک Cookie بزرگ به چند Cookie Header کوچک‌تر (Cookie Crumbs) را فراهم می‌کند (RFC 9113). این قابلیت برای بهبود فشرده‌سازی طراحی شده است، اما در آزمایش‌ها مشخص شد که در برخی شرایط، این Crumbها در Apache و Envoy در شمارش محدودیت تعداد هدرها لحاظ نمی‌شوند.</p>



<p class="wp-block-paragraph">در نتیجه، مهاجم می‌تواند بدون فعال شدن محدودیت تعداد هدر، تعداد زیادی Cookie Crumb ایجاد کند و هر Crumb هم ورودی جدیدی در HPACK ایجاد می‌کند و سربار حافظه را افزایش می‌دهد.</p>



<h2 class="wp-block-heading" id="h-وضعیت-وصله-ها-در-سرورهای-مختلف">وضعیت وصله‌ها در سرورهای مختلف</h2>



<p class="wp-block-paragraph">پس از افشای حمله HTTP/2 Bomb، مهم‌ترین سوال برای مدیران سیستم و مهندسان امنیت این است که سرورهای ما ایمن هستند؟ چه اقداماتی برای جلوگیری از حمله HTTP/2 Bomb باید انجام داد؟</p>



<p class="wp-block-paragraph">محققان Calif قبل از انتشار عمومی، آسیب‌پذیری را به تیم‌های توسعه گزارش کردند. با این حال، وضعیت وصله‌ها (پچ‌ها) در زمان انتشار برای سرورهای مختلف متفاوت بود. جدول زیر خلاصه‌ای از وضعیت هر سرور را نشان می‌دهد:</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><tbody><tr><td><strong>سرور</strong></td><td><strong>وضعیت</strong></td><td><strong>نسخه / توضیح</strong></td></tr><tr><td><strong>nginx</strong></td><td>وصله شده</td><td>1.29.8+ – اضافه شدن max_headers با پیش‌فرض ۱۰۰۰</td></tr><tr><td><strong>Apache httpd</strong></td><td>وصله شده</td><td>رفع شده در &nbsp;<a href="https://github.com/icing/mod_h2/releases">mod_http2 v2.0.41</a> &#8211; اگر قصد آپگرید ندارید، پیشنهاد می‌شود پروتکل http/1.1 را طوری تنظیم کنید که HTTP/2 غیر فعال شود.</td></tr><tr><td><strong>Microsoft IIS</strong></td><td>وصله نشده</td><td>در زمان نگارش این مقاله، مایکروسافت هنوز جزئیات فنی یا وصله رسمی برای IIS منتشر نکرده است.</td></tr><tr><td><strong>Envoy</strong></td><td>در حال بررسی</td><td>وصله منتشر شده، اما محققان همچنان در حال راستی‌آزمایی دقیق‌تر هستند. تا تأیید نهایی، بهتر است HTTP/2 را موقتاً غیرفعال کنید.</td></tr><tr><td><strong>Cloudflare Pingora</strong></td><td>محافظت معماری</td><td>به طور خودکار در برابر حمله محافظت ایجاد می‌کند</td></tr></tbody></table></figure>



<h2 class="wp-block-heading" id="h-راهکارهای-کاهش-آسیب-mitigation-strategies">راهکارهای کاهش آسیب (Mitigation Strategies)</h2>



<p class="wp-block-paragraph">چند اقدام موثر برای جلوگیری از حمله HTTP/2 Bomb وجود دارند که می‌توانید آن‌ها را اجرا کنید. این اقدامات را می‌توان در چند سطح اصلی اجرا کرد:</p>



<h3 class="wp-block-heading" id="h-ارتقا-به-نسخه-وصله-شده">ارتقا به نسخه وصله‌شده</h3>



<p class="wp-block-paragraph">نصب سریع وصله‌های رسمی اولین و مهم‌ترین گام است. برای سرورهایی که وصله منتشر شده، نسخه‌ها باید به‌روزرسانی شوند:</p>



<ul class="wp-block-list">
<li>انجین‌اکس: نسخه 1.29.8+</li>



<li>آپاچی httpd: نسخه <a href="https://github.com/icing/mod_h2/releases" type="link" id="https://github.com/icing/mod_h2/releases" target="_blank" rel="noreferrer noopener">mod_http2 v2.0.41</a></li>
</ul>



<h3 class="wp-block-heading" id="h-غیرفعال-کردن-موقت-http-2">غیرفعال کردن موقت HTTP/2</h3>



<p class="wp-block-paragraph">در سرورهایی که وصله در دسترس نیست یا قصد آصب وصله را ندارید، غیرفعال کردن پروتکل HTTP/2 و بازگشت به HTTP/1.1، می‌تواند به عنوان راهکار موقت عمل کند:</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><tbody><tr><td><strong>سرور</strong></td><td><strong>دستور غیرفعال‌سازی</strong></td></tr><tr><td><strong>nginx</strong></td><td>اگر قصد آپگرید ندارید، HTTP/2 را با <code>http2 off;</code> غیر فعال کنید.</td></tr><tr><td><strong>Apache httpd</strong></td><td>اگر قصد آپگرید ندارید، پیشنهاد می‌شود پروتکل http/1.1 را طوری تنظیم کنید که HTTP/2 غیر فعال شود.</td></tr><tr><td><strong>سایر سرورها</strong></td><td>مستندات فروشنده را بررسی کنید</td></tr></tbody></table></figure>



<h3 class="wp-block-heading" id="h-استفاده-از-reverse-proxy-یا-cdn">استفاده از Reverse Proxy یا CDN</h3>



<p class="wp-block-paragraph">قرار دادن سرور پشت یک Reverse Proxy یا CDN که وصله شده یا به‌طور ذاتی محافظت دارد، می‌تواند حمله را قبل از رسیدن به سرور اصلی متوقف کند. برای مثال:</p>



<ul class="wp-block-list">
<li>استفاده از Cloudflare که به صورت خودکار محافظت ارائه می‌کند</li>



<li>استفاده از nginx وصله‌شده به عنوان پروکسی جلوی سرورهای آسیب‌پذیر، محافظت ایجاد می‌کند.</li>
</ul>



<h3 class="wp-block-heading" id="h-اعمال-محدودیت-روی-هدرها-و-streamها">اعمال محدودیت روی هدرها و Streamها</h3>



<p class="wp-block-paragraph">به‌طور کلی، «حداکثر اندازه هدرهای Decode شده» و «حداکثر تعداد هدرها» دو محدودیت متفاوت هستند و هر سرور باید هر دو را اعمال کند. هر سرویس یا مؤلفه‌ای که ترافیک HTTP/2 را دریافت و پردازش می‌کند (مانند وب‌سرورها، Reverse Proxyها، لود بالانسرها و API Gatewayها)، باید تعداد فیلدهای هدر در هر درخواست را (از جمله Cookie Crumbها) مستقل از اندازه کلی آن‌ها محدود کند. همچنین، مدت‌زمان مجاز برای باز ماندن یک stream متوقف‌شده را بدون توجه به فعالیت WINDOW_UPDATE مشخص و محدود سازد.</p>



<h3 class="wp-block-heading" id="h-محدودیت-حافظه-memory-limits">محدودیت حافظه (Memory Limits)</h3>



<p class="wp-block-paragraph">اگر در حال حاضر امکان اعمال این کنترل‌ها را ندارید، بهتر است برای هر ورکر محدودیت حافظه تعریف کنید؛ برای مثال با استفاده از cgroups، دستور <code>ulimit -v</code> یا محدودیت‌های حافظه در کانتینرها. این محدودیت‌ها باید به اندازه‌ای سخت‌گیرانه باشند که در صورت وقوع حمله، ورکر آسیب‌دیده پیش از آنکه کل سیستم را وارد Swap کند، توسط OOM Killer متوقف و مجدداً راه‌اندازی شود. یک ورکر معمولاً به چندین گیگابایت حافظه نیاز ندارد؛ بنابراین متوقف شدن زودهنگام یک ورکر، سناریوی بسیار بهتری نسبت به این است که مهاجم بتواند کل سرور را برای مدت طولانی در آستانه ۹۵ درصد مصرف حافظه نگه دارد.</p>



<h3 class="wp-block-heading" id="h-محدودیت-نرخ-rate-limiting">محدودیت نرخ (Rate Limiting)</h3>



<p class="wp-block-paragraph">کنترل نرخ ایجاد اتصال‌ها یا استریم‌ها به ازای هر IP می‌تواند سرعت اجرای حمله را کاهش دهد و فرصت واکنش برای تیم امنیتی فراهم کند. این اقدام به تنهایی کافی نیست اما موثر است.</p>



<h2 class="wp-block-heading" id="h-نقش-هوش-مصنوعی-در-کشف-حمله-codex-effect">نقش هوش مصنوعی در کشف حمله (Codex Effect)</h2>



<p class="wp-block-paragraph">HTTP/2 Bomb توسط تیم امنیتی Calif با کمک OpenAI Codex شناسایی شد. در این پژوهش، Codex دو تکنیک شناخته‌شده یعنی HPACK Bomb و سوءاستفاده از HTTP/2 Flow Control را کنار هم قرار داد و اثر ترکیبی آن‌ها را آشکار کرد.</p>



<p class="wp-block-paragraph">این یافته نشان می‌دهد مدل‌های هوش مصنوعی می‌توانند در تحلیل RFCها، مستندات فنی و رفتار پروتکل‌ها به کشف سناریوهای حمله جدید کمک کنند. با این حال، هوش مصنوعی در این پژوهش نقش یک ابزار کمکی برای تحلیل و کشف الگوها را داشت و جایگزین پژوهشگران امنیتی نشد.</p>



<h2 class="wp-block-heading" id="h-جمع-بندی">جمع‌بندی</h2>



<p class="wp-block-paragraph">HTTP/2 Bomb یک آسیب‌پذیری جدید در پروتکل HTTP/2 نیست، بلکه روشی برای ترکیب دو قابلیت استاندارد این پروتکل یعنی HPACK و Flow Control است. همین موضوع باعث شد مکانیزم‌هایی که سال‌ها برای مقابله با HPACK Bomb یا محدود کردن اندازه هدرها طراحی شده بودند، در برخی پیاده‌سازی‌ها نتوانند از این حمله جلوگیری کنند.</p>



<p class="wp-block-paragraph">نتایج آزمایش‌ها نشان می‌دهد شدت تأثیر HTTP/2 Bomb به نحوه پیاده‌سازی HTTP/2 در هر محصول وابسته است. هرچند nginx ،Apache httpd ،Envoy و Microsoft IIS همگی تحت تأثیر این تکنیک قرار گرفته‌اند، اما میزان مصرف حافظه و ضریب بزرگنمایی حمله در آن‌ها یکسان نیست.</p>



<p class="wp-block-paragraph">برای کاهش ریسک و جلوگیری از حمله HTTP/2 Bomb، اولین اقدام باید ارتقا به نسخه‌های وصله‌شده باشد. در محیط‌هایی که امکان به‌روزرسانی فوری وجود ندارد، محدود کردن تعداد هدرها، کنترل طول عمر Streamها، اعمال محدودیت حافظه برای Workerها و استفاده از Reverse Proxyها یا CDNهای محافظت‌شده می‌تواند اثر حمله را کاهش دهد.</p>



<p class="wp-block-paragraph">شاید مهم‌ترین درس HTTP/2 Bomb این باشد که در امنیت نرم‌افزارها، همیشه مشکل از یک قابلیت منفرد نیست. گاهی ترکیب چند رفتار کاملاً استاندارد و قانونی می‌تواند به یک روش حمله جدید تبدیل شود که سال‌ها از دید پژوهشگران پنهان مانده است.</p>



<p class="wp-block-paragraph"></p>
<p>The post <a href="https://hamravesh.com/blog/discover-http-2-bomb-dos-attack/">حمله HTTP/2 Bomb چیست؟ کالبدشکافی حمله، تأثیر بر nginx و راهکارهای مقابله</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/discover-http-2-bomb-dos-attack/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Wiki.js چیست؟ مقایسه با رقبا و راهنمای نصب</title>
		<link>https://hamravesh.com/blog/what-is-wikijs/</link>
					<comments>https://hamravesh.com/blog/what-is-wikijs/#respond</comments>
		
		<dc:creator><![CDATA[هم‌روش]]></dc:creator>
		<pubDate>Wed, 03 Jun 2026 12:30:53 +0000</pubDate>
				<category><![CDATA[دواپس]]></category>
		<category><![CDATA[مقالات]]></category>
		<guid isPermaLink="false">https://hamravesh.com/blog/?p=5220</guid>

					<description><![CDATA[<p>Wiki.js یکی از محبوب‌ترین راهکارهای متن‌باز برای ایجاد پایگاه دانش و مستندسازی سازمانی است که به تیم‌ها کمک می‌کند مستندات، فرایندها و دانش فنی خود را به‌جای فایل‌ها و ابزارهای پراکنده، در یک مخزن متمرکز نگهداری و مدیریت کنند. در این مقاله بررسی می‌کنیم که Wiki.js چیست، چه مزایا و معایبی دارد، چه تفاوتی با [&#8230;]</p>
<p>The post <a href="https://hamravesh.com/blog/what-is-wikijs/">Wiki.js چیست؟ مقایسه با رقبا و راهنمای نصب</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">Wiki.js یکی از محبوب‌ترین راهکارهای متن‌باز برای ایجاد پایگاه دانش و مستندسازی سازمانی است که به تیم‌ها کمک می‌کند مستندات، فرایندها و دانش فنی خود را به‌جای فایل‌ها و ابزارهای پراکنده، در یک مخزن متمرکز نگهداری و مدیریت کنند. در این مقاله بررسی می‌کنیم که Wiki.js چیست، چه مزایا و معایبی دارد، چه تفاوتی با ابزارهای مشابه دارد و مراحل نصب Wiki.js با Docker چگونه انجام می‌شود.</p>



<h2 class="wp-block-heading" id="h-ابزار-wiki-js-چیست-و-چه-ویژگی-هایی-دارد">ابزار Wiki.js چیست و چه ویژگی‌هایی دارد؟</h2>



<p class="wp-block-paragraph">Wiki.js یک نرم‌افزار ویکی سازمانی متن‌باز و Self-Hosted است که برای مدیریت دانش، مستندسازی سازمانی و ایجاد ویکی داخلی سازمان استفاده می‌شود. این پلتفرم بر پایه Node.js توسعه یافته و از <a href="https://hamravesh.com/blog/what-is-postgresql/" type="link" id="https://hamravesh.com/blog/what-is-postgresql/" target="_blank" rel="noreferrer noopener">دیتابیس PostgreSQL</a> برای ذخیره‌سازی داده‌ها استفاده می‌کند.</p>



<p class="wp-block-paragraph">سازمان‌ها می‌توانند Wiki.js را روی سرور اختصاصی، ماشین مجازی یا کانتینرهای Docker اجرا کنند و مدیریت مستندات، دسترسی کاربران و زیرساخت نرم‌افزار را در محیط خود انجام دهند. همچنین این پلتفرم از روش‌های مختلف احراز هویت، ویرایش محتوا و یکپارچه‌سازی با ابزارهای توسعه، پشتیبانی می‌کند. برخی از قابلیت‌های اصلی Wiki.js عبارت‌اند از:</p>



<ul class="wp-block-list">
<li>ویرایشگرهای چندگانه: پشتیبانی از Markdown، ویرایشگر بصری (WYSIWYG) و HTML برای گروه‌های مختلف کاربران</li>



<li>همگام‌سازی با Git: امکان اتصال به مخازن Git برای نسخه‌بندی و نگهداری مستندات</li>



<li>احراز هویت سازمانی: پشتیبانی از LDAP ،SAML و OAuth2 برای مدیریت دسترسی کاربران</li>



<li>معماری ماژولار: امکان فعال یا غیرفعال کردن ماژول‌های مختلف بر اساس نیاز سازمان</li>
</ul>



<h2 class="wp-block-heading" id="h-چرا-شرکت-ها-به-wiki-داخلی-نیاز-دارند">چرا شرکت‌ها به Wiki داخلی نیاز دارند؟</h2>



<p class="wp-block-paragraph">ویکی داخلی سازمان ابزاری برای ثبت و نگهداری دانش سازمانی، مستندات فنی و فرایندهای کاری است. استفاده از این ابزارها به تیم‌ها کمک می‌کند دانش و مستندات سازمانی به افراد وابسته نباشد و در یک پایگاه دانش متمرکز نگهداری شود. رایج‌ترین کاربردهای یک نرم‌افزار ویکی سازمانی عبارت‌اند از:</p>



<ul class="wp-block-list">
<li>ثبت Runbookها و دستورالعمل‌های عملیاتی برای عیب‌یابی و مدیریت رخدادها</li>



<li>مستندسازی معماری سیستم، سرویس‌ها، تنظیمات و فرایندهای فنی</li>



<li>تسهیل فرایند آنبوردینگ نیروهای جدید از طریق دسترسی به مستندات متمرکز</li>



<li>مدیریت سیاست‌ها، رویه‌ها و سطوح دسترسی در بخش‌های مختلف سازمان</li>
</ul>



<h2 class="wp-block-heading" id="h-مزایای-wiki-js-چیست">مزایای Wiki.js چیست؟</h2>



<p class="wp-block-paragraph">ابزار Wiki.js به‌عنوان یک نرم‌افزار ویکی سازمانی، امکانات موردنیاز تیم‌های فنی و کاربران غیرفنی را در یک پلتفرم واحد ارائه می‌کند. بررسی مزایای زیر به خوبی نشان می‌دهد که دلیل محبوبیت ویکی جی اس چیست:</p>



<ul class="wp-block-list">
<li>ویرایشگرهای چندگانه: Wiki.js از Markdown، ویرایشگر بصری (WYSIWYG) و HTML پشتیبانی می‌کند. این موضوع باعث می‌شود کاربران فنی و غیرفنی بتوانند با روش موردنظر خود مستندات را ایجاد و ویرایش کنند.</li>



<li>همگام‌سازی با Git: امکان اتصال به مخازن GitHub و GitLab برای نسخه‌بندی و نگهداری مستندات فراهم است. این قابلیت به تیم‌های فنی کمک می‌کند تاریخچه تغییرات مستندات را مدیریت کنند، از محتوا نسخه پشتیبان داشته باشند و در صورت نیاز، مستندات را بین زیرساخت‌ها یا محیط‌های مختلف جابه‌جا کنند.</li>



<li>احراز هویت سازمانی: Wiki.js از LDAP ،SAML ،OAuth2 و احراز هویت دو عاملی (2FA) پشتیبانی می‌کند و امکان یکپارچه‌سازی با زیرساخت‌های هویتی سازمان را فراهم می‌کند.</li>



<li>نصب و استقرار ساده: نصب Wiki.js با Docker و Docker Compose به‌سادگی انجام می‌شود و فرایند راه‌اندازی آن روی بسیاری از محیط‌های لینوکسی از جمله نصب Wiki.js روی Ubuntu هم پیچیدگی زیادی ندارد.</li>



<li>عملکرد سبک: این پلتفرم بر پایه Node.js توسعه یافته و برای اجرا به منابع سخت‌افزاری محدودی نیاز دارد.</li>



<li>پشتیبانی از دیاگرام و مستندات فنی: امکان استفاده از ابزارهایی مانند draw.io ،Mermaid و PlantUML برای ایجاد فلوچارت‌ها، نمودارها و مستندات معماری وجود دارد.</li>



<li>معماری ماژولار: مدیر سیستم می‌تواند برخی قابلیت‌ها و ماژول‌ها را بر اساس نیاز سازمان فعال یا غیرفعال کند.</li>



<li>پشتیبانی از زبان‌های مختلف و RTL: ویکی جی اس از زبان‌های مختلف پشتیبانی می‌کند و با زبان‌های راست‌به‌چپ نیز سازگار است. این قابلیت برای ایجاد یک ویکی داخلی سازمان به زبان فارسی کاربردی است.</li>



<li>مدیریت دسترسی: امکان تعریف سطوح دسترسی مبتنی بر گروه‌ها و مسیر صفحات (Path-based Permissions) برای کنترل دسترسی کاربران وجود دارد.</li>



<li>موتور جستجو: سیستم جستجوی داخلی مبتنی بر PostgreSQL امکان جستجوی متن کامل در مستندات را فراهم می‌کند و در برخی سناریوها قابلیت استفاده از Elasticsearch نیز وجود دارد.</li>



<li>شخصی‌سازی و چندسکویی: این ابزار از حالت روشن و تاریک پشتیبانی می‌کند و امکان استفاده از CSS و JavaScript سفارشی را در اختیار مدیران قرار می‌دهد. همچنین روی لینوکس، ویندوز و macOS قابل اجرا است.</li>
</ul>



<h2 class="wp-block-heading" id="h-معایب-ویکی-جی-اس-چیست">معایب ویکی جی اس چیست؟</h2>



<p class="wp-block-paragraph">برای انتخاب هوشمندانه یک نرم‌افزار، شناخت مزایا کافی نیست و باید بدانید چالش‌ها و معایب Wiki.js چیست. مهم‌ترین نقاط ضعف این ابزار عبارتند از:</p>



<ul class="wp-block-list">
<li>وضعیت نسخه v3: توسعه نسخه سوم Wiki.js طی چند سال گذشته ادامه داشته است، اما تا سال ۲۰۲۶ نسخه v2 همچنان نسخه اصلی و پایدار محسوب می‌شود. به همین دلیل بهتر است ارزیابی فنی بر اساس قابلیت‌های موجود انجام شود.</li>



<li>عدم پشتیبانی از ویرایش هم‌زمان: Wiki.js قابلیت ویرایش هم‌زمان یک صفحه توسط چند کاربر را مشابه ابزارهایی مانند Confluence یا Google Docs ارائه نمی‌کند.</li>



<li>وابستگی به PostgreSQL: هرچند پشتیبانی از چند پایگاه داده در برخی بخش‌ها مطرح شده است، اما PostgreSQL همچنان مهم‌ترین و رایج‌ترین گزینه برای استفاده از قابلیت‌های اصلی پلتفرم محسوب می‌شود.</li>



<li>برخی قابلیت‌های محدود یا در حال توسعه: بخش‌هایی مانند سیستم نظرات یا برخی قابلیت‌های ویرایشگر بصری ممکن است نسبت به برخی رقبا امکانات کمتری در اختیار کاربران قرار دهند.</li>



<li>نبود سیستم Template داخلی: برای ساخت صفحات تکرارشونده، قابلیت قالب‌سازی داخلی محدودی وجود دارد و در برخی سناریوها لازم است ساختار صفحات به‌صورت دستی ایجاد شود.</li>



<li>منحنی یادگیری API: رابط برنامه‌نویسی کاربردی (API) مبتنی بر GraphQL انعطاف‌پذیری بالایی ارائه می‌دهد، اما ممکن است برای تیم‌هایی که تجربه کار با GraphQL ندارند به زمان بیشتری برای یادگیری نیاز داشته باشد.</li>
</ul>



<h2 class="wp-block-heading" id="h-مقایسه-wiki-js-با-confluence-bookstack-و-mediawiki">مقایسه Wiki.js با Confluence ،BookStack و MediaWiki</h2>



<p class="wp-block-paragraph">انتخاب ابزار مناسب برای مستندسازی سازمانی بستگی به نیازهای فنی، ساختار تیم، بودجه و نحوه استقرار زیرساخت دارد. برای درک بهتر اینکه تفاوت Wiki.js با سایر راهکارهای مطرح چیست، می‌توان آن را در کنار Confluence ،BookStack و MediaWiki بررسی کرد.</p>



<figure class="wp-block-image size-large"><img loading="lazy" decoding="async" width="1024" height="668" src="https://hamravesh.com/blog/wp-content/uploads/2026/06/Hamravesh-what-is-wikijs02-1024x668.webp" alt="Wiki.js چیست؟ مقایسه با Confluence ،BookStack و MediaWiki" class="wp-image-5240" srcset="https://hamravesh.com/blog/wp-content/uploads/2026/06/Hamravesh-what-is-wikijs02-1024x668.webp 1024w, https://hamravesh.com/blog/wp-content/uploads/2026/06/Hamravesh-what-is-wikijs02-300x196.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2026/06/Hamravesh-what-is-wikijs02-768x501.webp 768w, https://hamravesh.com/blog/wp-content/uploads/2026/06/Hamravesh-what-is-wikijs02-120x78.webp 120w, https://hamravesh.com/blog/wp-content/uploads/2026/06/Hamravesh-what-is-wikijs02.webp 1201w" sizes="auto, (max-width: 1024px) 100vw, 1024px" /></figure>



<p class="wp-block-paragraph"><a href="https://hamravesh.com/blog/what-is-confluence/" type="link" id="https://hamravesh.com/blog/what-is-confluence/" target="_blank" rel="noreferrer noopener">کانفلوئنس</a> یک پلتفرم تجاری است که به‌صورت گسترده در سازمان‌ها برای همکاری تیمی، مدیریت دانش و مستندسازی استفاده می‌شود. در سمت مقابل، Wiki.js به‌عنوان یک نرم‌افزار ویکی سازمانی متن‌باز، امکان استقرار روی زیرساخت اختصاصی سازمان را فراهم می‌کند و هزینه لایسنس ندارد.</p>



<p class="wp-block-paragraph">BookStack هم یک راهکار متن‌باز برای مستندسازی سازمانی است که از ساختار سلسله‌مراتبی مشخص (قفسه، کتاب، فصل و صفحه) استفاده می‌کند. این ساختار برای تیم‌هایی که به دنبال سازمان‌دهی ساده‌تر محتوا هستند می‌تواند مناسب باشد.</p>



<p class="wp-block-paragraph">MediaWiki که هسته اصلی ویکی‌پدیا را تشکیل می‌دهد، برای مدیریت پایگاه‌های دانش بزرگ و محتوای مشارکتی توسعه یافته است. در مقابل، Wiki.js تمرکز بیشتری بر استقرار سازمانی، یکپارچه‌سازی با Git و پشتیبانی از روش‌های مختلف احراز هویت دارد. برای مقایسه دقیق‌تر، فاکتورهای کلیدی این چهار ابزار در جدول زیر آورده شده است.</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><tbody><tr><td><strong>فاکتور کلیدی</strong></td><td><strong>Wiki.js</strong></td><td><strong>Confluence</strong></td><td><strong>BookStack</strong></td><td><strong>MediaWiki</strong></td></tr><tr><td><strong>نوع لایسنس و هزینه</strong></td><td>رایگان و متن‌باز</td><td>تجاری (اشتراک ماهانه)</td><td>رایگان و متن‌باز</td><td>رایگان و متن‌باز</td></tr><tr><td><strong>نحوه میزبانی (Hosting)</strong></td><td>Self-Hosted (داکر/سرور اختصاصی)</td><td>فقط ابری / دیتا سنتر</td><td>Self-Hosted (سرور اختصاصی)</td><td>Self-Hosted (سرور اختصاصی)</td></tr><tr><td><strong>ویرایش هم‌زمان (Real-time)</strong></td><td>ندارد&nbsp;</td><td>دارد (بسیار قدرتمند)</td><td>ندارد&nbsp;</td><td>ندارد&nbsp;</td></tr><tr><td><strong>همگام‌سازی با Git</strong></td><td>دارد (بومی و دوطرفه)</td><td>ندارد</td><td>ندارد</td><td>ندارد (نیاز به افزونه)</td></tr><tr><td><strong>نوع ویرایشگر (Editor)</strong></td><td>چندگانه (Markdown/بصری/HTML)</td><td>بصری پیشرفته</td><td>بصری + Markdown</td><td>Wikitext + بصری</td></tr><tr><td><strong>احراز هویت سازمانی</strong></td><td>بسیار جامع (LDAP ،SAML ،OIDC ،OAuth2 و ۱۵+ ارائه‌دهنده دیگر)&nbsp;</td><td>کامل (LDAP ،Active ،Directory ،SAML ،OIDC ،Crowd و Jira)</td><td>محدود (LDAP ،SAML ،OIDC)</td><td>محدود (نیازمند افزونه)</td></tr><tr><td><strong>ساختار درختی صفحات</strong></td><td>انعطاف‌پذیر (فولدرهای درختی)</td><td>ساختار درختی و سلسله‌مراتبی</td><td>ثابت (قفسه &gt; کتاب &gt; صفحه)</td><td>مسطح (دسته‌بندی‌محور)</td></tr><tr><td><strong>پشتیبانی از زبان فارسی</strong></td><td>دارد (بومی و RTL)</td><td>دارد</td><td>دارد (ترجمه جامعه کاربری)</td><td>دارد</td></tr><tr><td><strong>مناسب برای چه سازمانی؟</strong><strong>&nbsp;</strong></td><td>تیم‌های فنی، سازمان‌های نیازمند استقرار داخلی، شرکت‌های دارای زیرساخت Git و LDAP</td><td>سازمان‌های بزرگ استفاده‌کننده از اکوسیستم Atlassian&nbsp;</td><td>تیم‌های کوچک و متوسط که به راه‌اندازی ساده و سریع نیاز دارند&nbsp;</td><td>پایگاه‌های دانش بزرگ، پروژه‌های عمومی و جوامع کاربری گسترده&nbsp;</td></tr></tbody></table></figure>



<h2 class="wp-block-heading" id="h-راهنمای-نصب-wiki-js-با-docker">راهنمای نصب Wiki.js با Docker</h2>



<p class="wp-block-paragraph">استفاده از Docker و Docker Compose، یکی از رایج‌ترین روش‌ها برای راه‌اندازی Wiki.js به شمار می‌آید. این روش روی اکثر توزیع‌های لینوکس (مخصوصا برای نصب Wiki.js روی Ubuntu Server)، بسیار رایج و پایدار است. البته قبل از هرکاری باید پیش‌نیازهای زیر را فراهم کنید:</p>



<ul class="wp-block-list">
<li>سرور لینوکس با نصب Docker و Docker Compose نصب‌شده. می‌توانید راهنمای آموزش <a href="https://hamravesh.com/blog/install-docker-ubuntu/" type="link" id="https://hamravesh.com/blog/install-docker-ubuntu/">نصب داکر</a> و <a href="https://hamravesh.com/blog/install-docker-compose-on-ubuntu/" type="link" id="https://hamravesh.com/blog/install-docker-compose-on-ubuntu/" target="_blank" rel="noreferrer noopener">نصب Docker Compose</a> استفاده کنید.</li>



<li>حداقل ۱ گیگابایت رم (۲ گیگابایت توصیه می‌شود).</li>



<li>دامنه اختصاصی برای دسترسی در محیط پروداکشن (اختیاری).</li>



<li>یک مخزن Git برای همگام‌سازی محتوا (اختیاری).</li>
</ul>



<p class="wp-block-paragraph" id="h-گام-اول-ایجاد-ساختار-پوشه-پروژه"><strong>گام اول: ایجاد ساختار پوشه پروژه</strong></p>



<p class="wp-block-paragraph">ابتدا باید پوشه‌های مورد نیاز را برای ماندگاری داده‌های دیتابیس (Data Persist) ایجاد کنید و وارد آن شوید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>mkdir -p ~/wikijs/{db,config}

cd ~/wikijs</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">mkdir</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-p</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">~/wikijs/{db,config}</span></span>
<span class="line"></span>
<span class="line"><span style="color: #6CB6FF">cd</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">~/wikijs</span></span></code></pre></div>



<p class="wp-block-paragraph" id="h-گام-دوم-ایجاد-فایل-docker-compose-yml"><strong>گام دوم: ایجاد فایل docker-compose.yml</strong></p>



<p class="wp-block-paragraph">یک فایل با نام docker-compose.yml در همان پوشه بسازید و کانفیگ زیر را در آن قرار دهید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">YAML</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>version: "3.8"
services:
  db:
    image: postgres:16-alpine
    container_name: wikijs-db
    restart: unless-stopped
    environment:
      POSTGRES_DB: wikijs
      POSTGRES_USER: wikijs
      POSTGRES_PASSWORD: YOUR_STRONG_PASSWORD
    volumes:
      - ./db:/var/lib/postgresql/data
    networks:
      - wikijs-net
  wikijs:
    image: ghcr.io/requarks/wiki:2
    container_name: wikijs
    restart: unless-stopped
    depends_on:
      - db
    ports:
      - "3000:3000"
    environment:
      DB_TYPE: postgres
      DB_HOST: db
      DB_PORT: 5432
      DB_USER: wikijs
      DB_PASS: YOUR_STRONG_PASSWORD
      DB_NAME: wikijs
    networks:
      - wikijs-net
networks:
  wikijs-net:
    driver: bridge</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #8DDB8C">version</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">&quot;3.8&quot;</span></span>
<span class="line"><span style="color: #8DDB8C">services</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #8DDB8C">db</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">image</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">postgres:16-alpine</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">container_name</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">wikijs-db</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">restart</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">unless-stopped</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">environment</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #8DDB8C">POSTGRES_DB</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">wikijs</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #8DDB8C">POSTGRES_USER</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">wikijs</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #8DDB8C">POSTGRES_PASSWORD</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">YOUR_STRONG_PASSWORD</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">volumes</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">      - </span><span style="color: #96D0FF">./db:/var/lib/postgresql/data</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">networks</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">      - </span><span style="color: #96D0FF">wikijs-net</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #8DDB8C">wikijs</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">image</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">ghcr.io/requarks/wiki:2</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">container_name</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">wikijs</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">restart</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">unless-stopped</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">depends_on</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">      - </span><span style="color: #96D0FF">db</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">ports</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">      - </span><span style="color: #96D0FF">&quot;3000:3000&quot;</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">environment</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #8DDB8C">DB_TYPE</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">postgres</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #8DDB8C">DB_HOST</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">db</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #8DDB8C">DB_PORT</span><span style="color: #ADBAC7">: </span><span style="color: #6CB6FF">5432</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #8DDB8C">DB_USER</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">wikijs</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #8DDB8C">DB_PASS</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">YOUR_STRONG_PASSWORD</span></span>
<span class="line"><span style="color: #ADBAC7">      </span><span style="color: #8DDB8C">DB_NAME</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">wikijs</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">networks</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">      - </span><span style="color: #96D0FF">wikijs-net</span></span>
<span class="line"><span style="color: #8DDB8C">networks</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">  </span><span style="color: #8DDB8C">wikijs-net</span><span style="color: #ADBAC7">:</span></span>
<span class="line"><span style="color: #ADBAC7">    </span><span style="color: #8DDB8C">driver</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">bridge</span></span></code></pre></div>



<p class="wp-block-paragraph">حتما مقدار YOUR_STRONG_PASSWORD را با یک رمز عبور مناسب جایگزین کنید. این مقدار باید در تنظیمات PostgreSQL و Wiki.js یکسان باشد تا اتصال به دیتابیس برقرار شود. همچنین مراقب باشید که فاصله‌ها و ساختار خطوط در فایل YAML تغییر نکند.</p>



<p class="wp-block-paragraph" id="h-گام-سوم-اجرا-و-بررسی-لاگ-ها"><strong>گام سوم: اجرا و بررسی لاگ‌ها</strong></p>



<p class="wp-block-paragraph">برای بالا آوردن کانتینرها در پس‌زمینه، دستور زیر را اجرا کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>docker compose up -d</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">docker</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">compose</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">up</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-d</span></span></code></pre></div>



<p class="wp-block-paragraph">برای بررسی وضعیت سرویس، لاگ‌ها را مشاهده کنید</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>docker compose logs -f wikijs</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">docker</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">compose</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">logs</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-f</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">wikijs</span></span></code></pre></div>



<p class="wp-block-paragraph">در صورت مشاهده پیام &#8220;Listening on port 3000&#8243;، سرویس با موفقیت راه‌اندازی شده است. سپس می‌توانید آدرس زیر را در مرورگر باز کنید:</p>



<p class="wp-block-paragraph">http://&lt;SERVER-IP&gt;:3000</p>



<p class="wp-block-paragraph">در اولین ورود، صفحه راه‌اندازی اولیه Wiki.js نمایش داده می‌شود.</p>



<p class="wp-block-paragraph" id="h-گام-چهارم-تنظیم-اولیه-setup-wizard"><strong>گام چهارم: تنظیم اولیه (Setup Wizard)</strong></p>



<p class="wp-block-paragraph">در اولین ورود، صفحه راه‌اندازی اولیه ظاهر می‌شود که اطلاعات زیر را از شما می‌خواهد:</p>



<ul class="wp-block-list">
<li>Administrator Account: ایمیل و رمز عبور مدیر ارشد سیستم را تعیین کنید.</li>



<li>Site URL: آدرس نهایی دسترسی به ویکی را وارد کنید (مانند (<a href="https://wiki.your-domain.com" rel="nofollow">https://wiki.your-domain.com </a>).</li>



<li>Telemetry: وضعیت ارسال آمار ناشناس استفاده از ابزار را مشخص کنید.</li>
</ul>



<p class="wp-block-paragraph">پس از تکمیل این فرم، به‌طور مستقیم وارد داشبورد مدیریت می‌شوید.</p>



<p class="wp-block-paragraph"><strong>نکته:</strong> اگر Wiki.js را در محیط پروداکشن اجرا می‌کنید، بهتر است سرویس را پشت یک Reverse Proxy مانند Nginx یا Traefik قرار دهید. این روش امکان مدیریت گواهی SSL، استفاده از دامنه اختصاصی، هدایت ترافیک HTTPS و اعمال تنظیمات امنیتی را فراهم می‌کند. هرچند Wiki.js به‌صورت مستقیم روی پورت ۳۰۰۰ اجرا می‌شود، اما در بسیاری از استقرارهای سازمانی دسترسی کاربران از طریق Reverse Proxy انجام می‌شود.&nbsp;</p>



<p class="wp-block-paragraph" id="h-گام-پنجم-تنظیم-همگام-سازی-با-git"><strong>گام پنجم: تنظیم همگام‌سازی با Git&nbsp;</strong></p>



<p class="wp-block-paragraph">همگام‌سازی با Git (یا Git Sync) یکی از قابلیت‌های Wiki.js برای نسخه‌بندی و نگهداری مستندات در مخازن Git است. این قابلیت امکان مدیریت تاریخچه تغییرات، نگهداری نسخه‌های قبلی و بکاپ‌گیری از محتوای صفحات را فراهم می‌کند. برای فعال‌سازی این قابلیت مراحل زیر را انجام دهید:</p>



<p class="wp-block-paragraph">مرحله اول: به مسیر Administration &gt; Storage بروید.</p>



<p class="wp-block-paragraph">مرحله دوم: روی گزینه Git کلیک کرده و آن را فعال کنید.</p>



<p class="wp-block-paragraph">مرحله سوم: تنظیمات مخزن را در Wiki.js وارد کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">YAML</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>Authentication Type: SSH
Repository URL: git@github.com:your-org/wiki-content.git
Branch: main
SSH Private Key: (Deploy Key)
Sync Direction: Bi-directional
Sync Schedule: Every 5 minutes</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #8DDB8C">Authentication Type</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">SSH</span></span>
<span class="line"><span style="color: #8DDB8C">Repository URL</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">git@github.com:your-org/wiki-content.git</span></span>
<span class="line"><span style="color: #8DDB8C">Branch</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">main</span></span>
<span class="line"><span style="color: #8DDB8C">SSH Private Key</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">(Deploy Key)</span></span>
<span class="line"><span style="color: #8DDB8C">Sync Direction</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">Bi-directional</span></span>
<span class="line"><span style="color: #8DDB8C">Sync Schedule</span><span style="color: #ADBAC7">: </span><span style="color: #96D0FF">Every 5 minutes</span></span></code></pre></div>



<p class="wp-block-paragraph">بازه زمانی همگام‌سازی را تنظیم کنید (مثلا هر ۵ دقیقه).</p>



<p class="wp-block-paragraph">مرحله چهارم: یک Deploy Key ایجاد کنید:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>ssh-keygen -t ed25519 -f ~/wikijs/git-deploy-key -N ""</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">ssh-keygen</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-t</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">ed25519</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-f</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">~/wikijs/git-deploy-key</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-N</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">&quot;&quot;</span></span></code></pre></div>



<p class="wp-block-paragraph">مرحله پنجم: کلید عمومی ایجادشده را به‌عنوان Deploy Key در مخزن GitHub یا GitLab خود و با دسترسی write اضافه کنید.</p>



<p class="wp-block-paragraph"><strong>نکته:</strong> همگام‌سازی با Git می‌تواند نسخه‌ای از محتوای صفحات را در مخزن Git نگهداری کند، اما جایگزین بکاپ کامل Wiki.js نیست. از آنجا که اطلاعات اصلی پلتفرم در PostgreSQL ذخیره می‌شوند، توصیه می‌شود به‌صورت منظم از پایگاه داده و فایل‌های پیوست نسخه پشتیبان تهیه کنید. در محیط‌های عملیاتی، استفاده از بکاپ خودکار برای دیتابیس و فضای ذخیره‌سازی می‌تواند ریسک از دست رفتن اطلاعات را کاهش دهد.</p>



<p class="wp-block-paragraph" id="h-گام-آخر-به-روزرسانی-wiki-js"><strong>گام آخر: به‌روزرسانی Wiki.js</strong></p>



<p class="wp-block-paragraph">برای آپدیت پلتفرم به آخرین نسخه پایدار، کافیست کانتینرها را مجدداً Pull کنید تا فرایند مهاجرت دیتابیس (Migration) هم به طور خودکار انجام شود:</p>



<div class="wp-block-kevinbatdorf-code-block-pro" data-code-block-pro-font-family="Code-Pro-JetBrains-Mono" style="font-size:clamp(16px, 1rem, 24px);font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:clamp(24px, 1.5rem, 36px);--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)"><span style="display:flex;align-items:center;padding:10px 0px 10px 16px;margin-bottom:-2px;width:100%;text-align:left;background-color:#2d333d;color:#9eadbd">Bash</span><span role="button" tabindex="0" style="color:#adbac7;display:none" aria-label="Copy" class="code-block-pro-copy-button"><pre class="code-block-pro-copy-button-pre" aria-hidden="true"><textarea class="code-block-pro-copy-button-textarea" tabindex="-1" aria-hidden="true" readonly>docker compose pull wikijs
docker compose up -d wikijs</textarea></pre><svg xmlns="http://www.w3.org/2000/svg" style="width:24px;height:24px" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path class="with-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4"></path><path class="without-check" stroke-linecap="round" stroke-linejoin="round" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"></path></svg></span><pre class="shiki github-dark-dimmed" style="background-color: #22272e" tabindex="0"><code><span class="line"><span style="color: #F69D50">docker</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">compose</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">pull</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">wikijs</span></span>
<span class="line"><span style="color: #F69D50">docker</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">compose</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">up</span><span style="color: #ADBAC7"> </span><span style="color: #6CB6FF">-d</span><span style="color: #ADBAC7"> </span><span style="color: #96D0FF">wikijs</span></span></code></pre></div>



<h2 class="wp-block-heading" id="h-اجرای-wiki-js-روی-cloud">اجرای Wiki.js روی Cloud</h2>



<p class="wp-block-paragraph">با افزایش تعداد کاربران، حجم مستندات و نیازهای عملیاتی، معمولا نگهداری Wiki.js روی یک سرور واحد، چالش‌هایی مانند مدیریت بکاپ، به‌روزرسانی، دسترس‌پذیری و مقیاس‌پذیری را ایجاد کند. بسیاری از سازمان‌ها برای اینکه با این چالش‌ها مواجه نشوند، این پلتفرم را روی زیرساخت‌های ابری اجرا می‌کنند تا بخشی از مدیریت زیرساخت و نگهداری سرویس ساده‌تر شود. معمولا برای استقرار Wiki.js در محیط ابری از دو الگوی رایج استفاده می‌شود:</p>



<h3 class="wp-block-heading" id="h-راه-اندازی-روی-سکوهای-ابری-paas">راه‌اندازی روی سکوهای ابری (PaaS)</h3>



<p class="wp-block-paragraph">در این سناریو، نیازی به مدیریت سیستم‌عامل لینوکس یا پیکربندی دستی Docker ندارید و می‌توانید با استفاده از ایمیج رسمی Wiki.js، سرویس را روی سکوی ابری مستقر کنید. همچنین برخی سکوهای ابری هم قابلیت‌هایی مانند مقیاس‌پذیری خودکار را در اختیار شما قرار می‌دهند.</p>



<h3 class="wp-block-heading" id="h-معماری-ابری-مدیریت-شده-managed-services">معماری ابری مدیریت‌شده (Managed Services)</h3>



<p class="wp-block-paragraph">برای تضمین امنیت و پایداری در محیط‌های پروداکشن، پلتفرم ابری خود را بر پایه فاکتورهای زیر پیکربندی کنید:</p>



<ul class="wp-block-list">
<li>دیتابیس ابری مدیریت‌شده (Managed PostgreSQL): به‌جای اجرای PostgreSQL درون کانتینر، می‌توانید Wiki.js را به یک سرویس دیتابیس مدیریت‌شده متصل کنید تا مدیریت بکاپ، به‌روزرسانی و نگهداری پایگاه داده ساده‌تر شود.</li>



<li>ذخیره‌سازی ابری فایل‌ها (Object Storage): می‌توانید از طریق مسیر `Administration &gt; Storage` سرویس‌های ذخیره‌سازی سازگار با S3 را برای نگهداری تصاویر و فایل‌های پیوست مستندات پیکربندی کنید.</li>



<li>همگام‌سازی با Git: اتصال Wiki.js به مخازن GitHub یا GitLab، امکان نسخه‌بندی و نگهداری مستندات در یک مخزن مجزا را فراهم می‌کند.</li>
</ul>



<h3 class="wp-block-heading" id="h-راه-اندازی-wiki-js-بدون-مدیریت-زیرساخت">راه‌اندازی Wiki.js بدون مدیریت زیرساخت</h3>



<p class="wp-block-paragraph">برای راه‌اندازی سریع‌تر Wiki.js، می‌توانید از نسخه آماده این نرم‌افزار در بازارچه هم‌روش استفاده کنید. در این روش، نصب Docker، استقرار و به‌روزرسانی سرویس و بخشی از مدیریت زیرساخت به‌صورت خودکار انجام می‌شود تا تیم‌ها بتوانند به‌جای صرف زمان برای پیکربندی و نگهداری، روی تولید و مدیریت مستندات تمرکز کنند.</p>



<div class="wp-block-dh-blog-card-database-block card database">
<div class="wp-block-group row align-items-center is-nowrap is-layout-flex wp-container-core-group-is-layout-8f761849 wp-block-group-is-layout-flex">
<div class="wp-block-group col-md"><div class="wp-block-group__inner-container is-layout-flow wp-block-group-is-layout-flow">
<h3 class="wp-block-heading" id="h-سرویس-wiki-js-هم-روش-راه-اندازی-سریع-و-ساده">💡 سرویس Wiki.js هم‌روش؛ راه‌اندازی سریع و ساده</h3>



<p class="wp-block-paragraph"><br>✅ پرداخت به میزان استفاده (PAYG)<br>✅ بدون دغدغه نگهداری زیرساخت<br>✅ بکاپ خودکار روزانه</p>
</div></div>
</div>



<div class="wp-block-group col-md-auto"><div class="wp-block-group__inner-container is-layout-flow wp-block-group-is-layout-flow">
<p class="wp-block-paragraph" id="h-"></p>



<p class="btn btn--main btn--wide wp-block-paragraph"><a href="https://console.hamravesh.com/marketplace/explore/oneclick_wikijs" target="_blank" rel="noreferrer noopener">راه‌اندازی ویکی جی اس</a><a href="#"></a></p>
</div></div>
</div>



<h2 class="wp-block-heading" id="h-چه-سروری-برای-wiki-js-مناسب-است">چه سروری برای Wiki.js مناسب است؟</h2>



<p class="wp-block-paragraph">نیازمندی‌های Wiki.js به تعداد کاربران، حجم مستندات و نحوه استفاده از پلتفرم بستگی دارد. در این بخش از آموزش Wiki.js، مهم‌ترین نیازمندی‌های سخت‌افزاری و نرم‌افزاری این نرم‌افزار ویکی سازمانی را بررسی می‌کنیم.</p>



<h3 class="wp-block-heading" id="h-نیازمندی-های-سخت-افزاری-hardware">نیازمندی‌های سخت‌افزاری (Hardware)</h3>



<p class="wp-block-paragraph">میزان مصرف منابع در Wiki.js به تعداد کاربران هم‌زمان، حجم داده‌ها و سرویس‌های جانبی مورد استفاده بستگی دارد. برای بسیاری از سناریوهای سازمانی، منابع زیر قابل استفاده هستند:</p>



<ul class="wp-block-list">
<li>پردازنده (CPU): ویکی جی اس روی یک هسته پردازنده هم&nbsp; قابل اجرا است، اما برای پردازش‌های پس‌زمینه و بارهای کاری بیشتر، استفاده از حداقل دو هسته CPU توصیه می‌شود.</li>



<li>حافظه رم (RAM): حداقل ۱ گیگابایت رم برای اجرا موردنیاز است. البته در سناریوهای عملیاتی و استفاده طولانی‌مدت، تخصیص رم بیشتر می‌تواند پایداری و عملکرد بهتری فراهم کند.</li>



<li>فضای ذخیره‌سازی (Storage): حجم موردنیاز به تعداد مستندات و فایل‌های بارگذاری‌شده بستگی دارد. برای راه‌اندازی اولیه، استفاده از فضای ذخیره‌سازی SSD توصیه می‌شود.</li>
</ul>



<h3 class="wp-block-heading" id="h-نیازمندی-های-نرم-افزاری-و-شبکه-software-amp-network">نیازمندی‌های نرم‌افزاری و شبکه (Software &amp; Network)</h3>



<p class="wp-block-paragraph">علاوه بر سخت‌افزار، باید زیرساخت نرم‌افزاری هم با نیازهای Wiki.js سازگار باشد.</p>



<ul class="wp-block-list">
<li>پایگاه داده: استفاده از دیتابیس PostgreSQL نسخه 11 یا بالاتر الزامی است، زیرا تمرکز اصلی توسعه نسخه‌های جدید Wiki.js روی PostgreSQL قرار دارد و این دیتابیس، انتخاب استاندارد و پایدار این پلتفرم محسوب می‌شود.</li>



<li>محیط اجرا (Runtime): این پلتفرم بر پایه Node.js توسعه یافته است، اما در صورت استفاده از Docker نیازی به نصب مستقیم Node.js روی سرور خود ندارید. در واقع این پلتفرم به صورت پیش‌فرض درون ایمیج داکر قرار دارد.</li>



<li>وب‌سرور و شبکه: Wiki.js می‌تواند بدون Nginx یا Apache اجرا شود، اما در بسیاری از محیط‌های پروداکشن از Reverse Proxy برای مدیریت SSL، مسیریابی درخواست‌ها و تنظیمات شبکه استفاده می‌شود. همچنین استفاده از یک دامنه یا زیر دامنه اختصاصی برای استقرار ویکی داخلی سازمان، مدیریت و دسترسی به سرویس را ساده‌تر می‌کند.</li>
</ul>



<h2 class="wp-block-heading" id="h-جمع-بندی">جمع‌بندی</h2>



<p class="wp-block-paragraph">اگر به دنبال یک سیستم مستندسازی self-hosted هستید که هم با Git یکپارچه شود و هم روی زیرساخت اختصاصی شما اجرا شود، Wiki.js یکی از گزینه‌های جدی پیش‌رو است. Wiki.js در عمل بین دو نیاز مهم تعادل ایجاد می‌کند: از یک طرف سادگی استقرار و استفاده (به‌خصوص با Docker) و از طرف دیگر امکانات فنی مثل همگام‌سازی با گیت، احراز هویت سازمانی و کنترل دسترسی دقیق. به همین دلیل برای تیم‌های DevOps، تیم‌های توسعه نرم‌افزار و سازمان‌هایی که رویکرد زیرساخت‌محور دارند، انتخاب مناسبی محسوب می‌شود.</p>



<p class="wp-block-paragraph">با این حال، این ابزار برای سناریوهایی که نیاز به همکاری هم‌زمان پیشرفته، جریان‌های کاری پیچیده یا اکوسیستم یکپارچه سازمانی (در حد ابزارهایی مثل Confluence) دارند، ممکن است محدودیت‌هایی داشته باشد. بنابراین انتخاب Wiki.js زمانی منطقی است که اولویت شما «کنترل، سادگی زیرساخت و انعطاف‌پذیری» باشد، نه یک پلتفرم کاملاً enterprise با همه امکانات همکاری بلادرنگ.</p>



<p class="wp-block-paragraph"></p>
<p>The post <a href="https://hamravesh.com/blog/what-is-wikijs/">Wiki.js چیست؟ مقایسه با رقبا و راهنمای نصب</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/what-is-wikijs/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Jenkins چیست؟ نحوه کار، ویژگی‌ها و کاربردهای جنکینز</title>
		<link>https://hamravesh.com/blog/what-is-jenkins/</link>
					<comments>https://hamravesh.com/blog/what-is-jenkins/#respond</comments>
		
		<dc:creator><![CDATA[علی باقرزاده]]></dc:creator>
		<pubDate>Wed, 18 Mar 2026 15:30:00 +0000</pubDate>
				<category><![CDATA[دواپس]]></category>
		<category><![CDATA[مقالات]]></category>
		<guid isPermaLink="false">https://hamravesh.com/blog/?p=2540</guid>

					<description><![CDATA[<p>در پروژه‌های نرم‌افزاری مدرن، توسعه‌دهندگان به طور مداوم کدهای جدیدی به مخزن پروژه اضافه می‌کنند. اگر فرایند ساخت (Build)، تست و استقرار نرم‌افزار به صورت دستی انجام شود، تیم توسعه با مشکلاتی مانند خطاهای انسانی، کند شدن انتشار نسخه‌ها و دشواری در مدیریت تغییرات روبه‌رو می‌شود. به همین دلیل در بسیاری از تیم‌های توسعه از [&#8230;]</p>
<p>The post <a href="https://hamravesh.com/blog/what-is-jenkins/">Jenkins چیست؟ نحوه کار، ویژگی‌ها و کاربردهای جنکینز</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">در پروژه‌های نرم‌افزاری مدرن، توسعه‌دهندگان به طور مداوم کدهای جدیدی به مخزن پروژه اضافه می‌کنند. اگر فرایند ساخت (Build)، تست و استقرار نرم‌افزار به صورت دستی انجام شود، تیم توسعه با مشکلاتی مانند خطاهای انسانی، کند شدن انتشار نسخه‌ها و دشواری در مدیریت تغییرات روبه‌رو می‌شود. به همین دلیل در بسیاری از تیم‌های توسعه از ابزارهایی برای اتوماسیون فرایند توسعه نرم‌افزار استفاده می‌شود. این ابزارها معمولاً در چارچوب رویکرد DevOps استفاده می‌شوند. که هدف آن کوتاه‌تر کردن چرخه توسعه و انتشار نرم‌افزار است. یکی از شناخته‌شده‌ترین ابزارها در این حوزه Jenkins است. بسیاری از توسعه‌دهندگان هنگام آشنایی با DevOps با این سؤال روبه‌رو می‌شوند که جنکینز چیست و چه کاربردی دارد.</p>



<p class="wp-block-paragraph">در این مطلب بررسی می‌کنیم که جنکینز چگونه کار می‌کند، Jenkins Pipeline چه مفهومی دارد و مهم‌ترین کاربردها و ویژگی‌های Jenkins چیست.</p>



<h2 class="wp-block-heading" id="h-jenkins-چیست">Jenkins چیست؟</h2>



<p class="wp-block-paragraph">جنکینز یک سرور اتوماسیون متن‌باز است که برای خودکارسازی مراحل مختلف توسعه نرم‌افزار استفاده می‌شود. این ابزار به تیم‌های توسعه کمک می‌کند فرایندهایی مانند ساخت نرم‌افزار (Build)، اجرای تست‌ها و استقرار (Deployment) را به صورت خودکار انجام دهند.</p>



<p class="wp-block-paragraph">Jenkins یک برنامه مبتنی بر زبان جاوا است که روی سیستم‌عامل‌های مختلف مانند لینوکس، ویندوز و macOS اجرا می‌شود. این ابزار از طریق یک رابط کاربری وب مدیریت می‌شود و با استفاده از هزاران افزونه (Plugin) می‌تواند با ابزارهای مختلف توسعه نرم‌افزار یکپارچه شود.</p>



<p class="wp-block-paragraph">هدف اصلی جنکینز این است که مراحل تکراری در چرخه توسعه نرم‌افزار را خودکار کند. به عنوان مثال، زمانی که یک توسعه‌دهنده کدی را در مخزن پروژه ثبت می‌کند، جنکینز می‌تواند این مراحل را به طور خودکار انجام دهد:</p>



<ul class="wp-block-list">
<li>کد را دریافت کند</li>



<li>پروژه را Build کند</li>



<li>تست‌های خودکار را اجرا کند</li>



<li>در صورت موفق بودن مراحل قبلی، نرم‌افزار را در محیط مورد نظر مستقر کند</li>
</ul>



<p class="wp-block-paragraph">به این ترتیب، تیم توسعه سریع‌تر متوجه خطاها می‌شود و فرایند انتشار نسخه‌های جدید نرم‌افزار نیز قابل اعتمادتر می‌شود.</p>



<h2 class="wp-block-heading" id="h-jenkins-در-devops-چه-نقشی-دارد">Jenkins در DevOps چه نقشی دارد؟</h2>



<p class="wp-block-paragraph">جنکینز معمولاً در چارچوب فرایندهای <a href="https://hamravesh.com/blog/what-is-ci-cd" target="_blank" rel="noreferrer noopener">CI/CD</a> استفاده می‌شود. این اصطلاح به مجموعه‌ای از روش‌ها و ابزارها اشاره دارد که هدف آن‌ها خودکارسازی مراحل ادغام کد، تست و انتشار نرم‌افزار است.</p>



<figure class="wp-block-image size-large"><img loading="lazy" decoding="async" width="1024" height="673" src="https://hamravesh.com/blog/wp-content/uploads/2026/03/hamravesh-what-is-jenkins-02-1024x673.webp" alt="نقش CI/CD در جنکینز چیست" class="wp-image-4663" srcset="https://hamravesh.com/blog/wp-content/uploads/2026/03/hamravesh-what-is-jenkins-02-1024x673.webp 1024w, https://hamravesh.com/blog/wp-content/uploads/2026/03/hamravesh-what-is-jenkins-02-300x197.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2026/03/hamravesh-what-is-jenkins-02-768x505.webp 768w, https://hamravesh.com/blog/wp-content/uploads/2026/03/hamravesh-what-is-jenkins-02-120x79.webp 120w, https://hamravesh.com/blog/wp-content/uploads/2026/03/hamravesh-what-is-jenkins-02.webp 1201w" sizes="auto, (max-width: 1024px) 100vw, 1024px" /></figure>



<p class="wp-block-paragraph">در ادامه به صورت خلاصه سه مفهوم اصلی CI/CD و نقش جنکینز در آنها را بررسی می‌کنیم.</p>



<h3 class="wp-block-heading" id="h-continuous-integration-در-جنکینز">Continuous Integration در جنکینز</h3>



<p class="wp-block-paragraph">در روش <strong>Continuous Integration</strong> یا ادغام مداوم، توسعه‌دهندگان تغییرات کد خود را به صورت مکرر در یک مخزن مشترک ثبت می‌کنند. پس از هر تغییر، سیستم CI به صورت خودکار پروژه را Build می‌کند و تست‌ها را اجرا می‌کند. اگر مشکلی در کد وجود داشته باشد، خطا در همان مراحل اولیه شناسایی می‌شود. Jenkins یکی از ابزارهایی است که می‌تواند این فرایند را خودکار کند.</p>



<p class="wp-block-paragraph">برای مثال، وقتی یک برنامه‌نویس تغییر جدیدی را در مخزن Git ثبت می‌کند، Jenkins می‌تواند این مراحل را به طور خودکار انجام دهد:</p>



<ul class="wp-block-list">
<li>پروژه را Build کند</li>



<li>تست‌های واحد (Unit Test) را اجرا کند</li>



<li>نتیجه را به تیم توسعه گزارش دهد</li>
</ul>



<p class="wp-block-paragraph">این کار باعث می‌شود مشکلات خیلی زودتر شناسایی شوند.</p>



<h3 class="wp-block-heading" id="h-continuous-delivery-در-جنکینز">Continuous Delivery در جنکینز</h3>



<p class="wp-block-paragraph">مرحله بعدی <strong>Continuous Delivery</strong> است. در این روش، پس از Build و اجرای موفق تست‌ها، نسخه جدید نرم‌افزار آماده انتشار می‌شود. در این مرحله Jenkins می‌تواند نرم‌افزار را به صورت خودکار در محیط‌هایی مانند این موارد مستقر کند.</p>



<ul class="wp-block-list">
<li>محیط تست</li>



<li>محیط staging</li>



<li>یا محیط پیش‌تولید</li>
</ul>



<p class="wp-block-paragraph">در این حالت انتشار نهایی در محیط production معمولاً با تأیید انسانی انجام می‌شود.</p>



<h3 class="wp-block-heading" id="h-continuous-deployment-در-جنکینز">Continuous Deployment در جنکینز</h3>



<p class="wp-block-paragraph">در مدل <strong>Continuous Deployment</strong> کل فرایند انتشار نیز خودکار می‌شود. یعنی اگر تمام مراحل Build و تست با موفقیت انجام شوند، نسخه جدید نرم‌افزار بدون دخالت انسانی در محیط production منتشر می‌شود. جنکینز با استفاده از پایپ‌لاین‌ها و پلاگین‌های مختلف می‌تواند چنین فرایندی را پیاده‌سازی کند.</p>



<h2 class="wp-block-heading">نحوه کار Jenkins و معماری آن</h2>



<p class="wp-block-paragraph">Jenkins یک سرور اتوماسیون متن‌باز است که مراحل مختلف توسعه نرم‌افزار را به صورت خودکار اجرا می‌کند. این ابزار بر پایه زبان جاوا نوشته شده و روی سیستم‌عامل‌های مختلفی مانند لینوکس، ویندوز و macOS قابل اجرا است. Jenkins می‌تواند به شکل یک برنامه مستقل، یک servlet در سرورهای جاوا (مثل Tomcat یا Jetty) و یا در قالب کانتینر Docker راه‌اندازی شود.</p>



<h3 class="wp-block-heading">معماری Jenkins</h3>



<p class="wp-block-paragraph">معماری جنکینز بر اساس مدل Master/Agent طراحی شده است:</p>



<ul class="wp-block-list">
<li><strong>Master:</strong> بخش اصلی جنکینز و مسئول مدیریت پایپ‌لاین‌ها، زمان‌بندی Buildها، اجرای تست‌ها و جمع‌آوری گزارش‌ها است. Master همچنین وظیفه توزیع کارها به Agentها را بر عهده دارد.</li>



<li><strong>Agent:</strong><br>Agentها ماشین‌هایی هستند که جنکینز از طریق آن‌ها وظایف Build و تست را اجرا می‌کند. Agent می‌تواند روی سرور محلی یا روی ماشین‌های از راه دور قرار گیرد و به Jenkins Master متصل شود. این معماری اجازه می‌دهد Jenkins در مقیاس بزرگ، پروژه‌های متعدد را به صورت موازی و بهینه اجرا کند.</li>
</ul>



<p class="wp-block-paragraph">مزیت این مدل معماری این است که حتی اگر تعداد پروژه‌ها یا حجم Buildها زیاد شود، Jenkins با استفاده از Agentها می‌تواند بار پردازشی را توزیع کرده و عملکرد سیستم را حفظ کند.</p>



<h3 class="wp-block-heading">جریان کار Jenkins</h3>



<p class="wp-block-paragraph">فرایند اجرای یک Build یا پایپ‌لاین در جنکینز معمولاً شامل مراحل زیر است:</p>



<ol class="wp-block-list">
<li><strong>دریافت کد منبع:</strong> جنکینز تغییرات کد را از مخزن‌های Git ،SVN یا سایر سیستم‌های کنترل نسخه دریافت می‌کند.</li>



<li><strong>Build یا ساخت پروژه:</strong> جنکینز با استفاده از ابزارهای Build مانند Maven ،Gradle یا Ant پروژه را ساخته و بسته‌بندی می‌کند.</li>



<li><strong>اجرای تست‌ها:</strong> جنکینز تست‌های واحد (Unit Test) و تست‌های یکپارچه (Integration Test) را اجرا می‌کند. در صورت بروز خطا، تیم توسعه بلافاصله مطلع می‌شود.</li>



<li><strong>انتشار یا استقرار موقت:</strong> پس از موفقیت Build و تست‌ها، جنکینز می‌تواند نسخه نرم‌افزار را در محیط staging یا پیش‌تولید مستقر کند تا آماده انتشار نهایی شود.</li>



<li><strong>گزارش‌دهی و مانیتورینگ:</strong> جنکینز نتایج Build و تست‌ها را به صورت گزارش و نمودار ارائه می‌دهد و هرگونه خطا یا هشدار را ثبت می‌کند.</li>
</ol>



<h3 class="wp-block-heading" id="h-نقش-jenkinsfile-در-نحوه-کار-jenkins-چیست">نقش Jenkinsfile در نحوه کار Jenkins چیست؟</h3>



<p class="wp-block-paragraph">یک بخش کلیدی در نحوه کار Jenkins، فایل Jenkinsfile است. این فایل به صورت متن ساده نوشته می‌شود و تمام مراحل پایپ‌لاین را تعریف می‌کند. Jenkins این فایل را می‌خواند و Buildها و تست‌ها را طبق دستورالعمل‌های آن اجرا می‌کند.</p>



<p class="wp-block-paragraph">مزیت استفاده از Jenkinsfile این است که در آن پایپ‌لاین به صورت کد تعریف می‌شود، قابل نسخه‌بندی در مخزن پروژه است و تغییرات پایپ‌لاین با کد پروژه همگام می‌شوند.</p>



<p class="wp-block-paragraph">به این ترتیب، جنکینز نه تنها اجرای خودکار Build و تست را ممکن می‌کند، بلکه قابلیت کنترل و نگهداری پایپ‌لاین‌ها را نیز برای تیم توسعه فراهم می‌سازد.</p>



<h2 class="wp-block-heading" id="h-پایپ-لاین-jenkins-چیست">پایپ‌لاین Jenkins چیست؟</h2>



<figure class="wp-block-image size-large"><img loading="lazy" decoding="async" width="1024" height="668" src="https://hamravesh.com/blog/wp-content/uploads/2026/03/hamravesh-what-is-jenkins-03-1024x668.webp" alt="پایپ‌لاین جنکینز از توسعه تا پروداکشن" class="wp-image-4664" srcset="https://hamravesh.com/blog/wp-content/uploads/2026/03/hamravesh-what-is-jenkins-03-1024x668.webp 1024w, https://hamravesh.com/blog/wp-content/uploads/2026/03/hamravesh-what-is-jenkins-03-300x196.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2026/03/hamravesh-what-is-jenkins-03-768x501.webp 768w, https://hamravesh.com/blog/wp-content/uploads/2026/03/hamravesh-what-is-jenkins-03-120x78.webp 120w, https://hamravesh.com/blog/wp-content/uploads/2026/03/hamravesh-what-is-jenkins-03.webp 1201w" sizes="auto, (max-width: 1024px) 100vw, 1024px" /></figure>



<p class="wp-block-paragraph">Jenkins Pipeline مجموعه‌ای از مراحل و تسک‌ها است که جنکینز برای اجرای فرایندهای خودکار CI/CD اجرا می‌کند. به عبارت ساده، پایپ‌لاین مانند یک نقشه راه برای Jenkins است که مشخص می‌کند کدها چگونه Build، تست و در نهایت منتشر شوند. پایپ‌لاین‌ها این امکان را فراهم می‌کنند که:</p>



<ul class="wp-block-list">
<li>چندین مرحله مختلف به ترتیب مشخص اجرا شوند</li>



<li>وابستگی بین مراحل رعایت شود</li>



<li>خطاها سریع شناسایی و گزارش شوند</li>



<li>تمام مراحل به صورت خودکار و قابل تکرار انجام شوند</li>
</ul>



<h3 class="wp-block-heading">Pipeline as Code</h3>



<p class="wp-block-paragraph">برای مدیریت بهتر پایپ‌لاین‌ها، جنکینز از مفهوم Pipeline as Code استفاده می‌کند. این یعنی کل پایپ‌لاین در قالب یک فایل متنی به نام Jenkinsfile تعریف می‌شود و می‌توان آن را هم‌زمان با کد پروژه نسخه‌بندی کرد.</p>



<p class="wp-block-paragraph"><strong>مزایای Pipeline as Code</strong></p>



<ul class="wp-block-list">
<li>پایپ‌لاین برای همه اعضای تیم قابل مشاهده و بررسی است</li>



<li>تغییرات پایپ‌لاین با تغییرات کد پروژه همگام می‌شود</li>



<li>امکان اجرای پایپ‌لاین به صورت خودکار در محیط‌های مختلف فراهم است</li>
</ul>



<p class="wp-block-paragraph">مثال: در یک پروژه وب، Jenkinsfile می‌تواند شامل مراحل زیر باشد:</p>



<ol class="wp-block-list">
<li>ساخت پروژه با Gradle</li>



<li>اجرای تست واحد برای بررسی عملکرد هر بخش کوچک از کد</li>



<li>اجرای تست یکپارچه‌سازی برای بررسی عملکرد بخش‌ها در کنار هم</li>



<li>بسته‌بندی نهایی و آماده‌سازی برای استقرار</li>



<li>استقرار در محیط staging</li>
</ol>



<p class="wp-block-paragraph">جنکینز با خواندن Jenkinsfile، این مراحل را به ترتیب اجرا می‌کند و در صورت بروز خطا، فرایند متوقف و گزارش صادر می‌شود.</p>



<h3 class="wp-block-heading">Multibranch Pipeline</h3>



<p class="wp-block-paragraph">جنکینز می‌تواند پایپ‌لاین‌ها را برای چندین شاخه (Branch) مختلف پروژه اجرا کند. این قابلیت که به آن <strong>Multibranch Pipeline</strong> می‌گویند، باعث می‌شود:</p>



<ul class="wp-block-list">
<li>هر شاخه از مخزن کد، پایپ‌لاین مستقل خود را داشته باشد</li>



<li>هنگام اضافه شدن شاخه جدید، جنکینز به صورت خودکار آن را شناسایی و پایپ‌لاین مربوطه را اجرا کند</li>



<li>تست و Build برای هر شاخه به طور جداگانه انجام شود، بدون آنکه شاخه‌های دیگر تحت تاثیر قرار گیرند</li>
</ul>



<h3 class="wp-block-heading" id="h-سرعت-پایپ-لاین-و-بهینه-سازی-آن">سرعت پایپ‌لاین و بهینه‌سازی آن</h3>



<p class="wp-block-paragraph">جنکینز امکاناتی برای مدیریت سرعت اجرای پایپ‌لاین و پایداری آن دارد. به عنوان مثال، می‌توان متغیرها را در محدوده اجرای پایپ‌لاین ذخیره کرد تا مراحل بعدی از آن‌ها استفاده کنند. با این روش، حتی پایپ‌لاین‌های بزرگ و پیچیده نیز سریع‌تر اجرا می‌شوند و منابع بهینه مصرف می‌شوند.</p>



<h2 class="wp-block-heading" id="h-کاربردهای-اصلی-جنکینز-چیست">کاربردهای اصلی جنکینز چیست؟</h2>



<p class="wp-block-paragraph">جنکینز به تیم‌های توسعه نرم‌افزار کمک می‌کند تا مراحل تکراری و زمان‌بر توسعه را خودکار کنند و فرایند انتشار نرم‌افزار را سریع‌تر و قابل اعتمادتر بسازند. مهم‌ترین کاربردهای جنکینز عبارتند از:</p>



<h3 class="wp-block-heading">خودکارسازی ساخت پروژه</h3>



<p class="wp-block-paragraph">جنکینز می‌تواند پروژه‌ها را به صورت خودکار بسازد. هر زمان که توسعه‌دهندگان کد جدیدی به مخزن اضافه کنند، جنکینز تغییرات را دریافت کرده، پروژه را Build و آماده تست می‌کند. این کار باعث می‌شود تیم توسعه دیگر مجبور نباشد هر بار پروژه را دستی بسازد و به این ترتیب از خطاهای انسانی جلوگیری می‌شود.</p>



<h3 class="wp-block-heading">اجرای تست‌های خودکار</h3>



<p class="wp-block-paragraph">جنکینز توانایی اجرای انواع تست‌ها را دارد؛ از جمله تست‌های واحد که بخش‌های کوچک کد را بررسی می‌کنند و تست‌های یکپارچه‌سازی که عملکرد بخش‌ها در کنار هم را ارزیابی می‌کنند. اجرای خودکار تست‌ها باعث می‌شود مشکلات، به‌سرعت شناسایی شوند و کیفیت نرم‌افزار افزایش یابد.</p>



<h3 class="wp-block-heading">استقرار خودکار نرم‌افزار</h3>



<p class="wp-block-paragraph">پس از Build و اجرای موفق تست‌ها، جنکینز می‌تواند نرم‌افزار را در محیط‌های staging یا پیش‌تولید مستقر کند. این فرایند باعث می‌شود نسخه جدید، آماده انتشار در محیط تولید باشد و در صورت تمایل تیم توسعه، به سرعت منتشر شود.</p>



<h3 class="wp-block-heading">یکپارچه‌سازی با سیستم‌های کنترل نسخه و ابزارهای DevOps</h3>



<p class="wp-block-paragraph">جنکینز با مخزن‌های کد مانند Git و ابزارهای دیگر <a href="https://hamravesh.com/blog/what-is-devops" target="_blank" rel="noreferrer noopener">DevOps</a> یکپارچه می‌شود. این قابلیت باعث می‌شود که ادغام مداوم تغییرات کد با محیط‌های تست و تولید بدون دخالت دستی انجام شود.</p>



<h3 class="wp-block-heading">نظارت و گزارش‌دهی</h3>



<p class="wp-block-paragraph">جنکینز گزارش‌های دقیق از وضعیت Buildها، نتایج تست‌ها و عملکرد پایپ‌لاین ارائه می‌دهد. این گزارش‌ها به تیم توسعه کمک می‌کند مشکلات را سریع شناسایی و رفع کنند و فرآیند توسعه را شفاف‌تر مدیریت کنند.</p>



<h2 class="wp-block-heading" id="h-jenkins-چه-زمانی-استفاده-می-شود">Jenkins چه زمانی استفاده می‌شود؟</h2>



<p class="wp-block-paragraph" id="h-jenkins-چه-زمانی-استفاده-می-شود-جنکینز-معمولا-در-پروژه-هایی-استفاده-می-شود-که-تیم-توسعه-می-خواهد-فرایند-ساخت-تست-و-انتشار-نرم-افزار-را-تا-حد-امکان-خودکار-کند-در-چنین-پروژه-هایی-تغییرات-کد-به-طور-مداوم-در-مخزن-پروژه-ثبت-می-شود-و-لازم-است-هر-تغییر-سریع-بررسی-و-آزمایش-شود-تا-از-ایجاد-خطا-در-نسخه-های-جدید-جلوگیری-شود">جنکینز معمولاً در پروژه‌هایی استفاده می‌شود که تیم توسعه می‌خواهد فرایند ساخت، تست و انتشار نرم‌افزار را تا حد امکان خودکار کند. در چنین پروژه‌هایی، تغییرات کد به‌طور مداوم در مخزن پروژه ثبت می‌شود و لازم است هر تغییر سریع بررسی و آزمایش شود تا از ایجاد خطا در نسخه‌های جدید جلوگیری شود.</p>



<p class="wp-block-paragraph">یکی از رایج‌ترین موقعیت‌هایی که در آن از جنکینز استفاده می‌شود، پروژه‌هایی است که تیم توسعه به‌طور مرتب نسخه‌های جدیدی از نرم‌افزار منتشر می‌کند. در این شرایط، اجرای دستی مراحل ساخت پروژه، اجرای تست‌ها و استقرار نسخه جدید می‌تواند زمان‌بر و مستعد خطا باشد. جنکینز با خودکارسازی این مراحل به تیم‌ها کمک می‌کند روند انتشار نرم‌افزار را سریع‌تر و قابل اعتمادتر کنند.</p>



<p class="wp-block-paragraph">جنکینز همچنین در تیم‌هایی که از روش‌های توسعه مبتنی بر DevOps استفاده می‌کنند کاربرد زیادی دارد. در این تیم‌ها، هدف این است که فاصله بین نوشتن کد و انتشار آن در محیط عملیاتی تا حد ممکن کوتاه شود. جنکینز با اجرای خودکار پایپ‌لاین‌های ساخت و تست، این فرایند را ساده‌تر می‌کند.</p>



<p class="wp-block-paragraph">از طرف دیگر، در پروژه‌هایی که تعداد توسعه‌دهندگان زیاد است یا چند شاخه مختلف از کد به‌طور هم‌زمان در حال توسعه هستند، استفاده از جنکینز می‌تواند به مدیریت بهتر تغییرات کمک کند. در این حالت، هر تغییر کد می‌تواند به‌طور خودکار Build و تست شود تا مشکلات احتمالی سریع شناسایی شوند.</p>



<p class="wp-block-paragraph" id="h-jenkins-چه-زمانی-استفاده-می-شود">به طور خلاصه، جنکینز بیشتر در پروژه‌هایی استفاده می‌شود که در آن‌ها سرعت انتشار نسخه‌ها، کیفیت نرم‌افزار و خودکارسازی فرایندهای توسعه اهمیت زیادی دارد.</p>



<h2 class="wp-block-heading" id="h-ویژگی-های-کلیدی-جنکینز-چیست">ویژگی‌های کلیدی جنکینز چیست؟</h2>



<p class="wp-block-paragraph">جنکینز با چند ویژگی اصلی شناخته می‌شود:</p>



<p class="wp-block-paragraph"><strong>متن‌باز و رایگان</strong></p>



<p class="wp-block-paragraph">جنکینز یک پروژه اوپن‌سورس است و استفاده از آن کاملاً رایگان است. این موضوع باعث می‌شود تیم‌های توسعه بتوانند بدون محدودیت فرایندهای توسعه و انتشار نرم‌افزار خود را خودکار کنند و از منابع گسترده جامعه جنکینز برای یادگیری و حل مشکلات بهره ببرند.</p>



<p class="wp-block-paragraph"><strong>اکوسیستم پلاگین گسترده</strong></p>



<p class="wp-block-paragraph">جنکینز بیش از هزار پلاگین دارد که امکان یکپارچه‌سازی با ابزارهای مختلف توسعه نرم‌افزار، تست، کنترل نسخه و استقرار را فراهم می‌کند. این پلاگین‌ها باعث می‌شوند جنکینز بسیار انعطاف‌پذیر باشد و بتوان آن را برای نیازهای مختلف تیم‌ها سفارشی کرد.</p>



<p class="wp-block-paragraph"><strong>قابلیت تعریف پایپ‌لاین به صورت کد</strong></p>



<p class="wp-block-paragraph">با استفاده از Jenkinsfile، تیم توسعه می‌تواند کل مراحل Build، تست و استقرار را به صورت کد تعریف کند. این قابلیت باعث می‌شود پایپ‌لاین‌ها قابل نسخه‌بندی باشند و تغییرات به راحتی با کد پروژه همگام شوند.</p>



<p class="wp-block-paragraph"><strong>مقیاس‌پذیری</strong></p>



<p class="wp-block-paragraph">جنکینز با استفاده از معماری Master/Agent امکان اجرای همزمان پروژه‌های متعدد را دارد. این ویژگی به تیم‌های بزرگ اجازه می‌دهد که بار کاری را بین چند سرور توزیع کنند و عملکرد سیستم حفظ شود.</p>



<p class="wp-block-paragraph"><strong>امنیت مبتنی بر سرور</strong></p>



<p class="wp-block-paragraph">جنکینز قابلیت مدیریت دسترسی کاربران و استفاده از روش‌های احراز هویت امن را دارد. این ویژگی تضمین می‌کند که تنها افراد مجاز بتوانند به اجرای پایپ‌لاین‌ها و تغییرات دسترسی داشته باشند.</p>



<h3 class="wp-block-heading" id="h-مزایای-جنکینز">مزایای جنکینز</h3>



<p class="wp-block-paragraph">جنکینز به دلیل انعطاف‌پذیری بالا و جامعه کاربری گسترده، یکی از پرکاربردترین ابزارها در فرایندهای CI/CD محسوب می‌شود. بسیاری از تیم‌های توسعه از این ابزار برای ساده‌تر کردن فرایند ساخت، تست و انتشار نرم‌افزار استفاده می‌کنند. مهم‌ترین مزایای جنکینز عبارتند از:</p>



<ul class="wp-block-list">
<li>متن‌باز و رایگان</li>



<li>انعطاف‌پذیری بالا و اکوسیستم پلاگین گسترده</li>



<li>پشتیبانی از Pipeline as Code</li>



<li>مقیاس‌پذیر و قابل اجرا در محیط‌های مختلف</li>



<li>قابلیت یکپارچه‌سازی با ابزارهای DevOps</li>
</ul>



<h3 class="wp-block-heading" id="h-معایب-جنکینز">معایب جنکینز</h3>



<p class="wp-block-paragraph">در کنار مزایای متعدد، استفاده از جنکینز در برخی شرایط می‌تواند چالش‌هایی نیز ایجاد کند. به‌ویژه در پروژه‌های بزرگ یا سازمان‌هایی که زیرساخت پیچیده‌ای دارند، مدیریت و نگهداری این ابزار ممکن است نیازمند زمان و تخصص بیشتری باشد. برخی از محدودیت‌های جنکینز عبارتند از:</p>



<ul class="wp-block-list">
<li>پیکربندی و نگهداری در محیط‌های بزرگ می‌تواند پیچیده باشد</li>



<li>وابستگی زیاد به پلاگین‌ها ممکن است باعث مشکلات سازگاری شود</li>



<li>رابط کاربری کلاسیک ممکن است برای کاربران جدید کمی گیج‌کننده باشد</li>
</ul>



<h2 class="wp-block-heading" id="h-جمع-بندی">جمع‌بندی</h2>



<p class="wp-block-paragraph">در این مقاله بررسی کردیم که جنکینز چیست و چرا یکی از ابزارهای مهم در فرایندهای CI/CD محسوب می‌شود. جنکینز یک سرور اتوماسیون متن‌باز است که به تیم‌های توسعه کمک می‌کند مراحل مختلف توسعه نرم‌افزار مانند ساخت پروژه، اجرای تست‌ها و استقرار نسخه‌های جدید را به صورت خودکار انجام دهند.</p>



<p class="wp-block-paragraph">با استفاده از پایپ‌لاین‌ها در جنکینز می‌توان فرایند ساخت و انتشار نرم‌افزار را به شکل قابل تکرار و قابل مدیریت تعریف کرد. این موضوع باعث می‌شود خطاها زودتر شناسایی شوند و انتشار نسخه‌های جدید نرم‌افزار سریع‌تر و قابل اعتمادتر انجام شود.</p>



<p class="wp-block-paragraph">در عین حال، مانند هر ابزار دیگری، استفاده از جنکینز نیز چالش‌هایی دارد و راه‌اندازی و نگهداری آن در پروژه‌های بزرگ ممکن است نیازمند تجربه و پیکربندی دقیق باشد. با این حال، به دلیل انعطاف‌پذیری بالا و جامعه کاربری گسترده، جنکینز همچنان یکی از پرکاربردترین ابزارها برای خودکارسازی فرایندهای توسعه نرم‌افزار به شمار می‌رود.</p>
<p>The post <a href="https://hamravesh.com/blog/what-is-jenkins/">Jenkins چیست؟ نحوه کار، ویژگی‌ها و کاربردهای جنکینز</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/what-is-jenkins/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>خودکارسازی تست‌ها در چرخه دواپس</title>
		<link>https://hamravesh.com/blog/devops-automation-test/</link>
					<comments>https://hamravesh.com/blog/devops-automation-test/#respond</comments>
		
		<dc:creator><![CDATA[ارسطو عباسی]]></dc:creator>
		<pubDate>Sat, 23 Nov 2024 08:16:58 +0000</pubDate>
				<category><![CDATA[دواپس]]></category>
		<category><![CDATA[مقالات]]></category>
		<guid isPermaLink="false">https://hamravesh.com/blog/?p=3789</guid>

					<description><![CDATA[<p>در این مقاله از وبلاگ هم‌روش، به بررسی اهمیت خودکارسازی تست‌ها در چرخه دواپس و نحوه پیاده‌سازی آن می‌پردازیم.</p>
<p>The post <a href="https://hamravesh.com/blog/devops-automation-test/">خودکارسازی تست‌ها در چرخه دواپس</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">در دنیای فناوری اطلاعات که به سرعت در حال تحول است، سازمان‌ها به دنبال راه‌هایی هستند تا نرم‌افزارهای با کیفیت بالا را در کمترین زمان ممکن ارائه دهند. <strong><a href="https://hamravesh.com/blog/what-is-devops/">دواپس (DevOps)</a></strong> به عنوان رویکردی که توسعه (Development) و عملیات (Operations) را ترکیب می‌کند، به این نیاز پاسخ می‌دهد. یکی از اجزای حیاتی در چرخه دواپس، <strong>خودکارسازی تست‌ها</strong> است. در این مقاله از وبلاگ هم‌روش، به بررسی اهمیت خودکارسازی تست‌ها در چرخه دواپس و نحوه پیاده‌سازی آن می‌پردازیم.</p>



<h2 class="wp-block-heading" id="h-اهمیت-خودکارسازی-تست-ها-در-دواپس"><strong>اهمیت خودکارسازی تست‌ها در دواپس</strong></h2>



<p class="wp-block-paragraph">خودکارسازی تست‌ها در چرخه دواپس نقشی اساسی در بهبود کیفیت و کارایی فرآیند توسعه نرم‌افزار ایفا می‌کند. با استفاده از تست‌های خودکار، تیم‌های توسعه می‌توانند اطمینان حاصل کنند که هر تغییری در کد به سرعت و به طور مداوم بررسی می‌شود، بدون اینکه نیاز به دخالت دستی باشد. این امر سرعت تحویل نرم‌افزار را افزایش می‌دهد، زیرا فرآیندهای تکراری و زمان‌بر تست‌های دستی حذف می‌شوند و مشکلات احتمالی در مراحل اولیه توسعه شناسایی و رفع می‌گردند.</p>



<p class="wp-block-paragraph">به‌صورت کلی می‌توان مزایای زیر را در فرایند خودکارسازی تست‌ها در دواپس مشاهده کنید:</p>



<p class="wp-block-paragraph">۱. <strong>افزایش سرعت تحویل نرم‌افزار</strong></p>



<p class="wp-block-paragraph">با خودکارسازی تست‌ها، فرآیند تست به صورت مداوم و بدون دخالت انسانی انجام می‌شود. این امر باعث می‌شود که با هر تغییر در کد، تست‌ها به سرعت اجرا شوند و مشکلات احتمالی شناسایی شوند.</p>



<p class="wp-block-paragraph">۲. <strong>بهبود کیفیت و اطمینان</strong></p>



<p class="wp-block-paragraph">تست‌های خودکار دقیق‌تر و جامع‌تر هستند و احتمال خطای انسانی را کاهش می‌دهند. این موضوع به افزایش کیفیت نرم‌افزار و اطمینان از عملکرد صحیح آن کمک می‌کند.</p>



<p class="wp-block-paragraph">۳. <strong>کاهش هزینه‌ها</strong></p>



<p class="wp-block-paragraph">هرچند پیاده‌سازی اولیه تست‌های خودکار ممکن است هزینه‌بر باشد، اما در بلندمدت باعث کاهش هزینه‌های مرتبط با تست‌های دستی و رفع باگ‌های پس از انتشار می‌شود.</p>



<p class="wp-block-paragraph">۴. <strong>تسهیل <a href="https://hamravesh.com/blog/what-is-ci-cd/">یکپارچه‌سازی مداوم (CI) و تحویل مداوم (CD)</a></strong></p>



<p class="wp-block-paragraph">خودکارسازی تست‌ها اجزای کلیدی در پیاده‌سازی CI/CD هستند که امکان تحویل مداوم ویژگی‌های جدید به کاربران را فراهم می‌کنند.</p>



<figure class="wp-block-image size-large"><img loading="lazy" decoding="async" width="1024" height="536" src="https://hamravesh.com/blog/wp-content/uploads/2024/10/devops-testing-automation-1024x536.webp" alt="خودکارسازی تست‌ها در دواپس" class="wp-image-3791" srcset="https://hamravesh.com/blog/wp-content/uploads/2024/10/devops-testing-automation-1024x536.webp 1024w, https://hamravesh.com/blog/wp-content/uploads/2024/10/devops-testing-automation-300x157.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2024/10/devops-testing-automation-768x402.webp 768w, https://hamravesh.com/blog/wp-content/uploads/2024/10/devops-testing-automation.webp 1200w" sizes="auto, (max-width: 1024px) 100vw, 1024px" /></figure>



<h2 class="wp-block-heading" id="h-مراحل-پیاده-سازی-خودکارسازی-تست-ها-در-چرخه-دواپس"><strong>مراحل پیاده‌سازی خودکارسازی تست‌ها در چرخه دواپس</strong></h2>



<p class="wp-block-paragraph">پیاده‌سازی خودکارسازی تست‌ها در چرخه دواپس نیازمند یک رویکرد ساختاریافته و هماهنگ بین تیم‌های توسعه و عملیات است. در ادامه، مراحل کلیدی این فرآیند را بررسی می‌کنیم:</p>



<h3 class="wp-block-heading" id="h-۱-شناسایی-نیازها-و-تعیین-اهداف"><strong>۱. شناسایی نیازها و تعیین اهداف</strong></h3>



<p class="wp-block-paragraph">ابتدا باید نیازهای کسب‌وکار و اهداف خودکارسازی تست‌ها را مشخص کنید. این شامل تعیین انواع تست‌هایی است که باید خودکار شوند، مانند تست‌های واحد، یکپارچه‌سازی، عملکرد و رابط کاربری. همچنین، میزان پوشش تست و معیارهای موفقیت را تعریف کنید.</p>



<h3 class="wp-block-heading"><strong>۲. انتخاب ابزارها و چارچوب‌های مناسب</strong></h3>



<p class="wp-block-paragraph">با توجه به فناوری‌ها و زبان‌های برنامه‌نویسی مورد استفاده، ابزارها و چارچوب‌های مناسب را انتخاب کنید. ابزارهایی را برگزینید که با سیستم‌های CI/CD و محیط‌های توسعه شما سازگار باشند. برای مثال:</p>



<ul class="wp-block-list">
<li><strong><a href="https://www.selenium.dev/">Selenium</a></strong> برای تست‌های رابط کاربری وب</li>



<li><strong>JUnit</strong> یا <strong>TestNG</strong> برای تست‌های جاوا</li>



<li><strong>pytest</strong> برای تست‌های پایتون</li>



<li><strong>Jenkins</strong> ،<strong>GitLab CI/CD</strong> یا <strong>Azure DevOps</strong> برای یکپارچه‌سازی مداوم</li>
</ul>



<h3 class="wp-block-heading"><strong>۳. طراحی استراتژی تست</strong></h3>



<p class="wp-block-paragraph">یک استراتژی جامع برای خودکارسازی تست‌ها تدوین کنید. این استراتژی باید شامل موارد زیر باشد:</p>



<ul class="wp-block-list">
<li>تعیین موارد تست اولویت‌دار برای خودکارسازی</li>



<li>برنامه‌ریزی زمان‌بندی اجرای تست‌ها</li>



<li>تعریف سناریوهای تست و داده‌های مورد نیاز</li>



<li>مشخص کردن معیارهای قبول یا رد نتایج تست</li>
</ul>



<h3 class="wp-block-heading"><strong>۴. توسعه و نگارش تست‌های خودکار</strong></h3>



<p class="wp-block-paragraph">تست‌های خودکار را بر اساس استراتژی تدوین‌شده توسعه دهید. در این مرحله:</p>



<ul class="wp-block-list">
<li>از الگوهای طراحی مناسب برای افزایش قابلیت نگهداری استفاده کنید.</li>



<li>کد تست‌ها را مستندسازی کنید تا فهم و به‌روزرسانی آن‌ها آسان‌تر شود.</li>



<li>تست‌ها را به گونه‌ای بنویسید که مستقل و قابل تکرار باشند.</li>
</ul>



<h3 class="wp-block-heading"><strong>۵. ادغام تست‌ها با سیستم‌های یکپارچه‌سازی مداوم (CI)</strong></h3>



<p class="wp-block-paragraph">تست‌های خودکار را با سیستم‌های CI ادغام کنید تا با هر تغییر در کد منبع، به صورت خودکار اجرا شوند. این کار شامل:</p>



<ul class="wp-block-list">
<li>پیکربندی ابزارهای CI برای اجرای تست‌ها در زمان‌های مشخص یا بر اساس رویدادها</li>



<li>تنظیم اعلان‌ها و گزارش‌دهی برای نتایج تست‌ها</li>



<li>اطمینان از اینکه شکست در تست‌ها به طور مناسب مدیریت و گزارش می‌شود</li>
</ul>



<h3 class="wp-block-heading"><strong>۶. اجرای تست‌ها در محیط‌های متنوع</strong></h3>



<p class="wp-block-paragraph">تست‌ها را در محیط‌های مختلف مانند محیط‌های توسعه، آزمایش و تولید اجرا کنید تا از عملکرد صحیح نرم‌افزار در شرایط گوناگون اطمینان حاصل شود. این مرحله می‌تواند شامل:</p>



<ul class="wp-block-list">
<li>استفاده از شبیه‌سازها یا مجازی‌سازی برای ایجاد محیط‌های تست</li>



<li>اجرای تست‌ها در پلتفرم‌ها و دستگاه‌های مختلف در صورت نیاز</li>
</ul>



<h3 class="wp-block-heading"><strong>۷. نظارت و گزارش‌دهی مستمر</strong></h3>



<p class="wp-block-paragraph">سیستم‌های نظارتی و گزارش‌دهی را پیاده‌سازی کنید تا به صورت مداوم عملکرد تست‌ها را بررسی کنید. این کار به شما کمک می‌کند تا:</p>



<ul class="wp-block-list">
<li>روندهای عملکردی را شناسایی کنید</li>



<li>مشکلات تکراری را تشخیص دهید</li>



<li>بازخوردهای لازم را به تیم توسعه ارائه دهید</li>
</ul>



<h3 class="wp-block-heading"><strong>۸. بهینه‌سازی و نگهداری تست‌ها</strong></h3>



<p class="wp-block-paragraph">با گذشت زمان و تغییر در کد منبع، تست‌ها نیاز به به‌روزرسانی و بهینه‌سازی دارند. برای این منظور:</p>



<ul class="wp-block-list">
<li>فرآیندهای نگهداری منظم را تعیین کنید</li>



<li>تست‌های منسوخ یا غیرضروری را حذف کنید</li>



<li>پوشش تست را بر اساس ویژگی‌های جدید افزایش دهید</li>
</ul>



<h3 class="wp-block-heading"><strong>۹. آموزش و ترویج فرهنگ خودکارسازی</strong></h3>



<p class="wp-block-paragraph">تیم‌ها را آموزش دهید تا مهارت‌های لازم برای نوشتن و نگهداری تست‌های خودکار را کسب کنند. همچنین:</p>



<ul class="wp-block-list">
<li>مزایای خودکارسازی تست‌ها را برای سازمان تبیین کنید</li>



<li>بهترین شیوه‌ها و تجربیات موفق را به اشتراک بگذارید</li>



<li>فرهنگ همکاری و مسئولیت‌پذیری را تقویت کنید</li>
</ul>



<h3 class="wp-block-heading"><strong>۱۰. بازخورد و بهبود مستمر</strong></h3>



<p class="wp-block-paragraph">فرآیند خودکارسازی تست‌ها را به صورت مداوم ارزیابی و بهبود دهید. از بازخوردهای جمع‌آوری‌شده برای:</p>



<ul class="wp-block-list">
<li>اصلاح استراتژی‌ها و روش‌ها</li>



<li>به‌روزرسانی ابزارها و فناوری‌ها</li>



<li>ارتقاء کیفیت و کارایی فرآیند تست</li>
</ul>



<h2 class="wp-block-heading" id="h-بهترین-شیوه-ها-در-خودکارسازی-تست-ها"><strong>بهترین شیوه‌ها در خودکارسازی تست‌ها</strong></h2>


<div class="wp-block-image">
<figure class="aligncenter size-full is-resized"><img loading="lazy" decoding="async" width="933" height="467" src="https://hamravesh.com/blog/wp-content/uploads/2024/10/devops-testing-best-practices-edited.webp" alt="خودکارسازی تست در دواپس - بهترین روش‌ها" class="wp-image-3793" style="width:838px;height:auto" srcset="https://hamravesh.com/blog/wp-content/uploads/2024/10/devops-testing-best-practices-edited.webp 933w, https://hamravesh.com/blog/wp-content/uploads/2024/10/devops-testing-best-practices-edited-300x150.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2024/10/devops-testing-best-practices-edited-768x384.webp 768w" sizes="auto, (max-width: 933px) 100vw, 933px" /></figure>
</div>


<h3 class="wp-block-heading" id="h-شروع-کوچک-و-توسعه-تدریجی"><strong>شروع کوچک و توسعه تدریجی</strong></h3>



<p class="wp-block-paragraph">یکی از بهترین روش‌ها در خودکارسازی تست‌ها در چرخه دواپس، آغاز با مقیاس کوچک و گسترش تدریجی است. این رویکرد به سازمان‌ها امکان می‌دهد که با حداقل ریسک و پیچیدگی، فرآیند خودکارسازی را شروع کنند و به مرور زمان آن را بهبود بخشند. با تمرکز اولیه بر تست‌های حیاتی و ساده، تیم‌ها می‌توانند مهارت‌های لازم را کسب کرده و به تدریج اعتماد به نفس خود را در استفاده از ابزارها و تکنیک‌های خودکارسازی افزایش دهند.</p>



<p class="wp-block-paragraph">این روش اجازه می‌دهد تا مشکلات و چالش‌های اولیه، قبل از اینکه فرآیند به مقیاس بزرگ‌تری گسترش یابد، شناسایی و حل شوند. با پیشرفت تدریجی، سازمان می‌تواند پوشش تست‌های خودکار را افزایش داده و به بهبود کیفیت نرم‌افزار و سرعت تحویل دست یابد، بدون اینکه با ریسک‌های بزرگ و غیرمنتظره مواجه شود.</p>



<h3 class="wp-block-heading" id="h-نگهداری-منظم-تست-ها"><strong>نگهداری منظم تست‌ها</strong></h3>



<p class="wp-block-paragraph">نگهداری منظم تست‌های خودکار در چرخه دواپس برای تضمین کارایی و دقت فرآیند تست بسیار حائز اهمیت است. با گذشت زمان و تغییراتی که در کد منبع رخ می‌دهد، تست‌های خودکار ممکن است منسوخ شده یا دیگر با ساختار جدید نرم‌افزار سازگار نباشند. بنابراین، بررسی و به‌روزرسانی دوره‌ای تست‌ها ضروری است تا اطمینان حاصل شود که آن‌ها همچنان مشکلات واقعی را شناسایی می‌کنند و نتایج قابل اعتمادی ارائه می‌دهند.</p>



<h3 class="wp-block-heading" id="h-مستندسازی-کامل"><strong>مستندسازی کامل</strong></h3>



<p class="wp-block-paragraph">مستندسازی کامل نقش اساسی در خودکارسازی تست‌ها در چرخه دواپس ایفا می‌کند. این مستندسازی به تیم‌ها امکان می‌دهد تا فرآیندها، ابزارها و تست‌های خود را به صورت دقیق و شفاف ثبت کنند، که این امر به درک بهتر، همکاری مؤثرتر و نگهداری آسان‌تر منجر می‌شود. با داشتن مستندات جامع، اعضای تیم می‌توانند منطق و هدف پشت هر تست را درک کرده و در صورت نیاز به به‌روزرسانی یا رفع اشکال، به سرعت اقدام کنند. </p>



<p class="wp-block-paragraph">مستندسازی کامل همچنین به آموزش اعضای جدید و انتقال دانش درون سازمان کمک می‌کند، زیرا اطلاعات کلیدی به صورت مکتوب و در دسترس قرار دارد. در نهایت، مستندسازی دقیق باعث کاهش خطاهای ناشی از سوءتفاهم یا نبود اطلاعات می‌شود و به بهبود کیفیت و قابلیت اطمینان تست‌های خودکار کمک می‌کند.</p>



<h3 class="wp-block-heading" id="h-استفاده-از-داده-های-واقعی-در-فرایند-تستینگ"><strong>استفاده از داده‌های واقعی</strong> در فرایند تستینگ</h3>



<p class="wp-block-paragraph">استفاده از داده‌های واقعی در فرآیند خودکارسازی تست‌ها اهمیت ویژه‌ای دارد، زیرا این داده‌ها منعکس‌کننده شرایط و سناریوهای واقعی هستند که نرم‌افزار در محیط عملیاتی با آن‌ها روبه‌رو می‌شود. با بهره‌گیری از داده‌های واقعی، می‌توان عملکرد، کارایی و پایداری نرم‌افزار را به طور دقیق‌تر ارزیابی کرد و مشکلات پنهانی را که در شرایط آزمایشگاهی ممکن است نادیده گرفته شوند، شناسایی نمود. این امر به بهبود کیفیت نرم‌افزار و کاهش ریسک‌های مرتبط با انتشار کمک می‌کند. با این حال، باید به <strong>مسائل حریم خصوصی و امنیت داده‌ها</strong> توجه ویژه‌ای داشت و اطمینان حاصل کرد که اطلاعات حساس به درستی محافظت و ناشناس‌سازی شده‌اند.</p>



<h2 class="wp-block-heading" id="h-چالش-ها-و-مشکلات-خودکارسازی-تست-ها-و-راه-حل-ها">چالش‌ها و مشکلات خودکارسازی تست‌ها و راه‌حل‌ها</h2>



<figure class="wp-block-image size-large"><img loading="lazy" decoding="async" width="1867" height="1120" src="https://hamravesh.com/blog/wp-content/uploads/2024/10/problems-challenges-edited-1.webp" alt="چالش‌ها و مشکلات پیاده‌سازی تست خودکار دواپس" class="wp-image-3797" srcset="https://hamravesh.com/blog/wp-content/uploads/2024/10/problems-challenges-edited-1.webp 1867w, https://hamravesh.com/blog/wp-content/uploads/2024/10/problems-challenges-edited-1-300x180.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2024/10/problems-challenges-edited-1-1024x614.webp 1024w, https://hamravesh.com/blog/wp-content/uploads/2024/10/problems-challenges-edited-1-768x461.webp 768w, https://hamravesh.com/blog/wp-content/uploads/2024/10/problems-challenges-edited-1-1536x921.webp 1536w" sizes="auto, (max-width: 1867px) 100vw, 1867px" /></figure>



<p class="wp-block-paragraph">خودکارسازی تست‌ها در<a href="https://hamravesh.com/blog/category/devops/"> چرخه دواپس</a> مزایای بسیاری دارد، اما در مسیر پیاده‌سازی آن، سازمان‌ها با چالش‌ها و مشکلات متعددی مواجه می‌شوند. شناخت این چالش‌ها و ارائه راه‌حل‌های مناسب، کلید موفقیت در اجرای مؤثر خودکارسازی تست‌ها است. در ادامه، به برخی از مهم‌ترین چالش‌ها و راه‌حل‌های مرتبط با آن‌ها می‌پردازیم:</p>



<h3 class="wp-block-heading"><strong>۱. هزینه و زمان پیاده‌سازی اولیه</strong></h3>



<p class="wp-block-paragraph"><em>چالش:</em> پیاده‌سازی اولیه خودکارسازی تست‌ها ممکن است هزینه‌بر و زمان‌بر باشد. نیاز به ابزارهای تخصصی، آموزش تیم و توسعه تست‌های اولیه می‌تواند منابع قابل توجهی را مصرف کند.</p>



<p class="wp-block-paragraph"><em>راه‌حل:</em></p>



<ul class="wp-block-list">
<li><strong>شروع تدریجی:</strong> با خودکارسازی تست‌های حیاتی و پرکاربرد آغاز کنید تا بتوانید بازگشت سرمایه را سریع‌تر مشاهده کنید.</li>



<li><strong>استفاده از ابزارهای متن‌باز:</strong> از ابزارهای رایگان و متن‌باز که هزینه‌های لایسنس ندارند استفاده کنید.</li>



<li><strong>برنامه‌ریزی دقیق:</strong> با برنامه‌ریزی مناسب و تخصیص منابع بهینه، می‌توانید هزینه‌ها را کنترل کنید.</li>
</ul>



<h3 class="wp-block-heading"><strong>۲. پیچیدگی در تست برخی سناریوها</strong></h3>



<p class="wp-block-paragraph"><em>چالش:</em> برخی از سناریوهای تست، به ویژه آن‌هایی که وابستگی‌های پیچیده یا تعاملات کاربری دارند، ممکن است به سختی خودکارسازی شوند.</p>



<p class="wp-block-paragraph"><em>راه‌حل:</em></p>



<ul class="wp-block-list">
<li><strong>تجزیه سناریوها:</strong> سناریوهای پیچیده را به بخش‌های کوچکتر و قابل مدیریت تقسیم کنید.</li>



<li><strong>استفاده از ابزارهای پیشرفته:</strong> از ابزارها و چارچوب‌هایی استفاده کنید که قابلیت مدیریت تست‌های پیچیده را دارند.</li>



<li><strong>ترکیب تست‌های دستی و خودکار:</strong> در مواردی که خودکارسازی غیرممکن یا غیرمقرون‌به‌صرفه است، از تست‌های دستی استفاده کنید.</li>
</ul>



<h3 class="wp-block-heading"><strong>۳. نگهداری و به‌روزرسانی تست‌ها</strong></h3>



<p class="wp-block-paragraph"><em>چالش:</em> با تغییرات مداوم در کد منبع، تست‌های خودکار نیز نیاز به به‌روزرسانی دارند. نگهداری تست‌ها می‌تواند زمان‌بر و پرهزینه باشد.</p>



<p class="wp-block-paragraph"><em>راه‌حل:</em></p>



<ul class="wp-block-list">
<li><strong>استفاده از الگوهای طراحی مناسب:</strong> کد تست‌ها را به صورت ماژولار و قابل نگهداری بنویسید.</li>



<li><strong>مستندسازی دقیق:</strong> مستندسازی تست‌ها به فهم و به‌روزرسانی آن‌ها کمک می‌کند.</li>



<li><strong>فرآیندهای نگهداری منظم:</strong> برنامه‌ریزی برای بازبینی و به‌روزرسانی منظم تست‌ها ضروری است.</li>
</ul>



<h3 class="wp-block-heading"><strong>۴. مقاومت تیم در برابر تغییر</strong></h3>



<p class="wp-block-paragraph"><em>چالش:</em> تیم‌های توسعه و عملیات ممکن است در برابر پذیرش فرآیندهای جدید خودکارسازی مقاومت نشان دهند.</p>



<p class="wp-block-paragraph"><em>راه‌حل:</em></p>



<ul class="wp-block-list">
<li><strong>آموزش و توانمندسازی:</strong> آموزش‌های لازم را برای تیم‌ها فراهم کنید تا مهارت‌ها و دانش مورد نیاز را کسب کنند.</li>



<li><strong>نشان دادن مزایا:</strong> با ارائه مثال‌های موفق و نتایج ملموس، اهمیت خودکارسازی تست‌ها را نشان دهید.</li>



<li><strong>درگیر کردن تیم‌ها در فرآیند تصمیم‌گیری:</strong> با مشارکت دادن تیم‌ها در انتخاب ابزارها و فرآیندها، حس مالکیت و پذیرش را افزایش دهید.</li>
</ul>



<h2 class="wp-block-heading">در پایان</h2>



<p class="wp-block-paragraph">خودکارسازی تست‌ها در چرخه دواپس نه تنها به بهبود کیفیت نرم‌افزار کمک می‌کند، بلکه سرعت تحویل و رضایت مشتریان را نیز افزایش می‌دهد. با وجود چالش‌هایی که ممکن است در این مسیر وجود داشته باشد، مزایای آن بسیار بیشتر است و سرمایه‌گذاری در آن ارزشمند است.</p>
<p>The post <a href="https://hamravesh.com/blog/devops-automation-test/">خودکارسازی تست‌ها در چرخه دواپس</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/devops-automation-test/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Argo CD چیست‌؟ – تسهیل گیت‌آپس با کوبرنتیز</title>
		<link>https://hamravesh.com/blog/what-is-argocd/</link>
					<comments>https://hamravesh.com/blog/what-is-argocd/#respond</comments>
		
		<dc:creator><![CDATA[بابک خوش‌نویس]]></dc:creator>
		<pubDate>Mon, 11 Nov 2024 11:13:26 +0000</pubDate>
				<category><![CDATA[دواپس]]></category>
		<category><![CDATA[مقالات]]></category>
		<guid isPermaLink="false">https://hamravesh.com/blog/?p=3459</guid>

					<description><![CDATA[<p>argo cd ابزاری برای «استقرار مداوم» (CD) است که به‌طور ویژه برای کوبرنتیز طراحی شده است. در این مقاله با این ابزار بیشتر آشنا خواهیم شد.</p>
<p>The post <a href="https://hamravesh.com/blog/what-is-argocd/">Argo CD چیست‌؟ – تسهیل گیت‌آپس با کوبرنتیز</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">Argo CD ابزار قدرتمند استقرار مداوم (<a href="https://hamravesh.com/blog/what-is-ci-cd/">CD</a>) برای <a href="https://hamravesh.com/blog/what-is-kubernetes/">کوبرنتیز</a> است که از رویکرد گیت‌آپس استفاده می‌کند. در این مطلب، ضمن پاسخ به این پرسش که Argo CD چیست توضیح می‌دهیم که چگونه این ابزار فرآیند CI/CD را در محیط‌های کوبرنتیز بهبود می‌بخشد. ما ویژگی‌های کلیدی Argo CD، نحوه عملکرد آن در چارچوب گیت‌آپس و اجزای اصلی این سیستم را مورد بحث قرار خواهیم داد. همچنین، به این موضوع می‌پردازیم که چگونه Argo CD به تسهیل گیت‌آپس در کوبرنتیز کمک می‌کند و مزایای استفاده از آن را در فرآیند توسعه و استقرار نرم‌افزار بررسی خواهیم کرد.</p>



<h2 class="wp-block-heading" id="h-argo-cd-چیست">Argo CD چیست‌؟</h2>



<p class="wp-block-paragraph">«آرگو سی‌دی» (Argo CD) ابزار «استقرار مداوم» (Continues Integration | CD) محسوب می‌شود که به‌طور ویژه برای کوبرنتیز طراحی شده است. برخلاف ابزارهای استقرار مداوم خارجی که تنها از روش‌های استقرار مبتنی بر فشار (Push-Based) استفاده می‌کنند، Argo CD می‌تواند کدهای به‌روزشده را مستقیماً از مخازن گیت (<a href="https://hamravesh.com/blog/10-git-command/">Git</a>) دریافت کرده و آن‌ها را روی منابع کوبرنتیز مستقر کند. این ویژگی به توسعه‌دهندگان امکان می‌دهد تا هم پیکربندی زیرساخت و هم به‌روزرسانی‌های نرم‌افزار را در یک سیستم واحد مدیریت کنند. Argo CD ویژگی‌ها و قابلیت‌های کلیدی زیر را ارائه می‌دهد:</p>



<ul class="wp-block-list">
<li>استقرار دستی یا خودکار برنامه‌ها روی خوشهٔ کوبرنتیز</li>



<li>همگام‌سازی خودکار وضعیت برنامه با آخرین نسخهٔ پیکربندی اعلامی</li>



<li>رابط کاربری تحت وب و رابط خط فرمان (CLI)</li>



<li>توانایی نمایش مشکلات استقرار، تشخیص و رفع ناهماهنگی‌های پیکربندی</li>



<li>کنترل دسترسی مبتنی بر نقش (RBAC) که امکان مدیریت چند خوشه را فراهم می‌کند.</li>



<li>ورود یکپارچه (SSO) با ارائه‌دهندگانی مانند گیت‌لب، گیت‌هاب، مایکروسافت، OAuth2 ،OIDC، لینکدین، LDAP و SAML 2.0</li>



<li>پشتیبانی از وب‌هوک‌ها برای راه‌اندازی اقدامات در گیت‌لب، گیت‌هاب و بیت‌باکت.</li>
</ul>



<p class="wp-block-paragraph">این ویژگی‌ها به کاربران اجازه می‌دهند تا فرآیند استقرار و مدیریت برنامه‌های خود را در محیط کوبرنتیز به شکلی کارآمد و انعطاف‌پذیر انجام دهند.</p>



<h2 class="wp-block-heading" id="h-گیت-آپس-با-argo-cd-چیست">گیت‌آپس با Argo CD چیست؟</h2>



<p class="wp-block-paragraph">گیت‌آپس (GitOps) یک روش مهندسی نرم‌افزار است که از مخزن گیت به‌عنوان تنها منبع حقیقت استفاده می‌کند. در این روش، تیم‌ها پیکربندی‌های اعلامی را در گیت ثبت می‌کنند و از این پیکربندی‌ها برای ایجاد محیط‌های مورد نیاز در فرآیند تحویل مداوم استفاده می‌شود. در گیت‌آپس، هیچ تنظیم دستی محیط یا استفاده از اسکریپت‌های مجزا وجود ندارد، همه چیز از طریق مخزن گیت تعریف می‌شود.</p>



<p class="wp-block-paragraph">یکی از بخش‌های اساسی فرآیند گیت‌آپس، درخواست ادغام (Pull Request) است. نسخه‌های جدید پیکربندی از طریق درخواست ادغام معرفی می‌شوند، با شاخهٔ اصلی در مخزن گیت ترکیب می‌شوند و سپس نسخهٔ جدید به‌طور خودکار مستقر می‌شود. مخزن گیت شامل سابقهٔ کاملی از تمام تغییرات، از جمله تمام جزئیات محیط در هر مرحله از فرآیند است.</p>



<p class="wp-block-paragraph">آرگو سی‌دی مراحل پایانی فرآیند گیت‌آپس را مدیریت می‌کند و اطمینان حاصل می‌کند که پیکربندی‌های جدید به‌درستی روی خوشهٔ کوبرنتیز مستقر می‌شوند. به‌طور کلی، فرآیند Argo CD به این صورت عمل می‌کند:</p>



<ul class="wp-block-list">
<li>یک توسعه‌دهنده تغییراتی در برنامه ایجاد می‌کند و نسخهٔ جدیدی از تعاریف منابع کوبرنتیز را به مخزن گیت ارسال می‌کند.</li>



<li>یکپارچه‌سازی مداوم (Continuous Integration | CI) فعال می‌شود که منجر به ذخیرهٔ تصویر کانتینر جدید در یک مخزن می‌گردد.</li>



<li>توسعه‌دهنده درخواست ادغام (Pull Request) را صادر می‌کند که شامل تغییرات در مانیفست‌های کوبرنتیز است. این مانیفست‌ها می‌توانند به صورت دستی یا خودکار ایجاد شده باشند.</li>



<li>درخواست ادغام بررسی شده و تغییرات با شاخهٔ اصلی ترکیب می‌شوند. این عمل یک وب‌هوک را فعال می‌کند که به Argo CD اطلاع می‌دهد تغییری ایجاد شده است.</li>



<li>آرگو سی‌دی مخزن را کلون و وضعیت برنامه را با وضعیت فعلی خوشهٔ کوبرنتیز مقایسه می‌کند. سپس تغییرات لازم را در پیکربندی خوشه اعمال می‌کند.</li>



<li>کوبرنتیز از کنترلِرهای خود استفاده می‌کند تا تغییرات مورد نیاز در منابع خوشه را اعمال کند، تا زمانی که به پیکربندی مطلوب برسد.</li>



<li>Argo CD پیشرفت کار را نظارت می‌کند و زمانی که خوشهٔ کوبرنتیز آماده شد، گزارش می‌دهد که برنامه همگام شده است.</li>



<li>آرگو سی‌دی همچنین در جهت مخالف نیز کار می‌کند، یعنی تغییرات در خوشهٔ کوبرنتیز را نظارت می‌کند و اگر با پیکربندی فعلی در گیت مطابقت نداشته باشند، آن‌ها را نادیده می‌گیرد.</li>
</ul>



<h3 class="wp-block-heading" id="h-argo-cd-چطور-به-تسهیل-گیت-آپس-با-کوبرنتیز-کمک-می-کند">Argo CD چطور به تسهیل گیت‌آپس با کوبرنتیز کمک می‌کند؟</h3>



<ul class="wp-block-list">
<li><strong>عامل گیت‌آپس</strong> (<strong>GitOps Agent</strong>): Argo CD مسئول دریافت کدهای به‌روزشده از مخازن گیت و استقرار مستقیم آن‌ها روی منابع کوبرنتیز است. این ابزار هم پیکربندی زیرساخت و هم به‌روزرسانی‌های برنامه را در سیستمی واحد مدیریت می‌کند.</li>



<li><strong>تعاریف منابع سفارشی</strong> (<strong>CRD</strong> | <strong>Custom Resource Definitions</strong>): آرگو سی‌دی در فضای نام اختصاصی خود درون خوشهٔ کوبرنتیز فعالیت می‌کند. این ابزار CRDهای خاص خود را ارائه می‌دهد که API کوبرنتیز را گسترش داده و امکان تعریف وضعیت مطلوب برنامه را به شکلی اعلامی (Declarative) فراهم می‌کند. Argo CD بر اساس دستورالعمل‌های موجود در مخزن گیت یا مخزن Helm، از CRDهای خود برای اعمال تغییرات در فضای نام اختصاصی‌اش استفاده می‌کند.</li>



<li><strong>رابط خط فرمان</strong> (<strong>CLI</strong>): آرگو سی‌دی CLI قدرتمندی ارائه می‌دهد که شما را قادر می‌سازد با چند دستور ساده، تعاریف منابع YAML را ایجاد کنید. برای مثال، دستور <code>Argo CD app create</code> به شما اجازه می‌دهد با مشخص کردن چند پرچم، یک شیء Application معتبر ایجاد کنید که برنامهٔ شما را بدون نیاز به نوشتن دستی YAML توصیف می‌کند.</li>



<li><strong>رابط کاربری</strong>: Argo CD در این زمینه منحصر به فرد است که یک رابط کاربری تحت وب راحت ارائه می‌دهد که به شما امکان می‌دهد همان کار را انجام دهید، یعنی برنامه را تعریف کنید و از آرگو سی‌دی بخواهید پیکربندی‌های YAML مربوطه را ایجاد کند. همچنین به شما امکان می‌دهد پیکربندی کوبرنتیز حاصل را از نظر پادها و کانتینرها مشاهده کنید. اگرچه برخی ممکن است فکر کنند استفاده از رابط کاربری «گیت‌اپس واقعی» نیست، این درست نیست، زیرا رابط کاربری برای کنترل مستقیم خوشه استفاده نمی‌شود، بلکه فقط راهی آسان‌تر برای ایجاد پیکربندی اعلامی است.</li>



<li><strong>چند مستأجری</strong> (<strong>Multi-tenancy</strong>): آرگو سی‌دی از همکاری چندین تیم روی پروژه‌های مختلف در یک محیط کوبرنتیز به خوبی پشتیبانی می‌کند. CRDهای Argo CD می‌توانند محدود شوند تا فقط مخازن منبع متعلق به یک پروژهٔ خاص را بخوانند و می‌توانند طوری تنظیم شوند که برنامه‌ها را در خوشه و فضای نام خاصی مستقر کنند. هر نمونه CRD همچنین می‌تواند تنظیمات کنترل دسترسی مبتنی بر نقش (RBAC) خاص خود را داشته باشد.</li>



<li><strong>بهره‌گیری از ابزارهای موجود</strong>: بسیاری از سازمان‌ها قبلاً در پیکربندی‌های اعلامی مبتنی بر YAML، چارت‌های Helm ،Kustomize یا سایر سیستم‌ها سرمایه‌گذاری کرده‌اند. Argo CD هدفش استفاده از این سرمایه‌گذاری‌های موجود است، نه جایگزینی آن‌ها. این ابزار می‌تواند از هر یک از این فرمت‌ها برای ایجاد خودکار تعاریف CRD مربوطه استفاده کند.</li>
</ul>



<h2 class="wp-block-heading" id="h-argo-cd-چطور-کار-می-کند">Argo CD چطور کار می‌کند؟</h2>



<p class="wp-block-paragraph">هنگام استفاده از Argo CD، می‌توانید پیکربندی برنامه را با استفاده از چندین نوع مانیفست کوبرنتیز مشخص کنید، از جمله:</p>



<ul class="wp-block-list">
<li>مانیفست‌های ساده YAML یا JSON</li>



<li>چارت‌های Helm</li>



<li>Kustomize</li>



<li>برنامه‌های Ksonnet و Jsonnet</li>
</ul>



<p class="wp-block-paragraph">همچنین امکان استفاده از هر ابزار مدیریت پیکربندی سفارشی به‌عنوان یک افزونه نیز وجود دارد. Argo CD به‌طور خودکار وضعیت مطلوب یک برنامه را در محیط هدفِ مشخص‌شده مستقر می‌کند. به‌روزرسانی‌ها از طریق برچسب‌ها (Tags)، شاخه‌ها (Branches)، یا نسخه‌های خاص ثابت‌شده (Pinned Specific Versions) یک مانیفست در کامیت‌های گیت قابل ردیابی هستند.</p>


<div class="wp-block-image">
<figure class="aligncenter size-full"><img loading="lazy" decoding="async" width="512" height="488" src="https://hamravesh.com/blog/wp-content/uploads/2024/07/image-3.png" alt="نحوه کار Argo CD چیست" class="wp-image-3460" srcset="https://hamravesh.com/blog/wp-content/uploads/2024/07/image-3.png 512w, https://hamravesh.com/blog/wp-content/uploads/2024/07/image-3-300x286.png 300w" sizes="auto, (max-width: 512px) 100vw, 512px" /><figcaption class="wp-element-caption">منبع تصویر [<a href="https://argo-cd.readthedocs.io/en/stable/assets/argocd_architecture.png">+</a>] </figcaption></figure>
</div>


<p class="wp-block-paragraph">آرگو سی‌دی یک کنترلر کوبرنتیز است که وظیفهٔ نظارت مداوم بر تمام برنامه‌های در حال اجرا را بر عهده دارد. این ابزار، وضعیت فعلی برنامه‌ها را با وضعیت مطلوبی که در مخزن گیت تعریف شده، مقایسه می‌کند. اگر وضعیت فعلی یک برنامهٔ مستقر شده با وضعیت مطلوب آن تفاوت داشته باشد، Argo CD آن را به عنوان «ناهمگام» (OutOfSync) شناسایی می‌کند.</p>



<p class="wp-block-paragraph">آرگو سی‌دی این تفاوت‌ها را گزارش می‌دهد و با ارائهٔ نمایش‌های بصری، به توسعه‌دهندگان کمک می‌کند تا وضعیت فعلی را به صورت دستی یا خودکار با وضعیت مطلوب هماهنگ کنند. این ابزار قادر است هر تغییری که در وضعیت مطلوب (در مخزن گیت) ایجاد شود را به طور خودکار در محیط هدف اعمال کند. این قابلیت تضمین می‌کند که برنامه‌ها همواره در حالت همگام باقی بمانند.</p>



<h3 class="wp-block-heading" id="h-اجزای-اساسی-argo-cd-چیست">اجزای اساسی Argo CD چیست؟</h3>



<p class="wp-block-paragraph">در ادامه هر یک از اجزای اساسی Argo CD را معرفی می‌کنیم و آن‌ها را شرح می‌دهیم.</p>



<h4 class="wp-block-heading" id="h-api-در-argo-cd-چیست">API در Argo CD چیست؟</h4>



<p class="wp-block-paragraph">این سرویس، یک سرور API از نوع gRPC/REST است که رابط برنامه‌نویسی را برای اجزایی مانند رابط خط فرمان و رابط کاربری وب فراهم می‌کند. وظایف اصلی این سرویس عبارتند از:</p>



<ul class="wp-block-list">
<li>مدیریت برنامه‌ها و گزارش وضعیت آن‌ها</li>



<li>اجرای عملیات‌های برنامه مانند اقدامات تعیین‌شده توسط کاربر، همگام‌سازی و بازگشت به نسخه‌های قبلی</li>



<li>مدیریت اعتبارنامه‌های خوشه و مخزن که به صورت اسرار کوبرنتیز ذخیره می‌شوند</li>



<li>احراز هویت و واگذاری مجوز به ارائه‌دهندگان هویت شخص ثالث</li>



<li>اعمال سیاست‌های کنترل دسترسی مبتنی بر نقش (RBAC)</li>



<li>دریافت و ارسال رویدادهای وب‌هوک گیت</li>
</ul>



<h4 class="wp-block-heading" id="h-سرویس-مخزن-در-argo-cd">سرویس مخزن در Argo CD</h4>



<p class="wp-block-paragraph">این سرویس داخلی، مخزن گیت را به صورت محلی در حافظه پنهان ذخیره می‌کند و مانیفست‌های برنامه را نگهداری می‌کند. سرویس مخزن، مانیفست‌های کوبرنتیز را تولید می‌کند و بر اساس ورودی‌هایی مانند آدرس مخزن، مسیر برنامه، نسخه‌ها (مانند کامیت‌ها، برچسب‌ها، شاخه‌ها) و تنظیمات خاص قالب (مانند مقادیر Helm، محیط‌های Ksonnet، پارامترها) آن‌ها را برمی‌گرداند.</p>



<h4 class="wp-block-heading" id="h-کنترلر-برنامه">کنترلر برنامه</h4>



<p class="wp-block-paragraph">این جزء، یک کنترلر کوبرنتیز است که به‌طور مداوم برنامه‌ها را نظارت می‌کند و وضعیت هدف مشخص‌شده در مخزن گیت را با وضعیت فعلی هر برنامه مقایسه می‌کند. کنترلر برنامه‌ها تشخیص می‌دهد که چه زمانی یک برنامه ناهمگام است و در صورت مشخص شدن، می‌تواند اصلاحات را اعمال کند. این کنترلر همچنین قلاب‌هایی را که توسط کاربر برای رویدادهای چرخه حیات برنامه (مانند قبل از همگام‌سازی، همگام‌سازی و پس از همگام‌سازی) تعریف شده‌اند، فراخوانی می‌کند.</p>



<h2 class="wp-block-heading" id="h-جمع-بندی">جمع‌بندی</h2>



<p class="wp-block-paragraph">آرگو سی‌دی (Argo CD) یک ابزار قدرتمند استقرار مداوم برای کوبرنتیز است که با استفاده از رویکرد گیت‌آپس، فرآیند مدیریت و استقرار برنامه‌ها را بهبود می‌بخشد. این ابزار با ارائه ویژگی‌هایی مانند همگام‌سازی خودکار، رابط کاربری تحت وب، کنترل دسترسی مبتنی بر نقش و پشتیبانی از انواع مختلف مانیفست‌ها، به توسعه‌دهندگان امکان می‌دهد تا پیکربندی زیرساخت و به‌روزرسانی‌های نرم‌افزار را در یک سیستم واحد مدیریت کنند. </p>



<p class="wp-block-paragraph">آرگو سی‌دی با استفاده از اجزای کلیدی خود مانند API، سرویس مخزن و کنترلر برنامه، اطمینان حاصل می‌کند که وضعیت برنامه‌ها همواره با آخرین نسخه پیکربندی در مخزن گیت همگام باشد. این رویکرد نه تنها فرآیند استقرار را ساده‌تر می‌کند، بلکه قابلیت ردیابی، امنیت و ثبات بیشتری را در محیط‌های کوبرنتیز فراهم می‌آورد.</p>
<p>The post <a href="https://hamravesh.com/blog/what-is-argocd/">Argo CD چیست‌؟ – تسهیل گیت‌آپس با کوبرنتیز</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/what-is-argocd/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>ChatOps چیست؟ راهنمای کامل و جامع برای درک مفهوم ChatOps یا چت عملیاتی</title>
		<link>https://hamravesh.com/blog/what-is-chatops/</link>
					<comments>https://hamravesh.com/blog/what-is-chatops/#respond</comments>
		
		<dc:creator><![CDATA[ارسطو عباسی]]></dc:creator>
		<pubDate>Sun, 27 Oct 2024 08:06:30 +0000</pubDate>
				<category><![CDATA[دواپس]]></category>
		<category><![CDATA[مقالات]]></category>
		<guid isPermaLink="false">https://hamravesh.com/blog/?p=3807</guid>

					<description><![CDATA[<p>ChatOps رویکردی است که با ترکیب ابزارهای چت و اتوماسیون، امکان همکاری و ارتباط بهینه را فراهم می‌کند.</p>
<p>The post <a href="https://hamravesh.com/blog/what-is-chatops/">ChatOps چیست؟ راهنمای کامل و جامع برای درک مفهوم ChatOps یا چت عملیاتی</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">با افزایش نیاز به همکاری و اتوماسیون در تیم‌های فناوری اطلاعات، مفهومی به نام ChatOps به میان آمده است. اما ChatOps یا <strong>چت عملیاتی</strong> چیست و چگونه می‌تواند به بهبود فرآیندهای سازمانی کمک کند؟ در این مطلب از وبلاگ هم‌روش به بررسی کامل ChatOps می‌پردازیم.</p>



<p class="wp-block-paragraph">در دنیای فناوری اطلاعات و توسعه نرم‌افزار، همکاری موثر بین اعضای تیم از اهمیت بالایی برخوردار است. <strong>ChatOps</strong> رویکردی است که با ترکیب ابزارهای چت و اتوماسیون، امکان همکاری و ارتباط بهینه را فراهم می‌کند.</p>



<p class="wp-block-paragraph">مفهوم <strong>ChatOps</strong> برای اولین بار توسط <strong><a href="https://github.blog/engineering/infrastructure/using-chatops-to-help-actions-on-call-engineers/" target="_blank" rel="noreferrer noopener">GitHub</a></strong> معرفی شد، جایی که تیم‌های توسعه از ربات‌های چت برای اتوماسیون وظایف روزمره استفاده کردند. این رویکرد به سرعت در بین سازمان‌های دیگر محبوب شد و به یکی از روش‌های استاندارد همکاری تبدیل گردید.</p>



<h3 class="wp-block-heading" id="h-chatops-چگونه-کار-می-کند">ChatOps چگونه کار می‌کند؟</h3>



<figure class="wp-block-image size-full"><img loading="lazy" decoding="async" width="832" height="467" src="https://hamravesh.com/blog/wp-content/uploads/2024/10/chatops-work.webp" alt="ChatOps چگونه کار می‌کند؟" class="wp-image-3808" srcset="https://hamravesh.com/blog/wp-content/uploads/2024/10/chatops-work.webp 832w, https://hamravesh.com/blog/wp-content/uploads/2024/10/chatops-work-300x168.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2024/10/chatops-work-768x431.webp 768w" sizes="auto, (max-width: 832px) 100vw, 832px" /></figure>



<p class="wp-block-paragraph">در ChatOps، روند اصلی به این شکل است که تیم‌ها و سیستم‌ها با یکدیگر از طریق چت به‌طور مستقیم در ارتباط هستند. این سیستم به صورت بلادرنگ اطلاعات را تبادل می‌کند و از خودکارسازی برای ساده‌سازی فرآیندها بهره می‌برد. برای اینکه بهتر متوجه این روند شویم، موضوعات زیر را در نظر بگیرید:</p>



<p class="wp-block-paragraph"><strong>همکاری و شفافیت</strong>: تمام تعاملات و عملیات انجام شده در بستر چت قابل مشاهده برای همه اعضای تیم است. این باعث می‌شود که تمامی اعضا در جریان کارها و وضعیت سیستم‌ها باشند. همچنین، با توجه به اینکه تمام دستورات و خروجی‌ها در محیط چت ثبت می‌شود، تاریخچه‌ی کاملی از فعالیت‌ها در دسترس است که به تجزیه و تحلیل و بهبود فرآیندها کمک می‌کند.</p>



<p class="wp-block-paragraph"><strong>تعامل در یک بستر چت</strong>: تیم‌ها در یک محیط چت حضور دارند. این محیط می‌تواند شامل اعضای تیم‌های توسعه، عملیات، و حتی امنیت باشد. در اینجا، افراد از طریق پیام‌های چت می‌توانند با هم تعامل داشته باشند و با ابزارهای مختلف نیز ارتباط برقرار کنند.</p>



<p class="wp-block-paragraph"><strong>ربات‌های ChatOps</strong>: در این سیستم، ربات‌ها نقش اصلی را ایفا می‌کنند. این ربات‌ها به پلتفرم چت متصل می‌شوند و به‌گونه‌ای پیکربندی شده‌اند که دستورات یا کوئری‌های کاربران را دریافت کرده و بر اساس آن‌ها اقدام کنند. به عنوان مثال، اگر یک توسعه‌دهنده بخواهد کدی را دیپلوی کند، می‌تواند با ارسال دستور متنی به ربات این کار را انجام دهد. ربات دستور را می‌گیرد و دیپلوی را انجام می‌دهد.</p>



<p class="wp-block-paragraph"><strong>اتصال به ابزارهای مختلف</strong>: ربات ChatOps با استفاده از APIها و پلاگین‌ها به ابزارها و سیستم‌های مختلف متصل می‌شود. این ابزارها می‌توانند شامل ابزارهای مانیتورینگ (مانند Grafana یا <strong><a href="https://hamravesh.com/blog/what-is-prometheus/">Prometheus</a></strong>)، سیستم‌های کنترل ورژن (مانند GitLab یا GitHub)، سرویس‌های ابری (مانند AWS یا Azure)، و حتی دیتابیس‌ها و سیستم‌های CI/CD باشند. با این اتصالات، ربات قادر است اطلاعات و عملیات مختلف را از ابزارها دریافت و به کاربران ارائه دهد.</p>



<p class="wp-block-paragraph"><strong>اجرای خودکار عملیات</strong>: یکی از مزایای اصلی ChatOps این است که بسیاری از عملیات به صورت خودکار و بدون نیاز به دخالت دستی انجام می‌شود. به عنوان مثال، اگر ربات تشخیص دهد که سیستمی دچار مشکل شده، می‌تواند به‌صورت خودکار اقدامات مورد نیاز مانند راه‌اندازی مجدد سرویس یا اطلاع‌رسانی به تیم‌های مربوطه را انجام دهد.</p>



<h2 class="wp-block-heading" id="h-مزایای-استفاده-از-chatops">مزایای استفاده از ChatOps</h2>



<ul class="wp-block-list">
<li><strong>افزایش بهره‌وری</strong>: با اتوماسیون وظایف تکراری، زمان صرف شده برای انجام آن‌ها کاهش می‌یابد.</li>



<li><strong>بهبود همکاری تیمی</strong>: اطلاعات و فعالیت‌ها به صورت شفاف در دسترس همه اعضای تیم قرار می‌گیرد.</li>



<li><strong>کاهش خطاهای انسانی</strong>: اتوماسیون فرآیندها منجر به کاهش خطاهای ناشی از ورود دستی داده‌ها می‌شود.</li>



<li><strong>واکنش سریع به رویدادها</strong>: امکان مانیتورینگ و واکنش سریع به مشکلات و رویدادها فراهم می‌شود.</li>
</ul>



<h2 class="wp-block-heading" id="h-ابزارها-و-پلتفرم-های-کلیدی-در-chatops">ابزارها و پلتفرم‌های کلیدی در ChatOps</h2>



<ul class="wp-block-list">
<li><a href="https://docs.hamravesh.com/darkube/create/1click/RocketChat/" target="_blank" rel="noreferrer noopener"><strong>Rocket.Chat</strong>:</a> راکت‌چت پروژه چت گروهی متن‌بازی است که امروزه میان افراد و سازمان‌ها محبوبیت قابل‌توجهی پیدا کرده‌است. هدف پدید‌آورنده‌ آن ایجاد معادل متن‌باز مجانی برای نرم‌افزار محبوب Slack بوده‌ است.</li>



<li><strong>Slack</strong>: یکی از محبوب‌ترین پلتفرم‌های چت که با ربات‌ها و ابزارهای مختلف یکپارچه می‌شود.</li>



<li><strong>Microsoft Teams</strong>: پلتفرمی قدرتمند برای همکاری تیمی با امکان ادغام با ابزارهای اتوماسیون.</li>



<li><strong>Hubot</strong>: ربات چتی که توسط GitHub توسعه یافته و قابل سفارشی‌سازی است.</li>



<li><strong>Mattermost</strong>: پلتفرم متن‌باز برای چت سازمانی با قابلیت‌های ChatOps.</li>
</ul>



<h2 class="wp-block-heading" id="h-پیاده-سازی-chatops-در-سازمان-شما">پیاده‌سازی ChatOps در سازمان شما</h2>



<p class="wp-block-paragraph">برای شروع با <strong>ChatOps</strong>، مراحل زیر را می‌توانید دنبال کنید:</p>



<ol class="wp-block-list">
<li><strong>انتخاب پلتفرم چت مناسب</strong>: بر اساس نیازهای سازمان، پلتفرمی مانند Slack یا Microsoft Teams را انتخاب کنید.</li>



<li><strong>انتخاب ربات و ابزارهای اتوماسیون</strong>: رباتی مانند Hubot را برای یکپارچه‌سازی با پلتفرم چت انتخاب کنید.</li>



<li><strong>تعریف فرآیندها و وظایف قابل اتوماسیون</strong>: تعیین کنید که کدام وظایف می‌توانند اتوماسیون شوند.</li>



<li><strong>آموزش تیم</strong>: اعضای تیم را با روش‌های استفاده از ChatOps آشنا کنید.</li>



<li><strong>نظارت و بهبود مستمر</strong>: عملکرد سیستم را مانیتور کرده و بهبودهای لازم را اعمال کنید.</li>
</ol>



<h2 class="wp-block-heading" id="h-چالش-ها-و-ملاحظات">چالش‌ها و ملاحظات</h2>



<ul class="wp-block-list">
<li><strong>امنیت</strong>: اطمینان حاصل کنید که دسترسی‌ها و مجوزها به درستی تنظیم شده‌اند تا از سوءاستفاده جلوگیری شود.</li>



<li><strong>پذیرش فرهنگی</strong>: ممکن است برخی از اعضای تیم در ابتدا با تغییرات مخالفت کنند؛ بنابراین آموزش و تشویق آن‌ها مهم است.</li>



<li><strong>پیچیدگی فنی</strong>: پیاده‌سازی ChatOps ممکن است نیاز به تخصص فنی داشته باشد.</li>
</ul>



<h2 class="wp-block-heading" id="h-بهترین-روش-ها-برای-پیاده-سازی-chatops">بهترین روش‌ها برای پیاده‌سازی ChatOps</h2>



<ul class="wp-block-list">
<li><strong>شروع کوچک</strong>: ابتدا با اتوماسیون وظایف ساده شروع کنید و سپس به موارد پیچیده‌تر بپردازید.</li>



<li><strong>مستندسازی</strong>: تمام فرآیندها و دستورات را به صورت مستند نگه دارید.</li>



<li><strong>بازخورد مستمر</strong>: از اعضای تیم بازخورد بگیرید و سیستم را بهبود دهید.</li>



<li><strong>امنیت را جدی بگیرید</strong>: همیشه به مسائل امنیتی توجه داشته باشید و اقدامات لازم را انجام دهید.</li>
</ul>



<h2 class="wp-block-heading" id="h-در-پایان">در پایان</h2>



<p class="wp-block-paragraph"><strong>ChatOps</strong> رویکردی نوین است که می‌تواند به بهبود همکاری، افزایش بهره‌وری و تسریع فرآیندهای سازمانی کمک کند. با پیاده‌سازی صحیح و توجه به بهترین روش‌ها، سازمان‌ها می‌توانند از مزایای فراوان آن بهره‌مند شوند.</p>



<p class="wp-block-paragraph">اگر در پیاده‌سازی ابزارهای چت به مشکل برخورده‌اید می‌توانید به‌راحتی با استفاده از کنسول هم‌روش، یک اپلیکیشن <a href="https://docs.hamravesh.com/darkube/create/1click/RocketChat/" target="_blank" rel="noreferrer noopener"><strong>Rocket.Chat</strong></a> را تنها با چند کلیک برای سازمان و یا گروه خود پیاده‌سازی کنید. </p>
<p>The post <a href="https://hamravesh.com/blog/what-is-chatops/">ChatOps چیست؟ راهنمای کامل و جامع برای درک مفهوم ChatOps یا چت عملیاتی</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/what-is-chatops/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>CI/CD چیست؟ راهنمای جامع مفاهیم، کاربردها و مزایا</title>
		<link>https://hamravesh.com/blog/what-is-ci-cd/</link>
					<comments>https://hamravesh.com/blog/what-is-ci-cd/#respond</comments>
		
		<dc:creator><![CDATA[هم‌روش]]></dc:creator>
		<pubDate>Mon, 21 Oct 2024 08:16:57 +0000</pubDate>
				<category><![CDATA[دواپس]]></category>
		<category><![CDATA[مقالات]]></category>
		<guid isPermaLink="false">https://blog.hamravesh.com/blog/?p=453</guid>

					<description><![CDATA[<p>یکپارچه‌سازی مداوم و تحویل پیوسته یا CI/CD رویکردی مدرن در فرایند توسعه نرم‌افزار است که مزایای متعددی نسبت به مدل‌های سنتی مانند مدل آبشاری دارد. </p>
<p>The post <a href="https://hamravesh.com/blog/what-is-ci-cd/">CI/CD چیست؟ راهنمای جامع مفاهیم، کاربردها و مزایا</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph"><span style="font-weight: 400;">یکپارچه‌سازی مداوم و تحویل پیوسته (CI/CD) رویکرد نسبتا تازه‌ای در روش توسعه نرم‌افزار است که هدف اصلی آن بالا بردن سرعت ساخت نرم‌افزار و بهبود کارایی آن به‌صورت هم‌زمان است. بخش‌های اصلی این مدل، شامل یکپارچه‌سازی مداوم کدها، انجام تست‌ها به‌صورت خودکار و در ادامه توسعه مستمر نرم‌افزار در فرآیند ساخت تا لحظه تحویل به مشتری است.</span></p>



<h2 class="wp-block-heading" id="h-مدل-آبشاری-و-مشکلات-آن"><strong>مدل آبشاری و مشکلات آن</strong></h2>



<p class="wp-block-paragraph"><span style="font-weight: 400;">پیش از ایجاد CI/CD، مدل عام و رایج برای توسعه نرم‌افزارهای مختلف، «<strong><a href="https://hamravesh.com/blog/waterfall-development-methodology/">مدل آبشاری</a></strong>» بود. در مدل آبشاری، هر کدام از توسعه‌دهندگان نرم‌افزار در محیط ایزوله خود، به‌تنهایی کار می‌کردند. در این حالت، هر مرحله از نرم‌افزار به‌صورت مجزا ساخته شده و پس از اتمام، ساخت مرحله بعدی شروع می‌شد. در این روش قدیمی، معمولا توسعه و ساخت نرم‌افزار شامل مراحل مختلفی مثل جمع‌آوری نیازمندی‌ها، طراحی نرم‌افزار، کدنویسی، اجرای تست‌های مختلف و در نهایت اجرا و ساخت نرم‌افزار بود. در مدل آبشاری گاهی چند هفته زمان می‌برد تا یک فیچر توسعه پیدا کند و به دست مشتری برسد.&nbsp;</span></p>


<div class="wp-block-image">
<figure class="aligncenter size-large"><img loading="lazy" decoding="async" width="1024" height="482" src="https://hamravesh.com/blog/wp-content/uploads/2024/10/waterfal-model-1024x482.webp" alt="مدل آبشاری در توسعه نرم افزار" class="wp-image-3879" srcset="https://hamravesh.com/blog/wp-content/uploads/2024/10/waterfal-model-1024x482.webp 1024w, https://hamravesh.com/blog/wp-content/uploads/2024/10/waterfal-model-300x141.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2024/10/waterfal-model-768x362.webp 768w, https://hamravesh.com/blog/wp-content/uploads/2024/10/waterfal-model-1536x724.webp 1536w, https://hamravesh.com/blog/wp-content/uploads/2024/10/waterfal-model-2048x965.webp 2048w" sizes="auto, (max-width: 1024px) 100vw, 1024px" /></figure>
</div>


<p class="wp-block-paragraph"><span style="font-weight: 400;"></span><span style="font-weight: 400;">مدل آبشاری معایب مختلفی داشت که چند مورد از مهم‌ترین آن‌ها شامل موارد زیر هستند:</span></p>



<ul class="wp-block-list">
<li><b>اجرای کند مراحل مختلف</b><span style="font-weight: 400;">: از آن‌جا که در این مدل، مراحل باید به‌نوبت و پشت سر هم اجرا می‌شدند، سرعت انتشار مراحل مختلف نرم‌افزار کمتر می‌شد و پاسخ‌گویی به نیاز کاربر و ایجاد تغییرات مختلف بر اساس نیازهای او، بسیار سخت‌تر بود.</span></li>



<li><b>نرخ شکست بالا</b><span style="font-weight: 400;">: در مدل آبشاری، احتمال به‌نتیجه نرسیدن نرم‌افزار و شکست پروژه، به دلیل نبود تست‌های خودکار، بسیار بیشتر بود. در واقع همه توسعه‌دهنده‌ها باید به‌صورت دستی، کدها را تست می‌کردند و این موضوع، احتمال وقوع خطا و ایجاد باگ در نرم‌افزار را افزایش می‌داد.</span></li>



<li><b>همکاری محدود</b><span style="font-weight: 400;">: امکان هماهنگی و همکاری بین بخش‌های مختلف پروژه مثل بخش توسعه‌دهنده‌ها، تست‌کنندگان و سهام‌داران، در مدل آبشاری بسیار کم و محدود بود و به همین دلیل، یافتن خطا و رفع خطاهای موجود به یک کار بسیار پیچیده و سخت تبدیل می‌شد.</span></li>



<li><b>هزینه بالا</b><span style="font-weight: 400;">: حالت سنتی و دستی توسعه نرم‌افزار، هزینه بالایی داشت و بخش عمده بودجه به بخش تست، یافتن باگ‌ها و رفع خطا تعلق می‌گرفت.</span></li>



<li><b>کاهش سرعت و چابکی</b><span style="font-weight: 400;">: روش قبلی توسعه نرم‌افزار کاملا خطی بود و به همین دلیل، امکان ایجاد تغییر سریع در نرم‌افزار و یا پاسخ‌گویی به نیازهای جدید کاربر وجود نداشت.</span></li>
</ul>



<figure class="wp-block-gallery aligncenter has-nested-images columns-default is-cropped wp-block-gallery-1 is-layout-flex wp-block-gallery-is-layout-flex">
<figure class="wp-block-image size-large"><img loading="lazy" decoding="async" width="1024" height="482" data-id="3881" src="https://hamravesh.com/blog/wp-content/uploads/2024/10/waterfall-downside-1024x482.webp" alt="معایب مدل آبشاری" class="wp-image-3881" srcset="https://hamravesh.com/blog/wp-content/uploads/2024/10/waterfall-downside-1024x482.webp 1024w, https://hamravesh.com/blog/wp-content/uploads/2024/10/waterfall-downside-300x141.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2024/10/waterfall-downside-768x362.webp 768w, https://hamravesh.com/blog/wp-content/uploads/2024/10/waterfall-downside-1536x724.webp 1536w, https://hamravesh.com/blog/wp-content/uploads/2024/10/waterfall-downside-2048x965.webp 2048w" sizes="auto, (max-width: 1024px) 100vw, 1024px" /></figure>
</figure>



<h2 class="wp-block-heading" id="h-ci-cd-چیست"><strong>CI/CD چیست؟</strong></h2>



<p class="wp-block-paragraph"><span style="font-weight: 400;">حالا و با این توضیحات اولیه، این سوال مهم ایجاد می‌شود که یکپارچه سازی مداوم یا همان CI و تحویل پیوسته یا همان CD به چه معنا است؟ در توضیح این دو باید بگوییم که به‌صورت کلی CI/CD، روشی از توسعه نرم‌افزار است که با استفاده از آن، ساخت بخش‌های جدید نرم‌افزار و به‌روزرسانی‌های آن در هر زمان از مراحل ساخت و انتشار، به‌صورت کاملا قابل اطمینان و بدون آسیب‌زدن به بخش‌های دیگر، قابل انجام است. وقتی در بخش کدنویسی، تغییرات به‌صورت مستمر اتفاق می‌افتند، چرخه‌های توسعه نرم‌افزار هم به‌صورت مداوم و سریع‌تری منتشر شده و به مرحله اجرا می‌رسند.</span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">اصطلاح «CI/CD» ترکیبی از مخفف دو عبارت اصلی این مدل یعنی یکپارچه سازی مداوم یا Continuous Integration (CI) و تحویل پیوسته یا همان Continuous Delivery (CD) است. </span><span style="font-weight: 400;">اصطلاح CI/CD علاوه بر معنای لغوی خود، نشان‌دهنده یک فرهنگ سازمانی و اصول اجرایی است. در زمان استفاده از CI/CD، تمام اعضای تیم توسعه عادت می‌کنند که همه تغییرات انجام‌شده روی </span><span style="font-weight: 400;">کدهای خود را در بازه‌های زمانی کوتاه‌تر و به شکل پایدارتری روی سرور اصلی ثبت کنند.</span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">برای انواع تیم‌های اجرایی و عملیاتی (DevOps) و البته متدولوژی چابک، روش CI/CD بهترین رویکرد عملی است. در CI/CD دو فرآیند مهم یکپارچه‌سازی و اجرای نرم‌افزار به‌صورت اتوماتیک انجام می‌شود و تیم‌های توسعه نرم‌افزار با خیال راحت می‌توانند نیازمندی‌های سازمان را در نظر گرفته و نرم‌افزارهایی باکیفیت و امنیت بالا طراحی و تولید کنند.</span></p>



<p class="wp-block-paragraph">برای استفاده از قابلیت‌های CI/CD در کنسول هم‌روش می‌توانید&nbsp;<strong><a href="https://docs.hamravesh.com/darkube/ci-cd/github-actions/" target="_blank" rel="noreferrer noopener">راهنمای استفاده از Github Actions</a>&nbsp;</strong>در مستندات هم‌روش را مطالعه کنید.</p>



<h2 class="wp-block-heading" id="h-عملکرد-ci-cd-چگونه-است"><strong>عملکرد CI/CD چگونه است؟</strong></h2>



<p class="wp-block-paragraph"><span style="font-weight: 400;">به‌صورت کلی باید بگوییم که CI/CD یک فرآیند خودکار است که سه فعالیت اصلی یعنی یکپارچه‌سازی و هماهنگی کدها را انجام می‌دهد، تست‌ها را به‌صورت خودکار اجرا کرده و تغییرات ادامه‌دار انجام‌شده در فرآیند توسعه نرم‌افزار تا لحظه رسیدن به تحویل نهایی محصول را برعهده می‌گیرد. اجازه دهید که این سه گام را کمی بیشتر توضیح دهیم:</span></p>



<h3 class="wp-block-heading" id="h-یکپارچه-سازی-کدها">یکپارچه‌سازی کدها</h3>



<p class="wp-block-paragraph"><span style="font-weight: 400;">اولین بخش در فرآیند CI/CD، مرحله یکپارچه کردن کدها است. در این گام، هر کدام از توسعه‌دهنده‌های نرم‌افزار، کدهای خود را در یک سرور یا همان ریپازیتوری مثل گیت‌هاب، گیت‌لب یا بیت‌باکت، ثبت (Commit) می‌کنند. در این‌جا، همه کدهای ثبت‌شده توسط کاربران مختلف پروژه، با هم ترکیب شده و در یک پایگاه داده مرکزی، به‌صورت هماهنگ و یکپارچه قرار می‌گیرند.</span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">هدف اصلی این کار، تضمین وجود یکپارچگی در بین بخش‌های مختلف کد است. در واقع با این کار، فرآیند به شکل پایداری انجام شده و این اطمینان حاصل می‌شود که کدهای جدید، باعث تخریب بخش‌های قبلی نشده و هماهنگی میان اجزای مختلف را از بین نمی‌برند.</span></p>



<h3 class="wp-block-heading" id="h-تست-خودکار">تست خودکار</h3>



<p class="wp-block-paragraph"><span style="font-weight: 400;">به‌محض اینکه کدها با هم ترکیب و ادغام شدند، مرحله بعدی یعنی انجام خودکار تست‌ها شروع می‌شود. این مرحله شامل اجرای چند مرحله ارزیابی و تست است که از طریق این تست‌ها، این اطمینان ایجاد شود که تغییرات انجام شده در بخش قبلی، کارایی لازم را داشته باشد، کیفیت کدها در حد استاندارد تعریف شده باشد و از همه مهم‌تر اینکه کدها بدون خطا، اجرا شوند. این گام باعث می‌شود که خطاهای موجود در بخش‌های مختلف کدنویسی، قبل از اجرای نهایی و در همین مراحل اولیه توسعه مشخص شوند تا به‌راحتی بتوان آن‌ها را رفع کرد.</span></p>



<h3 class="wp-block-heading" id="h-استقرار-پیوسته">استقرار پیوسته</h3>



<p class="wp-block-paragraph"><span style="font-weight: 400;">بعد از اینکه تغییرات انجام شده بر روی کدها، از مرحله قبلی هم با موفقیت عبور کرد، به مرحله نهایی و به مرحله «استقرار پیوسته» می‌رسد. در این گام، همه تغییرات و کدهای جدید به‌صورت خودکار به محیط اصلی نرم‌افزار افزوده شده و برای تست‌های بیشتر آماده می‌شوند. </span><span style="font-weight: 400;">اجرای این مرحله، این تضمین را ایجاد می‌کند که نرم‌افزار به‌صورت مداوم با آخرین کدهای نوشته شده به‌روز می‌شود و بخش‌های کاربردی هم به‌سرعت و با قابلیت اطمینان بالا به دست کاربران می‌رسند.</span></p>



<h3 class="wp-block-heading" id="h-استقرار-در-production">استقرار در Production</h3>



<p class="wp-block-paragraph"><span style="font-weight: 400;">آخرین مرحله از روش CI/CD، بخش <a href="https://hamravesh.com/blog/production-development-staging/#:~:text=%D9%85%D8%AD%D8%B5%D9%88%D9%84%20%D9%86%D9%87%D8%A7%DB%8C%DB%8C%20%DB%8C%D8%A7-,Production,-%D9%85%D8%AD%DB%8C%D8%B7%20%D9%85%D8%AD%D8%B5%D9%88%D9%84%20%D9%86%D9%87%D8%A7%DB%8C%DB%8C"><strong>Production Deployment</strong></a> است. در این مرحله، همه تغییرات نرم‌افزار به دست کاربر نهایی می‌رسد. این مرحله هم شامل بخش‌های مختلفی مثل نظارت بر محیط اجرای نرم‌افزار، اطمینان یافتن از اجرای راحت و بدون خطای آن و یافتن و رفع خطاهای احتمالی در بخش‌های گوناگون است.</span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">چهار گام روش CI/CD در کنار هم فعالیت کرده و تضمین می‌کنند که همه تغییرات نرم‌افزار با هم یکپارچه شده، تست می‌شوند و به‌صورت کاملاً خودکار و بدون دخالت عوامل انسانی، در محیط نهایی نرم‌افزار اجرا شده و ثبت می‌شوند. این فرآیند خودکار باعث کاهش خطا خواهد شد، میزان کارایی را افزایش داده و باعث بهبود کلی کیفیت نرم‌افزار می‌شود.</span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">با توجه به همه این مزایا، می‌توان گفت که با استفاده از روش CI/CD، تیم‌های توسعه نرم‌افزار می‌توانند خیلی سریع‌تر مراحل مختلف و چرخه‌های نرم‌افزار را منتشر کنند، احتمال وجود خطاهای داخلی نرم‌افزار را کاهش دهند و تجربه بسیار بهتری در اختیار کاربران نهایی بگذارند.</span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">البته توجه کنید که این مراحل در فرآیند CI/CD در پروژه‌های مختلف یا حتی در پروژه‌های مشابه ولی در سازمان‌های مختلف، می‌توانند متفاوت باشند. برای مثال، شاید در بعضی تیم‌ها از تست‌های خودکار استفاده نکنند، در برخی تیم‌ها همه این مراحل چهارگانه را داشته باشند یا اصلا از این مرحله‌بندی‌ها استفاده نکنند. پس این روش توسعه نرم‌افزار، در هر محیط می‌تواند شکل تازه‌ای به خود بگیرد و در همه‌جا، دقیقا به یک شکل اجرا نمی‌شود.</span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">با وجود این، دو بخش مهم و کلیدی CI/CD، دو عامل یکپارچه‌سازی و Deployment هستند. بنابراین برای اینکه بگوییم یک تیم یا نرم‌افزار از روشCI/CD استفاده کرده‌اند، باید حتما کدها به‌صورت مستمر و مداوم، در یک ریپازیتوری راه دور ثبت شده و این کدها باید به‌صورت دائم و پس از هر یکپارچه‌سازی، در محیط اصلی اجرا شده باشند. حالا و پس از این توضیحات، یک سوال مهم دیگر هم ایجاد می‌شود:</span></p>



<h2 class="wp-block-heading" id="h-تفاوت-میان-ci-و-cd-چیست"><strong class="global-rtl">تفاوت میان CI</strong><strong> و </strong><strong class="global-rtl">CD چیست؟</strong></h2>



<p class="wp-block-paragraph"><span style="font-weight: 400;">یکپارچه‌سازی مداوم یا همان CI، شامل این بخش بسیار ساده و در عین حال خیلی مهم است که هر توسعه‌دهنده پس از ایجاد هر تغییر خیلی کوچک و جزئی در کدهای خود، تغییرات انجام شده را به کدهای اصلی اضافه کند. با توجه به حجم نیازمندی‌های این کار و تعداد گام‌هایی که در این حالت ایجاد می‌شوند، فرآیند یکپارچه‌سازی مداوم در مدل CI باعث می‌شود که تیم‌ها با خیال راحت کارهای ساخت، تست و جمع‌بندی نرم‌افزارهای خود را به‌صورت مستمر و به شکلی کاملا تضمین شده و اتوماتیک، انجام دهند.</span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">CI به ساده‌شدن فرآیند تغییر کدها کمک می‌کند و به همین خاطر، توسعه‌دهنده‌ها با خیال راحت، می‌توانند زمان خود را به بهبود کیفیت نرم‌افزار و ایجاد تغییرات بیشتر، اختصاص دهند.</span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">حالا و بعد از این توضیحات، باید بدانیم که تحویل پیوسته یا همان CD دقیقا شامل چه چیزهایی می‌شود. تحویل پیوسته فرآیندی است که از طریق آن، کدهای کامل‌شده به‌صورت کاملا خودکار به محیط‌های مختلف مثل بخش تست یا توسعه، تحویل داده می‌شوند. در واقع CD یک فرآیند مستمر و کاملا خودکار فراهم می‌کند که کدها به هر کدام از محیط‌های تست و توسعه برسند.</span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">«استقرار پیوسته»، مرحله بعد از تحویل پیوسته است. هر تغییری که با موفقیت از بخش تست‌های خودکار گذر کند، به‌صورت اتوماتیک در بخش اجرایی نرم‌افزار جای‌گذاری خواهد شد و این فرآیند پیوسته و همیشگی، استقرار پیوسته را به وجود می‌آورد. سازمان‌هایی که تحت نظارت رگولاتوری یا دیگر سازمان‌های کنترل کیفی نیستند، باید تحویل پیوسته را به‌عنوان هدف اصلی و مهم سازمان خود در نظر بگیرند.</span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">به‌صورت ساده و خلاصه باید بگوییم که CI مجموعه فعالیت‌هایی است که توسعه دهندگان در زمان نوشتن کدها، آن‌ها را انجام می‌دهند و CD، مجوعه فعالیت‌هایی است که بعد از اینکه کد کامل شد، به‌صورت خودکار اجرا خواهند شد.</span></p>



<figure class="wp-block-image size-large"><img loading="lazy" decoding="async" width="1024" height="482" src="https://hamravesh.com/blog/wp-content/uploads/2024/10/CI-CD-Pipeline-1024x482.webp" alt="پایپ لاین CI/CD" class="wp-image-3882" srcset="https://hamravesh.com/blog/wp-content/uploads/2024/10/CI-CD-Pipeline-1024x482.webp 1024w, https://hamravesh.com/blog/wp-content/uploads/2024/10/CI-CD-Pipeline-300x141.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2024/10/CI-CD-Pipeline-768x362.webp 768w, https://hamravesh.com/blog/wp-content/uploads/2024/10/CI-CD-Pipeline-1536x724.webp 1536w, https://hamravesh.com/blog/wp-content/uploads/2024/10/CI-CD-Pipeline-2048x965.webp 2048w" sizes="auto, (max-width: 1024px) 100vw, 1024px" /></figure>



<h2 class="wp-block-heading" id="h-پایپ-لاین-ci-cd-چیست"><strong>پایپ‌لاین CI/CD چیست؟</strong></h2>



<p class="wp-block-paragraph"><span style="font-weight: 400;">یک پایپ‌لاین CI/CD، فرآیند تحویل نرم‌افزارتان را به‌صورت اتوماتیک اجرا می‌کند. پایپ‌لاین کدها را می‌سازد و تست‌ها را اجرا می‌کند (CI)، و به‌صورت کاملا امن یک نسخه جدیدی از اپلیکیشن را منتشر می‌کند (CD).</span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">پایپ‌لاین‌های خودکار می‌توانند خطاهای انسانی را از بین ببرند، چرخه‌های بازخورد استانداردشده در اختیار توسعه‌دهندگان بگذارند و فرآیند مداوم بررسی کیفیت محصول را سرعت ببخشند.</span></p>



<h2 class="wp-block-heading" id="h-مزایای-ci-cd-چیست"><strong>مزایای CI/CD چیست؟</strong></h2>



<p class="wp-block-paragraph"><span style="font-weight: 400;">به‌صورت کلی، CI/CD این مزایا را دارد:</span></p>



<ul class="wp-block-list">
<li><span style="font-weight: 400;">تست‌های خودکار، امکان تحویل پیوسته را فراهم می‌کند که با وجود این قابلیت فوق‌العاده، کیفیت بالای نرم‌افزار، امنیت و افزایش سوددهی کدها در مسیر تولید، تضمین می‌شوند.</span></li>



<li><span style="font-weight: 400;">پایپ‌لاین‌های CI/CD باعث معرفی و بازاریابی بسیار سریع‌تر محصولات جدید شده، تجربه بسیار بهتری در اختیار کاربران نهایی می‌گذارد و بخش مهمی از فشار کاری بر دوش توسعه‌دهنده را از بین می‌برد.</span></li>



<li><span style="font-weight: 400;">افزایش فوق‌العاده سرعت ساخت با استفاده از پایپ‌لاین CI/CD، سرعت تحویل محصول به مشتری را افزایش داده و قابلیت‌های رقابتی سازمان‌ها را نیز بهبود می‌بخشد.</span></li>



<li><span style="font-weight: 400;">اتوماتیک‌بودن بخش اعظم کارها باعث می‌شود که اعضای تیم توسعه‌دهنده، زمان بیشتری در اختیار داشته باشند و این زمان را به ساخت قابلیت‌های متنوع و کدنویسی اختصاص دهند.</span></li>



<li><span style="font-weight: 400;">سازمان‌های دارای پایپ‌لاین CI/CD موفق، می‌توانند نیروهای بااستعداد و آماده‌ای را جذب کنند. با دور شدن سازمان‌ها از مدل سنتی آبشاری، مهندس‌ها و توسعه‌دهنده‌ها، دیگر درگیر فعالیت‌های تکراری که غالبا اتمام آن به تمام‌شدن دیگر بخش‌های بستگی دارد، نشده و می‌توانند به‌سرعت پیشرفت کنند.</span></li>
</ul>



<h2 class="wp-block-heading" id="h-ci-cd-و-دواپس"><strong>CI/CD و دواپس</strong></h2>



<p class="wp-block-paragraph"><span style="font-weight: 400;"><a href="https://hamravesh.com/blog/what-is-devops/">DevOps</a> مجموعه‌ای از فعالیت‌ها است که هدف آن این است که به سازمان‌ها کمک کند تا بتوانند سریع‌تر از حالت سنتی، نرم‌افزارها و سرویس‌های مختلف را تولید کنند. سازمان‌ها پس از استفاده از دواپس، می‌توانند خیلی سریع‌تر و بهتر به مشتریان خود سرویس داده و بهتر از همیشه در بازار رقابتی فعالیت کنند. در محیط DevOps، سازمان‌های موفق در همه فازهای فعالیت خود، امنیت را در هر کدام از چرخه‌های حیات توسعه نرم‌افزار در نظر می‌گیرند و به این روش کاری آن‌ها، DevSecOps می‌گویند.</span><span style="font-weight: 400;"></span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">نکته کلیدی <strong><a href="https://hamravesh.com/blog/what-is-devsecops/">DevSecOps</a></strong> این است که در همه فازهای ساخت نرم‌افزار، امنیت به‌صورت یکپارچه با سایر بخش‌ها ادغام می‌شود. با اجرای فعالیت‌های امنیتی در همان فازهای اولیه پس از ساخت هر بخش از نرم‌افزار و به‌صورت مستمر، سازمان‌ها می‌توانند با قابلیت اطمینان بالایی بخش‌های آسیب‌پذیر محصول خود را در سریع‌ترین زمان ممکن بیابند. به این شکل می‌توانند به‌سرعت تصمیم‌گیری کرده و میزان خطای نرم‌افزار خود را به شکل قابل توجهی کاهش دهند.</span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">بررسی امنیت نرم‌افزار در حالت‌های سنتی، تنها در زمان استقرار محصول نهایی انجام می‌شد. روش قدیمی در حال حاضر، قابلیت رقابت با رویکرد DevOps را ندارد و نمی‌تواند خود را با سرعت و چابکی این روش، مطابقت دهد.</span></p>



<p class="wp-block-paragraph"><span class="global-rtl" style="font-weight: 400;">در حال حاضر ابزارهای امنیتی باید به‌صورت کامل و دقیق در جریان کاری توسعه‌دهنده‌ها و پایپ‌لاین CI/CD ادغام شوند تا بتوانند با دوآپس هماهنگ شده و سرعت توسعه نرم‌افزار را کاهش ندهند.</span></p>



<p class="wp-block-paragraph"><span style="font-weight: 400;">پایپ‌لاین CI/CD یک بخش کوچک از فریم‌ورک DevOps/DevSecOps است. برای اجرای موفق پایپ‌لاین CI/CD، سازمان‌ها به ابزارهای مختلفی نیاز دارند تا با استفاده از آن ابزارها، بتوانند از ایجاد نقاط اصطکاک جلوگیری کرده و موانع مختلف در مسیر یکپارچه‌سازی و تحویل محصول نهایی را از بین ببرند. برای رسیدن به این هدف، تیم‌ها به زنجیره‌ای از ابزارها و تکنولوژی‌های مختلف نیاز دارند تا توسعه مبتنی بر همکاری و بدون موانع مختلف برای آن‌ها تسهیل شود و بتوانند به‌راحتی فرآیند توسعه را دنبال کنند.</span></p>



<h2 class="wp-block-heading" id="h-ابزارهای-ci-cd">ابزارهای CI/CD</h2>



<figure class="wp-block-image size-large"><img loading="lazy" decoding="async" width="1024" height="482" src="https://hamravesh.com/blog/wp-content/uploads/2024/10/CI-CD-Tools-1024x482.webp" alt="ابزارهای CI/CD" class="wp-image-3883" srcset="https://hamravesh.com/blog/wp-content/uploads/2024/10/CI-CD-Tools-1024x482.webp 1024w, https://hamravesh.com/blog/wp-content/uploads/2024/10/CI-CD-Tools-300x141.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2024/10/CI-CD-Tools-768x362.webp 768w, https://hamravesh.com/blog/wp-content/uploads/2024/10/CI-CD-Tools-1536x724.webp 1536w, https://hamravesh.com/blog/wp-content/uploads/2024/10/CI-CD-Tools-2048x965.webp 2048w" sizes="auto, (max-width: 1024px) 100vw, 1024px" /></figure>



<p class="wp-block-paragraph">برای پیاده‌سازی و استفاده بهینه از CI/CD ابزارهای مختلفی ساخته شده است. این ابزارها در خودکارسازی فرایندها، پیاده‌سازی درست پایپ‌لاین CI/CD، ادغام و یکپارچه‌سازی با ابزارهای مختلف و&#8230; به شما کمک می‌کنند. در ادامه ۳ مورد از محبوب‌ترین ابزارهای CI/CD معرفی شده است:</p>



<h3 class="wp-block-heading">۱. <strong>Jenkins</strong></h3>



<p class="wp-block-paragraph">Jenkins یکی از محبوب‌ترین ابزارهای CI/CD است که قابلیت اتوماسیون ساخت، تست و استقرار برنامه‌ها را فراهم می‌کند. این ابزار متن‌باز بوده و به راحتی قابل پیکربندی است و پلاگین‌های زیادی برای آن وجود دارد که می‌توان برای سفارشی‌سازی فرآیندها استفاده کرد.</p>



<p class="wp-block-paragraph"><strong>ویژگی‌ها:</strong></p>



<ul class="wp-block-list">
<li>متن‌باز و رایگان</li>



<li>دارای بیش از ۱۰۰۰ پلاگین برای انواع وظایف</li>



<li>قابل یکپارچه‌سازی با ابزارهای متنوع</li>
</ul>



<h3 class="wp-block-heading">۲. <strong>GitLab CI/CD</strong></h3>



<p class="wp-block-paragraph">GitLab شامل ابزارهای CI/CD به عنوان بخشی از پلتفرم خود است. با استفاده از GitLab CI، توسعه‌دهندگان می‌توانند کدهای خود را به سادگی و به صورت مداوم آزمایش، یکپارچه و استقرار دهند.</p>



<p class="wp-block-paragraph"><strong>ویژگی‌ها:</strong></p>



<ul class="wp-block-list">
<li>یکپارچه با GitLab (کنترل نسخه، مدیریت پروژه)</li>



<li>قابلیت پیاده‌سازی در محیط‌های مختلف (ابری، محلی)</li>



<li>پشتیبانی از pipeline‌های سفارشی</li>
</ul>



<h3 class="wp-block-heading">۳. <strong>CircleCI</strong></h3>



<p class="wp-block-paragraph">CircleCI یک ابزار اتوماسیون CI/CD قدرتمند است که به توسعه‌دهندگان کمک می‌کند تا فرآیندهای ساخت و تست خود را به صورت خودکار در زمان کم انجام دهند. این ابزار هم به صورت ابری و هم به صورت محلی در دسترس است.</p>



<p class="wp-block-paragraph"><strong>ویژگی‌ها:</strong></p>



<ul class="wp-block-list">
<li>سرعت بالا در اجرای pipeline‌ها</li>



<li>ادغام آسان با GitHub و Bitbucket</li>



<li>پشتیبانی از انواع زبان‌های برنامه‌نویسی</li>
</ul>



<p class="wp-block-paragraph">برای آشنایی با ابزارهای بیشتر می‌توانید مطلب «<strong><a href="https://hamravesh.com/blog/cicd-tools-for-kubernetes/">آشنایی با ۷ ابزار CI/CD در کوبرنتیز</a></strong>» را مطالعه کنید. </p>



<h2 class="wp-block-heading" id="h-جمع-بندی">جمع‌بندی</h2>



<p class="wp-block-paragraph">CI/CD یکی از رویکردهای مدرن در دنیای توسعه و استقرار نرم افزار بوده و بسیاری از شرکت‌های دنیا از این رویکرد برای ساخت محصولات‌شان استفاده می‌کنند. به همین دلیل در این مطلب از وبلاگ هم‌روش سعی کردیم تا شما را با چیستی CI/CD، عملکرد، مزایا و&#8230; آن آشنا شویم. حتما در آینده کاری خود روی یادگیری کامل CI/CD سرمایه‌گذاری کنید. </p>



<p class="wp-block-paragraph">برای استفاده از قابلیت‌های CI/CD در کنسول هم‌روش می‌توانید <strong><a href="https://docs.hamravesh.com/darkube/ci-cd/github-actions/" target="_blank" rel="noreferrer noopener">راهنمای استفاده از Github Actions</a> </strong>در مستندات هم‌روش را مطالعه کنید. </p>
<p>The post <a href="https://hamravesh.com/blog/what-is-ci-cd/">CI/CD چیست؟ راهنمای جامع مفاهیم، کاربردها و مزایا</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/what-is-ci-cd/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>قواعد مانیتورینگ در دنیای میکروسرویس‌ها</title>
		<link>https://hamravesh.com/blog/microservice-monitoring/</link>
					<comments>https://hamravesh.com/blog/microservice-monitoring/#respond</comments>
		
		<dc:creator><![CDATA[ارسطو عباسی]]></dc:creator>
		<pubDate>Mon, 14 Oct 2024 07:36:02 +0000</pubDate>
				<category><![CDATA[دواپس]]></category>
		<category><![CDATA[مقالات]]></category>
		<guid isPermaLink="false">https://hamravesh.com/blog/?p=3677</guid>

					<description><![CDATA[<p>قواعد اساسی مانیتورینگ نیاز به سازگاری با تکنولوژی‌های پایه‌ و تغییرات مداوم در دنیای میکروسرویس‌ها دارد. در این مطلب با این قواعد آشنا خواهیم شد. </p>
<p>The post <a href="https://hamravesh.com/blog/microservice-monitoring/">قواعد مانیتورینگ در دنیای میکروسرویس‌ها</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">یکی از اصلی‌ترین دلایل استفاده از معماری میکروسرویس‌، نیاز به افزایش سرعت در فرایند توسعه و تحویل محصولات نرم‌افزاری است. با استفاده از میکروسرویس، توسعه‌دهندگان می‌توانند ویژگی‌های جدید را با سرعت بیشتر و البته پایداری بهتری به کاربران تحویل دهند. اما یکی از چالش‌های این مسیر، ردگیری تغییرات و مانیتور کردن تمام سرویس‌ها در ساختار Microservices است.</p>



<p class="wp-block-paragraph">با در نظر گرفتن این موضوع، در این مطلب قصد داریم شما را با قواعدی آشنا کنیم که در زمینه مانیتورینگ میکروسرویس‌ها می‌توانند به شما کمک کنند. از آنجایی که افزایش تعداد سرویس‌ها، مدیریت، نگهداری و رفع خطای آن‌ها را سخت‌تر و پیچیده‌تر می‌کند، این قواعد می‌توانند به شما در انجام موارد گفته شده کمک بکنند.</p>



<h2 class="wp-block-heading" id="h-۱-کانتینرها-و-محتویات-آن-را-مانیتور-کنید">۱. کانتینرها و محتویات آن را مانیتور کنید</h2>



<p class="wp-block-paragraph">مانیتورینگ کانتینرها و محتویات آن‌ها در معماری میکروسرویس‌ها اهمیت بسیار بالایی دارد. در این نوع معماری، هر سرویس به طور مستقل در کانتینرهای جداگانه اجرا می‌شود و به همین دلیل، سیستم از بخش‌های کوچک و مستقل تشکیل شده که با یکدیگر تعامل می‌کنند. اهمیت مانیتورینگ کانتینرها در این معماری به دلایل زیر است:</p>



<ol class="wp-block-list">
<li><strong>اطمینان از عملکرد بهینه</strong>: با توجه به اینکه هر میکروسرویس به صورت جداگانه اجرا می‌شود، مانیتورینگ به شما کمک می‌کند عملکرد هر کانتینر را به‌طور مستقل بررسی کرده و مشکلات یا ناکارآمدی‌ها را شناسایی کنید. این باعث می‌شود مشکلات در هر سرویس زودتر شناسایی و رفع شوند.</li>



<li><strong>تضمین دسترس‌پذیری</strong>: میکروسرویس‌ها باید همیشه در دسترس باشند تا کل سیستم به درستی کار کند. مانیتورینگ منظم کانتینرها تضمین می‌کند که در صورت بروز مشکل در یکی از آن‌ها، سریعاً اقداماتی برای بازیابی یا جایگزینی انجام شود تا سرویس‌دهی قطع نشود.</li>



<li><strong>کشف مشکلات زودهنگام</strong>: مانیتورینگ به شما این امکان را می‌دهد که قبل از بروز مشکل جدی در عملکرد سیستم، علائم هشداردهنده مانند افزایش غیرعادی مصرف منابع، افت کارایی، یا مشکلات شبکه‌ای را تشخیص دهید.</li>



<li><strong>مدیریت منابع بهینه</strong>: کانتینرها منابع محدودی مانند حافظه و پردازنده دارند. مانیتورینگ مداوم استفاده از این منابع در هر کانتینر به مدیران سیستم کمک می‌کند تا از مصرف بهینه منابع اطمینان حاصل کنند و از بروز مشکلاتی مانند OOM (Out Of Memory) یا سربار زیاد جلوگیری کنند.</li>



<li><strong>افزایش امنیت</strong>: از طریق مانیتورینگ دقیق، شما می‌توانید فعالیت‌های مشکوک یا غیرعادی در داخل کانتینرها را شناسایی کنید. به‌ویژه در محیط‌هایی که سرویس‌ها به صورت توزیع‌شده و روی کانتینرهای مختلف اجرا می‌شوند، کشف زودهنگام فعالیت‌های ناخواسته و مخرب اهمیت زیادی دارد.</li>
</ol>



<figure class="wp-block-image size-full"><img loading="lazy" decoding="async" width="888" height="465" src="https://hamravesh.com/blog/wp-content/uploads/2024/10/Container_Performance.webp" alt="پرفورمنس کانتینر و بهینه‌سازی آن" class="wp-image-3813" srcset="https://hamravesh.com/blog/wp-content/uploads/2024/10/Container_Performance.webp 888w, https://hamravesh.com/blog/wp-content/uploads/2024/10/Container_Performance-300x157.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2024/10/Container_Performance-768x402.webp 768w" sizes="auto, (max-width: 888px) 100vw, 888px" /></figure>



<h2 class="wp-block-heading" id="h-۲-هشدار-روی-پرفورمنس-سرویس-نه-پرفورمنس-کانتینر">۲. هشدار روی پرفورمنس سرویس نه پرفورمنس کانتینر</h2>



<p class="wp-block-paragraph">هشدارها (Alerts) باید بر اساس عملکرد کلی سرویس‌ها تنظیم شوند، نه فقط عملکرد سطح پایین کانتینرهایی که آن سرویس‌ها را میزبانی می‌کنند. این تفاوت به‌خصوص در محیط‌های میکروسرویس و کانتینری اهمیت زیادی دارد. برای درک بهتر، می‌توان این موضوع را به دو بخش زیر تقسیم کرد:</p>



<h3 class="wp-block-heading" id="h-1-عملکرد-سرویس-service-performance">1. <strong>عملکرد سرویس (Service Performance)</strong></h3>



<p class="wp-block-paragraph">عملکرد سرویس به توانایی کلی یک سرویس یا اپلیکیشن در ارائه عملکرد مورد انتظار از دید کاربر یا مشتری اشاره دارد. معیارهایی که برای سرویس‌ها بررسی می‌شوند شامل:</p>



<ul class="wp-block-list">
<li><strong>زمان پاسخ‌دهی (Response Time):</strong> مدت زمانی که طول می‌کشد تا یک سرویس به درخواست کاربر پاسخ دهد.</li>



<li><strong>نرخ درخواست‌های موفق (Success Rate):</strong> درصد درخواست‌هایی که با موفقیت پردازش شده‌اند.</li>



<li><strong>زمان آپ‌تایم (Uptime):</strong> میزان در دسترس بودن سرویس برای کاربران.</li>



<li><strong>SLA و SLO:</strong> تضمین سطح خدماتی که برای سرویس‌ها مشخص شده‌اند.</li>
</ul>



<p class="wp-block-paragraph">اگر یکی از این موارد از حالت نرمال خارج شود، ممکن است کاربران دچار مشکل شوند. بنابراین، هشدارها باید به گونه‌ای تنظیم شوند که وقتی عملکرد کل سرویس (نه فقط یک بخش فنی) تحت تأثیر قرار گرفت، تیم‌ها باخبر شوند.</p>



<h3 class="wp-block-heading" id="h-۲-عملکرد-کانتینر-container-performance">۲. <strong>عملکرد کانتینر (Container Performance)</strong></h3>



<p class="wp-block-paragraph">کانتینرها بخش‌های زیرساختی کوچکتری هستند که سرویس‌ها را میزبانی می‌کنند. معیارهایی که در سطح کانتینر نظارت می‌شوند شامل مواردی مثل:</p>



<ul class="wp-block-list">
<li><strong>استفاده از CPU و حافظه:</strong> میزان استفاده کانتینر از منابع سیستم.</li>



<li><strong>وضعیت کانتینر (Container Status):</strong> آیا کانتینر فعال است یا نه.</li>



<li><strong>متریک‌های شبکه و I/O:</strong> عملکرد شبکه و دیسک کانتینر.</li>
</ul>



<p class="wp-block-paragraph">اگرچه نظارت بر عملکرد کانتینرها مهم است، ولی مشکلات در سطح کانتینر همیشه به معنای اختلال در عملکرد سرویس نیستند. مثلاً ممکن است یک کانتینر منابع بالایی مصرف کند، ولی تأثیری در زمان پاسخ‌دهی سرویس نداشته باشد.</p>



<h2 class="wp-block-heading" id="h-۳-سرویس-هایی-که-elastic-و-multi-location-هستند-را-مانیتور-کنید">۳. سرویس‌هایی که Elastic و Multi-Location هستند را مانیتور کنید</h2>



<p class="wp-block-paragraph">مانیتورینگ میکروسرویس‌ها به دو ویژگی اصلی سرویس‌ها در معماری‌های مدرن اشاره دارد: <strong>الستیک بودن (Elasticity)</strong> و <strong>چندمکانی بودن (Multi-location)</strong>. هر یک از این ویژگی‌ها نیاز به مانیتورینگ خاص و روش‌های ویژه‌ای برای نظارت دارند. در ادامه به‌صورت جداگانه با هرکدام از این موارد آشنا خواهیم شد:</p>



<h3 class="wp-block-heading" id="h-1-الاستیک-بودن-elasticity">1. <strong>الاستیک بودن (Elasticity)</strong></h3>



<p class="wp-block-paragraph">الاستیک بودن به توانایی سرویس‌ها برای مقیاس‌پذیری خودکار اشاره دارد. در محیط‌های میکروسرویس و کانتینری، به‌ویژه زمانی که از زیرساخت‌های ابری یا <strong><a href="https://hamravesh.com/managed-kubernetes?utm_source=blog&amp;utm_medium=blog&amp;utm_campaign=managed-kubernetes">کوبرنتیز (Kubernetes)</a></strong> استفاده می‌شود، سرویس‌ها می‌توانند به‌طور خودکار بر اساس تقاضا بزرگ‌تر یا کوچک‌تر شوند. به عنوان مثال:</p>



<ul class="wp-block-list">
<li>اگر تعداد درخواست‌ها افزایش یابد، سرویس می‌تواند به‌طور خودکار چندین نمونه (instance) از خودش را اجرا کند.</li>



<li>در زمان کاهش درخواست‌ها، تعداد این نمونه‌ها کاهش پیدا می‌کند تا منابع بهینه استفاده شوند.</li>
</ul>



<p class="wp-block-paragraph"><strong>مانیتورینگ سرویس‌های الاستیک</strong> به معنای این است که سیستم مانیتورینگ باید بتواند این تغییرات پویا را شناسایی کرده و عملکرد سرویس‌ها را به صورت دقیق تحت نظر بگیرد، حتی زمانی که تعداد نمونه‌ها یا منابع مورد استفاده تغییر می‌کند. این نوع مانیتورینگ باید به جای تمرکز بر یک نمونه یا سرور خاص، کل سرویس و رفتار آن را زیر نظر داشته باشد.</p>



<h3 class="wp-block-heading" id="h-2-چندمکانی-بودن-multi-location">2. <strong>چندمکانی بودن (Multi-location)</strong></h3>



<p class="wp-block-paragraph">در معماری‌های مدرن، سرویس‌ها معمولاً در چندین مکان جغرافیایی یا دیتاسنتر مختلف مستقر هستند تا توانایی دسترسی بالاتر و پایداری بیشتری داشته باشند. به این معنا که یک سرویس ممکن است به‌طور همزمان در دیتاسنترهای مختلف یا مناطق مختلف ابری (Cloud Regions) مستقر باشد. هدف از چندمکانی بودن سرویس‌ها:</p>



<ul class="wp-block-list">
<li><strong>کاهش تأخیر (Latency):</strong> کاربران می‌توانند به نزدیک‌ترین دیتاسنتر متصل شوند تا تجربه سریع‌تری داشته باشند.</li>
</ul>



<ul class="wp-block-list">
<li><strong>افزایش پایداری (Resilience):</strong> اگر یکی از مکان‌ها دچار مشکل شد، دیگر مکان‌ها می‌توانند به‌طور خودکار جایگزین آن شوند و سرویس‌دهی ادامه یابد.</li>
</ul>



<p class="wp-block-paragraph"><strong>مانیتورینگ سرویس‌های چندمکانی</strong> به این معناست که سیستم مانیتورینگ باید عملکرد سرویس در تمامی مکان‌ها را تحت نظر بگیرد و بتواند رفتار هر مکان را جداگانه و در کنار عملکرد کلی سرویس رصد کند. این نوع مانیتورینگ به ابزارهایی نیاز دارد که توانایی بررسی و مقایسه عملکرد سرویس در مکان‌های مختلف را داشته باشند و در صورت بروز مشکل در یکی از مکان‌ها، هشدار ارسال کنند.</p>



<h2 class="wp-block-heading" id="h-۴-مانیتورینگ-جامع-end-to-end-monitoring">۴. <strong>مانیتورینگ جامع (End-to-End Monitoring)</strong></h2>



<p class="wp-block-paragraph">یکی از اصول حیاتی در مانیتورینگ میکروسرویس‌ها، نظارت بر کل زنجیره سرویس‌ها است. باید بتوان عملکرد هر میکروسرویس را از نقطه آغاز تا انتها تحت نظر گرفت. این کار به ویژه زمانی اهمیت پیدا می‌کند که چندین میکروسرویس به صورت متوالی برای اجرای یک فرآیند با هم در تعامل هستند. در اینجا استفاده از ابزارهایی مانند <strong><a href="https://aws.amazon.com/what-is/distributed-tracing">distributed tracing</a></strong> به ما کمک می‌کند تا جریان درخواست‌ها را در طول سرویس‌ها پیگیری کنیم.</p>



<h3 class="wp-block-heading" id="h-ویژگی-های-کلیدی-مانیتورینگ-جامع-در-میکروسرویس-ها">ویژگی‌های کلیدی مانیتورینگ جامع در میکروسرویس‌ها</h3>



<ol class="wp-block-list">
<li><strong>مانیتورینگ سرویس‌های فردی:</strong> هر میکروسرویس به‌صورت جداگانه نظارت می‌شود تا بتوان معیارهایی مانند زمان پاسخ، مصرف منابع (CPU، حافظه)، خطاها و مشکلات احتمالی را بررسی کرد.</li>



<li><strong>مانیتورینگ تراکنشی:</strong> پیگیری تراکنش‌های کامل از ابتدا تا انتها، حتی اگر تراکنش‌ها از چندین میکروسرویس عبور کنند. این به مدیران کمک می‌کند تا مسیری را که درخواست‌ها طی می‌کنند ببینند و مشکلات احتمالی در هر نقطه را تشخیص دهند.</li>



<li><strong>لاگینگ توزیع‌شده:</strong> ذخیره و مدیریت لاگ‌ها به‌صورت مرکزی به‌طوری که <strong>لاگ‌های تمام میکروسرویس‌ها</strong> را به هم مرتبط سازد و تحلیل کاملی از جریان‌های رخدادها در سیستم فراهم آورد.</li>



<li><strong>مانیتورینگ سیستم‌های زیرساختی:</strong> پایش عملکرد زیرساخت‌هایی که میکروسرویس‌ها بر روی آن‌ها اجرا می‌شوند، مانند سرورها، کانتینرها، و ابزارهای <strong><a href="https://hamravesh.com/blog/what-is-orchestration/">ارکستریشن</a></strong>.</li>
</ol>



<h2 class="wp-block-heading" id="h-۵-مانیتورینگ-و-ساختار-سازمانی">۵. مانیتورینگ و ساختار سازمانی</h2>



<p class="wp-block-paragraph">منظور از <strong>مانیتورینگ و ساختار سازمانی</strong> این است که سیستم مانیتورینگ شما باید به گونه‌ای طراحی و پیاده‌سازی شود که با ساختار سازمانی شما هماهنگ باشد. این مفهوم در سازمان‌هایی که از میکروسرویس‌ها، کانتینرها و زیرساخت‌های مدرن استفاده می‌کنند، اهمیت بیشتری پیدا می‌کند. به عبارت دیگر، نحوه نظارت بر سرویس‌ها، سیستم‌ها و فرآیندها باید به شکلی باشد که مطابق با ساختار و نیازهای سازمانی باشد تا تیم‌ها بتوانند به طور مؤثر به مشکلات رسیدگی کنند و عملکرد بهینه را تضمین کنند.</p>



<h3 class="wp-block-heading">هدف از این کار چیست؟</h3>



<p class="wp-block-paragraph">هماهنگ‌سازی مانیتورینگ با ساختار سازمانی کمک می‌کند که:</p>



<ul class="wp-block-list">
<li><strong>تیم‌ها و نقش‌ها به وضوح مشخص شوند:</strong> هر تیم مسئول مانیتورینگ و رفع اشکال بخش‌های مشخصی از سیستم باشد که با مسئولیت‌ها و وظایف آن‌ها همخوانی دارد.</li>



<li><strong>پاسخ‌گویی سریع‌تر به مشکلات:</strong> زمانی که مانیتورینگ به شکل درستی با ساختار سازمانی همگام شده باشد، مشکلات و هشدارها به سرعت به تیم‌های مرتبط ارسال می‌شود و آن‌ها می‌توانند به سرعت به حل مشکلات بپردازند.</li>



<li><strong>تمرکز بر روی اولویت‌های سازمانی:</strong> هر بخش از سازمان بر اساس نیازهای خود مانیتورینگ مخصوص به خود را دارد. برای مثال، تیم توسعه بر روی متریک‌های مرتبط با عملکرد سرویس‌ها تمرکز می‌کند و تیم عملیات بر روی مصرف منابع و پایداری سیستم نظارت دارد.</li>
</ul>



<h3 class="wp-block-heading">چگونه این هماهنگی را ایجاد کنیم؟</h3>



<ol class="wp-block-list">
<li><strong>شناسایی بخش‌های کلیدی سازمان:</strong> ابتدا باید ساختار سازمانی خود را مشخص کنید و تعیین کنید که هر بخش یا تیم مسئول کدام سرویس‌ها یا سیستم‌ها است. برای مثال، در یک سازمان مبتنی بر میکروسرویس، ممکن است تیم‌های مختلفی برای توسعه، عملیات، پشتیبانی، و امنیت وجود داشته باشند که هر کدام بخش‌های خاصی از سیستم را مدیریت می‌کنند.</li>



<li><strong>تخصیص مسئولیت‌های مانیتورینگ:</strong> هر تیم باید مسئول مانیتورینگ بخشی از سیستم باشد که با مسئولیت‌های روزمره آن تیم هم‌راستا است. </li>



<li><strong>ایجاد داشبوردهای مرتبط:</strong> هر تیم باید به داشبوردهای مانیتورینگ مرتبط با وظایف خود دسترسی داشته باشد. برای مثال، تیم توسعه ممکن است داشبوردی داشته باشد که فقط وضعیت سرویس‌های خاصی را نمایش می‌دهد، در حالی که تیم امنیت داشبوردی دارد که فعالیت‌های غیرمعمول را رصد می‌کند.</li>



<li><strong>ایجاد پروتکل‌های هشداردهی بر اساس ساختار سازمانی:</strong> هشدارها باید به صورت مستقیم به تیم‌های مسئول ارسال شوند. برای مثال، اگر مشکلی در زیرساخت رخ دهد، هشدار به تیم عملیات ارسال شود و اگر مشکلی در کد یا سرویس رخ دهد، تیم توسعه مطلع شود.</li>
</ol>



<h2 class="wp-block-heading" id="h-در-پایان">در پایان</h2>



<p class="wp-block-paragraph">مانیتورینگ در دنیای میکروسرویس‌ها یک چالش پیچیده است که نیازمند رعایت اصول و قواعد خاصی است. از مانیتورینگ متریک‌ها و لاگ‌ها گرفته تا نظارت بر سلامت و هشدارها، هر کدام از این اقدامات در بهبود کارایی، تشخیص زودهنگام مشکلات و اطمینان از عملکرد صحیح سیستم نقش حیاتی دارند. با بهره‌گیری از ابزارهای مناسب و رویکردهای جامع، می‌توان به طور موثر مانیتورینگ میکروسرویس‌ها را انجام داد و از پایداری و کارایی سیستم اطمینان حاصل کرد.</p>
<p>The post <a href="https://hamravesh.com/blog/microservice-monitoring/">قواعد مانیتورینگ در دنیای میکروسرویس‌ها</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/microservice-monitoring/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>CaaS یا Container as a Service چیست؟</title>
		<link>https://hamravesh.com/blog/what-is-caas/</link>
					<comments>https://hamravesh.com/blog/what-is-caas/#respond</comments>
		
		<dc:creator><![CDATA[ارسطو عباسی]]></dc:creator>
		<pubDate>Sat, 12 Oct 2024 10:15:26 +0000</pubDate>
				<category><![CDATA[دواپس]]></category>
		<category><![CDATA[مقالات]]></category>
		<guid isPermaLink="false">https://hamravesh.com/blog/?p=3757</guid>

					<description><![CDATA[<p>CaaS یا Container as a Service یک سرویس ابری است که به توسعه‌دهندگان اجازه توسعه، استقرار و دیپلوی اپلیکیشن‌های کانتینرایز شده را می‌دهد. این سرویس روی قابل حمل بودن و مقیاس‌پذیری راحت نرم‌افزارها تمرکز دارد. اپلیکیشن‌های کانتینرایز شده به برنامه‌ها یا سرویس‌هایی اشاره دارند که در یک محیط ایزوله و مستقل به نام «کانتینر» اجرا [&#8230;]</p>
<p>The post <a href="https://hamravesh.com/blog/what-is-caas/">CaaS یا Container as a Service چیست؟</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">CaaS یا Container as a Service یک سرویس ابری است که به توسعه‌دهندگان اجازه توسعه، استقرار و دیپلوی <strong>اپلیکیشن‌های کانتینرایز شده</strong> را می‌دهد. این سرویس روی قابل حمل بودن و مقیاس‌پذیری راحت نرم‌افزارها تمرکز دارد. </p>



<p class="wp-block-paragraph">اپلیکیشن‌های کانتینرایز شده به برنامه‌ها یا سرویس‌هایی اشاره دارند که در یک محیط ایزوله و مستقل به نام «<strong><a href="https://hamravesh.com/blog/what-is-container/">کانتینر</a></strong>» اجرا می‌شوند. کانتینر یک بسته‌بندی استاندارد است که شامل تمام ملزومات مورد نیاز اپلیکیشن مانند کدها، کتابخانه‌ها، وابستگی‌ها و تنظیمات می‌شود. هدف اصلی کانتینرایز کردن اپلیکیشن‌ها این است که آن‌ها بتوانند به صورت پایدار و مستقل از محیط میزبانی (مانند سیستم‌عامل) اجرا شوند.</p>



<p class="wp-block-paragraph">CaaS در ساختار و دنیای پردازش ابری، بین IaaS (Infrastructure as a Service) و PaaS (Platform as a Service) قرار دارد. CaaS به کاربران اجازه می‌دهد تا با استفاده از زیرساخت‌های ابری (مانند IaaS) کانتینرهای نرم‌افزاری را اجرا و مدیریت کنند. در CaaS، برخلاف PaaS که مدیریت سیستم‌عامل و محیط اجرایی اپلیکیشن را به عهده می‌گیرد، کاربر، مسئول تنظیم و کنترل کانتینرها است، اما همچنان زیرساخت فیزیکی و مجازی توسط ارائه‌دهنده ابری مدیریت می‌شود. به این ترتیب، CaaS به توسعه‌دهندگان اجازه می‌دهد تا محیط اجرای برنامه‌های خود را دقیقاً مطابق نیازشان کانتینرایز و مدیریت کنند، بدون نیاز به مدیریت کامل زیرساخت (همانند IaaS) و یا محدودیت‌های یک محیط کاملاً مدیریت‌شده (مانند PaaS).</p>



<figure class="wp-block-image size-full"><img loading="lazy" decoding="async" width="830" height="285" src="https://hamravesh.com/blog/wp-content/uploads/2024/09/cloud-service-models-apps.webp" alt="جایگاه CaaS بین IaaS و PaaS" class="wp-image-3759" srcset="https://hamravesh.com/blog/wp-content/uploads/2024/09/cloud-service-models-apps.webp 830w, https://hamravesh.com/blog/wp-content/uploads/2024/09/cloud-service-models-apps-300x103.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2024/09/cloud-service-models-apps-768x264.webp 768w" sizes="auto, (max-width: 830px) 100vw, 830px" /></figure>



<h2 class="wp-block-heading" id="h-ویژگی-های-caas">ویژگی‌های CaaS</h2>



<p class="wp-block-paragraph">Containers as a Service (CaaS) یک پلتفرم ابری ارائه می‌دهد که کاربران می‌توانند با استفاده از آن فرآیندهای مجازی‌سازی مبتنی بر کانتینر و مدیریت کانتینرها را بهینه‌سازی کنند. ارائه‌دهندگان CaaS امکانات گسترده‌ای را فراهم می‌کنند که شامل مواردی مانند محیط‌های اجرایی کانتینر، لایه‌های <strong><a href="https://hamravesh.com/blog/what-is-orchestration/">ارکستریشن</a></strong> و مدیریت ذخیره‌سازی پایدار می‌شود. همچنین، CaaS دارای قابلیت‌های یکپارچه‌سازی منحصر به فردی است که به کسب‌وکارها کمک می‌کند تا زیرساخت‌های IT خود را بهینه کنند.</p>



<p class="wp-block-paragraph">ویژگی‌های اصلی CaaS شامل موارد زیر است:</p>



<ul class="wp-block-list">
<li>کانتینری‌سازی</li>



<li>ارکستریشن کانتینرها</li>



<li>شبکه‌سازی</li>



<li>پیکربندی پلتفرم</li>



<li>امنیت و کنترل دسترسی</li>



<li>یکپارچگی با سایر سرویس‌ها</li>
</ul>



<h2 class="wp-block-heading" id="h-مزایا-caas-به-نسبت-paas">مزایا CaaS به نسبت PaaS</h2>



<figure class="wp-block-image size-large"><img loading="lazy" decoding="async" width="1024" height="585" src="https://hamravesh.com/blog/wp-content/uploads/2024/09/CaaS-VS-PaaS-1024x585.webp" alt="CaaS در مقابل PaaS" class="wp-image-3760" srcset="https://hamravesh.com/blog/wp-content/uploads/2024/09/CaaS-VS-PaaS-1024x585.webp 1024w, https://hamravesh.com/blog/wp-content/uploads/2024/09/CaaS-VS-PaaS-300x171.webp 300w, https://hamravesh.com/blog/wp-content/uploads/2024/09/CaaS-VS-PaaS-768x439.webp 768w, https://hamravesh.com/blog/wp-content/uploads/2024/09/CaaS-VS-PaaS-1536x878.webp 1536w, https://hamravesh.com/blog/wp-content/uploads/2024/09/CaaS-VS-PaaS.webp 1792w" sizes="auto, (max-width: 1024px) 100vw, 1024px" /></figure>



<p class="wp-block-paragraph">CaaS (Container as a Service) نسبت به PaaS (Platform as a Service) مزایای متعددی دارد که باعث می‌شود در برخی سناریوها انتخاب بهتری برای توسعه‌دهندگان و کسب‌وکارها باشد. در ادامه، به برخی از مهم‌ترین مزایای CaaS نسبت به PaaS اشاره می‌شود:</p>



<h3 class="wp-block-heading">1. <strong>کنترل بیشتر روی زیرساخت</strong></h3>



<p class="wp-block-paragraph">در CaaS، کاربران کنترل بیشتری بر محیط کانتینری و زیرساخت دارند. برخلاف PaaS که بسیاری از جزئیات محیط زیرساخت را پنهان می‌کند و تنظیمات پیش‌فرض ارائه می‌دهد، در CaaS کاربران می‌توانند نحوه استقرار، پیکربندی و مدیریت کانتینرها را به دلخواه تنظیم کنند. این سطح از کنترل برای پروژه‌های پیچیده و سفارشی مفید است.</p>



<h3 class="wp-block-heading">2. <strong>انعطاف‌پذیری بالاتر</strong></h3>



<p class="wp-block-paragraph">CaaS انعطاف‌پذیری بیشتری در انتخاب ابزارها، کتابخانه‌ها، و نسخه‌های نرم‌افزار فراهم می‌کند، در حالی که PaaS ممکن است کاربران را به استفاده از ابزارهای خاص یا پیکربندی‌های از پیش تعیین‌شده محدود کند. این موضوع به توسعه‌دهندگان اجازه می‌دهد از فناوری‌های به‌روز و دلخواه استفاده کنند.</p>



<h3 class="wp-block-heading">3. <strong>پرتابل بودن کانتینرها</strong></h3>



<p class="wp-block-paragraph">کانتینرها در CaaS قابل حمل هستند و می‌توانند در هر محیطی، از سیستم‌های محلی تا فضای ابری یا چندین ارائه‌دهنده‌ی ابری، به راحتی اجرا شوند. این قابلیت باعث می‌شود که انتقال برنامه‌ها بین محیط‌های مختلف بدون مشکلات سازگاری صورت گیرد، در حالی که PaaS محدود به محیط‌ها و سرویس‌های خاص آن پلتفرم است.</p>



<h3 class="wp-block-heading">4. <strong>مدیریت بهینه منابع</strong></h3>



<p class="wp-block-paragraph">کانتینرها به دلیل سبک بودن و مصرف بهینه منابع، نسبت به محیط‌های PaaS که ممکن است شامل اجزای اضافی و غیرضروری باشند، کارایی بیشتری دارند. با CaaS، می‌توان از منابع سخت‌افزاری بهینه‌تر استفاده کرد و هزینه‌های محاسباتی را کاهش داد.</p>



<h3 class="wp-block-heading">5. <strong>پشتیبانی از معماری‌های پیچیده و چندلایه</strong></h3>



<p class="wp-block-paragraph">CaaS به راحتی می‌تواند معماری‌های پیچیده و چندلایه را مدیریت کند. به لطف ارکستریشن کانتینرها، ابزارهایی مانند Kubernetes اجازه مدیریت بارهای کاری بزرگ و پیچیده را فراهم می‌کنند. در مقابل، PaaS بیشتر برای پروژه‌های ساده‌تر و استانداردتر طراحی شده است و ممکن است توانایی مدیریت معماری‌های پیچیده را به همان اندازه نداشته باشد.</p>



<h2 class="wp-block-heading" id="h-کاربردهای-caas-در-توسعه-پروژه-ها">کاربردهای CaaS در توسعه پروژه‌ها</h2>



<p class="wp-block-paragraph">CaaS (Container as a Service) در توسعه پروژه‌ها کاربردهای گسترده‌ای دارد که به دلیل انعطاف‌پذیری، مقیاس‌پذیری و سادگی مدیریت کانتینرها بسیار مورد توجه قرار گرفته است. در ادامه به برخی از مهم‌ترین کاربردهای CaaS در توسعه پروژه‌ها اشاره می‌شود:</p>



<h3 class="wp-block-heading">1. <strong>پشتیبانی از DevOps و CI/CD</strong></h3>



<p class="wp-block-paragraph">CaaS یکی از مهم‌ترین ابزارها برای تیم‌های DevOps محسوب می‌شود. کانتینرها به توسعه‌دهندگان اجازه می‌دهند تا محیط توسعه و تولید یکسانی داشته باشند، که این امر از بروز مشکلات ناشی از ناسازگاری محیط‌ها جلوگیری می‌کند. همچنین، CaaS به طور کامل از فرآیندهای CI/CD (یکپارچه‌سازی و تحویل مستمر) پشتیبانی می‌کند و به توسعه‌دهندگان امکان می‌دهد تغییرات کد را به سرعت تست و مستقر کنند.</p>



<h3 class="wp-block-heading">2. <strong>مقیاس‌پذیری پویا</strong></h3>



<p class="wp-block-paragraph">یکی از مهم‌ترین مزایای CaaS در پروژه‌های توسعه نرم‌افزار، امکان مقیاس‌بندی خودکار و پویا است. با استفاده از ابزارهای اورکستراسیون مانند Kubernetes، می‌توان به راحتی تعداد کانتینرهای اجراشده را بر اساس نیاز پروژه یا ترافیک موجود تنظیم کرد. این قابلیت به پروژه‌ها امکان می‌دهد تا به شکل بهینه از منابع زیرساخت استفاده کنند.</p>



<h3 class="wp-block-heading">3. <strong>یکپارچگی با محیط‌های چند ابری و هیبریدی</strong></h3>



<p class="wp-block-paragraph">CaaS به دلیل قابل حمل بودن کانتینرها، امکان اجرای نرم‌افزارها در محیط‌های چند ابری یا هیبریدی (ترکیب ابر عمومی و خصوصی) را فراهم می‌کند. این ویژگی به شرکت‌ها و تیم‌های توسعه اجازه می‌دهد تا بدون وابستگی به یک ارائه‌دهنده ابری، پروژه‌های خود را در محیط‌های مختلف به اجرا درآورند و از بهترین امکانات هر محیط بهره‌مند شوند.</p>



<h3 class="wp-block-heading">4. <strong>مدیریت ساده‌تر زیرساخت</strong></h3>



<p class="wp-block-paragraph">استفاده از CaaS در پروژه‌ها باعث می‌شود که مدیریت زیرساخت بسیار ساده‌تر و خودکارتر شود. توسعه‌دهندگان به جای نگرانی درباره مدیریت ماشین‌های مجازی یا سخت‌افزار فیزیکی، می‌توانند بر توسعه و بهبود نرم‌افزار تمرکز کنند. کانتینرها به‌طور خودکار منابع را مدیریت و بهینه می‌کنند و تیم‌های IT نیز می‌توانند به‌راحتی زیرساخت را مدیریت کنند.</p>



<h3 class="wp-block-heading">5. <strong>بهبود چرخه توسعه و تست</strong></h3>



<p class="wp-block-paragraph">در فرآیندهای توسعه نرم‌افزار، تست کدها و بررسی کیفیت آنها یک چالش بزرگ است. با استفاده از CaaS، تیم‌ها می‌توانند به راحتی محیط‌های تست خود را به سرعت و با کمترین منابع راه‌اندازی کنند. از آنجایی که کانتینرها محیطی یکسان برای توسعه و تولید ارائه می‌دهند، مشکلات ناشی از ناسازگاری محیط‌ها به حداقل می‌رسد و چرخه توسعه و تست سرعت و دقت بیشتری پیدا می‌کند.</p>



<h3 class="wp-block-heading">6. <strong>پشتیبانی از میکروسرویس‌ها</strong></h3>



<p class="wp-block-paragraph">CaaS به خوبی با معماری <strong>میکروسرویس‌ها</strong> سازگار است. در این معماری، برنامه‌های بزرگ به چندین سرویس کوچک‌تر تقسیم می‌شوند که هر کدام در کانتینرهای جداگانه اجرا می‌شوند. این ساختار به تیم‌های توسعه اجازه می‌دهد هر میکروسرویس را به صورت جداگانه توسعه، تست و مستقر کنند. به کمک CaaS، مدیریت میکروسرویس‌ها، استقرار و مقیاس‌پذیری آنها بسیار ساده‌تر می‌شود.</p>



<h2 class="wp-block-heading" id="h-در-پایان">در پایان</h2>



<p class="wp-block-paragraph">در ساختار پلتفرم‌ها و سرویس‌های ابری، CaaS یکی از کاربردی‌ترین و مفید‌ترین سرویس‌ها برای توسعه‌دهندگان و تیم‌های برنامه‌نویسی مختلف است. البته این نکته را در نظر داشته باشید که CaaS می‌تواند مشکلاتی نیز داشته باشد. پیچیدگی در مدیریت زیرساخت، کنترل محدود، نیاز به تخصص فنی بیشتر و&#8230; از جمله این مشکلات هستند. اما همه پلتفرم‌ها و سرویس‌ها معایب و مزایایی دارند که با بررسی و مقایسه کامل می‌توانید به این نتیجه برسید که بهترین مورد برای شما کدام است. </p>
<p>The post <a href="https://hamravesh.com/blog/what-is-caas/">CaaS یا Container as a Service چیست؟</a> appeared first on <a href="https://hamravesh.com/blog">بلاگ هم‌روش</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://hamravesh.com/blog/what-is-caas/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
	</channel>
</rss>
