{"id":390,"date":"2017-07-28T17:41:10","date_gmt":"2017-07-28T14:41:10","guid":{"rendered":"https:\/\/iamakulov.com\/notes\/?p=390"},"modified":"2017-08-23T23:50:06","modified_gmt":"2017-08-23T20:50:06","slug":"resize-scroll","status":"publish","type":"post","link":"https:\/\/iamakulov.com\/notes\/resize-scroll\/","title":{"rendered":"How to optimize resizing or scrolling"},"content":{"rendered":"<p>If you listen for events like <code>mousewheel<\/code>, <code>resize<\/code> or <code>scroll<\/code>, your page could get slow. These events are generated multiple times per second, and if the event handler takes too much time, the browser won\u2019t catch with redrawing the page.<\/p>\n<p>This is what to do if you have such problem.<\/p>\n<h1 id=\"throttle\">Throttle<a href=\"https:\/\/iamakulov.com\/notes\/resize-scroll\/#throttle\" class=\"heading-link\" aria-label=\"Link to this section\" title=\"Link to this section\">#<\/a><\/h1>\n<div class='annotated-element annotated-element_has-code_no annotated-element_keep-size_no annotated-element_mobile-direction_content-then-annotation'>\n<div class='annotated-element__annotation'><a href='https:\/\/css-tricks.com\/the-difference-between-throttling-and-debouncing\/'>CSS-Tricks\u2019 article on throttling<\/a><\/div>\n<div class='annotated-element__content'>\n<p>By default, the event handler is executed on each event. Sometimes, when the handler is taking a long time, it might be acceptable to delay its execution to once per 100-200 ms. This \u201cdelaying\u201d can be achieved with the <a href=\"https:\/\/lodash.com\/docs\/#throttle\"><code>_.throttle<\/code> utility method<\/a>.<\/p>\n<\/div>\n<\/div>\n<p><em>When is this useful?<\/em> E.g. if you recalculate the page layout each time the browser resizes. If recalculating layout takes a long time, you could perform it less often.<\/p>\n<p><em>Before and after:<\/em><\/p>\n<pre><code class=\"javascript\">\/\/ Before\r\nwindow.addEventListener('resize', () => {\r\n  calculateLayout(); \/\/ Takes 20 ms\r\n});\r\n\r\n\/\/ After\r\nwindow.addEventListener('resize', _.throttle(() => {\r\n  calculateLayout(); \/\/ Still takes 20 ms, but now runs once in 100 ms\r\n}, 100));\r\n<\/code><\/pre>\n<h1 id=\"passive-true\">passive: true<a href=\"https:\/\/iamakulov.com\/notes\/resize-scroll\/#passive-true\" class=\"heading-link\" aria-label=\"Link to this section\" title=\"Link to this section\">#<\/a><\/h1>\n<div class='annotated-element annotated-element_has-code_no annotated-element_keep-size_no annotated-element_mobile-direction_content-then-annotation'>\n<div class='annotated-element__annotation'><a href='https:\/\/github.com\/WICG\/EventListenerOptions\/blob\/gh-pages\/explainer.md'>About <code>passive: true<\/code> on GitHub<\/a><\/div>\n<div class='annotated-element__content'>\n<p><code>passive: true<\/code> a flag that\u2019s passed into <code>addEventListener<\/code>. It tells the browser that the event handler will never call <code>event.preventDefault()<\/code>. Using this knowledge, the browser can start doing the event action (e.g. scrolling) without waiting for the JS code to finish. This makes the page smoother.<\/p>\n<\/div>\n<\/div>\n<div class='annotated-element annotated-element_has-code_no annotated-element_keep-size_no annotated-element_mobile-direction_content-then-annotation'>\n<div class='annotated-element__annotation'>Currently, <a href='https:\/\/gist.github.com\/iamakulov\/45803e89db2eb44a7a6be33a80ffcab7'>only <code>touchstart<\/code>, <code>touchmove<\/code> and <code>mousewheel<\/code><\/a> event handlers could be made passive.<\/div>\n<div class='annotated-element__content'>\n<p><em>When is this useful?<\/em> E.g. if you redraw the parallax background on each touch or scroll event. Most likely, it won\u2019t be a problem if the browser starts scrolling before the background finishes redrawing. If so, such event handler could be made passive.<\/p>\n<\/div>\n<\/div>\n<p><em>Before and after:<\/em><\/p>\n<pre><code >\/\/ Before:\r\nwindow.addEventListener('touchstart', updateBackground)\r\n\r\n\/\/ After:\r\nwindow.addEventListener('touchstart', updateBackground, {\r\n  passive: true\r\n})\r\n<\/code><\/pre>\n<h1 id=\"use-alternative-apis\">Use alternative APIs<a href=\"https:\/\/iamakulov.com\/notes\/resize-scroll\/#use-alternative-apis\" class=\"heading-link\" aria-label=\"Link to this section\" title=\"Link to this section\">#<\/a><\/h1>\n<p>For some common tasks, there are alternative APIs that help to perform the task easier and with better performance:<\/p>\n<ul>\n<li><strong><a href=\"https:\/\/developers.google.com\/web\/updates\/2016\/04\/intersectionobserver\">Intersection Observer<\/a><\/strong>. It helps if you need to detect when an element goes off the screen or intersects with another element. This API can replace the <code>scroll<\/code> and <code>resize<\/code> listeners.<\/li>\n<li><strong><a href=\"https:\/\/developer.mozilla.org\/en-US\/docs\/Web\/CSS\/Media_Queries\/Testing_media_queries#Receiving_query_notifications\"><code>window.matchMedia<\/code><\/a><\/strong>. This API can notify you when a specific media query becomes true. Helps if you need to e.g. update the page layout when the viewport reaches a specific width. It can replace the <code>resize<\/code> listeners.<\/li>\n<li><strong><a href=\"https:\/\/css-tricks.com\/position-sticky-2\/\"><code>position: sticky<\/code><\/a><\/strong>. This CSS property lets you  stick an element to the top when it reaches an edge of the viewport. Helps if you need to e.g. make a sticky page header. It can replace the <code>scroll<\/code> listeners that switch the element from <code>position: static<\/code> to <code>position: fixed<\/code> and vice versa.<\/li>\n<li>\n<div class='annotated-element annotated-element_has-code_no annotated-element_keep-size_no annotated-element_mobile-direction_content-then-annotation'>\n<div class='annotated-element__annotation'>At the moment of July 2017, the API is not yet well-supported. However, there\u2019s <a href='https:\/\/github.com\/que-etc\/resize-observer-polyfill'>a polyfill<\/a>.<\/div>\n<div class='annotated-element__content'>\n<p><strong><a href=\"https:\/\/developers.google.com\/web\/updates\/2016\/10\/resizeobserver\">Resize Observer<\/a><\/strong>. It helps if you need to detect when an element gets resized. This API can replace the <code>scroll<\/code> and <code>resize<\/code> listeners.<\/p>\n<\/div>\n<\/div>\n<p><em>Thanks to Vitali Kuzmich <a href=\"https:\/\/www.facebook.com\/iamakulov.page\/photos\/a.836528503179678.1073741828.818609548304907\/836548096511052\/?type=3&#038;comment_id=837203716445490&#038;comment_tracking=%7B%22tn%22%3A%22R%22%7D\">for mentioning this approach<\/a>.<\/em><\/p>\n<\/li>\n<\/ul>\n<h1 id=\"optimize-the-code-itself\">Optimize the code itself<a href=\"https:\/\/iamakulov.com\/notes\/resize-scroll\/#optimize-the-code-itself\" class=\"heading-link\" aria-label=\"Link to this section\" title=\"Link to this section\">#<\/a><\/h1>\n<div class='annotated-element annotated-element_has-code_no annotated-element_keep-size_no annotated-element_mobile-direction_content-then-annotation'>\n<div class='annotated-element__annotation'><a href='https:\/\/developers.google.com\/web\/fundamentals\/performance\/rendering\/#60fps_and_device_refresh_rates'>Why this 10 ms border is important<\/a><\/div>\n<div class='annotated-element__content'>\n<p>You can also make the event handler itself run faster. It should take not more than 10 ms to run.<\/p>\n<\/div>\n<\/div>\n<p>To analyze how much time your handler takes, use <a href=\"https:\/\/developer.mozilla.org\/en-US\/docs\/Web\/API\/Performance\">Web Performance API<\/a> or <a href=\"https:\/\/developers.google.com\/web\/tools\/chrome-devtools\/evaluate-performance\/\">the Performance tab in Chrome DevTools<\/a>:<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" src=\"https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/chrome_2017-07-28_16-30-37.png\" alt=\"\" width=\"1253\" height=\"884\" class=\"alignnone size-full wp-image-416\" srcset=\"https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/chrome_2017-07-28_16-30-37.png 1253w, https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/chrome_2017-07-28_16-30-37-300x212.png 300w, https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/chrome_2017-07-28_16-30-37-768x542.png 768w, https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/chrome_2017-07-28_16-30-37-1024x722.png 1024w, https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/chrome_2017-07-28_16-30-37-1200x847.png 1200w\" sizes=\"(max-width: 709px) 85vw, (max-width: 909px) 67vw, (max-width: 1362px) 62vw, 840px\" \/><\/p>\n<p>The optimization approach depends on your code. Try caching some data or skipping some computations. If you use React, you can try dropping parts of the render tree with <a href=\"https:\/\/facebook.github.io\/react\/docs\/optimizing-performance.html#avoid-reconciliation\">shouldComponentUpdate<\/a>. <\/p>\n<h1 id=\"and-this-is-what-wont-work\">And this is what won\u2019t work:<a href=\"https:\/\/iamakulov.com\/notes\/resize-scroll\/#and-this-is-what-wont-work\" class=\"heading-link\" aria-label=\"Link to this section\" title=\"Link to this section\">#<\/a><\/h1>\n<ul>\n<li><a href=\"https:\/\/developer.mozilla.org\/en-US\/docs\/Web\/API\/window\/requestAnimationFrame\"><code>requestAnimationFrame<\/code><\/a>. It doesn\u2019t help with slow event handlers and, by my tests, doesn\u2019t bring any benefits for fast ones. Seems like it\u2019s only useful for scheduling JS animations.<\/li>\n<li><a href=\"https:\/\/stackoverflow.com\/questions\/1687296\/what-is-dom-event-delegation\">Event delegation<\/a>. It optimizes the memory usage, not the speed.<\/li>\n<\/ul>\n<p>That\u2019s it. Optimize.<\/p>\n<p><!--p class=\"perf-consulting-snippet\">\n<mark>+1s in loading time of your app is \u22127% in conversion.<\/mark> I can help you make your app or site load and run faster \u2013 using these and even more optimization techniques: <a href=\"https:\/\/iamakulov.com\/perf-consulting\">iamakulov.com\/perf-consulting<\/a>\n<\/p-->\n","protected":false},"excerpt":{"rendered":"<p>If you listen for events like mousewheel, resize or scroll, your page could get slow. These events are generated multiple times per second, and if the event handler takes too much time, the browser won\u2019t catch with redrawing the page. This is what to do if you have such problem. Throttle# When is this useful? &hellip; <a href=\"https:\/\/iamakulov.com\/notes\/resize-scroll\/\" class=\"more-link\">Continue reading<span class=\"screen-reader-text\"> &#8220;How to optimize resizing or scrolling&#8221;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[1],"tags":[15],"yoast_head":"<!-- This site is optimized with the Yoast SEO plugin v23.5 - https:\/\/yoast.com\/wordpress\/plugins\/seo\/ -->\n<title>How to optimize resizing or scrolling - Ivan Akulov\u2019s blog<\/title>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/iamakulov.com\/notes\/resize-scroll\/\" \/>\n<meta property=\"og:locale\" content=\"en_US\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"How to optimize resizing or scrolling\" \/>\n<meta property=\"og:description\" content=\"And get rid of page junk\" \/>\n<meta property=\"og:url\" content=\"https:\/\/iamakulov.com\/notes\/resize-scroll\/\" \/>\n<meta property=\"og:site_name\" content=\"Ivan Akulov\u2019s blog\" \/>\n<meta property=\"article:publisher\" content=\"http:\/\/facebook.com\/iamakulov.page\" \/>\n<meta property=\"article:published_time\" content=\"2017-07-28T14:41:10+00:00\" \/>\n<meta property=\"article:modified_time\" content=\"2017-08-23T20:50:06+00:00\" \/>\n<meta property=\"og:image\" content=\"https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/Events-\u2013-for-post-1.png\" \/>\n\t<meta property=\"og:image:width\" content=\"1200\" \/>\n\t<meta property=\"og:image:height\" content=\"630\" \/>\n\t<meta property=\"og:image:type\" content=\"image\/png\" \/>\n<meta name=\"author\" content=\"Ivan Akulov\" \/>\n<meta name=\"twitter:card\" content=\"summary_large_image\" \/>\n<meta name=\"twitter:title\" content=\"How to optimize resizing or scrolling\" \/>\n<meta name=\"twitter:description\" content=\"And get rid of page junk\" \/>\n<meta name=\"twitter:image\" content=\"https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/Events-\u2013-for-post-1.png\" \/>\n<meta name=\"twitter:creator\" content=\"@iamakulov\" \/>\n<meta name=\"twitter:site\" content=\"@iamakulov\" \/>\n<meta name=\"twitter:label1\" content=\"Written by\" \/>\n\t<meta name=\"twitter:data1\" content=\"Ivan Akulov\" \/>\n\t<meta name=\"twitter:label2\" content=\"Est. reading time\" \/>\n\t<meta name=\"twitter:data2\" content=\"3 minutes\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\/\/schema.org\",\"@graph\":[{\"@type\":\"WebPage\",\"@id\":\"https:\/\/iamakulov.com\/notes\/resize-scroll\/\",\"url\":\"https:\/\/iamakulov.com\/notes\/resize-scroll\/\",\"name\":\"How to optimize resizing or scrolling - Ivan Akulov\u2019s blog\",\"isPartOf\":{\"@id\":\"https:\/\/iamakulov.com\/notes\/#website\"},\"primaryImageOfPage\":{\"@id\":\"https:\/\/iamakulov.com\/notes\/resize-scroll\/#primaryimage\"},\"image\":{\"@id\":\"https:\/\/iamakulov.com\/notes\/resize-scroll\/#primaryimage\"},\"thumbnailUrl\":\"https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/chrome_2017-07-28_16-30-37.png\",\"datePublished\":\"2017-07-28T14:41:10+00:00\",\"dateModified\":\"2017-08-23T20:50:06+00:00\",\"author\":{\"@id\":\"https:\/\/iamakulov.com\/notes\/#\/schema\/person\/ebf7b61bf573e7be5fe438f50ebd9b81\"},\"breadcrumb\":{\"@id\":\"https:\/\/iamakulov.com\/notes\/resize-scroll\/#breadcrumb\"},\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\/\/iamakulov.com\/notes\/resize-scroll\/\"]}]},{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\/\/iamakulov.com\/notes\/resize-scroll\/#primaryimage\",\"url\":\"https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/chrome_2017-07-28_16-30-37.png\",\"contentUrl\":\"https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/chrome_2017-07-28_16-30-37.png\",\"width\":1253,\"height\":884},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\/\/iamakulov.com\/notes\/resize-scroll\/#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Home\",\"item\":\"https:\/\/iamakulov.com\/notes\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"How to optimize resizing or scrolling\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\/\/iamakulov.com\/notes\/#website\",\"url\":\"https:\/\/iamakulov.com\/notes\/\",\"name\":\"Ivan Akulov\u2019s blog\",\"description\":\"Ivan Akulov writes about his front-end experience, React, webpack, and performance optimizations.\",\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\/\/iamakulov.com\/notes\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"en-US\"},{\"@type\":\"Person\",\"@id\":\"https:\/\/iamakulov.com\/notes\/#\/schema\/person\/ebf7b61bf573e7be5fe438f50ebd9b81\",\"name\":\"Ivan Akulov\",\"image\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\/\/iamakulov.com\/notes\/#\/schema\/person\/image\/\",\"url\":\"https:\/\/secure.gravatar.com\/avatar\/f68e4cd477cef1577c339e6f09736d3a?s=96&d=mm&r=g\",\"contentUrl\":\"https:\/\/secure.gravatar.com\/avatar\/f68e4cd477cef1577c339e6f09736d3a?s=96&d=mm&r=g\",\"caption\":\"Ivan Akulov\"},\"description\":\"I'm a software engineer specializing in web performance, JavaScript, and React. I\u2019m also a Google Developer Expert. I work at Framer.\",\"sameAs\":[\"http:\/\/iamakulov.com\",\"https:\/\/x.com\/iamakulov\"]}]}<\/script>\n<!-- \/ Yoast SEO plugin. -->","yoast_head_json":{"title":"How to optimize resizing or scrolling - Ivan Akulov\u2019s blog","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/iamakulov.com\/notes\/resize-scroll\/","og_locale":"en_US","og_type":"article","og_title":"How to optimize resizing or scrolling","og_description":"And get rid of page junk","og_url":"https:\/\/iamakulov.com\/notes\/resize-scroll\/","og_site_name":"Ivan Akulov\u2019s blog","article_publisher":"http:\/\/facebook.com\/iamakulov.page","article_published_time":"2017-07-28T14:41:10+00:00","article_modified_time":"2017-08-23T20:50:06+00:00","og_image":[{"width":1200,"height":630,"url":"https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/Events-\u2013-for-post-1.png","type":"image\/png"}],"author":"Ivan Akulov","twitter_card":"summary_large_image","twitter_title":"How to optimize resizing or scrolling","twitter_description":"And get rid of page junk","twitter_image":"https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/Events-\u2013-for-post-1.png","twitter_creator":"@iamakulov","twitter_site":"@iamakulov","twitter_misc":{"Written by":"Ivan Akulov","Est. reading time":"3 minutes"},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"WebPage","@id":"https:\/\/iamakulov.com\/notes\/resize-scroll\/","url":"https:\/\/iamakulov.com\/notes\/resize-scroll\/","name":"How to optimize resizing or scrolling - Ivan Akulov\u2019s blog","isPartOf":{"@id":"https:\/\/iamakulov.com\/notes\/#website"},"primaryImageOfPage":{"@id":"https:\/\/iamakulov.com\/notes\/resize-scroll\/#primaryimage"},"image":{"@id":"https:\/\/iamakulov.com\/notes\/resize-scroll\/#primaryimage"},"thumbnailUrl":"https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/chrome_2017-07-28_16-30-37.png","datePublished":"2017-07-28T14:41:10+00:00","dateModified":"2017-08-23T20:50:06+00:00","author":{"@id":"https:\/\/iamakulov.com\/notes\/#\/schema\/person\/ebf7b61bf573e7be5fe438f50ebd9b81"},"breadcrumb":{"@id":"https:\/\/iamakulov.com\/notes\/resize-scroll\/#breadcrumb"},"inLanguage":"en-US","potentialAction":[{"@type":"ReadAction","target":["https:\/\/iamakulov.com\/notes\/resize-scroll\/"]}]},{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/iamakulov.com\/notes\/resize-scroll\/#primaryimage","url":"https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/chrome_2017-07-28_16-30-37.png","contentUrl":"https:\/\/iamakulov.com\/notes2\/wp-content\/uploads\/2017\/07\/chrome_2017-07-28_16-30-37.png","width":1253,"height":884},{"@type":"BreadcrumbList","@id":"https:\/\/iamakulov.com\/notes\/resize-scroll\/#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https:\/\/iamakulov.com\/notes\/"},{"@type":"ListItem","position":2,"name":"How to optimize resizing or scrolling"}]},{"@type":"WebSite","@id":"https:\/\/iamakulov.com\/notes\/#website","url":"https:\/\/iamakulov.com\/notes\/","name":"Ivan Akulov\u2019s blog","description":"Ivan Akulov writes about his front-end experience, React, webpack, and performance optimizations.","potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/iamakulov.com\/notes\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"en-US"},{"@type":"Person","@id":"https:\/\/iamakulov.com\/notes\/#\/schema\/person\/ebf7b61bf573e7be5fe438f50ebd9b81","name":"Ivan Akulov","image":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/iamakulov.com\/notes\/#\/schema\/person\/image\/","url":"https:\/\/secure.gravatar.com\/avatar\/f68e4cd477cef1577c339e6f09736d3a?s=96&d=mm&r=g","contentUrl":"https:\/\/secure.gravatar.com\/avatar\/f68e4cd477cef1577c339e6f09736d3a?s=96&d=mm&r=g","caption":"Ivan Akulov"},"description":"I'm a software engineer specializing in web performance, JavaScript, and React. I\u2019m also a Google Developer Expert. I work at Framer.","sameAs":["http:\/\/iamakulov.com","https:\/\/x.com\/iamakulov"]}]}},"jetpack_featured_media_url":"","_links":{"self":[{"href":"https:\/\/iamakulov.com\/notes\/wp-json\/wp\/v2\/posts\/390"}],"collection":[{"href":"https:\/\/iamakulov.com\/notes\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/iamakulov.com\/notes\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/iamakulov.com\/notes\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/iamakulov.com\/notes\/wp-json\/wp\/v2\/comments?post=390"}],"version-history":[{"count":62,"href":"https:\/\/iamakulov.com\/notes\/wp-json\/wp\/v2\/posts\/390\/revisions"}],"predecessor-version":[{"id":506,"href":"https:\/\/iamakulov.com\/notes\/wp-json\/wp\/v2\/posts\/390\/revisions\/506"}],"wp:attachment":[{"href":"https:\/\/iamakulov.com\/notes\/wp-json\/wp\/v2\/media?parent=390"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/iamakulov.com\/notes\/wp-json\/wp\/v2\/categories?post=390"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/iamakulov.com\/notes\/wp-json\/wp\/v2\/tags?post=390"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}