نابود کردن فلسفه Plug در Phoenix


#1

با درود خدمت همه دوستان محترمم. من بر اساس نیازی می خواستم یک Plug بنویسم که نیاز بود در این پلاگ conn.params آبدیت شود یا به آن چیزی اضافه شود .

به عنوان مثال فکر کنید سه سرور داریم

۱. سرور اول آیپی و نام سیستم عامل رو jwt توکن می کنه و می فرسته به سرور دوم
۲. سرور دوم که api gateway ما هست jwt رو چک می کنه و از داخلش ip, os info رو برداشت می کنه به سرور سوم می فرسته
۳. لازم به ذکر هست تمام روتر های سرور سوم نیاز به os info, ip داره

پس من در api gateway اومدم ول به این صورت عمل کردم :

def init(_params) do

	end

	def call(%Plug.Conn{params: %{"ptoken" => ptoken}} = conn, params) do
    outputs = case Guardian.decode_and_verify(ptoken) do
           {:ok, climes} ->
             conn = %{conn | params: Map.merge(conn.params, %{"last_ip" => "#{climes["ip"]}"})}
             assign(conn, :user_ip_checked, params)
           {:error, _ms} ->
             conn
         	  |> put_status(403)
         		|> json(%{error_code: "403", error_msg: "You don't have an access."})
         	  |> halt()
     end
     outputs
	end

دو کار می کنه

  • اول می یاد چک می کنه ببینه توکن تایید شده است یا خیر
  • دوم می یاد از داخل توکن user ip و os info که هنوز ننوشتمش رو توی conn.params اضافه می کنه

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

در پست زیر بهم توضیح داده

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

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

You really shouldn’t be sending the entire contents of the Plug.Conn structure.

ایشون فرمودند که من نباید کل اطلاعات ساختار Plug.Conn رو ارسال کنم . ولی من فقط فقط یک پارامتر به فانکشن اضافه کردم نمی دونم چرا دقیقا این صحبت رو کردن

دلایلی رو هم آوردن به شرح زیر :

  • گفتن که در ورژن جدید Plug ممکنه کل ساختار و همینطور این داده ها تغییر کنند
  • و همینطور گفتند که با ساختار صحیح ارسال کنم

ولی تو پیشنهادات آخرش این مورد رو متوجه نشدم

Structure that information in a way the makes sense to your system. Your information structure has different reasons to change than those that will force a change on Plug.Conn.

شما نظرتون چی هست در این موارد چون فرد مذکور به من چنین چیزی گفته . البته من فکر می کنم ایشون درست فرموده ولی نظرات شما عزیزان هم مهمه مخصوصا @samdvr, @toomaj عزیز.

The idea is not to subvert the intent behind ‍Plug.Conn.params - it’s not a general data “dumping ground” - that is Plug.Conn.assigns job. So the strategy would be to put the information in Plug.Conn.assigns first and then combine it in the last possible moment. So start with

لازم به ذکر هست هم این پست جنبه آموزشی خواهد داشت هم جنبه حل مشکل. چون خیلی از این مشکلات کوچیک می تونه تبدیل به مشکلات بزرگ در پروژه بزرگ بشه مخصوصا در به روز رسانی چون من همین الان حدود ۵ پلاگ نوشتم که روتر های زیادی از سایتم درگیر اون هستند

منابع:
https://hexdocs.pm/plug/Plug.Conn.html#module-fetchable-fields


#2

سلام، من دارم میخونم، اما دقیقا مشکل چیه؟ چون اونجا شما زدی solved
البته من با ایشون موافقم چون باید پارامترها رو در assigns قرار بدین مگر اینکه دلیل واقعا خوبی وجود داشته باشه که اینطور بنظر نمیاد. و اون‌دوستمون هم دلایل درستی هم دادن که هم آینده نگرانست (future proof) و هم باعث بوجود آمدن پیچیدگی و tight coupling بی مورد نمیشه.


#3

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

این قسمت صحبتشون نفهمیدم
Structure that information in a way the makes sense to your system. Your information structure has different reasons to change than those that will force a change on Plug.Conn.

چند مورد مثل این

tight coupling رو نفهمیدم با اینکه قبلا و امروز هم در ویکی خوندم متوجه اون نشدم دقیقا چی هست

و

اینکه چنین دلیلی مثلا خوب حساب می شه که چنین کار که کردم انجام بشه البته بر اساس صحبت های اشون می خوام انجام بدم

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


#4

بله درست میگی شهریار جان، من گاهی با خستگی شدید میام اینجا و گاهی بعضی چیزا رو درست متوجه نمیشم. به هر حال پوزش میخوام🤗

in a way the makes sense

فقط بخشی از اون جمله رو نوشتم، اینکه گفتی متوجه این نشدی ممکنه دلیلش این باشه که چون یک اشتباه کوچیک توی جملش داره یکم خوندنش سخت شده،‌ بجای that makes نوشته the makes.

منظورش در ادامه جمله قبلیه، میگه یک تصمیم گیری اولیه در مورد حداقل دیتایی که لازم داری انجام بده و بعد جوری فرم دهی کن که برای سیتمی که از اون دیتا استفاده میکنه قابل درک باشه. منظورش دقیقا پروژه شما نبوده، این کلا کاریه که در اولین مراحل طراحی api انجام میشه. دو مرحله؛ ۱- تصمصم گیری در مورد دیتای اولیه و لازم بر اساس دیتای موجود یا قابل تولید، ۲- سازماندهی و structure به فرمتی که برامون قابل استفادست. احتمالا کاری که خود شما هم انجام میدی.

در مورد تایت کاپلینگ هم توی لینک زیر بحث شده البته از دیدگاه oop، اگر کافی نبود پیام بده که توضیح بدم.
اون قسمت اخر که گفته Explanation of the concept without code جالب توضیح داده، بد نیست فارسیشو بزاریم اینجا.


#5

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

ولی بسیار عالی بود لینکش با اینکه مدتی هست زبان شی گرایی کد نزدم و کامل نتونستم درک کنمش ولی لینک های پیوستی اون مثال های زیادی زده