Dev Perfects
40 subscribers
9.23K photos
1.26K videos
468 files
13K links
بخوام خیلی خلاصه بگم
این کانال میاد مطالب کانالای خفن تو حوزه تکنولوژی و برنامه نویسی رو جمع میکنه

پست پین رو بخونید
https://t.iss.one/dev_perfects/455


ارتباط:
https://t.iss.one/HidenChat_Bot?start=936082426
Download Telegram
ماکروسافت دیروز اعلام کرد که کامپایلر Typescript رو منتقل کرده روی Go (قبلا روی خود TypeScript بود)

یک دلیلی که من مخالف ترجمه فارسی خیلی از مباحث هستم همین موضوع هست؛ ماکروسافت نگفته کامپایلر رو بازنویسی می‌کنه بلکه دقیقا تاکید روی Port کردن داشته.
یعنی همون کدهای قبل رو کپی پیست می‌کنند توی یک فایل جدید و مطمئن میشن سینتکس و ... به Go تبدیل بشه. (واقعا فارسی توضیح دادن تفاوت rewrite, port کردن خیلی سخته)

بگذریم؛ توی این بحث طرفدارای Go و البته اونایی که درک درستی از موضوع نداشتند خواستند از آب گل‌الود ماهی بگیرند که دوره‌های Go خودشون رو بفروشند یا اینکه نفرت پراکنی کنند راجب Rust ؛ اول اینکه اگر بیشتر رصد کنید خیلی‌ها کمی ناامید شدند که چرا Rust انتخاب نشد.

مثلا نویسنده Vue که توی توییت‌های مختلف توضیح داده که Go برای بعضی کاربردها مثل web assembly مناسب نیست و ...

اما بعنوان کسی که علاقه بسیاری به Rust دارم بنظرم تیم TypeScript تصمیم خوبی گرفته؛ اگر قرار به بازنویسی کامل TypeScript بود قطعا Rust بهترین گزینه می‌شد و با توجه به اینکه تیم کرنل ویندوز هم داره خیلی از لایبراری‌های اصلی رو میبره روی Rust نشون میده مشکلی هم با این قضیه نیست.

اما تیم TypeScript نمی‌خواد مجدد همه چیز رو از بیخ بازنویسی کنه و فقط داره Port می‌کنه تا زمان کامپایل رو کاهش بده؛ برای همین نیازی به سختی‌های Rust, C نداره و البته همین Port کردن کم هزینه هم حداقل بهش 10x سرعت داده.

دلیل انتخاب Golang بجای Rust, C فقط این موضوع بوده؛ خواستم شفاف بشیم روش.
Forwarded from Linuxor ?
آیا باید همه زبان های برنامه نویسی رو تست کنیم که ببینیم به کدوم علاقه داریم؟


توی ریاضیات و احتمالات یه مسئله داریم به اسم توقف بهینه OSP که می‌گه برای اینکه تایم هدر نره 37% از اپشن هارو فقط برسی کنید تا معیار سنجش به دست بیاد، این یعنی 37% از زبان هارو باید از لحاظ سینتکسی، کاربرد و بازار کار باید فقط برسی کنید تا معیار دستتون بیاد بعد بهینه ترین زبان مناسب خودتون رو بعد از اینکه قبلی هارو برسی کردید می‌تونین انتخاب کنید.

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


@Linuxor
Forwarded from Code Module | کد ماژول (Mahan-Heydari)
🥶 چه آینده ای در انتظار Typescript هست ؟

🔵تایپ‌اسکریپت 5.8.2 آخرین نسخه رسمی که تا امروز (13 مارس 2025) منتشر شده، که در 27 فوریه 2025 اومده. این نسخه بیشتر روی بهبودهای کوچک و رفع مشکلات تمرکز داشته و چیز خیلی عجیب و غریبی توش نیست. طبق اعلام تیم تایپ‌اسکریپت توی وبلاگ رسمی‌شون، چندتا تغییر اصلی داشته:

بهبود type checking ها: مثلاً بررسی دقیق‌تر تایپ هایی که توی شرط‌ها برمی‌گردن یا وقتی به یه چیزی با ایندکس دسترسی پیدا می‌کنی.

