دوستان شرکت گوگل مارو تحریم کرده و از این به بعد حتی واسه ساخت اکانت جیمیل با مکافات ربروییم💔
راست و دروغش هنوز کامل مشخص نشده
راست و دروغش هنوز کامل مشخص نشده
خبری
❤7🗿4
سلام، خسته نباشید 🌱
یه نکتهی کوچیک راجع به Tailwind CSS میخواستم بگم که شاید به کارتون بیاد.
توی طراحی معمولاً برای هر سکشن یا بخشی که میخوایم پیادهسازی کنیم، یه Width، Height و... مشخص شده که معمولاً بر اساس Pixel هست.
حالا برای تبدیل این مقدارها به مقادیر Tailwind، معمولاً میتونیم از مقادیر موجود توی داکیومنت خود Tailwind استفاده کنیم؛ ولی خب بعضی وقتا ممکنه داکیومنت برامون باز نشه، بهش دسترسی نداشته باشیم یا اصلاً حوصلهی باز کردنش رو نداشته باشیم 😄
اینجا یه راه خیلی ساده داریم 👇
مثلاً فرض کنید عرض سکشن ما 250px هست و میخوایم مقدار مناسبش رو برای Tailwind پیدا کنیم.
کافیه 250 رو تقسیم بر 4 کنیم:
250 ÷ 4 = 62.5
پس مقدار Tailwind ما میشه:
w-62.5
البته بسته به نیازتون میتونید مقدار رو گرد کنید و از "w-62" یا مقدار دقیقتر استفاده کنید.
🔸 دلیلش هم اینه که مقیاس پیشفرض Tailwind معمولاً بر اساس هر واحد = 0.25rem هست که در تنظیمات پیشفرض، معادل 4px در نظر گرفته میشه.
پس بهصورت خلاصه:
Pixel ÷ 4 = مقدار Tailwind
مثلاً:
100px → 25
200px → 50
250px → 62.5
400px → 100
یه ترفند سادهست، ولی وقتی زیاد با Tailwind کار کنید، خیلی به دردتون میخوره. 🚀
یه نکتهی کوچیک راجع به Tailwind CSS میخواستم بگم که شاید به کارتون بیاد.
توی طراحی معمولاً برای هر سکشن یا بخشی که میخوایم پیادهسازی کنیم، یه Width، Height و... مشخص شده که معمولاً بر اساس Pixel هست.
حالا برای تبدیل این مقدارها به مقادیر Tailwind، معمولاً میتونیم از مقادیر موجود توی داکیومنت خود Tailwind استفاده کنیم؛ ولی خب بعضی وقتا ممکنه داکیومنت برامون باز نشه، بهش دسترسی نداشته باشیم یا اصلاً حوصلهی باز کردنش رو نداشته باشیم 😄
اینجا یه راه خیلی ساده داریم 👇
مثلاً فرض کنید عرض سکشن ما 250px هست و میخوایم مقدار مناسبش رو برای Tailwind پیدا کنیم.
کافیه 250 رو تقسیم بر 4 کنیم:
250 ÷ 4 = 62.5
پس مقدار Tailwind ما میشه:
w-62.5
البته بسته به نیازتون میتونید مقدار رو گرد کنید و از "w-62" یا مقدار دقیقتر استفاده کنید.
🔸 دلیلش هم اینه که مقیاس پیشفرض Tailwind معمولاً بر اساس هر واحد = 0.25rem هست که در تنظیمات پیشفرض، معادل 4px در نظر گرفته میشه.
پس بهصورت خلاصه:
Pixel ÷ 4 = مقدار Tailwind
مثلاً:
100px → 25
200px → 50
250px → 62.5
400px → 100
یه ترفند سادهست، ولی وقتی زیاد با Tailwind کار کنید، خیلی به دردتون میخوره. 🚀
❤12
تیلویند یا بوتاسترپ؟
یکی از انتخابهای همیشگی در شروع پروژههای فرانتاند 👇
پس کدوم رو انتخاب کنیم؟
اگر سرعت و کامپوننتهای آماده برات مهمتره بوت استرپ واسه توعه.
اگر آزادی طراحی و ساخت UI اختصاصی میخوای تیلویند انتخاب توعه.
در نهایت، هیچکدوم برای همه پروژهها «بهتر» نیست؛ انتخاب درست به نیاز پروژه بستگی داره.
یکی از انتخابهای همیشگی در شروع پروژههای فرانتاند 👇
Bootstrapــــ
• کامپوننتهای آماده
• شروع سریعتر
• مناسب پنلها و رابطهای استاندارد
• یادگیری اولیه سادهتر
Tailwind CSS
• آزادی بیشتر در طراحی
• مبتنی بر کلاسهای Utility
• مناسب طراحیهای اختصاصی
• کنترل بیشتر روی ظاهر کامپوننتها
پس کدوم رو انتخاب کنیم؟
اگر سرعت و کامپوننتهای آماده برات مهمتره بوت استرپ واسه توعه.
اگر آزادی طراحی و ساخت UI اختصاصی میخوای تیلویند انتخاب توعه.
در نهایت، هیچکدوم برای همه پروژهها «بهتر» نیست؛ انتخاب درست به نیاز پروژه بستگی داره.
❤6🔥3👏1
</awat>
از دلِ نومیدی، امیدها بجوشد مولانا
ای آنکه طبیب دردِ مایی
این درد زِ حد رفت چه میفرمایی؟!
بزرگداشت مولانای ایران گرامی باد
این درد زِ حد رفت چه میفرمایی؟!
مولانا
بزرگداشت مولانای ایران گرامی باد
❤6🔥3✍2
🚀 ۴ سایت برای دموهای آماده JavaScript
اگر برای پروژههای فرانتاند دنبال ایده و نمونهکد آماده هستید، این ۴ سایت را ببینید:
🌐 https://codepen.io/
🌐 https://jsfiddle.net/
🌐 https://tympanus.net/codrops/
🌐 https://threejs.org/examples/
@awat_dev
اگر برای پروژههای فرانتاند دنبال ایده و نمونهکد آماده هستید، این ۴ سایت را ببینید:
🔹 CodePen
دموهای متنوع HTML، CSS و JavaScript
🌐 https://codepen.io/
🔹 JSFiddle
تست و اجرای سریع کدهای JavaScript
🌐 https://jsfiddle.net/
🔹 Codrops
انیمیشنها و افکتهای حرفهای برای وب
🌐 https://tympanus.net/codrops/
🔹 Three.js Examples
دموهای جذاب سهبعدی و WebGL
🌐 https://threejs.org/examples/
@awat_dev
❤8🔥1
برف، سرما، کوهستان، طاعون، 2027
البته هیچ چیز قطعی نیست!
Perhaps the start of a disastrous season.
البته هیچ چیز قطعی نیست!
🗿4👾3❤2🕊2🤝2
توی دوران دبستان به همهمون گفتن یه «مثلث آتش» داریم. یعنی چی؟
اگه یکی از این سه تا نباشه، آتشی در کار نیست❌
توی حرفهای شدن توی کار هم دقیقاً همین قضیه برقراره:
❌ اگر دانش نداشته باشی : چیزی برای ارائه دادن نداری.
❌ اگر تمرین نداشته باشی : دانشی که کسب کردی بیفایدهست، چون فقط با تمرینه که ملکهی ذهن میشه.
❌ اگر بازخورد نداشته باشی : یعنی نتیجهی تمرینت رو بررسی نمیکنی و خودت رو با حرفهایترها مقایسه نمیکنی؛ همین جلوی رشدت رو میگیره.
همیشه همیشه همیشه این مثلث رو توی کارتون رعایت کنید اگر میخاید بهترین باشید
@awat_dev
آتش = هوا + ماده سوختی + گرما
اگه یکی از این سه تا نباشه، آتشی در کار نیست❌
توی حرفهای شدن توی کار هم دقیقاً همین قضیه برقراره:
حرفهای شدن = کسب دانش + تمرین + بازخورد
❌ اگر دانش نداشته باشی : چیزی برای ارائه دادن نداری.
❌ اگر تمرین نداشته باشی : دانشی که کسب کردی بیفایدهست، چون فقط با تمرینه که ملکهی ذهن میشه.
❌ اگر بازخورد نداشته باشی : یعنی نتیجهی تمرینت رو بررسی نمیکنی و خودت رو با حرفهایترها مقایسه نمیکنی؛ همین جلوی رشدت رو میگیره.
همیشه همیشه همیشه این مثلث رو توی کارتون رعایت کنید اگر میخاید بهترین باشید
@awat_dev
❤10🔥3🤝3🤩2💯2🆒1
Idempotent & Safe methods در HTTP 🌐
دو مفهوم مهم HTTP که خیلی وقتها با هم اشتباه گرفته میشن: Safe و Idempotent.
SAFE METHOD 🛡
یه متد وقتی Safe (ایمن) محسوب میشه که هدف اصلی ریکوئست فقط خوندن اطلاعات باشه و منجر به تغییر معنادار و عمدی resource نشه.
مثلا:
اینجا فقط اطلاعات کاربر رو میخونیم. پس GET یه متد safe محسوب میشه.
البته سرور ممکنه برای این ریکوئست لاگ یا کش ایجاد کنه. اینها safe بودن GET رو نقض نمیکنن. چون منظور از تغییر، تغییر هدفمند و عمدی هست. مثل عوض کردن نام کاربر.
HEAD و OPTIONS هم safe هستن.
اما POST و PUT و PATCH و DELETE برای ایجاد تغییر طراحی شدن.
IDEMPOTENT METHOD 🔄
idempotent (هم توان؟!) بودن یعنی اگر یه ریکوئست رو چند بار اجرا کنیم اثر نهایی اون روی سرور با اجرای یکباره ریکوئست یکسان باشه.
به زبون ریاضی:
f(f(x)) = f(x)
مثلا اگر این ریکوئست رو هزار بار هم بفرستیم، در نهایت داریم: name = awat
پس PUT با اینکه safe نیست، idempotent هست.
DELETE هم idempotent محسوب میشه:
بار اول کاربر حذف میشه. ریکوئستهای بعدی ممکنه 404 برگردونن، اما وضعیت نهایی همچنان اینه که کاربر حذف شده. دقیقا مثل دفعه اول.
مشخصه که همه متدهای safe تو دسته idempotentها هم قرار میگیرن.
و یه نکته مهم 🧨
idempotency فقط به اسم متد وابسته نیست. نحوه پیادهسازی اندپوینت هم اهمیت داره.
مثلا
هر بار که ریکوئست رو میفرستیم یه واحد به سن اضافه میشه.
اینجا اجرای دوباره ریکوئست، اثر جدیدی ایجاد میکنه؛ بنابراین این عملیات idempotent نیست.
البته گفتیم HTTP متد PUT رو idempotent معرفی کرده. پس این اندپوینت درست طراحی نشده و برای این عملیات بهتره از PATCH استفاده کنیم.
حالا خود PATCH تو کدوم دستهست؟
ضمانت خاصی براش نداریم. این موضوع به نحوه طراحیمون بستگی داره.
مثلا این یه عملیات idempotent هست:
اما اگر همچین اندپوینتی داشته باشیم:
نتیجه میشه:
18 >> 19 >> 20
پس non-idempotent محسوب میشه.
POST و خطر Retry ☠️
POST رسما idempotent تعریف نشده. این موضوع تو عملیاتهای حساسی مثل تراکنش اهمیت زیادی داره.
مثلا:
فرض کنید پرداخت با موفقیت انجام میشه، اما به هر دلیلی کلاینت برای همین پرداخت دوباره درخواست بفرسته.
اگر سرور این دو ریکوئست رو دو تراکنش متمایز در نظر بگیره، مبلغ دو بار از موجودی کاربر کسر میشه.
برای جلوگیری از این مشکل میتونیم از idempotency key داخل هدر استفاده کنیم:
سرور این کلید و نتیجه تراکنش رو ذخیره میکنه. اگر همون ریکوئست دوباره با کلید "abc123" فرستاده شه (retry)، سرور به جای انجام دوباره تراکنش، نتیجه قبلی رو برمیگردونه.
البته این کلید باعث نمیشه POST ماهیت idempotent بگیره؛ ما با این مکانیزم صرفا یه عملیات مشخص رو در برابر ریکوئستهای تکراری مقاوم میکنیم.
پس دو سوال متفاوت داریم:
Safe:
Idempotent:
مطالعه بیشتر در MDN 🤓
Safe
Idempotent
Idempotency-Key header
@awat_dev
دو مفهوم مهم HTTP که خیلی وقتها با هم اشتباه گرفته میشن: Safe و Idempotent.
SAFE METHOD 🛡
یه متد وقتی Safe (ایمن) محسوب میشه که هدف اصلی ریکوئست فقط خوندن اطلاعات باشه و منجر به تغییر معنادار و عمدی resource نشه.
مثلا:
GET /users/1
اینجا فقط اطلاعات کاربر رو میخونیم. پس GET یه متد safe محسوب میشه.
البته سرور ممکنه برای این ریکوئست لاگ یا کش ایجاد کنه. اینها safe بودن GET رو نقض نمیکنن. چون منظور از تغییر، تغییر هدفمند و عمدی هست. مثل عوض کردن نام کاربر.
HEAD و OPTIONS هم safe هستن.
اما POST و PUT و PATCH و DELETE برای ایجاد تغییر طراحی شدن.
IDEMPOTENT METHOD 🔄
idempotent (هم توان؟!) بودن یعنی اگر یه ریکوئست رو چند بار اجرا کنیم اثر نهایی اون روی سرور با اجرای یکباره ریکوئست یکسان باشه.
به زبون ریاضی:
f(f(x)) = f(x)
مثلا اگر این ریکوئست رو هزار بار هم بفرستیم، در نهایت داریم: name = awat
PUT /users/1
{
"name": "awat"
}
پس PUT با اینکه safe نیست، idempotent هست.
DELETE هم idempotent محسوب میشه:
DELETE /users/1
بار اول کاربر حذف میشه. ریکوئستهای بعدی ممکنه 404 برگردونن، اما وضعیت نهایی همچنان اینه که کاربر حذف شده. دقیقا مثل دفعه اول.
مشخصه که همه متدهای safe تو دسته idempotentها هم قرار میگیرن.
و یه نکته مهم 🧨
idempotency فقط به اسم متد وابسته نیست. نحوه پیادهسازی اندپوینت هم اهمیت داره.
مثلا
PUT /users/1
{
"operation": "increment_age"
}
هر بار که ریکوئست رو میفرستیم یه واحد به سن اضافه میشه.
اینجا اجرای دوباره ریکوئست، اثر جدیدی ایجاد میکنه؛ بنابراین این عملیات idempotent نیست.
البته گفتیم HTTP متد PUT رو idempotent معرفی کرده. پس این اندپوینت درست طراحی نشده و برای این عملیات بهتره از PATCH استفاده کنیم.
حالا خود PATCH تو کدوم دستهست؟
ضمانت خاصی براش نداریم. این موضوع به نحوه طراحیمون بستگی داره.
مثلا این یه عملیات idempotent هست:
PATCH /users/1
{
"name": "awat"
}
اما اگر همچین اندپوینتی داشته باشیم:
PATCH /users/1
{
"operation": "increment_age"
}
نتیجه میشه:
18 >> 19 >> 20
پس non-idempotent محسوب میشه.
POST و خطر Retry ☠️
POST رسما idempotent تعریف نشده. این موضوع تو عملیاتهای حساسی مثل تراکنش اهمیت زیادی داره.
مثلا:
POST /payments
{
"amount": 100
}
فرض کنید پرداخت با موفقیت انجام میشه، اما به هر دلیلی کلاینت برای همین پرداخت دوباره درخواست بفرسته.
اگر سرور این دو ریکوئست رو دو تراکنش متمایز در نظر بگیره، مبلغ دو بار از موجودی کاربر کسر میشه.
برای جلوگیری از این مشکل میتونیم از idempotency key داخل هدر استفاده کنیم:
POST /payments
Idempotency-Key: abc123
{
"amount": 100
}
سرور این کلید و نتیجه تراکنش رو ذخیره میکنه. اگر همون ریکوئست دوباره با کلید "abc123" فرستاده شه (retry)، سرور به جای انجام دوباره تراکنش، نتیجه قبلی رو برمیگردونه.
البته این کلید باعث نمیشه POST ماهیت idempotent بگیره؛ ما با این مکانیزم صرفا یه عملیات مشخص رو در برابر ریکوئستهای تکراری مقاوم میکنیم.
پس دو سوال متفاوت داریم:
Safe:
هدف از طراحی این عملیات تغییر عمدی در سرور بوده؟
Idempotent:
اگر همین ریکوئست رو دوباره بفرستیم، وضعیت نهایی سرور مثل نتیجه اجرای اول باقی میمونه؟
مطالعه بیشتر در MDN 🤓
Safe
Idempotent
Idempotency-Key header
@awat_dev
❤8👏4🆒1
سه تا از مخرب ترین حملات سایبری تاریخ
∆ نوتپتیا توسط روسیه در 2017
∆ استاکسنت توسط آمریکا و اسرائیل علیه ایران 2010
∆ کولونیال پایپلاین احتمالا توسط روسیه 2021
@awat_dev
∆ نوتپتیا توسط روسیه در 2017
شرکتهای اوکراینی از یه نرمافزار حسابداری به اسم M.E.Doc استفاده میکردن. هکرها این نرمافزار رو هک کردن و از طریق آپدیتش، ویروس رو پخش کردن، ده میلیارد دلار خسارت جهانی وارد شد و شبکه یکی از غول های کشتیرانی در هفت دقیقه نابود شد
∆ استاکسنت توسط آمریکا و اسرائیل علیه ایران 2010
یه فلش مموری توسط یک مهندس ایرانی به کامپیوترهای نطنز وصل شد و ویروس منتقل شد.
حدود ۱۰۰۰ سانتریفیوژ رو از کار انداخت و روند غنیسازی اورانیوم رو متوقف کرد.
سیستم طوری دستکاری شده بود که اپراتورها همه چیز عادی میدیدن، در حالی که سانتریفیوژها داشتن خراب میشدن.
∆ کولونیال پایپلاین احتمالا توسط روسیه 2021
بزرگترین خط لوله سوخت آمریکا هک شد. از یه VPN قدیمی بدون احراز هویت دو مرحلهای وارد شدند.
کل خط لوله تعطیل شد، کمبود بنزین و وضعیت اضطراری در ۱۷ ایالت.
۴.۴ میلیون دلار باج پرداخت شد.
@awat_dev
🗿5❤3💯3
یه نکته بسیار مهم رو گفتم امشب باهاتون در میون بزارم
کد هایی که میزنید رو درک کنید نه اینکه اونارو حفظ کنید، قرار نیست سینتکس تک تک متُد ها یا ویژگی های HTML و CSS رو از بر باشید.
چیزی که شما رو از یه کد نویسِ کپی کن جدا میکنه اینه که بدونید:
ممکنه فردا سینتکس یه متد رو یادتون نباشه؛ مهم نیست، سرچش میکنید. اما اگه منطق پشت کد رو نفهمیده باشید،
با عوض شدن پروژه، مشکل همچنان همراهتونه.
برنامهنویسی حفظ کردن کد نیست؛
برنامهنویسی یعنی یاد بگیری چطور فکر کنی و چطور مسئله رو تحلیل کنی که پس فردا به باگ های فضایی خوردی بتونی از پسشون بر بیای.
@awat_dev
کد هایی که میزنید رو درک کنید نه اینکه اونارو حفظ کنید، قرار نیست سینتکس تک تک متُد ها یا ویژگی های HTML و CSS رو از بر باشید.
چیزی که شما رو از یه کد نویسِ کپی کن جدا میکنه اینه که بدونید:
° چرا این کد رو نوشتید
° این کد چه کاری واستون انجام میده
° کِی و کجا ازش استفاده میشه
ممکنه فردا سینتکس یه متد رو یادتون نباشه؛ مهم نیست، سرچش میکنید. اما اگه منطق پشت کد رو نفهمیده باشید،
با عوض شدن پروژه، مشکل همچنان همراهتونه.
برنامهنویسی حفظ کردن کد نیست؛
برنامهنویسی یعنی یاد بگیری چطور فکر کنی و چطور مسئله رو تحلیل کنی که پس فردا به باگ های فضایی خوردی بتونی از پسشون بر بیای.
@awat_dev
❤8🔥3🆒1
از درون آشفته و ظاهر، چو کوهی استوار
رنجها اینگونه مارا مرد بار آوردهاند
رنجها اینگونه مارا مرد بار آوردهاند
صائب
❤12
❌قابل توجه اونایی که بین کار و درس تعادل ندارن و آخرش یکی رو انتخاب میکنن:
یه روز بشینین برنامه بچینین؛ بگین امروز فلان درس، فلان قسمت پروژه و فلان کار. بعد وقتتون رو نگاه کنین و کارا رو متناسب با همون تقسیم کنین، یه استراحت کوچیک کنین و شروع کنین.
سعی کنین آخر روز، هرچقدر شده، تیک کاراتون رو بزنین. اون وقته که شب با حس سبکی سر روی بالش میذارین، چون میدونین وقتتون رو هدر ندادین.
نتیجه این برنامه ریزی خستگی هست، ولی خستگیِ خوشاینده
@awat_dev
یه روز بشینین برنامه بچینین؛ بگین امروز فلان درس، فلان قسمت پروژه و فلان کار. بعد وقتتون رو نگاه کنین و کارا رو متناسب با همون تقسیم کنین، یه استراحت کوچیک کنین و شروع کنین.
سعی کنین آخر روز، هرچقدر شده، تیک کاراتون رو بزنین. اون وقته که شب با حس سبکی سر روی بالش میذارین، چون میدونین وقتتون رو هدر ندادین.
نتیجه این برنامه ریزی خستگی هست، ولی خستگیِ خوشاینده
این حس رو فقط کسی میفهمه که تجربه کرده
@awat_dev
❤7🔥5🆒1