در این مقاله به بحث service discovery خواهیم پرداخت بر طبق مقاله های قبل با یک مثال به طرح مشکل و ارائه راه حل چالش موجود می پردازیم سر فصل های این مقاله شامل:

تعریف مسئله

معرفی الگوی service discovery

انواع روش های پیاده سازی

پیاده سازی Service discovery با الگوی Client‑Side

پیاده سازی Service discovery با الگوی server-side

بررسی service register و انواع روش های پیاده سازی آن

پیاده سازی service register با الگوی Self‑Registration

پیاده سازی service register با الگوی Third‑Party

باید آگاه بود که معماری میکروسرویسی دارای چالش ها و نکات خاص خود می باشد که برای حل چالش های پیش رو روش ها و الگو های متفاوتی مطرح شده است که در این مقاله متمرکز بر روی الگوی service discovery خواهیم بود . امیدوارم که این مقاله و ترجمه برای شما خواننده عزیز سودمند باشد.

علی لطفی

تعریف مسئله

فرض بر این نماییم که شما دارای یک سیستم که بر مبنایی معماری میکرو سرویس طراحی شده است می باشید و میکرو سرویس های خود را  بر روی سرورهای مختلف بصورت مستقل از یکدیگر استقرار نموده ایده و هر میکرو سرویس با آگاهی از آدرس فیزیکی هر میکرو سرویس  اقدام به فراخوانی سرویس های مورد نیاز از آن می نمایید خوب به نظر مشکلی وجود ندارد پس از مدتی به دلایل مختلف نیازمند تغییر آدرس های این میکروسرویسی ها می شویم در اینصورت هر میکرو سرویس باید تنظیمات  مربوط به آدرس های  سرویس ها  را ویرایش نمایید بنابراین همانطور که مشاهده می نمایید اساسی ترین مشکل وابسته بودن میکروسرویسی ها به آدرس فیزیکی یکدیگر می باشد بنابراین این وابسته بودن در صورت تغییر زیاد آدرس ها می تواند مشکل ساز و سیستم را دچار مشکل نمایید و  با هر تغییر آدرس هر میکرو سرویس ما نیازمند تغییر تنظیمات در دیگر  میکرو سرویس ها هستیم مشکل در تغییر آدرس ها نیست مشکل مورد نظر ما وابسته بودن میکرو سرویس ها  به این تغییر می باشد.

 امروز با بحث میکرو سرویس و  cloud امکان تغییر آدرس ها بصورت متناوب وجود دارد دلایلی از قبیل:

  • اضافه شدن یک نود دیگر به منظور scale out کردن یک node
  • از دست رفتن یک میکرو سرویس و جایگزین کردن یک Node به جای آن
  • Upgrades شدن میکروسرویس ها
  • و..

همانطور که مشاهده می کنید این تغییرات می تواند بصورت زیاد اتفاق رخ دهد و هر بار شما مجبور به تغییر تنظیمات میکرو سرویس ها خواهید شد  حال با هر روشی که این تنظیمات انجام شده است مثلا اگر در config فایل ذخیره نموده اید ویا مثلا hard code کرده اید و…به هر حال به دلیل این وابستگی که به آدرس فیزیکی وجود دارد با تغییر هر آدرس فیزیکی مجبور به اعمال برخی تغییرات خواهید بود.

Service discovery

در این الگو به جای آنکه کلاینت ها که میتواند یک میکرو سرویس باشد به جای آنکه که  مستقیم از آدرس موردنظر مطلع باشد این آدرس رو از یک کامپوننتی به نام  service registry استعلام می کند  و آدرس سرویس مورد نظر را به دست خواهد آورد به جای آنکه کلاینت ها مستقیما آدرس را داشته باشند از  service registry  بر اساس نام سرویس استعلام خواهد کرد و یک و یا  لیستی از آدرس های موجود از سرویس مورد نظر را به کلاینت خواهد داد  در واقع نکته قابل اهمیت در این روش در این است که کلاینت ها و میکرو سرویس های قصد فراخوانی دارند به طور کامل از مکان فیزیکی مقصد  بی اطلاع بوده و با استعلام از service registry آدرس سرویس ها را دریافت خواهند کرد با این تغییر اگر آدرس فیزیکی سرویسی تغییر کند  تنها باید service registry آدرس قدیم را به جدید تغییر دهد. بدون آنکه نیاز باید در همه میکروسرویس ها و یا کلاینت ها آدرس فیزیکی را تغییر دهیم.