پشتیبانی بهتر از ابزارهای ویرایشگر : مثل مرتب کردن importها بدون توجه به بزرگ یا کوچیک بودن حروف، که با بقیه ابزارها بهتر جور دربیاد.

رفع اشکالات: یه سری باگ‌های نسخه‌های آزمایشی رو درست کردن.

‼️این نسخه بیشتر یه به‌روزرسانی معمولی بود و برای اکثر برنامه‌نویس‌ها تغییر بزرگی توی کارشون ایجاد نکرد، مگر اینکه از یه سری ویژگی خاص استفاده می‌کردن که حالا دقیق‌تر شده.

⚡️حالا خبر بزرگ : تایپ‌اسکریپت 7.0 با زبان Go

حالا بریم سراغ چیزی که همه رو توی شبکه‌های اجتماعی و جاهای دیگه هیجان‌زده کرده. طبق پست‌هایی که توی X دیدم و یه اعلامیه که ظاهراً 11 مارس 2025 توی وبلاگ تایپ‌اسکریپت منتشر شده، تیم مایکروسافت داره روی یه نسخه کاملاً جدید کار می‌کنه که با زبان Go بازنویسی شده. یعنی کمپایلر تایپ‌اسکریپت که الان با خودش نوشته شده و به جاوااسکریپت تبدیل می‌شه، قراره به یه برنامه مستقل و سریع با Go تبدیل بشه.

👩‍💻چرا Go رو انتخاب کردن؟

🔵سرعت: توی پست‌های X گفته شده که تست‌های اولیه نشون می‌ده این نسخه تا 10 برابر سریع‌تر از نسخه الان کار می‌کنه. مثلاً توی پروژه‌های بزرگ مثل VS Code که از سرور تایپ‌اسکریپت (tsserver) زیاد استفاده می‌کنه، این سرعت می‌تونه کار رو خیلی راحت‌تر کنه.

🔵کارایی: Go یه زبان کامپایل‌شده‌ست و خیلی بهینه‌تر از جاوااسکریپت اجرا می‌شه، مخصوصاً برای کارای سنگین مثل بررسی نوع‌ها توی پروژه‌های بزرگ.

چیا قراره عوض بشه ؟

🔵پرفورمنس بهتر : اگه این 10 برابر سریع‌تر بودن واقعی باشه، برای پروژه‌های بزرگ که الان بررسی نوع‌هاشون گاهی چند ثانیه یا حتی چند دقیقه طول می‌کشه، یه تغییر بزرگه.

🔵سرور سریع‌تر: چون VS Code و خیلی از ویرایشگرها از tsserver برای تحلیل کد استفاده می‌کنن، این می‌تونه تجربه برنامه‌نویسی رو خیلی بهتر کنه.

هنوز معلوم نیست این تغییر به Go روی خود زبان (مثل دستورات یا ویژگی‌ها) اثر می‌ذاره یا فقط کمپایلر رو عوض می‌کنه 🏖️

#typescript #go #news
@CodeModule
Please open Telegram to view this post
VIEW IN TELEGRAM
Forwarded from Curious Geek ⚡️
vercel/ms
یک پکیج ساده که واحد زمان رو هرطور بنویسیم میگه چند میلی ثانیه هستش.
میلی ثانیه بهش بدیم برعکس کار می‌کنه و میگه چند دقیقه / ساعت / روز هستش.
ورژن جدید jsonwebtoken روی تایپ اسکریپت موقع تنظیم expiresIn برای استفاده از .env به این پکیج نیاز داره.
https://github.com/vercel/ms
البته که به ساده سازی تکمیل فایل .env هم کمک می‌کنه.
🆔 @Hiradsajde
📣 پروژه Nova جایگزین Nouveau خواهد شد.

🗣️ سال‌ها قبل FreeDesktop تصمیم گرفت با بازنویسی درایورهای گرافیک‌های انویدیا و انتشار آن به صورت آزاد، پروژه Nouveau (نوو) را آغار کند. اما اکنون پس از بی‌جان شدن نوو که سال‌هاست توسعه فعالی ندارد، تصمیم گرفته شده آن را با زبان Rust، تحت عنوان Nova منتشر کنند. البته نوا فقط محدود به گرافیک‌های سری RTX20 (تورینگ) به بعد است و مدل‌های قبلی را پشتیبانی نخواهد کرد.

