[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"verticals":3,"tag-webdev-8":44,"search-suggestions":299,"tags-all":324},[4,20,32],{"id":5,"slug":6,"name":7,"tagline":8,"description":9,"accentFrom":10,"accentTo":11,"icon":12,"defaultLocale":13,"locales":14,"features":16,"position":19},"019fe637-3d33-714b-b57f-23e163ffca0c","dev","Web Development","Read it. Run it. Prove it.","A post a day on modern web development — most with an editable playground and a quiz that explains every answer. Free, no account needed.","violet-500","cyan-400","◇","en",[13,15],"fa",{"courses":17,"paths":17,"articles":17,"exams":18,"flashcards":18,"packages":17,"community":17,"certificates":17,"teams":17,"commerce":17},true,false,0,{"id":21,"slug":22,"name":23,"tagline":24,"description":25,"accentFrom":26,"accentTo":10,"icon":27,"defaultLocale":13,"locales":28,"features":30,"position":31},"019fe637-3dc2-754c-8657-0f175bfee7c6","lang","Languages","Learn a language the way you learn a codebase.","Grammar explained the way good documentation explains an API — one idea at a time, each with a quiz.","amber-400","⌘",[13,15,29],"es",{"courses":18,"paths":18,"articles":17,"exams":18,"flashcards":17,"packages":18,"community":17,"certificates":17,"teams":18,"commerce":18},2,{"id":33,"slug":34,"name":35,"tagline":36,"description":37,"accentFrom":38,"accentTo":39,"icon":40,"defaultLocale":13,"locales":41,"features":42,"position":43},"7b3c16f2-931d-410e-802e-e1fa4edab7de","soft","Soft Skills","The half of the job nobody wrote documentation for.","Weekly, on the parts of working life that decide more than your code does — first weeks, meetings, interviews, promotions, and the people around you. Written from what actually happens, and recorded as a podcast you can listen to on the walk.","emerald-400","teal-300","◉",[13],{"courses":18,"paths":18,"articles":17,"exams":18,"flashcards":18,"packages":18,"community":17,"certificates":18,"teams":18,"commerce":18},3,{"items":45,"meta":294},[46,80,99,122,142,165,183,201,222,240,258,276],{"id":47,"slug":48,"title":49,"subtitle":50,"excerpt":51,"coverUrl":52,"locale":13,"readingMinutes":53,"publishedAt":54,"viewCount":55,"likeCount":19,"commentCount":19,"author":56,"vertical":61,"topic":62,"tags":65,"_count":77,"playground":79,"hasQuiz":17,"hasPlayground":17},"019fe660-416e-7357-854c-5a7b56d68629","css-logical-properties","Your `margin-left` doesn't exist in Arabic. CSS logical properties fix that.",null,"Physical CSS properties like `margin-left` and `padding-right` break silently when a layout needs to support right-to-left languages. Logical properties replace the physical axis with a writing-mode-aware model — one codebase, every direction.","\u002Fmedia\u002Fcovers\u002Fcss-logical-properties.png",5,"2026-07-17T08:18:05.044Z",412,{"id":57,"name":58,"username":59,"avatarUrl":50,"headline":60},"019fe637-3c25-7088-9034-39c9f15dc3c8","Parsa Jiravand","parsa","Frontend engineer · building bestpractic",{"slug":6,"name":7,"accentFrom":10,"accentTo":11},{"slug":63,"name":64},"css","CSS",[66,68,71,74],{"slug":63,"name":67,"color":50},"Css",{"slug":69,"name":70,"color":50},"webdev","Webdev",{"slug":72,"name":73,"color":50},"frontend","Frontend",{"slug":75,"name":76,"color":50},"html","Html",{"assessments":78},1,{"slug":48},{"id":81,"slug":82,"title":83,"subtitle":50,"excerpt":84,"coverUrl":85,"locale":13,"readingMinutes":86,"publishedAt":87,"viewCount":88,"likeCount":19,"commentCount":19,"author":89,"vertical":90,"topic":91,"tags":92,"_count":97,"playground":98,"hasQuiz":17,"hasPlayground":17},"019fe660-39f9-768b-be22-fcd49b6abf6d","css-subgrid-nested-grid-alignment","Your CSS Grid cards look misaligned. `subgrid` is the fix you didn't know existed.","CSS Grid controls your outer container, but its children can't participate in the same tracks. `subgrid` closes that gap — nested elements align to the parent grid's rows and columns without padding hacks, fixed heights, or JavaScript measurements.","\u002Fmedia\u002Fcovers\u002Fcss-subgrid-nested-grid-alignment.png",4,"2026-07-16T08:21:27.248Z",499,{"id":57,"name":58,"username":59,"avatarUrl":50,"headline":60},{"slug":6,"name":7,"accentFrom":10,"accentTo":11},{"slug":63,"name":64},[93,94,95,96],{"slug":63,"name":67,"color":50},{"slug":69,"name":70,"color":50},{"slug":72,"name":73,"color":50},{"slug":75,"name":76,"color":50},{"assessments":78},{"slug":82},{"id":100,"slug":101,"title":102,"subtitle":50,"excerpt":103,"coverUrl":104,"locale":13,"readingMinutes":53,"publishedAt":105,"viewCount":106,"likeCount":19,"commentCount":19,"author":107,"vertical":108,"topic":109,"tags":112,"_count":120,"playground":121,"hasQuiz":17,"hasPlayground":17},"019fe660-32b6-757d-a975-3860df795f67","immutable-array-methods","Your `.sort()` is mutating state. JavaScript finally gave you the fix.","The classic array methods — sort, reverse, splice — mutate the original array, silently breaking React state updates and surprising anyone who forgot to spread first. ES2023 added four immutable counterparts: toSorted, toReversed, toSpliced, and with.","\u002Fmedia\u002Fcovers\u002Fimmutable-array-methods.png","2026-07-15T08:22:28.270Z",268,{"id":57,"name":58,"username":59,"avatarUrl":50,"headline":60},{"slug":6,"name":7,"accentFrom":10,"accentTo":11},{"slug":110,"name":111},"javascript","JavaScript",[113,115,116,117],{"slug":110,"name":114,"color":50},"Javascript",{"slug":69,"name":70,"color":50},{"slug":72,"name":73,"color":50},{"slug":118,"name":119,"color":50},"react","React",{"assessments":78},{"slug":101},{"id":123,"slug":124,"title":125,"subtitle":50,"excerpt":126,"coverUrl":127,"locale":13,"readingMinutes":86,"publishedAt":128,"viewCount":129,"likeCount":19,"commentCount":19,"author":130,"vertical":131,"topic":132,"tags":133,"_count":140,"playground":141,"hasQuiz":17,"hasPlayground":17},"019fe660-2b2e-71fb-a0d1-fd1509765d3b","object-groupby-replace-reduce","You've been writing this `reduce` a hundred times. `Object.groupBy` does it in one.","Grouping an array by a key is one of the most common data transforms in frontend code. You've been wiring it by hand with `reduce` for years. `Object.groupBy` is the native version — no helper, no library, no ceremony.","\u002Fmedia\u002Fcovers\u002Fobject-groupby-replace-reduce.png","2026-07-14T08:16:56.309Z",241,{"id":57,"name":58,"username":59,"avatarUrl":50,"headline":60},{"slug":6,"name":7,"accentFrom":10,"accentTo":11},{"slug":110,"name":111},[134,135,136,137],{"slug":110,"name":114,"color":50},{"slug":69,"name":70,"color":50},{"slug":72,"name":73,"color":50},{"slug":138,"name":139,"color":50},"node","Node",{"assessments":78},{"slug":124},{"id":143,"slug":144,"title":145,"subtitle":50,"excerpt":146,"coverUrl":147,"locale":13,"readingMinutes":148,"publishedAt":149,"viewCount":150,"likeCount":19,"commentCount":19,"author":151,"vertical":152,"topic":153,"tags":154,"_count":163,"playground":164,"hasQuiz":17,"hasPlayground":17},"019fe660-2335-7652-9e51-7c6f28871874","weekly-javascript-event-loop","JavaScript Event Loop Explained: The Complete Guide","Learn how the JavaScript event loop really works — call stack, microtasks, and macrotasks — with worked examples, edge cases, and a cheat sheet.","\u002Fmedia\u002Fcovers\u002Fweekly-javascript-event-loop.png",13,"2026-07-13T09:36:33.464Z",539,{"id":57,"name":58,"username":59,"avatarUrl":50,"headline":60},{"slug":6,"name":7,"accentFrom":10,"accentTo":11},{"slug":110,"name":111},[155,156,157,160],{"slug":110,"name":114,"color":50},{"slug":69,"name":70,"color":50},{"slug":158,"name":159,"color":50},"tutorial","Tutorial",{"slug":161,"name":162,"color":50},"programming","Programming",{"assessments":78},{"slug":144},{"id":166,"slug":167,"title":168,"subtitle":50,"excerpt":169,"coverUrl":170,"locale":13,"readingMinutes":53,"publishedAt":171,"viewCount":172,"likeCount":19,"commentCount":19,"author":173,"vertical":174,"topic":175,"tags":176,"_count":181,"playground":182,"hasQuiz":17,"hasPlayground":17},"019fe660-1be2-74dd-aa56-0c8fd84204fd","promise-concurrency-all-settled-any-race","You reach for `Promise.all` for every concurrent request. Here's when to use the other three.","`Promise.all` fails the moment any one request fails. `allSettled`, `any`, and `race` each solve a different concurrency problem — dashboard partial results, CDN failover, and timeouts. Here's the taxonomy.","\u002Fmedia\u002Fcovers\u002Fpromise-concurrency-all-settled-any-race.png","2026-07-13T09:36:32.501Z",221,{"id":57,"name":58,"username":59,"avatarUrl":50,"headline":60},{"slug":6,"name":7,"accentFrom":10,"accentTo":11},{"slug":110,"name":111},[177,178,179,180],{"slug":110,"name":114,"color":50},{"slug":69,"name":70,"color":50},{"slug":72,"name":73,"color":50},{"slug":138,"name":139,"color":50},{"assessments":78},{"slug":167},{"id":184,"slug":185,"title":186,"subtitle":50,"excerpt":187,"coverUrl":188,"locale":13,"readingMinutes":86,"publishedAt":189,"viewCount":190,"likeCount":19,"commentCount":19,"author":191,"vertical":192,"topic":193,"tags":194,"_count":199,"playground":200,"hasQuiz":17,"hasPlayground":17},"019fe660-1462-723e-9605-66ffa7e98f42","popover-api-native-popovers","Your dropdown is a div. The browser has a native popover now.","Custom dropdowns, tooltips, and menus built with stacked divs and click-outside listeners — the Popover API landed in every browser in 2024, and the baseline version is two HTML attributes.","\u002Fmedia\u002Fcovers\u002Fpopover-api-native-popovers.png","2026-07-12T08:24:42.323Z",254,{"id":57,"name":58,"username":59,"avatarUrl":50,"headline":60},{"slug":6,"name":7,"accentFrom":10,"accentTo":11},{"slug":110,"name":111},[195,196,197,198],{"slug":69,"name":70,"color":50},{"slug":72,"name":73,"color":50},{"slug":110,"name":114,"color":50},{"slug":63,"name":67,"color":50},{"assessments":78},{"slug":185},{"id":202,"slug":203,"title":204,"subtitle":50,"excerpt":205,"coverUrl":206,"locale":13,"readingMinutes":53,"publishedAt":207,"viewCount":208,"likeCount":19,"commentCount":19,"author":209,"vertical":210,"topic":211,"tags":214,"_count":220,"playground":221,"hasQuiz":17,"hasPlayground":17},"019fe660-0d25-72d6-8fd8-3cf3c3592e54","typescript-satisfies-operator","Your TypeScript config objects are losing type information. `satisfies` fixes it.","Type annotations widen your object types and erase the precise values TypeScript inferred. The `satisfies` operator validates against a type without changing what TypeScript keeps — you get the check without the widening.","\u002Fmedia\u002Fcovers\u002Ftypescript-satisfies-operator.png","2026-07-11T08:03:26.200Z",316,{"id":57,"name":58,"username":59,"avatarUrl":50,"headline":60},{"slug":6,"name":7,"accentFrom":10,"accentTo":11},{"slug":212,"name":213},"typescript","TypeScript",[215,217,218,219],{"slug":212,"name":216,"color":50},"Typescript",{"slug":69,"name":70,"color":50},{"slug":110,"name":114,"color":50},{"slug":72,"name":73,"color":50},{"assessments":78},{"slug":203},{"id":223,"slug":224,"title":225,"subtitle":50,"excerpt":226,"coverUrl":227,"locale":13,"readingMinutes":86,"publishedAt":228,"viewCount":229,"likeCount":19,"commentCount":19,"author":230,"vertical":231,"topic":232,"tags":233,"_count":238,"playground":239,"hasQuiz":17,"hasPlayground":17},"019fe660-0596-7433-9dc2-0fc620be2d0f","structuredclone-deep-clone","You've been deep-cloning objects with a JSON hack. `structuredClone` does it right.","JSON.parse(JSON.stringify(obj)) silently corrupts Dates, Maps, Sets, and undefined values. structuredClone is the native replacement — no library, no import, no surprises.","\u002Fmedia\u002Fcovers\u002Fstructuredclone-deep-clone.png","2026-07-10T09:43:33.966Z",216,{"id":57,"name":58,"username":59,"avatarUrl":50,"headline":60},{"slug":6,"name":7,"accentFrom":10,"accentTo":11},{"slug":110,"name":111},[234,235,236,237],{"slug":110,"name":114,"color":50},{"slug":69,"name":70,"color":50},{"slug":72,"name":73,"color":50},{"slug":138,"name":139,"color":50},{"assessments":78},{"slug":224},{"id":241,"slug":242,"title":243,"subtitle":50,"excerpt":244,"coverUrl":245,"locale":13,"readingMinutes":86,"publishedAt":246,"viewCount":247,"likeCount":19,"commentCount":19,"author":248,"vertical":249,"topic":250,"tags":251,"_count":256,"playground":257,"hasQuiz":17,"hasPlayground":17},"019fe65f-fe39-767c-9ce8-da4db5144b1d","css-nesting-sass-replaced","You kept Sass for one reason. Native CSS nesting just ended it.","CSS has supported nesting natively since 2023 — pseudo-classes, pseudo-elements, and @media queries nested inside the rules they belong to. No compiler required.","\u002Fmedia\u002Fcovers\u002Fcss-nesting-sass-replaced.png","2026-07-09T09:48:41.505Z",198,{"id":57,"name":58,"username":59,"avatarUrl":50,"headline":60},{"slug":6,"name":7,"accentFrom":10,"accentTo":11},{"slug":63,"name":64},[252,253,254,255],{"slug":63,"name":67,"color":50},{"slug":69,"name":70,"color":50},{"slug":72,"name":73,"color":50},{"slug":110,"name":114,"color":50},{"assessments":78},{"slug":242},{"id":259,"slug":260,"title":261,"subtitle":50,"excerpt":262,"coverUrl":263,"locale":13,"readingMinutes":53,"publishedAt":264,"viewCount":265,"likeCount":19,"commentCount":19,"author":266,"vertical":267,"topic":268,"tags":269,"_count":274,"playground":275,"hasQuiz":17,"hasPlayground":17},"019fe65f-f67a-7038-9c0d-874d6c8ece3c","css-property-registered-custom-properties","You can't transition a CSS variable. @property says otherwise.","CSS custom properties are string substitution — the browser doesn't know a number from a color. Register one with @property and it gains a real type, an initial value, and the ability to animate.","\u002Fmedia\u002Fcovers\u002Fcss-property-registered-custom-properties.png","2026-07-08T08:36:23.824Z",340,{"id":57,"name":58,"username":59,"avatarUrl":50,"headline":60},{"slug":6,"name":7,"accentFrom":10,"accentTo":11},{"slug":63,"name":64},[270,271,272,273],{"slug":63,"name":67,"color":50},{"slug":69,"name":70,"color":50},{"slug":72,"name":73,"color":50},{"slug":110,"name":114,"color":50},{"assessments":78},{"slug":260},{"id":277,"slug":278,"title":279,"subtitle":50,"excerpt":280,"coverUrl":281,"locale":13,"readingMinutes":53,"publishedAt":282,"viewCount":283,"likeCount":19,"commentCount":19,"author":284,"vertical":285,"topic":286,"tags":287,"_count":292,"playground":293,"hasQuiz":17,"hasPlayground":17},"019fe65f-ef22-765a-97c7-cdfdbb168024","scroll-driven-animations","Your scroll listener is doing CSS's job","Reading progress bars, reveal-on-scroll effects, parallax — you've been writing these in JavaScript. CSS scroll-driven animations bind them directly to scroll position, off the main thread, in a handful of lines.","\u002Fmedia\u002Fcovers\u002Fscroll-driven-animations.png","2026-07-06T10:47:02.014Z",219,{"id":57,"name":58,"username":59,"avatarUrl":50,"headline":60},{"slug":6,"name":7,"accentFrom":10,"accentTo":11},{"slug":63,"name":64},[288,289,290,291],{"slug":63,"name":67,"color":50},{"slug":69,"name":70,"color":50},{"slug":72,"name":73,"color":50},{"slug":110,"name":114,"color":50},{"assessments":78},{"slug":278},{"page":295,"perPage":296,"total":297,"totalPages":298},8,12,107,9,[300,301,303,305,307,309,311,312,315,318,319,321],{"slug":69,"name":70,"articles":297},{"slug":110,"name":114,"articles":302},89,{"slug":72,"name":73,"articles":304},72,{"slug":63,"name":67,"articles":306},36,{"slug":158,"name":159,"articles":308},35,{"slug":212,"name":216,"articles":310},15,{"slug":118,"name":119,"articles":148},{"slug":313,"name":314,"articles":296},"performance","Performance",{"slug":316,"name":317,"articles":298},"browser","Browser",{"slug":138,"name":139,"articles":298},{"slug":75,"name":76,"articles":320},7,{"slug":322,"name":323,"articles":320},"accessibility","Accessibility",[325,326,327,328,329,330,331,332,333,334,335,336,337,339,342,345,348,351,354,357,360,363,366,369,372,375,378,381,384,387,390,393,396,399,402,405],{"slug":69,"name":70,"color":50,"articles":297},{"slug":110,"name":114,"color":50,"articles":302},{"slug":72,"name":73,"color":50,"articles":304},{"slug":63,"name":67,"color":50,"articles":306},{"slug":158,"name":159,"color":50,"articles":308},{"slug":212,"name":216,"color":50,"articles":310},{"slug":118,"name":119,"color":50,"articles":148},{"slug":313,"name":314,"color":50,"articles":296},{"slug":138,"name":139,"color":50,"articles":298},{"slug":316,"name":317,"color":50,"articles":298},{"slug":75,"name":76,"color":50,"articles":320},{"slug":322,"name":323,"color":50,"articles":320},{"slug":161,"name":162,"color":50,"articles":338},6,{"slug":340,"name":341,"color":50,"articles":338},"grammar","Grammar",{"slug":343,"name":344,"color":50,"articles":86},"nestjs","Nestjs",{"slug":346,"name":347,"color":50,"articles":86},"nextjs","Nextjs",{"slug":349,"name":350,"color":50,"articles":86},"apis","Apis",{"slug":352,"name":353,"color":50,"articles":43},"nuxt","Nuxt",{"slug":355,"name":356,"color":50,"articles":43},"ssr","SSR",{"slug":358,"name":359,"color":50,"articles":43},"ai","Ai",{"slug":361,"name":362,"color":50,"articles":43},"vue","Vue",{"slug":364,"name":365,"color":50,"articles":31},"security","Security",{"slug":367,"name":368,"color":50,"articles":31},"async","Async",{"slug":370,"name":371,"color":50,"articles":31},"forms","Forms",{"slug":373,"name":374,"color":50,"articles":31},"api","API",{"slug":376,"name":377,"color":50,"articles":31},"english","English",{"slug":379,"name":380,"color":50,"articles":31},"verbs","Verbs",{"slug":382,"name":383,"color":50,"articles":31},"spanish","Spanish",{"slug":385,"name":386,"color":50,"articles":31},"a1","A1",{"slug":388,"name":389,"color":50,"articles":31},"a2","A2",{"slug":391,"name":392,"color":50,"articles":31},"tenses","Tenses",{"slug":394,"name":395,"color":50,"articles":31},"turkish","Turkish",{"slug":397,"name":398,"color":50,"articles":31},"career","Career",{"slug":400,"name":401,"color":50,"articles":31},"beginners","Beginners",{"slug":403,"name":404,"color":50,"articles":31},"productivity","Productivity",{"slug":406,"name":407,"color":50,"articles":31},"discuss","Discuss"]