برای پیاده سازی این الگو دو روش وجود دارد

1.Client‑Side Pattern

2.Server-Side Pattern

پیاده سازی Service discovery با الگوی Client‑Side

در این روش مرکزی به نام service registry وجود دارد که آدرس تمام سرویس های موجود بر روی تمام میکرو سرویس های سیستم ما را دارا می باشد در واقعه مشابه یک دفترچه تلفنی می باشد که بر اساس نام مورد نیاز شماره تلفن و یا حتی شماره تلفن های که  از این شخص وجود دارد را به شما خواهد داد بنابراین   کلاینتی که  نیاز به فراخوانی سرویس از یک میکرو سرویس دارد از  service registry آدرس های سرویس موجود را استعلام می کند در پاسخ یک و یا لیستی از آدرس های  میکروسرویس که این سرویس را  ارائه می دهند را بر میگرداند اما سوال اینجا خواهد بود چرا ممکن است لیستی از آد رس ها را به شما دهد. فرض کنید که میکروسرویسی که سرویس مورد نظر شما را ارائه می دهد میکرو سرویس مهم و با اهمیتی می باشد بنابراین تصمیم گرفته اید که این میکرو سرویس را مقیاس پذیری افقی (scale out)  کنید بنابراین با این روش شما چند نود از میکرو سرویس مورد نظر خود خواهید داشت و زمانی که از service registry اقدام به استعلام می نمایید به جای یک آدرس ممکن است چند آدرس را به کلاینت باز خواهد گشت مثل اینکه از یک شخص چند شماره تلفن داشته باشید. در مرحله بعد این کلاینت است که  تصمیم خواهد گرفت با  چه الگو ریتمی اقدام به انتخاب کدام آدرس برای صدا زدن نماید ممکن است هر بار به  صورت ترتیبی این عملیات را انجام دهد و یا ممکن است بصورت شانسی انتخاب نمایید و یا غیره.

بنابراین این کلاینت می باشد که با توجه به ظرفیت موجود تصمیم خواهد گرفت که از این منابع به چه صورت استفاده نمایید. روش های مختلف وجود دارد که بنابر نیازمندی و تصمیم شما می توانید استفاده نمایید.

Service registry چگونه این آدرس ها را جمع آوری می کند نیز روش های مربوط به خود را دارد که در ادامه به توضیح آن خواهیم پرداخت اما بصورت کلی هر سرویس که start می شود بصورت پیش فرض خود را در  این کامپوننت ریجستر کرده و در زمانی که stop شد به این کامپوننت اعلام می دارد که از سرویس دهی خارج شده و از لیست سرویس های فعال حذف گردد .بنابراین همانطور که مشاهده می کنید این قسمت مانند یک map می باشد که بر اساس نام سرویس ها آدرس های لازم را اراده می دهد.

به بررسی مزایا و معایب این روش می پردازیم.

مزایا :

همانطور که مشاهده نمودید در این روش بر خلاف روش قبل کلاینت ها اطلاعی از مکان فیزیکی آدرس ها ندارد و بنابراین میکرو سرویس ها می توانند آزادانه اقدام به تغییر آدرس فیزیکی می نمایند  بدون اینکه نگران به وجود آمدن مشکل در سیستم باشند کلاینت با آگاهی از آدرس های موجود از سرویس مورد نظر می تواند روش های هوشمندانی که در انتخاب میکروسرویس مورد نظر برای فراخوانی سرویس مورد نظر داشته باشند که بر مبنایی نیاز و مسئله انتخاب شوند.

معایب :