💡 ظاهرا باید منتظر حضور Nova در لینوکس نسخه ۶.۱۵ باشیم.

📱 مخزن گیت‌لب
🔹🔹🔹🔹🔹
#news #nova #nouveau #rust #nvidia
🔹🔹🔹🔹🔹
✈️ تلگرام
™️ توییتر
📺 یوتیوب
🐘 ماستودون
🖥 وبسایت
Please open Telegram to view this post
VIEW IN TELEGRAM
Forwarded from یه شعر (Poem Bot)
حافظ | غزلیات | غزل شمارهٔ ۲۳۳

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

#حافظ | گنجور
📍@iipoem
Forwarded from Geek Alerts
This media is not supported in your browser
VIEW IN TELEGRAM
الان میتونید با مدل Gemini 2.0 Flash Experimental همزمان متن و عکس تولید کنید، مثلا بهش بگید رسپی یه غذا رو براتون بنویسه، میاد عکس تمام مراحل رو هم براتون میسازه، اگه میخواید استفاده کنید میتونید وارد سایت زیر بشید و رایگان هست. فرق اصلیش با دیگر مدل‌ها اینه که این مدل به صورت پیش‌فرض خروجی multimodal می‌ده و هماهنگی بین متن و تصویر رو خیلی بهتر توش می‌بینید.

احتمالا بیشترین چیزی که کاربرد داشته باشه تولید محتوا هست.

🔗 aistudio.google.com
🤓 @geekalerts
Please open Telegram to view this post
VIEW IN TELEGRAM
Forwarded from Huge Thinker
تابحال شده یک قرارداد حقوقی رو بخواید بخونید و امضا کنید اما بقدری متن طویل و پر از اصطلاحات پیچیده است که درکش سخته و از جهتی زمان برای خوندنش هم شاید کافی نباشه و به نوعی با قرار گرفتن در یک عمل انجام شده بدون آگاهی چیزی رو امضا کنیم که بار حقوقی داشته باشه.

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

سرویس legal-simplifier یا ساده ساز حقوقی.

https://legal-simplifier-hub.netlify.app

منطق سختی پشتش نیست، صرفا یکسری اصطلاحات رو به دنبالش میگرده و سعی میکنه پیداشون کنه از داخل متن:

const fallbackDefinitions: Record<string, string> = {
'وجه التزام': 'مبلغی که در صورت عدم انجام تعهد باید پرداخت شود.',
'عین مستاجره': 'مال غیرمنقولی که مورد اجاره قرار گرفته است.',
'انتقال قطعی': 'انتقال مالکیت به صورت رسمی و قانونی به خریدار.',
'فسخ قرارداد': 'پایان دادن به قرارداد قبل از موعد مقرر با توجه به شرایط ذکر شده در قرارداد.',
'ضمانت اجرایی': 'ابزاری برای تضمین اجرای تعهدات طرفین قرارداد.'
}


ایده اصلی من اینکه درآینده بتونم ML و الگوریتم های مرسوم Text prossecing هم قاطیش کنم و کمی جذابش کنم :) و درنهایت اگه بتونید کلی متن حقوقی بهش بدید و خروجیش رو باهام به اشتراک بزارید تا اشکالاتش رو دربیاریم که خیلی دمتون گرمه 💫
Forwarded from Seyed Mahdi Notes (Seyed Mahdi)
قیمت ارز و دلار و ... لحظه ای . برای یکی از دوستان هست
@iran98price
پیام اخر ادیت میشه که اسپم نشه:)
Forwarded from Sadra Codes
سامان (از رفیقای گلم) یه ایده خفن پیاده کرده. توی چنلش قیمت لحظه‌ای ارزها رو به نمایش می‌ذاره. منظورم از لحظه‌ای اینه که اسپم نمی‌کنه و آخرین پیام کانال هر لحظه آپدیت میشه. ایده جالبیه! :)

@iran98price
Audio
رقص بهار

شهرداد روحانی
#بی_کلام
@nost_music 🔁
Forwarded from LinNews (Benyamin)
نُوا (NOVA) جایگزین Nouveau خواهد شد.

#NVIDIA #Nouveau #Driver #GPU #NOVA

نُوا، یک درایور DRM لینوکس برای کارت‌های گرافیکی ان‌ویدیا است که با زبان Rust نوشته شده و RedHat آن را توسعه داده است. درایور NOVA ازGPUهایی پشتیبانی می‌کند که دارای GPU System Processor(GSP) باشند. این درحالیست که بسیاری از انتزاعات هنوز درحال توسعه هستند یا به‌طور کامل در نسخه بالادست لینوکس قرار نگرفته اند.
این درایور جدید، از کارت‌های گرافیکی Turing (سری RTX 2000) و جدیدتر پشتیبانی می‌کند. همچنین، در تلاش است تا مدرن و قدرتمند باشد. درضمن، GSP الزامیست زیرا وجود GSP باعث سادگی در توسعه درایور می‌شود.

دنیلو کرومریک (Danilo Krummrich) از RedHat، نسخه بسیار ابتدایی درایور را برای ادغام در کرنل لینوکس ارسال کرده است. البته هنوز برای استفاده روزمره یا سازمانی مناسب نیست، زیرا درحال حاضر هدف حضور NOVA به عنوان بخشی از معماری کرنل است.

منبع خبر


@LinAcademy | @LinNews
Forwarded from LinNews (A k)
Forwarded from LinNews (A k)
بالاخره AMD نسخه‌ی 25.3.1 درایور خود را منتشر کرد.
#AMD #RDNA4 #GPU #Driver #Adernalin
این بروزرسانی اولین حضور معماری RDNA 4 هست و عملکرد بهتری را برای سخت افزارهای جدید AMD ارائه می دهد.
ویژگی های اصلی:
پشتیبانی از محصولات جدید:
کارت های گرافیک RX 9070 XT و RX 9070
پردازنده های Ryzen AI Max+ 395 و Ryzen AI 300 Series با گرافیک های Radeon 840m و 860m
فناوری های جدید:
ویژگی AMD FSR 4: بهبود کیفیت تصویر در بازی ها با استفاده از الگوریتم های مبتنی بر یادگیری ماشین
ویژگی نسخه 2.1 فریم جنریشن سخت افزاری AFMF : کاهش تاری و بهبود کیفیت فریم ها در بازی ها
ویژگی AMD Chat: یک ربات مبتنی بر هوش مصنوعی که به سوالات کاربران درباره سخت افزار AMD پاسخ می دهد
ویژگی AMD Image Inspector: ابزاری برای بهبود کیفیت بازی ها با استفاده از هوش مصنوعی
بهبود عملکرد هوش مصنوعی:
افزایش سرعت در نرم افزارهایی مانند Adobe Lightroom (تا ۷۰٪) و DaVinci Resolve تا (۱۰٪)
پشتیبانی از بازی های جدید:
بازی هایی مانند FragPunk و Split Fiction به طور رسمی پشتیبانی شد.
بهبود پشتیبانی از توسعه دهندگان:
اضافه شدن اطلاعات جدید برای معماری های RDNA 4 و RDNA 3.5
انتشار SDK جدید برای بهبود تجربه ی استریمینگ و رسانه
مشکلات شناخته شده:
برخی مشکلات مانند کاهش عملکرد در بازی های Assetto Corsa Competizione و کرش در بازی Marvel's Spider-Man 2 گزارش شده اند. کاربران می توانند به طور موقت با غیرفعال کردن برخی ویژگی ها مانند AMD Image Inspector این مشکلات را برطرف کنند.
این بروزسانی با ارائه ی پشتیبانی از سخت افزارهای جدید و بهبود عملکرد، تجربه ی بهتری را برای کاربران AMD فراهم می کند. برای دریافت حداکثر عملکرد، باید نرم افزار را به نسخه ی آخر ارتقا دهید.
@LinAcademy | @LinNews
#5min_Rust