اما مشکلی که در این روش وجود دارد فرض کنید که کلاینت ها  و میکرو سرویس های  که قصد فراخوانی سرویس ها رو دارند  با زبانهای متفاوتی نوشته شده است و همانطور که گفته شد بعد از اینکه از service registry لیست سرویس های فعال موجود را می گیرم بر مبنایی الگوریتمی باید تصمیم گرفت از کدام استفاده نماییم بنابراین اگر هر میکرو سرویس یا کلاینت شما با زبانهای متفاوتی نوشته شده باشد شما مجبور خواهید بود که این منطق را در تمام میکرو سرویس های خود تکرار کنید حتی اگر هم از یک زبان استفاده نمایید بازهم مجبور به داشتن این منطق در تمام میکروسرویس ها و یا کلاینت های خود خواهید بود بنابراین مشکل تکرار منطق در تمام سرویس ها خواهید بود بنابراین یک وابستگی دیگر.

پیاده سازی Service discovery با الگوی server-side

همانطور که در روش قبل مشاهده نمودید کلاینت ها برای فراخوانی سرویس ها از سرویس ریجستر آدرس و یا آدرس های که از این سرویس موجود است را استعلام خواهد نمود و این کلاینت ها می باشند که تصمیم خواهند گرفت که بر مبنایی چه سیاستی اقدام به فراخوانی سرویس ها نمایید.و  این سیاست در تمام سرویس ها باید پیاده سازی شود .

در روش دوم ما از یک load balancer استفاده خواهیم نمود که این وظیفه انتخاب سرویس ها با چه سیاستی و با چه روشی را بر عهده خواهد گرفت مانند اینکه این وظیفه از تمام کلاینت ها گرفته و به Load balancer  منتقل کرده ایم وload balancer با استعلام از service registry آدرس تمام سرویس ها موجود را دریافت خواهد نمود اکنون با توحه سیاست های مشخص و سرویس های موجود تصمیم خواهد گرفت که این درخواست به دست کدام سرویس برسید بر خلاف روش قبل که این کلاینت ها بودند که بصورت مستقیم با service registry کار می کردند و خود تصمیم می گرفتن از آدرس های موجود کدام سرویس ها را فراخوانی کنند در این روش یک لایه abstraction ایجاد شده است که تمامی این جزئیات از کلاینت ها مخفی شده است و دیگر کلاینت ها درگیر این موضوع نخواهند بود.

همانطور که مشاهده می کنید کلاینت ها در خواست های خود را به load balancer خواند داد و این component بر مبنایی سیاست ها مورد نظر این درخواست ها را به سرویس مورد نظر انتقال(route) خواهد داد .

و اما مزایا و معایب این روش

مزایا :

همانطور که در این روش مشاهده نمودید وظیفه استعلام سرویس ها و انتخاب سرویس ها بصورت کامل از کلاینت ها گرفته شده است و به load balancer منتقل شده است بنابراین کلاینت ها ساده تر و وبا پیچیدگی کمتری نوشته خواهد شد.

معایب :

معایب قابل اشاره load balancer باید بتواند با سرعت بالا و همیشه دسترس باشند بنابراین این بخش به گونه ای طراحی شود که بتواند در هر شرایطی با سرعت و توانمندی بالایی عمل نمایید. بنابراین اگر load balancer از کار بیفتد تمام سیستم ها از کار خواهد افتاد بنابراین ما یک point of failure در سیستم خواهیم داشت.

بررسی service register و انواع روش های پیاده سازی آن

یکی از بخش های مهم در این الگو service registry می باشد که مانند یک دفترچه تماس آدرس تمامی سرویس های موجود را داراست و بر اساس درخواست لیستی از آدرس های موجود از سرویس را ارائه خواهد داد. اما نکته ای که در ادامه به آن خواهیم پرداخت این موضوع خواهد بود که این ماژول چگونه از  آدرس فیزیکی سرویس ها  موجود مطلع شده و این آدرس ها را مدیریت می کند که در ادامه برای پیاده سازی این ماژول دو روش وجود دارد که به بررسی آن خواهیم پرداخت و اما نکته ای دیگر در دسترس نبودن این ماژول عملا باعث به وجود آوردن مشکلات اساسی برای سیستم خواهد شد .به همین دلیل در طراحی اینگونه سیستم ها سعی می شود به گونه ای طراحی بشنوند که در برابر بروز خطا دارای  تاب آوری  بالای خواهد بود و این سیستم ها بصورت کلاستر شده در نظر خواهند گرفت که با سرعت بالای قادر به پاسخگویی باشیم.

برای پیاده این ماژول دو راه وجود دارد :

1.پیاده سازی service register با الگوی Self‑Registration

2.پیاده سازی service register با الگوی Third‑Party

SelfRegistration

در این روش میکرو سرویس ها وظیفه خواهند داشت که لیست سرویس های خود را در service register ثبت نمایند و در صورتی که Stop شدن نیز  سرویس های خود را deregister  کرده . بنابراین همانطور که مشاهده می نمایید وظیفه register و deregister شدن سرویس ها بر عهده خود میکرو سرویس ها می باشد و service register  هیچ وظیفه ای در این رابطه به عهده نخواهند گرفت و   نکته ای که وجود دارد در صورت لزوم در بازه زمانی های هر سرویس یک سیگنال به service registry خواهد داد تا باعث عدم expire شدن از سوی service registry  گردد با این روش service registry مطمئن خواهد بود که سرویس ها در دسترس هستند و در صورتی که به طور نخواسته از دسترس خارج شده اند آگاه گردد.  و آنها را از لیست سرویس های فعال خارج کند.

این روش دارای مزایا و معایب خاص خود می باشد

مزایا :

از مزایای این روش می توان به سادگی پیاده سازی آن ارشاره کرد و هر میکرو سرویس باید سرویس های که ارائه می دهد را در service registry معرفی نمایید.

معایب :

از معایب آن می توان به این موضوع اشاره کرد که شما باید این فرآیند ثبت و لغو را در تمام میکرو سرویس ها پیاده سازی کنید به دلیل که این وظیفه به عهده هر میکرو سرویس واگذار شده است  و اگر میکرو سرویس ها با زبان های متفاوتی نوشته است شما مجبور به پیاده سازی این فرآیند به زبان های برنامه نویسی متفاوتی خواهید بود.

ThirdParty

درا این روش وظیفه ثبت سرویس ها و لغو و همچنین بررسی فعال بودن سرویس از کلاینت ها گرفته و یک کامپوننتی به نام Registrar واگذار میکنیم. در این روش این کامپوننت وظیفه دارد به روش های مختلف  مانند سرکشی و یا از طریق رویداد سرویس های فعال را از میکرو سرویس ها استعلام نمایید و اطلاعات سرویس ها را در service registry ثبت خواهد نمود و همچنین با دنبال کردن وضعیت سرویس ها مثلا اگر یک سرویس از دسترس خارج شد service registry را ویرایش نموده و از لیست سرویس های فعال خارج خواهد نمود  .

مزایا و معایب این روش

مزایا :

از مزایای این روش ساده شدن سرویس ها می باشد چون دیگر نیاز نیست میکرو سرویس ها سرویس های  خود را در service registry ثبت نمایند و این بخش به Registry منتقل شده است که به روش های مختلف این اطلاعات را کسب خواهد کرد.

معایب :

وقتی این وظیفه را به یک بخش خاص واگذار می کنم با توجه به وابسته شدن همه ای سیستم به آن در صورتی که مشکلی بر آن بخش پیش بیاد کل سیستم تحت شعاع قرار خواهد گرفت . بنابراین هم باید این بخش را خیلی خوب نوشت .

دوستان خوبم امیدوارم لذت برده باشید و خوشحالم میشم که در این مورد با هم دانشمون رو به اشتراک بگذارید

https://Github.com/LotfiAli

LotfiAliDev@gmail.com

منبع :

https://www.nginx.com/blog/service-discovery-in-a-microservices-architecture/

دسته بندی شده در:

برچسب ها:

,