قبل از اینکه دوپایی بپریم توی معرفی انواع Data type توی Rust یک تفاوت رو بین Rust, Python ببینیم.
توی rust بر خلاف python برنامه‌نویس نمی‌تونه هر زمانی که دلش خواست توی متغییر مقداری با دیتا تابپ متفاوت بریزه؛ کد زیر توی پایتون درست هست:
my_var  = 5
print(f"The content is {my_var} of type {type(my_var).__name__}")
my_var = "@pyrust"
print(f"The content is {my_var} of type {type(my_var).__name__}")

اما توی rust شما اجازه اینکار رو ندارید
fn main() {
let my_var: i32 = 5;
println!("The content is {my_var} of type {}", std::any::type_name::<i32>());

my_var = "Hello"; // ٍError: expected `i32`, found `&str`
}


پس توی rust خیلی مهم هست که مشخص کنید متغیر شما از چه نوعی باید باشه؛‌ البته توی خیلی موارد نیازی به نوشتن نداره و خود کامپایلر می‌تونه بر اساس استفاده‌ای که از متغییر می‌کنید (اولین نوع داده‌ای‌ که داخلش می‌ریزید) تصمیم بگیره.

پس با این حساب یادگیری Data Type مهم میشه و اولین نوع داده‌ای که بررسی می‌کنیم Integer خواهد بود.
بازم بر خلاف پایتون نوع int توی rust خودش چندین مدل داره؛ بصورت پیش‌فرض اگر هیچ موردی رو انتخاب نکنید کامپایلر برای شما i32 رو درنظر می‌گیره ولی این یعنی چی ؟
i32 : i = Signed, 32 = 32-bit value

اگر نوع int شما با i شروع شده بود یعنی Signed هست و این به این معنی هست که این نوع داده شامل اعداد صحیح مثبت و منفی می‌شه.
عدد 32 نشان دهنده تعداد بیت حافظه هست و محدوده اعدادی که این مقدار می‌تونه نگهداره رو شامل میشه.

برای راحتی من با i8, u8 مثال میزم:
اینجا u به معنی unsigned هست و یعنی این نوع داده اعداد منفی قبول نمی‌کنه؛ برای اینکه بفهمیم یک نوع داده چه رنج اعدادی رو داخل خودش نگهداری می‌کنه می‌تونیم از فرمول زیر استفاده کنیم:

i8 : Signed, 8bit
برای بدست آوردن رنج signed کافیه تعداد bit رو داخل این فرمول بذارید :
[-2^(n-1), (2^(n-1))-1] ==> [-2^7, (2^7)-1) ==> [-128, 127]

u8
برای بدست آوردن رنج unsigned ها کافیه تعداد bit رو داخل این فرمول بذارید:
(2^n)-1 ==> (2^8)-1 ==> 255


علامت ^ نماد توان هست.

اگر با اعداد باینری کمی آشنایی داشته باشید نیازی به حفظ کردن فرمول‌ها نیست؛ توی نوع unsigned ازونجایی که عدد مثبت و منفی رو قبول می‌کنه پس ۱ بیت رو از دست میده برای اینکه مشخص کنه عدد منفی هست یا مثبت پس این یعنی بخش توان فرمول -1 رو خواهد داشت فقط برای unsigned ها
اما توی هر دوحالت حاصل محسابات و به توان رسوندن همیشه -1 رو توی بخش مثبت هم داره؛ خیلی ساده دلیلش اینه که بزرگترین عدد مثبتی رو وقتی می‌تونید بسازید که همه‌ی بیت‌های باینری 1 باشند و هروقت بیت اول (از راست) مقدار 1 بگیره حاصل حتما عددی فرد خواهد بود.

بر همین اساس شما همه‌ی آنچه برای درک جدول تصویر پیوست لازمه رو می‌دونید؛ فقط یک مورد می‌مونه :

arch | isize | usize


که یعنی این نوع به معماری سیستم بستگی داره (معماری سیستم روی index گذاری برای دسترسی به خانه‌های RAM مهم هست) برای همین هرجا صحبت از دسترسی به حافظه یا index , ... باشه این نوع داده رو خواهید دید. اگر سیستم ۳۲ بیتی باشه مقدار isize = i32, usize = u32 خواهند بود و برای سیستم‌های ۶۴ بیتی مقادیر isize=i64, usize=u64 رو خواهیم داشت.

بعد از اون نوع داده float رو داریم؛ شامل f32, f64 تفاوتشون توی precision هست (تعداد اعدادی که بعد از اعشار میاد)

f32 precision: 6-9 digits
f64 precision: 15-17 digits

یعنی برای نوع داده f32 بعد از ۶-۹ رقم اعشار دقت رو از دست می‌دیم و حاصل محاسبات بعد از ۶-۹ رقم اعشار رند شده خواهد بود؛ برای f64 این مقدار به ۱۵-۱۷ میرسه؛ بصورت دیفالت کامپایلر متغیرها رو f64 درنظر میگیره مگر اینکه شما مشخص کنید نوع داده چیز دیگری باشه.

اگر رند کردن براتون قابل قبول نیست Decimal رو باید در نظر بگیرید که خب توی این مرحله راجبش صحبت نمی‌کنیم.


برای تعیین نوع داده هم بعد از ساخت متغییر و قبل از مقدار دهی می‌تونید نوع داده رو مشخص کنید:
let red_pixel: u8 = 25;
let my_negative_number: i32 = -5654891;
let pi: f64 = 3.14


بیشترین سوالی که پرسیده میشه؛ آیا باید همیشه برای پرفورمنس بیشتر کوچکترین نوع داده رو انتخاب کنیم ؟
خیر.
اولین و مهمترین موضوع؛ اجرا شدن درست برنامه هست؛ اما بعضی وقتا کاملا میشه مطمئن بود نوع داده‌ای باید چه مقداری باشه.
مثلا فرض کنید ما دارید یک برنامه برای پردازش تصاویر jpg می‌نویسید؛ توی این تصاویر همیشه مقدار هر پیکسل بین 0-255 خواهد بود و این یعنی شما برای متغییرهای کار با پیکسل می‌تونید با خیالت راحت نوع داده رو روی u8 تعریف کنید.
اما برای مواردی که مطمئن نیستید i32 شروع خوبی هست که پیش‌فرض کامپایلر هم همین مقدار هست.
#5min_Rust

از حالت‌های دیگه‌ای که می‌تونید نوع داده رو مشخص کنید استفاده از _ و البته as که ممکن توی کدهای دیگران ببیند.
در نهایت
std::<TYPE>::MIN
std::<TYPE>::MAX

رو هم برای دیدن کوچکترین و بزرگترین مقدار اون نوع داده می‌تونید print کنید.
Forwarded from Geek Alerts
گوگل میگه همه‌ی بازی‌های اندروید روی ویندوز با Google Play Games در دسترس میشن، قبلا اینجوری بود که توسعه‌دهنده‌ها خودشون انتخاب میکردن بازیشون روی این پلتفرم بیاد ولی الان پیش‌فرض همه بازی‌ها میان.

از طرفی گوگل میگه بازی‌هایی که استانداردهای بازی توی کامپیوتر رو هم رعایت کرده باشن (مثلا با دسته بشه بازی کرد) یه سری نشان مثل بهینه‌شده بهشون میده که متوجه بشید.

https://play.google.com/googleplaygames
🔗 theverge
🤓 @geekalerts
Please open Telegram to view this post
VIEW IN TELEGRAM
Forwarded from  (Amiria Maher)
دنبال کاری؟

بیا تو:
@BAFO_channel

@easyhirng


#موقت
Forwarded from Geek Alerts
عربستان سعودی بازی Pokémon Go را خریداری کرد

در واقع شرکت Scopely خریدار جدید بازی هست که میشه زیرمجموعه‌ی یه شرکت عربستانی به اسم Savvy Games و این شرکت هم مال صندوق سرمایه‌گذاری عمومی دولت عربستان سعودیه.

میشه یه جورایی گفت الان پوکمون گو غیر مستقیم متعلق به دولت عربستان سعودی هست.

🔗 404media
🤓 @geekalerts
Please open Telegram to view this post
VIEW IN TELEGRAM