{"id":92815,"date":"2025-01-13T18:44:45","date_gmt":"2025-01-13T15:14:45","guid":{"rendered":"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/"},"modified":"2025-01-13T18:44:45","modified_gmt":"2025-01-13T15:14:45","slug":"%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java","status":"publish","type":"post","link":"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/","title":{"rendered":"\u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0633\u0637\u0644 \u062a\u0648\u06a9\u0646 (Redis &#038; Java)"},"content":{"rendered":"<div data-article-id=\"2204158\" id=\"article-body\">\n<blockquote>\n<p>\u0627\u06cc\u0646 \u0645\u0642\u0627\u0644\u0647 \u062f\u0631 \u06cc\u0648\u062a\u06cc\u0648\u0628 \u0646\u06cc\u0632 \u0645\u0648\u062c\u0648\u062f \u0627\u0633\u062a!<\/p>\n<\/blockquote>\n<p><img decoding=\"async\" src=\"https:\/\/media2.dev.to\/dynamic\/image\/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto\/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Ft58edaghnxrbmjdyhkf7.png\" loading=\"lazy\" width=\"800\" height=\"450\" alt=\"\" title=\"\"><\/p>\n<p>\u0631\u0627 <strong>\u0633\u0637\u0644 \u062a\u0648\u06a9\u0646<\/strong> \u0627\u0644\u06af\u0648\u0631\u06cc\u062a\u0645 \u06cc\u06a9 \u0645\u06a9\u0627\u0646\u06cc\u0633\u0645 \u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0627\u0646\u0639\u0637\u0627\u0641 \u067e\u0630\u06cc\u0631 \u0648 \u06a9\u0627\u0631\u0622\u0645\u062f \u0627\u0633\u062a. \u0627\u06cc\u0646 \u06a9\u0627\u0631 \u0628\u0627 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u06cc\u06a9 \u0633\u0637\u0644 \u0628\u0627 \u0646\u0634\u0627\u0646\u0647\u200c\u0647\u0627 \u0628\u0627 \u0646\u0631\u062e \u062b\u0627\u0628\u062a (\u0645\u062b\u0644\u0627\u064b \u06cc\u06a9 \u062a\u0648\u06a9\u0646 \u062f\u0631 \u062b\u0627\u0646\u06cc\u0647) \u06a9\u0627\u0631 \u0645\u06cc\u200c\u06a9\u0646\u062f. \u0647\u0631 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u06cc\u06a9 \u062a\u0648\u06a9\u0646 \u0645\u0635\u0631\u0641 \u0645\u06cc \u06a9\u0646\u062f \u0648 \u0627\u06af\u0631 \u062a\u0648\u06a9\u0646\u06cc \u062f\u0631 \u062f\u0633\u062a\u0631\u0633 \u0646\u0628\u0627\u0634\u062f\u060c \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0631\u062f \u0645\u06cc \u0634\u0648\u062f. \u0633\u0637\u0644 \u062f\u0627\u0631\u0627\u06cc \u062d\u062f\u0627\u06a9\u062b\u0631 \u0638\u0631\u0641\u06cc\u062a \u0627\u0633\u062a\u060c \u0628\u0646\u0627\u0628\u0631\u0627\u06cc\u0646 \u062a\u0627 \u0632\u0645\u0627\u0646\u06cc \u06a9\u0647 \u0627\u0646\u0641\u062c\u0627\u0631 \u0627\u0632 \u062a\u0639\u062f\u0627\u062f \u062a\u0648\u06a9\u0646\u200c\u0647\u0627\u06cc \u0645\u0648\u062c\u0648\u062f \u062f\u0631 \u0633\u0637\u0644 \u062a\u062c\u0627\u0648\u0632 \u0646\u06a9\u0646\u062f\u060c \u0645\u06cc\u200c\u062a\u0648\u0627\u0646\u062f \u0627\u0632 \u062a\u0631\u0627\u0641\u06cc\u06a9 \u0639\u0628\u0648\u0631 \u06a9\u0646\u062f.<\/p>\n<blockquote>\n<p>\u0628\u0647 \u062f\u0646\u0628\u0627\u0644 \u06cc\u06a9 \u0627\u0644\u06af\u0648\u0631\u06cc\u062a\u0645 \u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0645\u062a\u0641\u0627\u0648\u062a \u0647\u0633\u062a\u06cc\u062f\u061f \u0631\u0627\u0647\u0646\u0645\u0627\u06cc \u0636\u0631\u0648\u0631\u06cc \u0631\u0627 \u0628\u0631\u0631\u0633\u06cc \u06a9\u0646\u06cc\u062f.<\/p>\n<\/blockquote>\n<div id=\"ez-toc-container\" class=\"ez-toc-v2_0_84 counter-hierarchy ez-toc-counter-rtl ez-toc-grey ez-toc-container-direction\">\n<div class=\"ez-toc-title-container\">\n<p class=\"ez-toc-title\" style=\"cursor:inherit\">\u0641\u0647\u0631\u0633\u062a \u0645\u0637\u0627\u0644\u0628<\/p>\n<span class=\"ez-toc-title-toggle\"><a href=\"#\" class=\"ez-toc-pull-right ez-toc-btn ez-toc-btn-xs ez-toc-btn-default ez-toc-toggle\" aria-label=\"Toggle Table of Content\"><span class=\"ez-toc-js-icon-con\"><span class=\"\"><span class=\"eztoc-hide\" style=\"display:none;\">Toggle<\/span><span class=\"ez-toc-icon-toggle-span\"><svg style=\"fill: #999;color:#999\" xmlns=\"http:\/\/www.w3.org\/2000\/svg\" class=\"list-377408\" width=\"20px\" height=\"20px\" viewBox=\"0 0 24 24\" fill=\"none\"><path d=\"M6 6H4v2h2V6zm14 0H8v2h12V6zM4 11h2v2H4v-2zm16 0H8v2h12v-2zM4 16h2v2H4v-2zm16 0H8v2h12v-2z\" fill=\"currentColor\"><\/path><\/svg><svg style=\"fill: #999;color:#999\" class=\"arrow-unsorted-368013\" xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"10px\" height=\"10px\" viewBox=\"0 0 24 24\" version=\"1.2\" baseProfile=\"tiny\"><path d=\"M18.2 9.3l-6.2-6.3-6.2 6.3c-.2.2-.3.4-.3.7s.1.5.3.7c.2.2.4.3.7.3h11c.3 0 .5-.1.7-.3.2-.2.3-.5.3-.7s-.1-.5-.3-.7zM5.8 14.7l6.2 6.3 6.2-6.3c.2-.2.3-.5.3-.7s-.1-.5-.3-.7c-.2-.2-.4-.3-.7-.3h-11c-.3 0-.5.1-.7.3-.2.2-.3.5-.3.7s.1.5.3.7z\"\/><\/svg><\/span><\/span><\/span><\/a><\/span><\/div>\n<nav><ul class='ez-toc-list ez-toc-list-level-1 ' ><ul class='ez-toc-list-level-3' ><li class='ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-1\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%B4%D8%A7%D8%AE%D8%B5\" >\u0634\u0627\u062e\u0635<\/a><\/li><\/ul><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-2\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%DA%86%DA%AF%D9%88%D9%86%D9%87_%DA%A9%D8%A7%D8%B1_%D9%85%DB%8C_%DA%A9%D9%86%D8%AF\" >\u0686\u06af\u0648\u0646\u0647 \u06a9\u0627\u0631 \u0645\u06cc \u06a9\u0646\u062f<\/a><ul class='ez-toc-list-level-3' ><li class='ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-3\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#1_%D9%86%D8%B1%D8%AE_%D9%BE%D8%B1_%DA%A9%D8%B1%D8%AF%D9%86_%D9%85%D8%AC%D8%AF%D8%AF_%D8%AA%D9%88%DA%A9%D9%86_%D8%B1%D8%A7_%D8%AA%D8%B9%D8%B1%DB%8C%D9%81_%DA%A9%D9%86%DB%8C%D8%AF\" >1. \u0646\u0631\u062e \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f \u062a\u0648\u06a9\u0646 \u0631\u0627 \u062a\u0639\u0631\u06cc\u0641 \u06a9\u0646\u06cc\u062f<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-4\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#2_%D9%BE%DB%8C%DA%AF%DB%8C%D8%B1%DB%8C_%D9%85%D8%B5%D8%B1%D9%81_%D8%AA%D9%88%DA%A9%D9%86\" >2. \u067e\u06cc\u06af\u06cc\u0631\u06cc \u0645\u0635\u0631\u0641 \u062a\u0648\u06a9\u0646<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-5\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#3_%D8%AF%D9%88%D8%A8%D8%A7%D8%B1%D9%87_%D9%BE%D8%B1_%DA%A9%D8%B1%D8%AF%D9%86_%D8%AA%D9%88%DA%A9%D9%86_%D9%87%D8%A7\" >3. \u062f\u0648\u0628\u0627\u0631\u0647 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u062a\u0648\u06a9\u0646 \u0647\u0627<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-6\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#4_%D8%A8%D8%B1%D8%B1%D8%B3%DB%8C_%D9%85%D8%AD%D8%AF%D9%88%D8%AF%DB%8C%D8%AA_%D9%86%D8%B1%D8%AE\" >4. \u0628\u0631\u0631\u0633\u06cc \u0645\u062d\u062f\u0648\u062f\u06cc\u062a \u0646\u0631\u062e<\/a><\/li><\/ul><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-7\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D9%86%D8%AD%D9%88%D9%87_%D9%BE%DB%8C%D8%A7%D8%AF%D9%87_%D8%B3%D8%A7%D8%B2%DB%8C_%D8%A2%D9%86_%D8%A8%D8%A7_Redis_%D9%88_Java\" >\u0646\u062d\u0648\u0647 \u067e\u06cc\u0627\u062f\u0647 \u0633\u0627\u0632\u06cc \u0622\u0646 \u0628\u0627 Redis \u0648 Java<\/a><ul class='ez-toc-list-level-3' ><li class='ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-8\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#1_%D8%AA%D8%B9%D8%AF%D8%A7%D8%AF_%D8%B1%D9%85%D8%B2_%D9%81%D8%B9%D9%84%DB%8C_%D9%88_%D8%A2%D8%AE%D8%B1%DB%8C%D9%86_%D8%B2%D9%85%D8%A7%D9%86_%D9%BE%D8%B1_%DA%A9%D8%B1%D8%AF%D9%86_%D8%B1%D8%A7_%D8%A8%D8%A7%D8%B2%DB%8C%D8%A7%D8%A8%DB%8C_%DA%A9%D9%86%DB%8C%D8%AF\" >1. \u062a\u0639\u062f\u0627\u062f \u0631\u0645\u0632 \u0641\u0639\u0644\u06cc \u0648 \u0622\u062e\u0631\u06cc\u0646 \u0632\u0645\u0627\u0646 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0631\u0627 \u0628\u0627\u0632\u06cc\u0627\u0628\u06cc \u06a9\u0646\u06cc\u062f<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-9\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#2_%D8%AF%D8%B1_%D8%B5%D9%88%D8%B1%D8%AA_%D9%84%D8%B2%D9%88%D9%85_%D8%AA%D9%88%DA%A9%D9%86_%D9%87%D8%A7_%D8%B1%D8%A7_%D8%AF%D9%88%D8%A8%D8%A7%D8%B1%D9%87_%D9%BE%D8%B1_%DA%A9%D9%86%DB%8C%D8%AF_%D9%88_%D8%B3%D8%B7%D9%84_%D8%B1%D8%A7_%D8%A8%D9%87_%D8%B1%D9%88%D8%B2_%DA%A9%D9%86%DB%8C%D8%AF\" >2. \u062f\u0631 \u0635\u0648\u0631\u062a \u0644\u0632\u0648\u0645 \u062a\u0648\u06a9\u0646 \u0647\u0627 \u0631\u0627 \u062f\u0648\u0628\u0627\u0631\u0647 \u067e\u0631 \u06a9\u0646\u06cc\u062f \u0648 \u0633\u0637\u0644 \u0631\u0627 \u0628\u0647 \u0631\u0648\u0632 \u06a9\u0646\u06cc\u062f<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-10\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#3_%D8%A7%D8%AC%D8%A7%D8%B2%D9%87_%DB%8C%D8%A7_%D8%B1%D8%AF_%D8%AF%D8%B1%D8%AE%D9%88%D8%A7%D8%B3%D8%AA\" >3. \u0627\u062c\u0627\u0632\u0647 \u06cc\u0627 \u0631\u062f \u062f\u0631\u062e\u0648\u0627\u0633\u062a<\/a><\/li><\/ul><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-11\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D9%BE%DB%8C%D8%A7%D8%AF%D9%87_%D8%B3%D8%A7%D8%B2%DB%8C_%D8%A2%D9%86_%D8%A8%D8%A7_Jedis\" >\u067e\u06cc\u0627\u062f\u0647 \u0633\u0627\u0632\u06cc \u0622\u0646 \u0628\u0627 Jedis<\/a><ul class='ez-toc-list-level-3' ><li class='ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-12\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#Jedis_%D8%B1%D8%A7_%D8%A8%D9%87_%D9%81%D8%A7%DB%8C%D9%84_Maven_%D8%AE%D9%88%D8%AF_%D8%A7%D8%B6%D8%A7%D9%81%D9%87_%DA%A9%D9%86%DB%8C%D8%AF\" >Jedis \u0631\u0627 \u0628\u0647 \u0641\u0627\u06cc\u0644 Maven \u062e\u0648\u062f \u0627\u0636\u0627\u0641\u0647 \u06a9\u0646\u06cc\u062f:<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-13\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%A7%DB%8C%D8%AC%D8%A7%D8%AF_%DB%8C%DA%A9_TokenBucketRateLimiter_%DA%A9%D9%84%D8%A7%D8%B3\" >\u0627\u06cc\u062c\u0627\u062f \u06cc\u06a9 TokenBucketRateLimiter \u06a9\u0644\u0627\u0633:<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-14\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%AF%D8%B1%D8%AE%D9%88%D8%A7%D8%B3%D8%AA_%D9%87%D8%A7_%D8%B1%D8%A7_%D8%AA%D8%A7%DB%8C%DB%8C%D8%AF_%DA%A9%D9%86%DB%8C%D8%AF\" >\u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0647\u0627 \u0631\u0627 \u062a\u0627\u06cc\u06cc\u062f \u06a9\u0646\u06cc\u062f<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-15\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D9%BE%DB%8C%D8%A7%D8%AF%D9%87_%D8%B3%D8%A7%D8%B2%DB%8C_%DA%A9%D8%A7%D9%85%D9%84\" >\u067e\u06cc\u0627\u062f\u0647 \u0633\u0627\u0632\u06cc \u06a9\u0627\u0645\u0644<\/a><\/li><\/ul><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-16\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%A2%D8%B2%D9%85%D8%A7%DB%8C%D8%B4_%D9%85%D8%AD%D8%AF%D9%88%D8%AF_%DA%A9%D9%86%D9%86%D8%AF%D9%87_%D9%86%D8%B1%D8%AE_%D9%85%D8%A7\" >\u0622\u0632\u0645\u0627\u06cc\u0634 \u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0645\u0627<\/a><ul class='ez-toc-list-level-3' ><li class='ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-17\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%A7%D9%81%D8%B2%D9%88%D8%AF%D9%86_%D9%88%D8%A7%D8%A8%D8%B3%D8%AA%DA%AF%DB%8C_%D9%87%D8%A7\" >\u0627\u0641\u0632\u0648\u062f\u0646 \u0648\u0627\u0628\u0633\u062a\u06af\u06cc \u0647\u0627<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-18\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%B1%D8%A7%D9%87_%D8%A7%D9%86%D8%AF%D8%A7%D8%B2%DB%8C_%DA%A9%D9%84%D8%A7%D8%B3_%D8%AA%D8%B3%D8%AA\" >\u0631\u0627\u0647 \u0627\u0646\u062f\u0627\u0632\u06cc \u06a9\u0644\u0627\u0633 \u062a\u0633\u062a<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-19\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%A2%D9%85%D8%A7%D8%AF%D9%87_%D8%B3%D8%A7%D8%B2%DB%8C_%D9%85%D8%AD%DB%8C%D8%B7_%D9%82%D8%A8%D9%84_%D8%A7%D8%B2_%D9%87%D8%B1_%D8%A2%D8%B2%D9%85%D9%88%D9%86\" >\u0622\u0645\u0627\u062f\u0647 \u0633\u0627\u0632\u06cc \u0645\u062d\u06cc\u0637 \u0642\u0628\u0644 \u0627\u0632 \u0647\u0631 \u0622\u0632\u0645\u0648\u0646<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-20\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%AA%D9%85%DB%8C%D8%B2_%DA%A9%D8%B1%D8%AF%D9%86_%D8%A8%D8%B9%D8%AF_%D8%A7%D8%B2_%D9%87%D8%B1_%D8%A2%D8%B2%D9%85%D8%A7%DB%8C%D8%B4\" >\u062a\u0645\u06cc\u0632 \u06a9\u0631\u062f\u0646 \u0628\u0639\u062f \u0627\u0632 \u0647\u0631 \u0622\u0632\u0645\u0627\u06cc\u0634<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-21\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%B1%D8%A7%D9%87_%D8%A7%D9%86%D8%AF%D8%A7%D8%B2%DB%8C_%DA%A9%D8%A7%D9%85%D9%84\" >\u0631\u0627\u0647 \u0627\u0646\u062f\u0627\u0632\u06cc \u06a9\u0627\u0645\u0644<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-22\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%A8%D8%B1%D8%B1%D8%B3%DB%8C_%D8%AF%D8%B1%D8%AE%D9%88%D8%A7%D8%B3%D8%AA%E2%80%8C%D9%87%D8%A7_%D8%AF%D8%B1_%D8%B8%D8%B1%D9%81%DB%8C%D8%AA_%D8%B3%D8%B7%D9%84\" >\u0628\u0631\u0631\u0633\u06cc \u062f\u0631\u062e\u0648\u0627\u0633\u062a\u200c\u0647\u0627 \u062f\u0631 \u0638\u0631\u0641\u06cc\u062a \u0633\u0637\u0644<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-23\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%AA%D8%A3%DB%8C%DB%8C%D8%AF_%D8%AF%D8%B1%D8%AE%D9%88%D8%A7%D8%B3%D8%AA_%D9%87%D8%A7_%D9%88%D9%82%D8%AA%DB%8C_%D8%B3%D8%B7%D9%84_%D8%AE%D8%A7%D9%84%DB%8C_%D8%A7%D8%B3%D8%AA_%D8%B1%D8%AF_%D9%85%DB%8C_%D8%B4%D9%88%D8%AF\" >\u062a\u0623\u06cc\u06cc\u062f \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0647\u0627 \u0648\u0642\u062a\u06cc \u0633\u0637\u0644 \u062e\u0627\u0644\u06cc \u0627\u0633\u062a \u0631\u062f \u0645\u06cc \u0634\u0648\u062f<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-24\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%B3%D8%B7%D9%84_%D8%AA%D8%A3%DB%8C%DB%8C%D8%AF_%D8%A8%D9%87_%D8%AA%D8%AF%D8%B1%DB%8C%D8%AC_%D8%AF%D9%88%D8%A8%D8%A7%D8%B1%D9%87_%D9%BE%D8%B1_%D9%85%DB%8C_%D8%B4%D9%88%D8%AF\" >\u0633\u0637\u0644 \u062a\u0623\u06cc\u06cc\u062f \u0628\u0647 \u062a\u062f\u0631\u06cc\u062c \u062f\u0648\u0628\u0627\u0631\u0647 \u067e\u0631 \u0645\u06cc \u0634\u0648\u062f<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-25\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%AA%D8%A3%DB%8C%DB%8C%D8%AF_%D9%85%D8%AF%DB%8C%D8%B1%DB%8C%D8%AA_%D9%85%D8%B3%D8%AA%D9%82%D9%84_%DA%86%D9%86%D8%AF%DB%8C%D9%86_%D9%85%D8%B4%D8%AA%D8%B1%DB%8C\" >\u062a\u0623\u06cc\u06cc\u062f \u0645\u062f\u06cc\u0631\u06cc\u062a \u0645\u0633\u062a\u0642\u0644 \u0686\u0646\u062f\u06cc\u0646 \u0645\u0634\u062a\u0631\u06cc<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-26\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%AA%D8%A3%DB%8C%DB%8C%D8%AF_%D8%AF%D9%88%D8%A8%D8%A7%D8%B1%D9%87_%D9%BE%D8%B1_%DA%A9%D8%B1%D8%AF%D9%86_%D8%AA%D9%88%DA%A9%D9%86_%D8%A7%D8%B2_%D8%B8%D8%B1%D9%81%DB%8C%D8%AA_%D8%B3%D8%B7%D9%84_%D8%AA%D8%AC%D8%A7%D9%88%D8%B2_%D9%86%D9%85%DB%8C_%DA%A9%D9%86%D8%AF\" >\u062a\u0623\u06cc\u06cc\u062f \u062f\u0648\u0628\u0627\u0631\u0647 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u062a\u0648\u06a9\u0646 \u0627\u0632 \u0638\u0631\u0641\u06cc\u062a \u0633\u0637\u0644 \u062a\u062c\u0627\u0648\u0632 \u0646\u0645\u06cc \u06a9\u0646\u062f<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-27\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%D8%AA%D8%A3%DB%8C%DB%8C%D8%AF_%D8%AF%D8%B1%D8%AE%D9%88%D8%A7%D8%B3%D8%AA_%D9%87%D8%A7%DB%8C_%D8%B1%D8%AF_%D8%B4%D8%AF%D9%87_%D8%A8%D8%B1_%D8%AA%D8%B9%D8%AF%D8%A7%D8%AF_%D8%AA%D9%88%DA%A9%D9%86_%D9%87%D8%A7_%D8%AA%D8%A3%D8%AB%DB%8C%D8%B1_%D9%86%D9%85%DB%8C_%DA%AF%D8%B0%D8%A7%D8%B1%D8%AF\" >\u062a\u0623\u06cc\u06cc\u062f \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0647\u0627\u06cc \u0631\u062f \u0634\u062f\u0647 \u0628\u0631 \u062a\u0639\u062f\u0627\u062f \u062a\u0648\u06a9\u0646 \u0647\u0627 \u062a\u0623\u062b\u06cc\u0631 \u0646\u0645\u06cc \u06af\u0630\u0627\u0631\u062f<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-28\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#GitHub_Repo\" >GitHub Repo<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-29\" href=\"https:\/\/nabfollower.com\/blog\/%d9%85%d8%ad%d8%af%d9%88%d8%af-%da%a9%d9%86%d9%86%d8%af%d9%87-%d9%86%d8%b1%d8%ae-%d8%b3%d8%b7%d9%84-%d8%aa%d9%88%da%a9%d9%86-redis-java\/#%DA%A9%D9%86%D8%AC%DA%A9%D8%A7%D9%88_%D8%A8%D9%85%D8%A7%D9%86\" >\u06a9\u0646\u062c\u06a9\u0627\u0648 \u0628\u0645\u0627\u0646!<\/a><\/li><\/ul><\/li><\/ul><\/nav><\/div>\n<h3><span class=\"ez-toc-section\" id=\"%D8%B4%D8%A7%D8%AE%D8%B5\"><\/span>\n<p>  \u0634\u0627\u062e\u0635<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<ul>\n<li>\n<p><strong>\u0645\u0642\u062f\u0645\u0647<\/strong><\/p>\n<\/li>\n<li>\n<p><strong>\u0646\u062d\u0648\u0647 \u0639\u0645\u0644\u06a9\u0631\u062f \u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0633\u0637\u0644 \u062a\u0648\u06a9\u0646<\/strong><\/p>\n<\/li>\n<li>\n<p><strong>\u067e\u06cc\u0627\u062f\u0647 \u0633\u0627\u0632\u06cc \u0628\u0627 Redis \u0648 Java<\/strong><\/p>\n<\/li>\n<li>\n<p><strong>\u062a\u0633\u062a \u0628\u0627 TestContainers \u0648 AssertJ<\/strong><\/p>\n<\/li>\n<li>\n<p><strong>\u0646\u062a\u06cc\u062c\u0647 \u06af\u06cc\u0631\u06cc (Repo GitHub)<\/strong><\/p>\n<\/li>\n<\/ul>\n<h2><span class=\"ez-toc-section\" id=\"%DA%86%DA%AF%D9%88%D9%86%D9%87_%DA%A9%D8%A7%D8%B1_%D9%85%DB%8C_%DA%A9%D9%86%D8%AF\"><\/span>\n<p>  \u0686\u06af\u0648\u0646\u0647 \u06a9\u0627\u0631 \u0645\u06cc \u06a9\u0646\u062f<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p><img decoding=\"async\" src=\"https:\/\/media2.dev.to\/dynamic\/image\/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto\/https%3A%2F%2Fcdn-images-1.medium.com%2Fmax%2F2160%2F1%2A7cDKq5yh5RD0ygvb3mVwfQ.gif\" loading=\"lazy\" width=\"800\" height=\"400\" alt=\"\" title=\"\"><\/p>\n<h3><span class=\"ez-toc-section\" id=\"1_%D9%86%D8%B1%D8%AE_%D9%BE%D8%B1_%DA%A9%D8%B1%D8%AF%D9%86_%D9%85%D8%AC%D8%AF%D8%AF_%D8%AA%D9%88%DA%A9%D9%86_%D8%B1%D8%A7_%D8%AA%D8%B9%D8%B1%DB%8C%D9%81_%DA%A9%D9%86%DB%8C%D8%AF\"><\/span>\n<p>  1. <strong>\u0646\u0631\u062e \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f \u062a\u0648\u06a9\u0646 \u0631\u0627 \u062a\u0639\u0631\u06cc\u0641 \u06a9\u0646\u06cc\u062f<\/strong><br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0646\u0631\u062e\u06cc \u0631\u0627 \u062a\u0646\u0638\u06cc\u0645 \u06a9\u0646\u06cc\u062f \u06a9\u0647 \u062a\u0648\u06a9\u0646 \u0647\u0627 \u0628\u0627 \u0622\u0646 \u0628\u0647 \u0633\u0637\u0644 \u0627\u0636\u0627\u0641\u0647 \u0634\u0648\u0646\u062f\u060c \u0645\u0627\u0646\u0646\u062f 1 \u062a\u0648\u06a9\u0646 \u062f\u0631 \u062b\u0627\u0646\u06cc\u0647 \u06cc\u0627 10 \u062a\u0648\u06a9\u0646 \u062f\u0631 \u062f\u0642\u06cc\u0642\u0647.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"2_%D9%BE%DB%8C%DA%AF%DB%8C%D8%B1%DB%8C_%D9%85%D8%B5%D8%B1%D9%81_%D8%AA%D9%88%DA%A9%D9%86\"><\/span>\n<p>  2. <strong>\u067e\u06cc\u06af\u06cc\u0631\u06cc \u0645\u0635\u0631\u0641 \u062a\u0648\u06a9\u0646<\/strong><br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0628\u0631\u0627\u06cc \u0647\u0631 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0648\u0631\u0648\u062f\u06cc\u060c \u06cc\u06a9 \u062a\u0648\u06a9\u0646 \u0627\u0632 \u0633\u0637\u0644 \u06a9\u0645 \u06a9\u0646\u06cc\u062f.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"3_%D8%AF%D9%88%D8%A8%D8%A7%D8%B1%D9%87_%D9%BE%D8%B1_%DA%A9%D8%B1%D8%AF%D9%86_%D8%AA%D9%88%DA%A9%D9%86_%D9%87%D8%A7\"><\/span>\n<p>  3. <strong>\u062f\u0648\u0628\u0627\u0631\u0647 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u062a\u0648\u06a9\u0646 \u0647\u0627<\/strong><br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0628\u0647 \u0637\u0648\u0631 \u0645\u062f\u0627\u0648\u0645 \u0633\u0637\u0644 \u0631\u0627 \u0628\u0627 \u0646\u0631\u062e \u062a\u0639\u0631\u06cc\u0641 \u0634\u062f\u0647\u060c \u062a\u0627 \u062d\u062f\u0627\u06a9\u062b\u0631 \u0638\u0631\u0641\u06cc\u062a \u0622\u0646\u060c \u062f\u0648\u0628\u0627\u0631\u0647 \u067e\u0631 \u06a9\u0646\u06cc\u062f\u060c \u0627\u0637\u0645\u06cc\u0646\u0627\u0646 \u062d\u0627\u0635\u0644 \u06a9\u0646\u06cc\u062f \u06a9\u0647 \u062a\u0648\u06a9\u0646 \u0647\u0627\u06cc \u0627\u0633\u062a\u0641\u0627\u062f\u0647 \u0646\u0634\u062f\u0647 \u0645\u06cc \u062a\u0648\u0627\u0646\u0646\u062f \u0628\u0631\u0627\u06cc \u0627\u0646\u0641\u062c\u0627\u0631\u0647\u0627\u06cc \u0622\u06cc\u0646\u062f\u0647 \u062c\u0645\u0639 \u0634\u0648\u0646\u062f.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"4_%D8%A8%D8%B1%D8%B1%D8%B3%DB%8C_%D9%85%D8%AD%D8%AF%D9%88%D8%AF%DB%8C%D8%AA_%D9%86%D8%B1%D8%AE\"><\/span>\n<p>  4. <strong>\u0628\u0631\u0631\u0633\u06cc \u0645\u062d\u062f\u0648\u062f\u06cc\u062a \u0646\u0631\u062e<\/strong><br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0642\u0628\u0644 \u0627\u0632 \u067e\u0631\u062f\u0627\u0632\u0634 \u062f\u0631\u062e\u0648\u0627\u0633\u062a\u060c \u0628\u0631\u0631\u0633\u06cc \u06a9\u0646\u06cc\u062f \u06a9\u0647 \u0622\u06cc\u0627 \u062a\u0648\u06a9\u0646 \u0647\u0627\u06cc \u06a9\u0627\u0641\u06cc \u062f\u0631 \u0633\u0637\u0644 \u0648\u062c\u0648\u062f \u062f\u0627\u0631\u062f \u06cc\u0627 \u062e\u06cc\u0631. \u0627\u06af\u0631 \u0633\u0637\u0644 \u062e\u0627\u0644\u06cc \u0627\u0633\u062a\u060c \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0631\u0627 \u0631\u062f \u06a9\u0646\u06cc\u062f \u062a\u0627 \u0632\u0645\u0627\u0646\u06cc \u06a9\u0647 \u062a\u0648\u06a9\u0646 \u0647\u0627 \u062f\u0648\u0628\u0627\u0631\u0647 \u067e\u0631 \u0634\u0648\u0646\u062f.<\/p>\n<h2><span class=\"ez-toc-section\" id=\"%D9%86%D8%AD%D9%88%D9%87_%D9%BE%DB%8C%D8%A7%D8%AF%D9%87_%D8%B3%D8%A7%D8%B2%DB%8C_%D8%A2%D9%86_%D8%A8%D8%A7_Redis_%D9%88_Java\"><\/span>\n<p>  \u0646\u062d\u0648\u0647 \u067e\u06cc\u0627\u062f\u0647 \u0633\u0627\u0632\u06cc \u0622\u0646 \u0628\u0627 Redis \u0648 Java<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>\u0628\u0631\u0627\u06cc <strong>\u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0633\u0637\u0644 \u062a\u0648\u06a9\u0646<\/strong>Redis \u06cc\u06a9 \u0631\u0648\u0634 \u06a9\u0627\u0631\u0622\u0645\u062f \u0628\u0631\u0627\u06cc \u0631\u062f\u06cc\u0627\u0628\u06cc \u0646\u0634\u0627\u0646\u0647 \u0647\u0627 \u0648 \u067e\u06cc\u0627\u062f\u0647 \u0633\u0627\u0632\u06cc \u0627\u0644\u06af\u0648\u0631\u06cc\u062a\u0645 \u0627\u0631\u0627\u0626\u0647 \u0645\u06cc \u062f\u0647\u062f. \u062f\u0631 \u0627\u06cc\u0646\u062c\u0627 \u0646\u062d\u0648\u0647 \u0627\u0646\u062c\u0627\u0645 \u0622\u0646 \u0622\u0645\u062f\u0647 \u0627\u0633\u062a:<\/p>\n<h3><span class=\"ez-toc-section\" id=\"1_%D8%AA%D8%B9%D8%AF%D8%A7%D8%AF_%D8%B1%D9%85%D8%B2_%D9%81%D8%B9%D9%84%DB%8C_%D9%88_%D8%A2%D8%AE%D8%B1%DB%8C%D9%86_%D8%B2%D9%85%D8%A7%D9%86_%D9%BE%D8%B1_%DA%A9%D8%B1%D8%AF%D9%86_%D8%B1%D8%A7_%D8%A8%D8%A7%D8%B2%DB%8C%D8%A7%D8%A8%DB%8C_%DA%A9%D9%86%DB%8C%D8%AF\"><\/span>\n<p>  1. \u062a\u0639\u062f\u0627\u062f \u0631\u0645\u0632 \u0641\u0639\u0644\u06cc \u0648 \u0622\u062e\u0631\u06cc\u0646 \u0632\u0645\u0627\u0646 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0631\u0627 \u0628\u0627\u0632\u06cc\u0627\u0628\u06cc \u06a9\u0646\u06cc\u062f<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0627\u0628\u062a\u062f\u0627 \u062a\u0639\u062f\u0627\u062f \u0631\u0645\u0632 \u0641\u0639\u0644\u06cc \u0648 \u0622\u062e\u0631\u06cc\u0646 \u0632\u0645\u0627\u0646 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f \u0631\u0627 \u0628\u0627\u0632\u06cc\u0627\u0628\u06cc \u06a9\u0646\u06cc\u062f:<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>GET rate_limit:<clientid>:count  \nGET rate_limit:<clientid>:lastRefill  \n<\/clientid><\/clientid><\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<p>\u0627\u06af\u0631 \u0627\u06cc\u0646 \u06a9\u0644\u06cc\u062f\u0647\u0627 \u0648\u062c\u0648\u062f \u0646\u062f\u0627\u0634\u062a\u0646\u062f\u060c \u062a\u0639\u062f\u0627\u062f \u062a\u0648\u06a9\u0646 \u0647\u0627 \u0631\u0627 \u0628\u0647 \u062d\u062f\u0627\u06a9\u062b\u0631 \u0638\u0631\u0641\u06cc\u062a \u0633\u0637\u0644 \u0645\u0642\u062f\u0627\u0631\u062f\u0647\u06cc \u06a9\u0646\u06cc\u062f \u0648 \u0628\u0627 \u0627\u0633\u062a\u0641\u0627\u062f\u0647 \u0627\u0632 SET\u060c \u0632\u0645\u0627\u0646 \u0641\u0639\u0644\u06cc \u0631\u0627 \u0628\u0647 \u0639\u0646\u0648\u0627\u0646 \u0622\u062e\u0631\u06cc\u0646 \u0632\u0645\u0627\u0646 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f \u062a\u0646\u0638\u06cc\u0645 \u06a9\u0646\u06cc\u062f.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"2_%D8%AF%D8%B1_%D8%B5%D9%88%D8%B1%D8%AA_%D9%84%D8%B2%D9%88%D9%85_%D8%AA%D9%88%DA%A9%D9%86_%D9%87%D8%A7_%D8%B1%D8%A7_%D8%AF%D9%88%D8%A8%D8%A7%D8%B1%D9%87_%D9%BE%D8%B1_%DA%A9%D9%86%DB%8C%D8%AF_%D9%88_%D8%B3%D8%B7%D9%84_%D8%B1%D8%A7_%D8%A8%D9%87_%D8%B1%D9%88%D8%B2_%DA%A9%D9%86%DB%8C%D8%AF\"><\/span>\n<p>  2. \u062f\u0631 \u0635\u0648\u0631\u062a \u0644\u0632\u0648\u0645 \u062a\u0648\u06a9\u0646 \u0647\u0627 \u0631\u0627 \u062f\u0648\u0628\u0627\u0631\u0647 \u067e\u0631 \u06a9\u0646\u06cc\u062f \u0648 \u0633\u0637\u0644 \u0631\u0627 \u0628\u0647 \u0631\u0648\u0632 \u06a9\u0646\u06cc\u062f<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u067e\u0633 \u0627\u0632 \u067e\u0631\u062f\u0627\u0632\u0634 \u0647\u0631 \u062f\u0631\u062e\u0648\u0627\u0633\u062a\u060c \u062a\u0639\u062f\u0627\u062f \u062a\u0648\u06a9\u0646\u200c\u0647\u0627 \u0648 \u0622\u062e\u0631\u06cc\u0646 \u0632\u0645\u0627\u0646 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f \u0631\u0627 \u0628\u0647\u200c\u0631\u0648\u0632\u0631\u0633\u0627\u0646\u06cc \u06a9\u0646\u06cc\u062f:<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>SET rate_limit:<clientid>:count <new_token_count>  \nSET rate_limit:<clientid>:lastRefill <current_time>  \n<\/current_time><\/clientid><\/new_token_count><\/clientid><\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<h3><span class=\"ez-toc-section\" id=\"3_%D8%A7%D8%AC%D8%A7%D8%B2%D9%87_%DB%8C%D8%A7_%D8%B1%D8%AF_%D8%AF%D8%B1%D8%AE%D9%88%D8%A7%D8%B3%D8%AA\"><\/span>\n<p>  3. \u0627\u062c\u0627\u0632\u0647 \u06cc\u0627 \u0631\u062f \u062f\u0631\u062e\u0648\u0627\u0633\u062a<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0627\u06af\u0631 \u062a\u0648\u06a9\u0646\u200c\u0647\u0627 \u062f\u0631 \u062f\u0633\u062a\u0631\u0633 \u0647\u0633\u062a\u0646\u062f\u060c \u0628\u0647 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0627\u062c\u0627\u0632\u0647 \u062f\u0647\u06cc\u062f \u0648 \u062a\u0639\u062f\u0627\u062f \u0631\u0627 \u0628\u0627 \u0627\u0633\u062a\u0641\u0627\u062f\u0647 \u0627\u0632:<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>DECR rate_limit:<clientid>:count\n<\/clientid><\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<h2><span class=\"ez-toc-section\" id=\"%D9%BE%DB%8C%D8%A7%D8%AF%D9%87_%D8%B3%D8%A7%D8%B2%DB%8C_%D8%A2%D9%86_%D8%A8%D8%A7_Jedis\"><\/span>\n<p>  \u067e\u06cc\u0627\u062f\u0647 \u0633\u0627\u0632\u06cc \u0622\u0646 \u0628\u0627 Jedis<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p><strong>\u062c\u062f\u06cc<\/strong> \u06cc\u06a9 \u06a9\u062a\u0627\u0628\u062e\u0627\u0646\u0647 \u0645\u062d\u0628\u0648\u0628 \u062c\u0627\u0648\u0627 \u0627\u0633\u062a \u06a9\u0647 \u0628\u0631\u0627\u06cc \u062a\u0639\u0627\u0645\u0644 \u0628\u0627 **Redis ** \u0627\u0633\u062a\u0641\u0627\u062f\u0647 \u0645\u06cc \u0634\u0648\u062f \u0648 \u0645\u0627 \u0627\u0632 \u0622\u0646 \u0628\u0631\u0627\u06cc \u067e\u06cc\u0627\u062f\u0647 \u0633\u0627\u0632\u06cc \u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u062e\u0648\u062f \u0627\u0633\u062a\u0641\u0627\u062f\u0647 \u062e\u0648\u0627\u0647\u06cc\u0645 \u06a9\u0631\u062f \u0632\u06cc\u0631\u0627 \u06cc\u06a9 API \u0633\u0627\u062f\u0647 \u0648 \u0634\u0647\u0648\u062f\u06cc \u0628\u0631\u0627\u06cc \u0627\u062c\u0631\u0627\u06cc \u062f\u0633\u062a\u0648\u0631\u0627\u062a Redis \u0627\u0632 \u0628\u0631\u0646\u0627\u0645\u0647 \u0647\u0627\u06cc JVM \u0627\u0631\u0627\u0626\u0647 \u0645\u06cc \u062f\u0647\u062f.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"Jedis_%D8%B1%D8%A7_%D8%A8%D9%87_%D9%81%D8%A7%DB%8C%D9%84_Maven_%D8%AE%D9%88%D8%AF_%D8%A7%D8%B6%D8%A7%D9%81%D9%87_%DA%A9%D9%86%DB%8C%D8%AF\"><\/span>\n<p>  <strong>Jedis \u0631\u0627 \u0628\u0647 \u0641\u0627\u06cc\u0644 Maven \u062e\u0648\u062f \u0627\u0636\u0627\u0641\u0647 \u06a9\u0646\u06cc\u062f<\/strong>:<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0622\u062e\u0631\u06cc\u0646 \u0646\u0633\u062e\u0647 \u0631\u0627 \u0627\u06cc\u0646\u062c\u0627 \u0628\u0631\u0631\u0633\u06cc \u06a9\u0646\u06cc\u062f.<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code><dependency>\n    <groupid>redis.clients<\/groupid>\n    <artifactid>jedis<\/artifactid>\n    <version>5.2.0<\/version>\n<\/dependency>\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<h3><span class=\"ez-toc-section\" id=\"%D8%A7%DB%8C%D8%AC%D8%A7%D8%AF_%DB%8C%DA%A9_TokenBucketRateLimiter_%DA%A9%D9%84%D8%A7%D8%B3\"><\/span>\n<p>  \u0627\u06cc\u062c\u0627\u062f \u06cc\u06a9 <strong>TokenBucketRateLimiter<\/strong> \u06a9\u0644\u0627\u0633:<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u06a9\u0644\u0627\u0633 \u0628\u0631\u06af\u0632\u0627\u0631 \u062e\u0648\u0627\u0647\u062f \u0634\u062f:<\/p>\n<ol>\n<li>\n<p>\u06cc\u06a9 \u0646\u0645\u0648\u0646\u0647 Jedis \u0631\u0627 \u0628\u067e\u0630\u06cc\u0631\u06cc\u062f.<\/p>\n<\/li>\n<li>\n<p>\u062d\u062f\u0627\u06a9\u062b\u0631 \u0638\u0631\u0641\u06cc\u062a \u0633\u0637\u0644 \u062a\u0648\u06a9\u0646 \u0631\u0627 \u062a\u0639\u0631\u06cc\u0641 \u06a9\u0646\u06cc\u062f.<\/p>\n<\/li>\n<li>\n<p>\u0646\u0631\u062e \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f \u062a\u0648\u06a9\u0646 (\u062a\u0648\u06a9\u0646 \u062f\u0631 \u062b\u0627\u0646\u06cc\u0647) \u0631\u0627 \u0645\u0634\u062e\u0635 \u06a9\u0646\u06cc\u062f.<\/p>\n<\/li>\n<\/ol>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>    package io.redis;\n\n    import redis.clients.jedis.Jedis;\n    import redis.clients.jedis.Transaction;\n\n    public class TokenBucketRateLimiter {\n        private final Jedis jedis;\n        private final int bucketCapacity; \/\/ Maximum tokens the bucket can hold\n        private final double refillRate; \/\/ Tokens refilled per second\n\n        public TokenBucketRateLimiter(Jedis jedis, int bucketCapacity, double refillRate) {\n            this.jedis = jedis;\n            this.bucketCapacity = bucketCapacity;\n            this.refillRate = refillRate;\n        }\n    }\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<h3><span class=\"ez-toc-section\" id=\"%D8%AF%D8%B1%D8%AE%D9%88%D8%A7%D8%B3%D8%AA_%D9%87%D8%A7_%D8%B1%D8%A7_%D8%AA%D8%A7%DB%8C%DB%8C%D8%AF_%DA%A9%D9%86%DB%8C%D8%AF\"><\/span>\n<p>  \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0647\u0627 \u0631\u0627 \u062a\u0627\u06cc\u06cc\u062f \u06a9\u0646\u06cc\u062f<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0648\u0638\u06cc\u0641\u0647 \u0627\u0635\u0644\u06cc \u0627\u06cc\u0646 \u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0627\u06cc\u0646 \u0627\u0633\u062a \u06a9\u0647 \u062a\u0639\u06cc\u06cc\u0646 \u06a9\u0646\u062f \u0622\u06cc\u0627 \u06cc\u06a9 \u0645\u0634\u062a\u0631\u06cc \u062a\u0648\u06a9\u0646 \u0647\u0627\u06cc \u06a9\u0627\u0641\u06cc \u0628\u0631\u0627\u06cc \u067e\u0631\u062f\u0627\u0632\u0634 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u062e\u0648\u062f \u062f\u0627\u0631\u062f \u06cc\u0627 \u062e\u06cc\u0631. \u0627\u06af\u0631 \u0628\u0644\u0647\u060c \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0645\u062c\u0627\u0632 \u0627\u0633\u062a \u0648 \u062a\u0648\u06a9\u0646 \u0647\u0627 \u06a9\u0633\u0631 \u0645\u06cc \u0634\u0648\u0646\u062f. \u062f\u0631 \u063a\u06cc\u0631 \u0627\u06cc\u0646 \u0635\u0648\u0631\u062a \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0645\u0633\u062f\u0648\u062f \u0645\u06cc \u0634\u0648\u062f.<\/p>\n<p><strong>\u0645\u0631\u062d\u0644\u0647 1: \u06a9\u0644\u06cc\u062f\u0647\u0627 \u0631\u0627 \u0627\u06cc\u062c\u0627\u062f \u06a9\u0646\u06cc\u062f<\/strong><br \/>\u0645\u0627 \u062a\u0639\u062f\u0627\u062f \u062a\u0648\u06a9\u0646 \u0647\u0631 \u0645\u0634\u062a\u0631\u06cc \u0648 \u0622\u062e\u0631\u06cc\u0646 \u0632\u0645\u0627\u0646 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f \u0631\u0627 \u0628\u0627 \u0627\u0633\u062a\u0641\u0627\u062f\u0647 \u0627\u0632 \u06a9\u0644\u06cc\u062f\u0647\u0627\u06cc \u0645\u0646\u062d\u0635\u0631 \u0628\u0647 \u0641\u0631\u062f \u062f\u0631 Redis \u0630\u062e\u06cc\u0631\u0647 \u0645\u06cc \u06a9\u0646\u06cc\u0645. \u06a9\u0644\u06cc\u062f\u0647\u0627 \u0628\u0647 \u0634\u06a9\u0644 \u0632\u06cc\u0631 \u062e\u0648\u0627\u0647\u0646\u062f \u0628\u0648\u062f:<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>public boolean isAllowed(String clientId) {\n    String keyCount = \"rate_limit:\" + clientId + \":count\";\n    String keyLastRefill = \"rate_limit:\" + clientId + \":lastRefill\";\n}\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<p>\u0628\u0647 \u0639\u0646\u0648\u0627\u0646 \u0645\u062b\u0627\u0644\u060c \u0627\u06af\u0631 \u0634\u0646\u0627\u0633\u0647 \u0645\u0634\u062a\u0631\u06cc user123 \u0628\u0627\u0634\u062f\u060c \u06a9\u0644\u06cc\u062f\u0647\u0627\u06cc \u0622\u0646\u0647\u0627 rate_limit:user123:count \u0648 rate_limit:user123:lastRefill \u062e\u0648\u0627\u0647\u062f \u0628\u0648\u062f.<\/p>\n<p><strong>\u0645\u0631\u062d\u0644\u0647 2: \u0648\u0627\u06a9\u0634\u06cc \u0648\u0636\u0639\u06cc\u062a \u0641\u0639\u0644\u06cc<\/strong><br \/>\u0645\u0627 \u0627\u0632 \u062f\u0633\u062a\u0648\u0631 GET Redis \u0628\u0631\u0627\u06cc \u0628\u0627\u0632\u06cc\u0627\u0628\u06cc \u062a\u0639\u062f\u0627\u062f \u062a\u0648\u06a9\u0646 \u0641\u0639\u0644\u06cc \u0648 \u0622\u062e\u0631\u06cc\u0646 \u0632\u0645\u0627\u0646 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0627\u0633\u062a\u0641\u0627\u062f\u0647 \u0645\u06cc \u06a9\u0646\u06cc\u0645. \u0627\u06af\u0631 \u06a9\u0644\u06cc\u062f\u0647\u0627 \u0648\u062c\u0648\u062f \u0646\u062f\u0627\u0634\u062a\u0647 \u0628\u0627\u0634\u0646\u062f\u060c \u0641\u0631\u0636 \u0645\u06cc \u06a9\u0646\u06cc\u0645 \u0633\u0637\u0644 \u067e\u0631 \u0627\u0633\u062a \u0648 \u0622\u062e\u0631\u06cc\u0646 \u0632\u0645\u0627\u0646 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f\u060c \u0645\u0647\u0631 \u0632\u0645\u0627\u0646\u06cc \u0641\u0639\u0644\u06cc \u0627\u0633\u062a.<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>public boolean isAllowed(String clientId) {\n    String keyCount = \"rate_limit:\" + clientId + \":count\";\n    String keyLastRefill = \"rate_limit:\" + clientId + \":lastRefill\";\n\n    Transaction transaction = jedis.multi();\n    transaction.get(keyLastRefill);\n    transaction.get(keyCount);\n    var results = transaction.exec();\n\n    long currentTime = System.currentTimeMillis();\n    long lastRefillTime = results.get(0) != null ? Long.parseLong((String) results.get(0)) : currentTime;\n    int tokenCount = results.get(1) != null ? Integer.parseInt((String) results.get(1)) : bucketCapacity;\n}\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<p><strong>\u0645\u0631\u062d\u0644\u0647 3: \u062a\u0648\u06a9\u0646 \u0647\u0627 \u0631\u0627 \u062f\u0648\u0628\u0627\u0631\u0647 \u067e\u0631 \u06a9\u0646\u06cc\u062f<\/strong><br \/>\u0628\u0631 \u0627\u0633\u0627\u0633 \u0632\u0645\u0627\u0646 \u0633\u067e\u0631\u06cc \u0634\u062f\u0647 \u0627\u0632 \u0622\u062e\u0631\u06cc\u0646 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f\u060c \u0645\u062d\u0627\u0633\u0628\u0647 \u06a9\u0646\u06cc\u062f \u06a9\u0647 \u0686\u0647 \u062a\u0639\u062f\u0627\u062f \u0646\u0634\u0627\u0646\u0647 \u0628\u0627\u06cc\u062f \u0627\u0636\u0627\u0641\u0647 \u0634\u0648\u062f. \u0627\u0637\u0645\u06cc\u0646\u0627\u0646 \u062d\u0627\u0635\u0644 \u06a9\u0646\u06cc\u062f \u06a9\u0647 \u0633\u0637\u0644 \u0627\u0632 \u062d\u062f\u0627\u06a9\u062b\u0631 \u0638\u0631\u0641\u06cc\u062a \u062e\u0648\u062f \u062a\u062c\u0627\u0648\u0632 \u0646\u0645\u06cc \u06a9\u0646\u062f.<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>long elapsedTimeMs = currentTime - lastRefillTime;\ndouble elapsedTimeSecs = elapsedTimeMs \/ 1000.0;\nint tokensToAdd = (int) (elapsedTimeSecs * refillRate);\n\ntokenCount = Math.min(bucketCapacity, tokenCount + tokensToAdd);\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<p><strong>\u0645\u0631\u062d\u0644\u0647 4: \u062f\u0631 \u062f\u0633\u062a\u0631\u0633 \u0628\u0648\u062f\u0646 \u062a\u0648\u06a9\u0646 \u0631\u0627 \u0628\u0631\u0631\u0633\u06cc \u06a9\u0646\u06cc\u062f<\/strong><br \/>\u0628\u0631\u0627\u06cc \u062a\u0639\u06cc\u06cc\u0646 \u0627\u06cc\u0646\u06a9\u0647 \u0622\u06cc\u0627 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0645\u062c\u0627\u0632 \u0627\u0633\u062a \u06cc\u0627 \u062e\u06cc\u0631\u060c \u062a\u0639\u062f\u0627\u062f \u0631\u0645\u0632 \u0641\u0639\u0644\u06cc \u0631\u0627 \u0645\u0642\u0627\u06cc\u0633\u0647 \u06a9\u0646\u06cc\u062f. <strong>\u0627\u06af\u0631 \u062a\u0648\u06a9\u0646\u200c\u0647\u0627 \u062f\u0631 \u062f\u0633\u062a\u0631\u0633 \u0647\u0633\u062a\u0646\u062f\u060c \u06cc\u06a9 \u062a\u0648\u06a9\u0646 \u06a9\u0633\u0631 \u06a9\u0646\u06cc\u062f. \u062f\u0631 \u063a\u06cc\u0631 \u0627\u06cc\u0646 \u0635\u0648\u0631\u062a\u060c \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0631\u0627 \u0645\u0633\u062f\u0648\u062f \u06a9\u0646\u06cc\u062f.<\/strong><\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>boolean isAllowed = tokenCount &gt; 0;\n\nif (isAllowed) {\n    tokenCount--;\n}\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<p><strong>\u0645\u0631\u062d\u0644\u0647 5: Redis \u0631\u0627 \u0628\u0647 \u0631\u0648\u0632 \u06a9\u0646\u06cc\u062f<\/strong><br \/>\u0645\u0627 \u062a\u0639\u062f\u0627\u062f \u062a\u0648\u06a9\u0646 \u0647\u0627 \u0648 \u0622\u062e\u0631\u06cc\u0646 \u0632\u0645\u0627\u0646 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f \u0631\u0627 \u062f\u0631 Redis \u0628\u0647 \u0631\u0648\u0632 \u0645\u06cc \u06a9\u0646\u06cc\u0645. \u0627\u0632 \u06cc\u06a9 \u062a\u0631\u0627\u06a9\u0646\u0634 \u0628\u0631\u0627\u06cc \u0627\u0637\u0645\u06cc\u0646\u0627\u0646 \u0627\u0632 \u0628\u0647 \u0631\u0648\u0632 \u0631\u0633\u0627\u0646\u06cc \u0627\u062a\u0645\u06cc \u0627\u0633\u062a\u0641\u0627\u062f\u0647 \u06a9\u0646\u06cc\u062f:<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>Transaction transaction = jedis.multi();\ntransaction.set(keyLastRefill, String.valueOf(currentTime)); \/\/ Update last refill time\ntransaction.set(keyCount, String.valueOf(tokenCount));       \/\/ Update token count\ntransaction.exec();\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<h3><span class=\"ez-toc-section\" id=\"%D9%BE%DB%8C%D8%A7%D8%AF%D9%87_%D8%B3%D8%A7%D8%B2%DB%8C_%DA%A9%D8%A7%D9%85%D9%84\"><\/span>\n<p>  \u067e\u06cc\u0627\u062f\u0647 \u0633\u0627\u0632\u06cc \u06a9\u0627\u0645\u0644<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u06a9\u062f \u06a9\u0627\u0645\u0644 \u06a9\u0644\u0627\u0633 FixedWindowRateLimiter \u062f\u0631 \u0627\u06cc\u0646\u062c\u0627 \u0622\u0645\u062f\u0647 \u0627\u0633\u062a:<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>package io.redis;\n\nimport redis.clients.jedis.Jedis;\nimport redis.clients.jedis.Transaction;\n\npublic class TokenBucketRateLimiter {\n    private final Jedis jedis;\n    private final int bucketCapacity; \/\/ Maximum tokens the bucket can hold\n    private final double refillRate; \/\/ Tokens refilled per second\n\n    public TokenBucketRateLimiter(Jedis jedis, int bucketCapacity, double refillRate) {\n        this.jedis = jedis;\n        this.bucketCapacity = bucketCapacity;\n        this.refillRate = refillRate;\n    }\n\n    public boolean isAllowed(String clientId) {\n        String keyCount = \"rate_limit:\" + clientId + \":count\";\n        String keyLastRefill = \"rate_limit:\" + clientId + \":lastRefill\";\n\n        long currentTime = System.currentTimeMillis();\n\n        \/\/ Fetch current state\n        Transaction transaction = jedis.multi();\n        transaction.get(keyLastRefill);\n        transaction.get(keyCount);\n        var results = transaction.exec();\n\n        long lastRefillTime = results.get(0) != null ? Long.parseLong((String) results.get(0)) : currentTime;\n        int tokenCount = results.get(1) != null ? Integer.parseInt((String) results.get(1)) : bucketCapacity;\n\n        \/\/ Refill tokens\n        long elapsedTimeMs = currentTime - lastRefillTime;\n        double elapsedTimeSecs = elapsedTimeMs \/ 1000.0;\n        int tokensToAdd = (int) (elapsedTimeSecs * refillRate);\n        tokenCount = Math.min(bucketCapacity, tokenCount + tokensToAdd);\n\n        \/\/ Check if the request is allowed\n        boolean isAllowed = tokenCount &gt; 0;\n\n        if (isAllowed) {\n            tokenCount--; \/\/ Consume one token\n        }\n\n        \/\/ Update Redis state\n        transaction = jedis.multi();\n        transaction.set(keyLastRefill, String.valueOf(currentTime));\n        transaction.set(keyCount, String.valueOf(tokenCount));\n        transaction.exec();\n\n        return isAllowed;\n    }\n}\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<p>\u0648 \u0645\u0627 \u0622\u0645\u0627\u062f\u0647 \u0634\u0631\u0648\u0639 \u0622\u0632\u0645\u0627\u06cc\u0634 \u0631\u0641\u062a\u0627\u0631 \u0622\u0646 \u0647\u0633\u062a\u06cc\u0645!<\/p>\n<h2><span class=\"ez-toc-section\" id=\"%D8%A2%D8%B2%D9%85%D8%A7%DB%8C%D8%B4_%D9%85%D8%AD%D8%AF%D9%88%D8%AF_%DA%A9%D9%86%D9%86%D8%AF%D9%87_%D9%86%D8%B1%D8%AE_%D9%85%D8%A7\"><\/span>\n<p>  \u0622\u0632\u0645\u0627\u06cc\u0634 \u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0645\u0627<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>\u0628\u0631\u0627\u06cc \u0627\u0637\u0645\u06cc\u0646\u0627\u0646 \u0627\u0632 \u0627\u06cc\u0646\u06a9\u0647 \u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0633\u0637\u0644 \u062a\u0648\u06a9\u0646 \u0645\u0627 \u0645\u0637\u0627\u0628\u0642 \u0627\u0646\u062a\u0638\u0627\u0631 \u0631\u0641\u062a\u0627\u0631 \u0645\u06cc \u06a9\u0646\u062f\u060c \u0622\u0632\u0645\u0627\u06cc\u0634 \u0647\u0627\u06cc\u06cc \u0631\u0627 \u0628\u0631\u0627\u06cc \u0633\u0646\u0627\u0631\u06cc\u0648\u0647\u0627\u06cc \u0645\u062e\u062a\u0644\u0641 \u0645\u06cc \u0646\u0648\u06cc\u0633\u06cc\u0645. \u0628\u0631\u0627\u06cc \u0627\u06cc\u0646 \u06a9\u0627\u0631 \u0627\u0632 \u0633\u0647 \u0627\u0628\u0632\u0627\u0631 \u0627\u0633\u062a\u0641\u0627\u062f\u0647 \u0645\u06cc \u06a9\u0646\u06cc\u0645:<\/p>\n<ol>\n<li>\n<p><strong>Redis Test Containers<\/strong>: \u0627\u06cc\u0646 \u06a9\u062a\u0627\u0628\u062e\u0627\u0646\u0647 \u06cc\u06a9 \u0638\u0631\u0641 Redis \u062c\u062f\u0627 \u0634\u062f\u0647 \u0631\u0627 \u0628\u0631\u0627\u06cc \u0622\u0632\u0645\u0627\u06cc\u0634 \u0645\u06cc \u0686\u0631\u062e\u0627\u0646\u062f. \u0627\u06cc\u0646 \u0628\u062f\u0627\u0646 \u0645\u0639\u0646\u06cc \u0627\u0633\u062a \u06a9\u0647 \u0645\u0627 \u062f\u0631 \u0637\u0648\u0644 \u0622\u0632\u0645\u0627\u06cc\u0634\u0627\u062a \u062e\u0648\u062f \u0646\u06cc\u0627\u0632\u06cc \u0628\u0647 \u062a\u06a9\u06cc\u0647 \u0628\u0631 \u0633\u0631\u0648\u0631 Redis \u062e\u0627\u0631\u062c\u06cc \u0646\u062f\u0627\u0631\u06cc\u0645. \u067e\u0633 \u0627\u0632 \u0627\u0646\u062c\u0627\u0645 \u0622\u0632\u0645\u0627\u06cc\u0634\u0627\u062a\u060c \u0638\u0631\u0641 \u0645\u062a\u0648\u0642\u0641 \u0645\u06cc \u0634\u0648\u062f \u0648 \u0647\u06cc\u0686 \u062f\u0627\u062f\u0647 \u0627\u06cc \u0628\u0627\u0642\u06cc \u0646\u0645\u06cc \u0645\u0627\u0646\u062f.<\/p>\n<\/li>\n<li>\n<p><strong>\u0648\u0627\u062d\u062f 5<\/strong>: \u0686\u0627\u0631\u0686\u0648\u0628 \u0622\u0632\u0645\u0627\u06cc\u0634\u06cc \u0627\u0635\u0644\u06cc \u0645\u0627\u060c \u06a9\u0647 \u0628\u0647 \u0645\u0627 \u06a9\u0645\u06a9 \u0645\u06cc\u200c\u06a9\u0646\u062f \u062a\u0633\u062a\u200c\u0647\u0627 \u0631\u0627 \u0628\u0627 \u0631\u0648\u0634\u200c\u0647\u0627\u06cc \u0686\u0631\u062e\u0647 \u062d\u06cc\u0627\u062a \u0645\u0627\u0646\u0646\u062f @BeforeEach \u0648 @AfterEach \u062a\u0639\u0631\u06cc\u0641 \u0648 \u0633\u0627\u062e\u062a\u0627\u0631 \u062f\u0647\u06cc\u0645.<\/p>\n<\/li>\n<li>\n<p><strong>AssertJ<\/strong>: \u06a9\u062a\u0627\u0628\u062e\u0627\u0646\u0647 \u0627\u06cc \u06a9\u0647 \u0627\u0638\u0647\u0627\u0631\u0627\u062a \u0631\u0627 \u062e\u0648\u0627\u0646\u0627 \u0648 \u0631\u0633\u0627 \u0645\u06cc \u06a9\u0646\u062f\u060c \u0645\u0627\u0646\u0646\u062f assertThat(result).isTrue().<\/p>\n<\/li>\n<\/ol>\n<p>\u0628\u06cc\u0627\u06cc\u06cc\u062f \u0628\u0627 \u0627\u0641\u0632\u0648\u062f\u0646 \u0648\u0627\u0628\u0633\u062a\u06af\u06cc \u0647\u0627\u06cc \u0644\u0627\u0632\u0645 \u0628\u0647 pom.xml \u062e\u0648\u062f \u0634\u0631\u0648\u0639 \u06a9\u0646\u06cc\u0645.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"%D8%A7%D9%81%D8%B2%D9%88%D8%AF%D9%86_%D9%88%D8%A7%D8%A8%D8%B3%D8%AA%DA%AF%DB%8C_%D9%87%D8%A7\"><\/span>\n<p>  \u0627\u0641\u0632\u0648\u062f\u0646 \u0648\u0627\u0628\u0633\u062a\u06af\u06cc \u0647\u0627<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0622\u0646\u0686\u0647 \u0634\u0645\u0627 \u062f\u0631 \u0641\u0627\u06cc\u0644 Maven pom.xml \u062e\u0648\u062f \u0646\u06cc\u0627\u0632 \u062f\u0627\u0631\u06cc\u062f \u062f\u0631 \u0627\u06cc\u0646\u062c\u0627 \u0622\u0645\u062f\u0647 \u0627\u0633\u062a:<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code><dependency>\n    <groupid>org.junit.jupiter<\/groupid>\n    <artifactid>junit-jupiter-engine<\/artifactid>\n    <version>5.10.0<\/version>\n    <scope>test<\/scope>\n<\/dependency>\n<dependency>\n    <groupid>com.redis<\/groupid>\n    <artifactid>testcontainers-redis<\/artifactid>\n    <version>2.2.2<\/version>\n    <scope>test<\/scope>\n<\/dependency>\n<dependency>\n    <groupid>org.assertj<\/groupid>\n    <artifactid>assertj-core<\/artifactid>\n    <version>3.11.1<\/version>\n    <scope>test<\/scope>\n<\/dependency>\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<p>\u0647\u0646\u06af\u0627\u0645\u06cc \u06a9\u0647 \u0627\u06cc\u0646 \u0648\u0627\u0628\u0633\u062a\u06af\u06cc \u0647\u0627 \u0631\u0627 \u0627\u0636\u0627\u0641\u0647 \u06a9\u0631\u062f\u06cc\u062f\u060c \u0622\u0645\u0627\u062f\u0647 \u0634\u0631\u0648\u0639 \u0646\u0648\u0634\u062a\u0646 \u06a9\u0644\u0627\u0633 \u0622\u0632\u0645\u0627\u06cc\u0634\u06cc \u062e\u0648\u062f \u0647\u0633\u062a\u06cc\u062f.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"%D8%B1%D8%A7%D9%87_%D8%A7%D9%86%D8%AF%D8%A7%D8%B2%DB%8C_%DA%A9%D9%84%D8%A7%D8%B3_%D8%AA%D8%B3%D8%AA\"><\/span>\n<p>  \u0631\u0627\u0647 \u0627\u0646\u062f\u0627\u0632\u06cc \u06a9\u0644\u0627\u0633 \u062a\u0633\u062a<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0627\u0648\u0644\u06cc\u0646 \u0645\u0631\u062d\u0644\u0647 \u0627\u06cc\u062c\u0627\u062f \u06cc\u06a9 \u06a9\u0644\u0627\u0633 \u0622\u0632\u0645\u0627\u06cc\u0634\u06cc \u0628\u0627 \u0646\u0627\u0645 FixedWindowRateLimiterTest \u0627\u0633\u062a. \u062f\u0631 \u062f\u0627\u062e\u0644\u060c \u0645\u0627 \u0633\u0647 \u062c\u0632\u0621 \u0627\u0635\u0644\u06cc \u0631\u0627 \u062a\u0639\u0631\u06cc\u0641 \u062e\u0648\u0627\u0647\u06cc\u0645 \u06a9\u0631\u062f:<\/p>\n<ol>\n<li>\n<p><strong>\u0638\u0631\u0641 \u062a\u0633\u062a \u0631\u062f\u06cc\u0633<\/strong>: \u0627\u06cc\u0646 \u06cc\u06a9 \u0646\u0645\u0648\u0646\u0647 Redis \u0631\u0627 \u062f\u0631 \u06cc\u06a9 \u0638\u0631\u0641 Docker \u0631\u0627\u0647 \u0627\u0646\u062f\u0627\u0632\u06cc \u0645\u06cc \u06a9\u0646\u062f.<\/p>\n<\/li>\n<li>\n<p><strong>\u0646\u0645\u0648\u0646\u0647 Jedis<\/strong>: \u0628\u0631\u0627\u06cc \u0627\u0631\u0633\u0627\u0644 \u062f\u0633\u062a\u0648\u0631\u0627\u062a \u0628\u0647 \u0638\u0631\u0641 Redis \u0645\u062a\u0635\u0644 \u0645\u06cc \u0634\u0648\u062f.<\/p>\n<\/li>\n<li>\n<p><strong>\u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e<\/strong>: \u0646\u0645\u0648\u0646\u0647 \u0648\u0627\u0642\u0639\u06cc TokenBucketRateLimiter \u06a9\u0647 \u062f\u0631 \u062d\u0627\u0644 \u0622\u0632\u0645\u0627\u06cc\u0634 \u0647\u0633\u062a\u06cc\u0645.<\/p>\n<\/li>\n<\/ol>\n<p>\u062f\u0631 \u0627\u06cc\u0646\u062c\u0627 \u0627\u0633\u06a9\u0644\u062a \u06a9\u0644\u0627\u0633 \u0622\u0632\u0645\u0627\u06cc\u0634\u06cc \u0645\u0627 \u0628\u0647 \u0646\u0638\u0631 \u0645\u06cc \u0631\u0633\u062f:<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>public class TokenBucketRateLimiterTest {\n\n    private static RedisContainer redisContainer;\n    private Jedis jedis;\n    private TokenBucketRateLimiter rateLimiter;\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<h3><span class=\"ez-toc-section\" id=\"%D8%A2%D9%85%D8%A7%D8%AF%D9%87_%D8%B3%D8%A7%D8%B2%DB%8C_%D9%85%D8%AD%DB%8C%D8%B7_%D9%82%D8%A8%D9%84_%D8%A7%D8%B2_%D9%87%D8%B1_%D8%A2%D8%B2%D9%85%D9%88%D9%86\"><\/span>\n<p>  \u0622\u0645\u0627\u062f\u0647 \u0633\u0627\u0632\u06cc \u0645\u062d\u06cc\u0637 \u0642\u0628\u0644 \u0627\u0632 \u0647\u0631 \u0622\u0632\u0645\u0648\u0646<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0642\u0628\u0644 \u0627\u0632 \u0627\u062c\u0631\u0627\u06cc \u0647\u0631 \u0622\u0632\u0645\u0627\u06cc\u0634\u06cc\u060c \u0628\u0627\u06cc\u062f \u0627\u0632 \u062a\u0645\u06cc\u0632 \u0628\u0648\u062f\u0646 \u0645\u062d\u06cc\u0637 Redis \u0627\u0637\u0645\u06cc\u0646\u0627\u0646 \u062d\u0627\u0635\u0644 \u06a9\u0646\u06cc\u0645. \u062f\u0631 \u0627\u06cc\u0646\u062c\u0627 \u06a9\u0627\u0631\u06cc \u0627\u0633\u062a \u06a9\u0647 \u0645\u0627 \u0627\u0646\u062c\u0627\u0645 \u062e\u0648\u0627\u0647\u06cc\u0645 \u062f\u0627\u062f:<\/p>\n<ol>\n<li>\n<p><strong>\u0628\u0647 Redis \u0645\u062a\u0635\u0644 \u0634\u0648\u06cc\u062f<\/strong>: \u0627\u0632 \u06cc\u06a9 \u0646\u0645\u0648\u0646\u0647 Jedis \u0628\u0631\u0627\u06cc \u0627\u062a\u0635\u0627\u0644 \u0628\u0647 \u0638\u0631\u0641 Redis \u0627\u0633\u062a\u0641\u0627\u062f\u0647 \u06a9\u0646\u06cc\u062f.<\/p>\n<\/li>\n<li>\n<p><strong>Flush Data<\/strong>: \u062f\u0627\u062f\u0647 \u0647\u0627\u06cc \u0628\u0627\u0642\u06cc\u0645\u0627\u0646\u062f\u0647 \u0631\u0627 \u062f\u0631 Redis \u067e\u0627\u06a9 \u06a9\u0646\u06cc\u062f \u062a\u0627 \u0627\u0632 \u0646\u062a\u0627\u06cc\u062c \u062b\u0627\u0628\u062a \u0628\u0631\u0627\u06cc \u0647\u0631 \u0622\u0632\u0645\u0627\u06cc\u0634 \u0627\u0637\u0645\u06cc\u0646\u0627\u0646 \u062d\u0627\u0635\u0644 \u06a9\u0646\u06cc\u062f.<\/p>\n<\/li>\n<\/ol>\n<p>\u0645\u0627 \u0627\u06cc\u0646 \u0631\u0627 \u062f\u0631 \u06cc\u06a9 \u0631\u0648\u0634 \u0645\u0634\u0631\u0648\u062d \u0634\u062f\u0647 \u0628\u0627 @BeforeEach \u062a\u0646\u0638\u06cc\u0645 \u0645\u06cc \u06a9\u0646\u06cc\u0645 \u06a9\u0647 \u0642\u0628\u0644 \u0627\u0632 \u0647\u0631 \u0645\u0648\u0631\u062f \u0622\u0632\u0645\u0627\u06cc\u0634\u06cc \u0627\u062c\u0631\u0627 \u0645\u06cc \u0634\u0648\u062f.<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>@BeforeAll\nstatic void startContainer() {\n    redisContainer = new RedisContainer(\"redis:latest\");\n    redisContainer.withExposedPorts(6379).start();\n}\n\n@BeforeEach\nvoid setup() {\n    jedis = new Jedis(redisContainer.getHost(), redisContainer.getFirstMappedPort());\n    jedis.flushAll();\n}\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<blockquote>\n<p>FLUSHALL \u06cc\u06a9 \u062f\u0633\u062a\u0648\u0631 \u0648\u0627\u0642\u0639\u06cc Redis \u0627\u0633\u062a \u06a9\u0647 \u062a\u0645\u0627\u0645 \u06a9\u0644\u06cc\u062f\u0647\u0627\u06cc \u062a\u0645\u0627\u0645 \u067e\u0627\u06cc\u06af\u0627\u0647 \u062f\u0627\u062f\u0647 \u0647\u0627\u06cc \u0645\u0648\u062c\u0648\u062f \u0631\u0627 \u062d\u0630\u0641 \u0645\u06cc \u06a9\u0646\u062f. \u0627\u0637\u0644\u0627\u0639\u0627\u062a \u0628\u06cc\u0634\u062a\u0631 \u062f\u0631 \u0645\u0648\u0631\u062f \u0622\u0646 \u0631\u0627 \u062f\u0631 \u0627\u0633\u0646\u0627\u062f \u0631\u0633\u0645\u06cc \u0628\u062e\u0648\u0627\u0646\u06cc\u062f.<\/p>\n<\/blockquote>\n<h3><span class=\"ez-toc-section\" id=\"%D8%AA%D9%85%DB%8C%D8%B2_%DA%A9%D8%B1%D8%AF%D9%86_%D8%A8%D8%B9%D8%AF_%D8%A7%D8%B2_%D9%87%D8%B1_%D8%A2%D8%B2%D9%85%D8%A7%DB%8C%D8%B4\"><\/span>\n<p>  \u062a\u0645\u06cc\u0632 \u06a9\u0631\u062f\u0646 \u0628\u0639\u062f \u0627\u0632 \u0647\u0631 \u0622\u0632\u0645\u0627\u06cc\u0634<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u067e\u0633 \u0627\u0632 \u0647\u0631 \u062a\u0633\u062a\u060c \u0628\u0627\u06cc\u062f \u0627\u062a\u0635\u0627\u0644 Jedis \u0631\u0627 \u0628\u0628\u0646\u062f\u06cc\u0645 \u062a\u0627 \u0645\u0646\u0627\u0628\u0639 \u0622\u0632\u0627\u062f \u0634\u0648\u062f. \u0627\u06cc\u0646 \u062a\u0636\u0645\u06cc\u0646 \u0645\u06cc \u06a9\u0646\u062f \u06a9\u0647 \u0647\u06cc\u0686 \u0627\u062a\u0635\u0627\u0644 \u0637\u0648\u0644\u0627\u0646\u06cc \u0645\u062f\u062a \u062f\u0631 \u0622\u0632\u0645\u0627\u06cc\u0634 \u0647\u0627\u06cc \u0628\u0639\u062f\u06cc \u062a\u062f\u0627\u062e\u0644 \u0646\u062f\u0627\u0634\u062a\u0647 \u0628\u0627\u0634\u062f.<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>@AfterEach\nvoid tearDown() {\n    jedis.close();\n}\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<h3><span class=\"ez-toc-section\" id=\"%D8%B1%D8%A7%D9%87_%D8%A7%D9%86%D8%AF%D8%A7%D8%B2%DB%8C_%DA%A9%D8%A7%D9%85%D9%84\"><\/span>\n<p>  \u0631\u0627\u0647 \u0627\u0646\u062f\u0627\u0632\u06cc \u06a9\u0627\u0645\u0644<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u062f\u0631 \u0627\u06cc\u0646\u062c\u0627 \u0646\u062d\u0648\u0647 \u0638\u0627\u0647\u0631 \u06a9\u0644\u0627\u0633 \u062a\u0633\u062a \u06a9\u0627\u0645\u0644 \u0628\u0627 \u0647\u0645\u0647 \u0686\u06cc\u0632 \u062f\u0631 \u0645\u062d\u0644 \u0627\u0633\u062a:<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>public class TokenBucketRateLimiterTest {\n\n    private static RedisContainer redisContainer;\n    private Jedis jedis;\n    private TokenBucketRateLimiter rateLimiter;\n\n    @BeforeAll\n    static void startContainer() {\n        redisContainer = new RedisContainer(\"redis:latest\");\n        redisContainer.withExposedPorts(6379).start();\n    }\n\n    @AfterAll\n    static void stopContainer() {\n        redisContainer.stop();\n    }\n\n    @BeforeEach\n    void setup() {\n        jedis = new Jedis(redisContainer.getHost(), redisContainer.getFirstMappedPort());\n        jedis.flushAll();\n    }\n\n    @AfterEach\n    void tearDown() {\n        jedis.close();\n    }\n}\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<h3><span class=\"ez-toc-section\" id=\"%D8%A8%D8%B1%D8%B1%D8%B3%DB%8C_%D8%AF%D8%B1%D8%AE%D9%88%D8%A7%D8%B3%D8%AA%E2%80%8C%D9%87%D8%A7_%D8%AF%D8%B1_%D8%B8%D8%B1%D9%81%DB%8C%D8%AA_%D8%B3%D8%B7%D9%84\"><\/span>\n<p>  \u0628\u0631\u0631\u0633\u06cc \u062f\u0631\u062e\u0648\u0627\u0633\u062a\u200c\u0647\u0627 \u062f\u0631 \u0638\u0631\u0641\u06cc\u062a \u0633\u0637\u0644<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0627\u06cc\u0646 \u062a\u0633\u062a \u062a\u0636\u0645\u06cc\u0646 \u0645\u06cc\u200c\u06a9\u0646\u062f \u06a9\u0647 \u0645\u062d\u062f\u0648\u062f\u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u062f\u0631\u062e\u0648\u0627\u0633\u062a\u200c\u0647\u0627 \u0631\u0627 \u062f\u0631 \u0638\u0631\u0641\u06cc\u062a \u0633\u0637\u0644 \u062a\u0639\u0631\u06cc\u0641\u200c\u0634\u062f\u0647 \u0627\u062c\u0627\u0632\u0647 \u0645\u06cc\u200c\u062f\u0647\u062f.<\/p>\n<p>\u0645\u0627 \u0622\u0646 \u0631\u0627 \u0628\u0627 a \u067e\u06cc\u06a9\u0631\u0628\u0646\u062f\u06cc \u0645\u06cc \u06a9\u0646\u06cc\u0645 <strong>\u0638\u0631\u0641\u06cc\u062a \u0627\u0632<\/strong> <strong>5 \u062a\u0648\u06a9\u0646<\/strong> \u0648 \u0627\u0644\u0641 <strong>\u0646\u0631\u062e \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f \u06cc\u06a9 \u062a\u0648\u06a9\u0646 \u062f\u0631 \u062b\u0627\u0646\u06cc\u0647<\/strong>\u060c \u0633\u067e\u0633 \u0628\u0627 isAllowed (&#8220;\u0645\u0634\u062a\u0631\u06cc-1&#8221;) \u062a\u0645\u0627\u0633 \u0628\u06af\u06cc\u0631\u06cc\u062f <strong>5 \u0628\u0627\u0631<\/strong>.<\/p>\n<p>\u0647\u0631 \u062a\u0645\u0627\u0633 \u0628\u0627\u06cc\u062f \u062f\u0631\u0633\u062a \u0628\u0627\u0634\u062f \u0648 \u062a\u0623\u06cc\u06cc\u062f \u06a9\u0646\u062f \u06a9\u0647 \u0645\u062d\u062f\u0648\u062f\u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0628\u0647 \u062f\u0631\u0633\u062a\u06cc \u062f\u0631\u062e\u0648\u0627\u0633\u062a\u200c\u0647\u0627 \u0631\u0627 \u062f\u0631 \u0638\u0631\u0641\u06cc\u062a \u0631\u062f\u06cc\u0627\u0628\u06cc \u06a9\u0631\u062f\u0647 \u0648 \u0627\u062c\u0627\u0632\u0647 \u0645\u06cc\u200c\u062f\u0647\u062f.<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>@Test\nvoid shouldAllowRequestsWithinBucketCapacity() {\n    rateLimiter = new TokenBucketRateLimiter(jedis, 5, 1.0);\n    for (int i = 1; i &lt;= 5; i++) {\n        assertThat(rateLimiter.isAllowed(\"client-1\"))\n            .withFailMessage(\"Request %d should be allowed within bucket capacity\", i)\n            .isTrue();\n    }\n}\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<h3><span class=\"ez-toc-section\" id=\"%D8%AA%D8%A3%DB%8C%DB%8C%D8%AF_%D8%AF%D8%B1%D8%AE%D9%88%D8%A7%D8%B3%D8%AA_%D9%87%D8%A7_%D9%88%D9%82%D8%AA%DB%8C_%D8%B3%D8%B7%D9%84_%D8%AE%D8%A7%D9%84%DB%8C_%D8%A7%D8%B3%D8%AA_%D8%B1%D8%AF_%D9%85%DB%8C_%D8%B4%D9%88%D8%AF\"><\/span>\n<p>  \u062a\u0623\u06cc\u06cc\u062f \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0647\u0627 \u0648\u0642\u062a\u06cc \u0633\u0637\u0644 \u062e\u0627\u0644\u06cc \u0627\u0633\u062a \u0631\u062f \u0645\u06cc \u0634\u0648\u062f<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0627\u06cc\u0646 \u062a\u0633\u062a \u062a\u0636\u0645\u06cc\u0646 \u0645\u06cc\u200c\u06a9\u0646\u062f \u06a9\u0647 \u0645\u062d\u062f\u0648\u062f\u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u062f\u0631\u062e\u0648\u0627\u0633\u062a\u200c\u0647\u0627 \u0631\u0627 \u067e\u0633 \u0627\u0632 \u062e\u0627\u0644\u06cc \u0634\u062f\u0646 \u0633\u0637\u0644 \u0628\u0647 \u062f\u0631\u0633\u062a\u06cc \u0631\u062f \u0645\u06cc\u200c\u06a9\u0646\u062f.<\/p>\n<p>\u067e\u06cc\u06a9\u0631\u0628\u0646\u062f\u06cc \u0634\u062f\u0647 \u0628\u0627 a <strong>\u0638\u0631\u0641\u06cc\u062a \u0627\u0632<\/strong> <strong>5 \u062a\u0648\u06a9\u0646<\/strong> \u0648 \u0627\u0644\u0641 <strong>\u0646\u0631\u062e \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f \u06cc\u06a9 \u062a\u0648\u06a9\u0646 \u062f\u0631 \u062b\u0627\u0646\u06cc\u0647<\/strong>\u060c \u0645\u0627 \u0645\u062c\u0627\u0632 \u0647\u0633\u062a\u06cc\u0645 (&#8220;\u0645\u0634\u062a\u0631\u06cc-1&#8221;) <strong>5 \u0628\u0627\u0631<\/strong> \u0648 \u0627\u0646\u062a\u0638\u0627\u0631 \u062f\u0627\u0631\u06cc\u0645 \u0647\u0645\u0647 \u0628\u0647 \u0648\u0627\u0642\u0639\u06cc\u062a \u0628\u0631\u06af\u0631\u062f\u0646\u062f.<\/p>\n<p>\u062f\u0631 \u062a\u0645\u0627\u0633 \u0634\u0634\u0645\u060c \u0628\u0627\u06cc\u062f false \u0631\u0627 \u0628\u0631\u06af\u0631\u062f\u0627\u0646\u062f\u060c \u0628\u0627 \u062a\u0623\u06cc\u06cc\u062f \u0627\u06cc\u0646\u06a9\u0647 \u0645\u062d\u062f\u0648\u062f\u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u062f\u0631\u062e\u0648\u0627\u0633\u062a\u200c\u0647\u0627 \u0631\u0627 \u067e\u0633 \u0627\u0632 \u062e\u0627\u0644\u06cc \u0634\u062f\u0646 \u0633\u0637\u0644 \u0645\u0633\u062f\u0648\u062f \u0645\u06cc\u200c\u06a9\u0646\u062f.<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>@Test\nvoid shouldDenyRequestsOnceBucketIsEmpty() {\n    rateLimiter = new TokenBucketRateLimiter(jedis, 5, 1.0);\n    for (int i = 1; i &lt;= 5; i++) {\n        assertThat(rateLimiter.isAllowed(\"client-1\"))\n            .withFailMessage(\"Request %d should be allowed within bucket capacity\", i)\n            .isTrue();\n    }\n    assertThat(rateLimiter.isAllowed(\"client-1\"))\n        .withFailMessage(\"Request beyond bucket capacity should be denied\")\n        .isFalse();\n}\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<h3><span class=\"ez-toc-section\" id=\"%D8%B3%D8%B7%D9%84_%D8%AA%D8%A3%DB%8C%DB%8C%D8%AF_%D8%A8%D9%87_%D8%AA%D8%AF%D8%B1%DB%8C%D8%AC_%D8%AF%D9%88%D8%A8%D8%A7%D8%B1%D9%87_%D9%BE%D8%B1_%D9%85%DB%8C_%D8%B4%D9%88%D8%AF\"><\/span>\n<p>  \u0633\u0637\u0644 \u062a\u0623\u06cc\u06cc\u062f \u0628\u0647 \u062a\u062f\u0631\u06cc\u062c \u062f\u0648\u0628\u0627\u0631\u0647 \u067e\u0631 \u0645\u06cc \u0634\u0648\u062f<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0627\u06cc\u0646 \u062a\u0633\u062a \u062a\u0636\u0645\u06cc\u0646 \u0645\u06cc \u06a9\u0646\u062f \u06a9\u0647 \u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0633\u0631\u0639\u062a \u067e\u0633 \u0627\u0632 \u0647\u0631 \u062b\u0627\u0646\u06cc\u0647 \u0633\u0637\u0644 \u0631\u0627 \u0628\u0647 \u062f\u0631\u0633\u062a\u06cc \u067e\u0631 \u0645\u06cc \u06a9\u0646\u062f.<\/p>\n<p>\u067e\u06cc\u06a9\u0631\u0628\u0646\u062f\u06cc \u0634\u062f\u0647 \u0628\u0627 a <strong>\u0638\u0631\u0641\u06cc\u062a \u0627\u0632<\/strong> <strong>5 \u062a\u0648\u06a9\u0646<\/strong> \u0648 \u0627\u0644\u0641 <strong>\u0646\u0631\u062e \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f \u06cc\u06a9 \u062a\u0648\u06a9\u0646 \u062f\u0631 \u062b\u0627\u0646\u06cc\u0647<\/strong>\u060c 5 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0627\u0648\u0644 (isAllowed (&#8220;\u0645\u0634\u062a\u0631\u06cc-1&#8221;)) \u062f\u0631\u0633\u062a \u0627\u0633\u062a\u060c \u062f\u0631 \u062d\u0627\u0644\u06cc \u06a9\u0647 \u062f\u0631\u062e\u0648\u0627\u0633\u062a 6 \u0631\u062f \u0645\u06cc \u0634\u0648\u062f (\u0646\u0627\u062f\u0631\u0633\u062a).<\/p>\n<p>\u067e\u0633 \u0627\u0632 \u062f\u0648 \u062b\u0627\u0646\u06cc\u0647 \u0627\u0646\u062a\u0638\u0627\u0631\u060c \u062f\u0648 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0628\u0639\u062f\u06cc \u0645\u062c\u0627\u0632 \u0648 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0633\u0648\u0645 \u0631\u062f \u0645\u06cc \u0634\u0648\u062f. \u062a\u0623\u06cc\u06cc\u062f \u0631\u0641\u062a\u0627\u0631 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f \u0647\u0645\u0627\u0646\u0637\u0648\u0631 \u06a9\u0647 \u0627\u0646\u062a\u0638\u0627\u0631 \u0645\u06cc \u0631\u0648\u062f \u06a9\u0627\u0631 \u0645\u06cc \u06a9\u0646\u062f.<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>    @Test\n    void shouldRefillTokensGraduallyAndAllowRequestsOverTime() throws InterruptedException {\n        rateLimiter = new TokenBucketRateLimiter(jedis, 5, 1.0);\n        String clientId = \"client-1\";\n\n        for (int i = 1; i &lt;= 5; i++) {\n            assertThat(rateLimiter.isAllowed(clientId))\n                .withFailMessage(\"Request %d should be allowed within bucket capacity\", i)\n                .isTrue();\n        }\n        assertThat(rateLimiter.isAllowed(clientId))\n            .withFailMessage(\"Request beyond bucket capacity should be denied\")\n            .isFalse();\n\n        TimeUnit.SECONDS.sleep(2);\n\n        assertThat(rateLimiter.isAllowed(clientId))\n            .withFailMessage(\"Request after partial refill should be allowed\")\n            .isTrue();\n        assertThat(rateLimiter.isAllowed(clientId))\n            .withFailMessage(\"Second request after partial refill should be allowed\")\n            .isTrue();\n        assertThat(rateLimiter.isAllowed(clientId))\n            .withFailMessage(\"Request beyond available tokens should be denied\")\n            .isFalse();\n    }\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<h3><span class=\"ez-toc-section\" id=\"%D8%AA%D8%A3%DB%8C%DB%8C%D8%AF_%D9%85%D8%AF%DB%8C%D8%B1%DB%8C%D8%AA_%D9%85%D8%B3%D8%AA%D9%82%D9%84_%DA%86%D9%86%D8%AF%DB%8C%D9%86_%D9%85%D8%B4%D8%AA%D8%B1%DB%8C\"><\/span>\n<p>  \u062a\u0623\u06cc\u06cc\u062f \u0645\u062f\u06cc\u0631\u06cc\u062a \u0645\u0633\u062a\u0642\u0644 \u0686\u0646\u062f\u06cc\u0646 \u0645\u0634\u062a\u0631\u06cc<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0627\u06cc\u0646 \u062a\u0633\u062a \u062a\u0636\u0645\u06cc\u0646 \u0645\u06cc \u06a9\u0646\u062f \u06a9\u0647 \u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0686\u0646\u062f\u06cc\u0646 \u0645\u0634\u062a\u0631\u06cc \u0631\u0627 \u0628\u0647 \u0637\u0648\u0631 \u0645\u0633\u062a\u0642\u0644 \u0645\u062f\u06cc\u0631\u06cc\u062a \u0645\u06cc \u06a9\u0646\u062f.<\/p>\n<p>\u067e\u06cc\u06a9\u0631\u0628\u0646\u062f\u06cc \u0634\u062f\u0647 \u0628\u0627 a <strong>\u0638\u0631\u0641\u06cc\u062a \u0627\u0632<\/strong> <strong>5 \u062a\u0648\u06a9\u0646<\/strong> \u0648 \u0627\u0644\u0641 <strong>\u0646\u0631\u062e \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f \u06cc\u06a9 \u062a\u0648\u06a9\u0646 \u062f\u0631 \u062b\u0627\u0646\u06cc\u0647<\/strong>\u060c 5 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0627\u0648\u0644 (isAllowed (&#8220;\u0645\u0634\u062a\u0631\u06cc-1&#8221;)) \u062f\u0631\u0633\u062a \u0627\u0633\u062a\u060c \u062f\u0631 \u062d\u0627\u0644\u06cc \u06a9\u0647 \u062f\u0631\u062e\u0648\u0627\u0633\u062a 6 \u0631\u062f \u0645\u06cc \u0634\u0648\u062f (\u0646\u0627\u062f\u0631\u0633\u062a).<\/p>\n<p>\u0628\u0647 \u0637\u0648\u0631 \u0647\u0645\u0632\u0645\u0627\u0646\u060c \u0647\u0631 5 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0627\u0632 <strong>\u0645\u0634\u062a\u0631\u06cc-2<\/strong> \u0645\u062c\u0627\u0632 \u0647\u0633\u062a\u0646\u062f (\u062f\u0631\u0633\u062a)\u060c \u062a\u0623\u06cc\u06cc\u062f \u0645\u06cc \u06a9\u0646\u062f \u06a9\u0647 \u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0634\u0645\u0627\u0631\u0646\u062f\u0647 \u0647\u0627\u06cc \u062c\u062f\u0627\u06af\u0627\u0646\u0647 \u0627\u06cc \u0631\u0627 \u0628\u0631\u0627\u06cc \u0647\u0631 \u0645\u0634\u062a\u0631\u06cc \u0646\u06af\u0647 \u0645\u06cc \u062f\u0627\u0631\u062f.<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>@Test\nvoid shouldHandleMultipleClientsIndependently() {\n    rateLimiter = new TokenBucketRateLimiter(jedis, 5, 1.0);\n\n    String clientId1 = \"client-1\";\n    String clientId2 = \"client-2\";\n\n    for (int i = 1; i &lt;= 5; i++) {\n        assertThat(rateLimiter.isAllowed(clientId1))\n            .withFailMessage(\"Client 1 request %d should be allowed\", i)\n            .isTrue();\n    }\n    assertThat(rateLimiter.isAllowed(clientId1))\n        .withFailMessage(\"Client 1 request beyond bucket capacity should be denied\")\n        .isFalse();\n\n    for (int i = 1; i &lt;= 5; i++) {\n        assertThat(rateLimiter.isAllowed(clientId2))\n            .withFailMessage(\"Client 2 request %d should be allowed\", i)\n            .isTrue();\n    }\n}\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<h3><span class=\"ez-toc-section\" id=\"%D8%AA%D8%A3%DB%8C%DB%8C%D8%AF_%D8%AF%D9%88%D8%A8%D8%A7%D8%B1%D9%87_%D9%BE%D8%B1_%DA%A9%D8%B1%D8%AF%D9%86_%D8%AA%D9%88%DA%A9%D9%86_%D8%A7%D8%B2_%D8%B8%D8%B1%D9%81%DB%8C%D8%AA_%D8%B3%D8%B7%D9%84_%D8%AA%D8%AC%D8%A7%D9%88%D8%B2_%D9%86%D9%85%DB%8C_%DA%A9%D9%86%D8%AF\"><\/span>\n<p>  \u062a\u0623\u06cc\u06cc\u062f \u062f\u0648\u0628\u0627\u0631\u0647 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u062a\u0648\u06a9\u0646 \u0627\u0632 \u0638\u0631\u0641\u06cc\u062a \u0633\u0637\u0644 \u062a\u062c\u0627\u0648\u0632 \u0646\u0645\u06cc \u06a9\u0646\u062f<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0627\u06cc\u0646 \u062a\u0633\u062a \u062a\u0623\u06cc\u06cc\u062f \u0645\u06cc\u200c\u06a9\u0646\u062f \u06a9\u0647 \u0645\u062d\u062f\u0648\u062f\u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0633\u0637\u0644 \u062a\u0648\u06a9\u0646 \u0628\u0647 \u062f\u0631\u0633\u062a\u06cc \u062a\u0648\u06a9\u0646\u200c\u0647\u0627 \u0631\u0627 \u062a\u0627 \u0638\u0631\u0641\u06cc\u062a \u062a\u0639\u0631\u06cc\u0641\u200c\u0634\u062f\u0647 \u0628\u062f\u0648\u0646 \u062a\u062c\u0627\u0648\u0632 \u0627\u0632 \u0622\u0646 \u067e\u0631 \u0645\u06cc\u200c\u06a9\u0646\u062f.<\/p>\n<p>\u067e\u06cc\u06a9\u0631\u0628\u0646\u062f\u06cc \u0634\u062f\u0647 \u0628\u0627 a <strong>\u0638\u0631\u0641\u06cc\u062a 3 \u062a\u0648\u06a9\u0646<\/strong> \u0648 \u0627\u0644\u0641 <strong>\u0646\u0631\u062e \u0634\u0627\u0631\u0698 \u0645\u062c\u062f\u062f 2 \u062a\u0648\u06a9\u0646 \u062f\u0631 \u062b\u0627\u0646\u06cc\u0647<\/strong>\u060c 3 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0627\u0648\u0644 (isAllowed (&#8220;\u0645\u0634\u062a\u0631\u06cc-1&#8221;)) \u062f\u0631\u0633\u062a \u0627\u0633\u062a\u060c \u062f\u0631 \u062d\u0627\u0644\u06cc \u06a9\u0647 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0686\u0647\u0627\u0631\u0645 \u0631\u062f \u0645\u06cc \u0634\u0648\u062f (\u0646\u0627\u062f\u0631\u0633\u062a) \u06a9\u0647 \u0646\u0634\u0627\u0646 \u0645\u06cc \u062f\u0647\u062f \u0633\u0637\u0644 \u062e\u0627\u0644\u06cc \u0627\u0633\u062a.<\/p>\n<p>\u067e\u0633 \u0627\u0632 3 \u062b\u0627\u0646\u06cc\u0647 \u0627\u0646\u062a\u0638\u0627\u0631 (\u0628\u0631\u0627\u06cc \u067e\u0631 \u06a9\u0631\u062f\u0646 6 \u0698\u062a\u0648\u0646 \u06a9\u0627\u0641\u06cc \u0627\u0633\u062a)\u060c \u0633\u0637\u0644 \u0641\u0642\u0637 \u062a\u0627 \u062d\u062f\u0627\u06a9\u062b\u0631 \u0638\u0631\u0641\u06cc\u062a 3 \u0698\u062a\u0648\u0646 \u067e\u0631 \u0645\u06cc \u0634\u0648\u062f. 3 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0628\u0639\u062f\u06cc \u0645\u062c\u0627\u0632 \u0627\u0633\u062a (\u062f\u0631\u0633\u062a \u0627\u0633\u062a)\u060c \u0627\u0645\u0627 \u0647\u0631 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0627\u0636\u0627\u0641\u06cc \u0631\u062f \u0645\u06cc \u0634\u0648\u062f (\u0646\u0627\u062f\u0631\u0633\u062a)\u060c \u062a\u0623\u06cc\u06cc\u062f \u0645\u06cc \u06a9\u0646\u062f \u06a9\u0647 \u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e\u060c \u0645\u062d\u062f\u0648\u062f\u06cc\u062a \u0638\u0631\u0641\u06cc\u062a \u0645\u0634\u062e\u0635 \u0634\u062f\u0647 \u0631\u0627 \u0628\u062f\u0648\u0646 \u062a\u0648\u062c\u0647 \u0628\u0647 \u0645\u0627\u0632\u0627\u062f \u067e\u0631 \u06a9\u0631\u062f\u0646 \u0645\u062c\u062f\u062f \u062d\u0641\u0638 \u0645\u06cc \u06a9\u0646\u062f.<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>@Test\nvoid shouldRefillTokensUpToCapacityWithoutExceedingIt() throws InterruptedException {\n    int capacity = 3;\n    double refillRate = 2.0;\n    String clientId = \"client-1\";\n    rateLimiter = new TokenBucketRateLimiter(jedis, capacity, refillRate);\n\n    for (int i = 1; i &lt;= capacity; i++) {\n        assertThat(rateLimiter.isAllowed(clientId))\n            .withFailMessage(\"Request %d should be allowed within initial bucket capacity\", i)\n            .isTrue();\n    }\n    assertThat(rateLimiter.isAllowed(clientId))\n        .withFailMessage(\"Request beyond bucket capacity should be denied\")\n        .isFalse();\n\n    TimeUnit.SECONDS.sleep(3);\n\n    for (int i = 1; i &lt;= capacity; i++) {\n        assertThat(rateLimiter.isAllowed(clientId))\n            .withFailMessage(\"Request %d should be allowed as bucket refills up to capacity\", i)\n            .isTrue();\n    }\n    assertThat(rateLimiter.isAllowed(clientId))\n        .withFailMessage(\"Request beyond bucket capacity should be denied\")\n        .isFalse();\n}\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<h3><span class=\"ez-toc-section\" id=\"%D8%AA%D8%A3%DB%8C%DB%8C%D8%AF_%D8%AF%D8%B1%D8%AE%D9%88%D8%A7%D8%B3%D8%AA_%D9%87%D8%A7%DB%8C_%D8%B1%D8%AF_%D8%B4%D8%AF%D9%87_%D8%A8%D8%B1_%D8%AA%D8%B9%D8%AF%D8%A7%D8%AF_%D8%AA%D9%88%DA%A9%D9%86_%D9%87%D8%A7_%D8%AA%D8%A3%D8%AB%DB%8C%D8%B1_%D9%86%D9%85%DB%8C_%DA%AF%D8%B0%D8%A7%D8%B1%D8%AF\"><\/span>\n<p>  \u062a\u0623\u06cc\u06cc\u062f \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0647\u0627\u06cc \u0631\u062f \u0634\u062f\u0647 \u0628\u0631 \u062a\u0639\u062f\u0627\u062f \u062a\u0648\u06a9\u0646 \u0647\u0627 \u062a\u0623\u062b\u06cc\u0631 \u0646\u0645\u06cc \u06af\u0630\u0627\u0631\u062f<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0627\u06cc\u0646 \u062a\u0633\u062a \u062a\u0636\u0645\u06cc\u0646 \u0645\u06cc\u200c\u06a9\u0646\u062f \u06a9\u0647 \u0645\u062d\u062f\u0648\u062f\u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0633\u0637\u0644 \u062a\u0648\u06a9\u0646 \u062f\u0631\u062e\u0648\u0627\u0633\u062a\u200c\u0647\u0627\u06cc \u0631\u062f \u0634\u062f\u0647 \u0631\u0627 \u0647\u0646\u06af\u0627\u0645 \u0628\u0647\u200c\u0631\u0648\u0632\u0631\u0633\u0627\u0646\u06cc \u062a\u0639\u062f\u0627\u062f \u062a\u0648\u06a9\u0646\u200c\u0647\u0627 \u0645\u062d\u0627\u0633\u0628\u0647 \u0646\u0645\u06cc\u200c\u06a9\u0646\u062f.<\/p>\n<p>\u067e\u06cc\u06a9\u0631\u0628\u0646\u062f\u06cc \u0634\u062f\u0647 \u0628\u0627 a <strong>\u0638\u0631\u0641\u06cc\u062a 3 \u062a\u0648\u06a9\u0646<\/strong> \u0648 \u0627\u0644\u0641 <strong>\u0646\u0631\u062e \u0634\u0627\u0631\u0698 \u0645\u062c\u062f\u062f 0.5 \u062a\u0648\u06a9\u0646 \u062f\u0631 \u062b\u0627\u0646\u06cc\u0647<\/strong>\u060c 3 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0627\u0648\u0644 (isAllowed (&#8220;\u0645\u0634\u062a\u0631\u06cc-1&#8221;)) \u0645\u062c\u0627\u0632 \u0647\u0633\u062a\u0646\u062f (\u062f\u0631\u0633\u062a \u0627\u0633\u062a) \u06a9\u0647 \u0633\u0637\u0644 \u0631\u0627 \u062e\u0627\u0644\u06cc \u0645\u06cc \u06a9\u0646\u062f. \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0686\u0647\u0627\u0631\u0645 \u0631\u062f \u0645\u06cc \u0634\u0648\u062f (\u0646\u0627\u062f\u0631\u0633\u062a)\u060c \u0628\u0627 \u062a\u0627\u06cc\u06cc\u062f \u062e\u0627\u0644\u06cc \u0628\u0648\u062f\u0646 \u0633\u0637\u0644.<\/p>\n<p>\u0633\u067e\u0633 \u062a\u0639\u062f\u0627\u062f \u062a\u0648\u06a9\u0646\u200c\u0647\u0627\u06cc Redis (rate_limit:client-1:count) \u062a\u0623\u06cc\u06cc\u062f \u0645\u06cc\u200c\u0634\u0648\u062f \u062a\u0627 \u0627\u0637\u0645\u06cc\u0646\u0627\u0646 \u062d\u0627\u0635\u0644 \u0634\u0648\u062f \u06a9\u0647 \u0646\u0634\u0627\u0646\u0647\u200c\u0647\u0627\u06cc \u0628\u0627\u0642\u06cc\u200c\u0645\u0627\u0646\u062f\u0647 \u0631\u0627 \u0628\u0647 \u0637\u0648\u0631 \u062f\u0642\u06cc\u0642 \u0645\u0646\u0639\u06a9\u0633 \u0645\u06cc\u200c\u06a9\u0646\u062f (0 \u062f\u0631 \u0627\u06cc\u0646 \u0645\u0648\u0631\u062f) \u0648 \u0634\u0627\u0645\u0644 \u062f\u0631\u062e\u0648\u0627\u0633\u062a\u200c\u0647\u0627\u06cc \u0631\u062f \u0634\u062f\u0647 \u0646\u0645\u06cc\u200c\u0634\u0648\u062f. \u0627\u06cc\u0646 \u062a\u0623\u06cc\u06cc\u062f \u0645\u06cc \u06a9\u0646\u062f \u06a9\u0647 \u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u062a\u0646\u0647\u0627 \u0632\u0645\u0627\u0646\u06cc \u062a\u0639\u062f\u0627\u062f \u062a\u0648\u06a9\u0646 \u0647\u0627 \u0631\u0627 \u0628\u0647 \u0631\u0648\u0632 \u0645\u06cc \u06a9\u0646\u062f \u06a9\u0647 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0647\u0627 \u0628\u0627 \u0645\u0648\u0641\u0642\u06cc\u062a \u067e\u0631\u062f\u0627\u0632\u0634 \u0634\u0648\u0646\u062f.<\/p>\n<div class=\"highlight js-code-highlight\">\n<pre class=\"highlight plaintext\"><code>@Test\nvoid testRateLimitDeniedRequestsAreNotCounted() {\n    int capacity = 3;\n    double refillRate = 0.5;\n    String clientId = \"client-1\";\n    rateLimiter = new TokenBucketRateLimiter(jedis, capacity, refillRate);\n\n    for (int i = 1; i &lt;= capacity; i++) {\n        assertThat(rateLimiter.isAllowed(clientId))\n            .withFailMessage(\"Request %d should be allowed\", i)\n            .isTrue();\n    }\n    assertThat(rateLimiter.isAllowed(clientId))\n        .withFailMessage(\"This request should be denied\")\n        .isFalse();\n\n    String key = \"rate_limit:\" + clientId + \":count\";\n    int requestCount = Integer.parseInt(jedis.get(key));\n    assertThat(requestCount)\n        .withFailMessage(\"The count should match remaining tokens and not include denied requests\")\n        .isEqualTo(0);\n}\n<\/code><\/pre>\n<div class=\"highlight__panel js-actions-panel\">\n<div class=\"highlight__panel-action js-fullscreen-code-action\">\n    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-on\"><title>\u0648\u0627\u0631\u062f \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M16 3h6v6h-2V5h-4V3zM2 3h6v2H4v4H2V3zm18 16v-4h2v6h-6v-2h4zM4 19h4v2H2v-6h2v4z\"\/>\n<\/svg><\/p>\n<p>    <svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"20px\" height=\"20px\" viewbox=\"0 0 24 24\" class=\"highlight-action crayons-icon highlight-action--fullscreen-off\"><title>\u0627\u0632 \u062d\u0627\u0644\u062a \u062a\u0645\u0627\u0645 \u0635\u0641\u062d\u0647 \u062e\u0627\u0631\u062c \u0634\u0648\u06cc\u062f<\/title>\n    <path d=\"M18 7h4v2h-6V3h2v4zM8 9H2V7h4V3h2v6zm10 8v4h-2v-6h6v2h-4zM8 15v6H6v-4H2v-2h6z\"\/>\n<\/svg><\/p>\n<\/div>\n<\/div>\n<\/div>\n<p>\u0622\u06cc\u0627 \u0631\u0641\u062a\u0627\u0631 \u062f\u06cc\u06af\u0631\u06cc \u0648\u062c\u0648\u062f \u062f\u0627\u0631\u062f \u06a9\u0647 \u0628\u0627\u06cc\u062f \u0628\u0631\u0631\u0633\u06cc \u06a9\u0646\u06cc\u0645\u061f \u062f\u0631 \u0646\u0638\u0631\u0627\u062a \u0628\u0647 \u0645\u0646 \u0627\u0637\u0644\u0627\u0639 \u062f\u0647\u06cc\u062f!<\/p>\n<p>Token Bucket Rate Limiter \u06cc\u06a9 \u0631\u0648\u0634 \u0645\u0646\u0639\u0637\u0641 \u0648 \u06a9\u0627\u0631\u0622\u0645\u062f \u0628\u0631\u0627\u06cc \u0645\u062f\u06cc\u0631\u06cc\u062a \u0646\u0631\u062e \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0627\u0633\u062a <strong>\u0631\u062f\u06cc\u0633<\/strong> \u0622\u0646 \u0631\u0627 \u0641\u0648\u0642 \u0627\u0644\u0639\u0627\u062f\u0647 \u0633\u0631\u06cc\u0639 \u0648 \u0642\u0627\u0628\u0644 \u0627\u0639\u062a\u0645\u0627\u062f \u0645\u06cc \u06a9\u0646\u062f.<\/p>\n<p>\u0628\u0627 \u0627\u0633\u062a\u0641\u0627\u062f\u0647 \u0627\u0632 \u062f\u0633\u062a\u0648\u0631\u0627\u062a\u06cc \u0645\u0627\u0646\u0646\u062f GET\u060c SET \u0648 MULTI\/EXEC\u060c \u0631\u0627\u0647 \u062d\u0644\u06cc \u0631\u0627 \u067e\u06cc\u0627\u062f\u0647 \u0633\u0627\u0632\u06cc \u06a9\u0631\u062f\u06cc\u0645 \u06a9\u0647 \u062a\u0639\u062f\u0627\u062f \u062a\u0648\u06a9\u0646 \u0647\u0627 \u0631\u0627 \u0631\u062f\u06cc\u0627\u0628\u06cc \u0645\u06cc \u06a9\u0646\u062f\u060c \u062a\u0648\u06a9\u0646 \u0647\u0627 \u0631\u0627 \u0628\u0647 \u0635\u0648\u0631\u062a \u067e\u0648\u06cc\u0627 \u0628\u0631 \u0627\u0633\u0627\u0633 \u0632\u0645\u0627\u0646 \u0633\u067e\u0631\u06cc \u0634\u062f\u0647 \u067e\u0631 \u0645\u06cc \u06a9\u0646\u062f \u0648 \u062a\u0636\u0645\u06cc\u0646 \u0645\u06cc \u06a9\u0646\u062f \u06a9\u0647 \u0633\u0637\u0644 \u0647\u0631\u06af\u0632 \u0627\u0632 \u0638\u0631\u0641\u06cc\u062a \u062a\u0639\u0631\u06cc\u0641 \u0634\u062f\u0647 \u062e\u0648\u062f \u062a\u062c\u0627\u0648\u0632 \u0646\u0645\u06cc \u06a9\u0646\u062f.<\/p>\n<p>\u0628\u0627 \u0627\u0633\u062a\u0641\u0627\u062f\u0647 \u0627\u0632 <strong>\u062c\u062f\u06cc<\/strong>\u060c \u0645\u0627 \u06cc\u06a9 \u0631\u0648\u0634\u0646 \u0648 \u0634\u0647\u0648\u062f\u06cc \u0633\u0627\u062e\u062a\u0647 \u0627\u06cc\u0645 <strong>\u062c\u0627\u0648\u0627<\/strong> \u067e\u06cc\u0627\u062f\u0647 \u0633\u0627\u0632\u06cc\u060c \u0648 \u0628\u0627 \u0622\u0632\u0645\u0627\u06cc\u0634 \u06a9\u0627\u0645\u0644 \u0628\u0627 \u0627\u0633\u062a\u0641\u0627\u062f\u0647 \u0627\u0632 Redis TestContainers\u060c JUnit 5 \u0648 AssertJ\u060c \u0645\u06cc \u062a\u0648\u0627\u0646\u06cc\u0645 \u0628\u0627 \u0627\u0637\u0645\u06cc\u0646\u0627\u0646 \u0628\u0631\u0631\u0633\u06cc \u06a9\u0646\u06cc\u0645 \u06a9\u0647 \u0645\u0637\u0627\u0628\u0642 \u0627\u0646\u062a\u0638\u0627\u0631 \u06a9\u0627\u0631 \u0645\u06cc \u06a9\u0646\u062f.<\/p>\n<p>\u0627\u06cc\u0646 \u0631\u0648\u06cc\u06a9\u0631\u062f \u067e\u0627\u06cc\u0647\u200c\u0627\u06cc \u0642\u0648\u06cc \u0628\u0631\u0627\u06cc \u0645\u062f\u06cc\u0631\u06cc\u062a \u0645\u062d\u062f\u0648\u062f\u06cc\u062a\u200c\u0647\u0627\u06cc \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0627\u0631\u0627\u0626\u0647 \u0645\u06cc\u200c\u062f\u0647\u062f \u0648 \u062f\u0631 \u0639\u06cc\u0646 \u062d\u0627\u0644 \u0627\u0645\u06a9\u0627\u0646 \u0645\u062f\u06cc\u0631\u06cc\u062a \u0627\u0646\u0641\u062c\u0627\u0631\u06cc \u0648 \u062f\u0648\u0628\u0627\u0631\u0647 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u062a\u062f\u0631\u06cc\u062c\u06cc \u0631\u0627 \u0641\u0631\u0627\u0647\u0645 \u0645\u06cc\u200c\u06a9\u0646\u062f \u0648 \u062f\u0631 \u0635\u0648\u0631\u062a \u0646\u06cc\u0627\u0632 \u0628\u0631\u0627\u06cc \u0633\u0646\u0627\u0631\u06cc\u0648\u0647\u0627\u06cc \u0645\u062d\u062f\u0648\u062f\u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u067e\u06cc\u0634\u0631\u0641\u062a\u0647\u200c\u062a\u0631 \u0633\u0627\u0632\u06af\u0627\u0631 \u0627\u0633\u062a.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"GitHub_Repo\"><\/span>\n<p>  GitHub Repo<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>\u0634\u0645\u0627 \u0645\u06cc \u062a\u0648\u0627\u0646\u06cc\u062f \u0627\u06cc\u0646 \u067e\u06cc\u0627\u062f\u0647 \u0633\u0627\u0632\u06cc \u0631\u0627 \u062f\u0631 <strong>\u062c\u0627\u0648\u0627<\/strong> \u0648 <strong>\u06a9\u0627\u062a\u0644\u06cc\u0646<\/strong>:<\/p>\n<h3><span class=\"ez-toc-section\" id=\"%DA%A9%D9%86%D8%AC%DA%A9%D8%A7%D9%88_%D8%A8%D9%85%D8%A7%D9%86\"><\/span>\n<p>  \u06a9\u0646\u062c\u06a9\u0627\u0648 \u0628\u0645\u0627\u0646!<br \/>\n<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<\/p><\/div>\n","protected":false},"excerpt":{"rendered":"<p>\u0627\u06cc\u0646 \u0645\u0642\u0627\u0644\u0647 \u062f\u0631 \u06cc\u0648\u062a\u06cc\u0648\u0628 \u0646\u06cc\u0632 \u0645\u0648\u062c\u0648\u062f \u0627\u0633\u062a! \u0631\u0627 \u0633\u0637\u0644 \u062a\u0648\u06a9\u0646 \u0627\u0644\u06af\u0648\u0631\u06cc\u062a\u0645 \u06cc\u06a9 \u0645\u06a9\u0627\u0646\u06cc\u0633\u0645 \u0645\u062d\u062f\u0648\u062f \u06a9\u0646\u0646\u062f\u0647 \u0646\u0631\u062e \u0627\u0646\u0639\u0637\u0627\u0641 \u067e\u0630\u06cc\u0631 \u0648 \u06a9\u0627\u0631\u0622\u0645\u062f \u0627\u0633\u062a. \u0627\u06cc\u0646 \u06a9\u0627\u0631 \u0628\u0627 \u067e\u0631 \u06a9\u0631\u062f\u0646 \u06cc\u06a9 \u0633\u0637\u0644 \u0628\u0627 \u0646\u0634\u0627\u0646\u0647\u200c\u0647\u0627 \u0628\u0627 \u0646\u0631\u062e \u062b\u0627\u0628\u062a (\u0645\u062b\u0644\u0627\u064b \u06cc\u06a9 \u062a\u0648\u06a9\u0646 \u062f\u0631 \u062b\u0627\u0646\u06cc\u0647) \u06a9\u0627\u0631 \u0645\u06cc\u200c\u06a9\u0646\u062f. \u0647\u0631 \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u06cc\u06a9 \u062a\u0648\u06a9\u0646 \u0645\u0635\u0631\u0641 \u0645\u06cc \u06a9\u0646\u062f \u0648 \u0627\u06af\u0631 \u062a\u0648\u06a9\u0646\u06cc \u062f\u0631 \u062f\u0633\u062a\u0631\u0633 \u0646\u0628\u0627\u0634\u062f\u060c \u062f\u0631\u062e\u0648\u0627\u0633\u062a \u0631\u062f &hellip;<\/p>\n","protected":false},"author":2,"featured_media":92816,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"fifu_image_url":"https:\/\/media2.dev.to\/dynamic\/image\/width=1000,height=500,fit=cover,gravity=auto,format=auto\/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fl878wu203dbtm3fi21yd.png","fifu_image_alt":"","footnotes":""},"categories":[339],"tags":[],"class_list":["post-92815","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-dev"],"_links":{"self":[{"href":"https:\/\/nabfollower.com\/blog\/wp-json\/wp\/v2\/posts\/92815","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/nabfollower.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/nabfollower.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/nabfollower.com\/blog\/wp-json\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/nabfollower.com\/blog\/wp-json\/wp\/v2\/comments?post=92815"}],"version-history":[{"count":0,"href":"https:\/\/nabfollower.com\/blog\/wp-json\/wp\/v2\/posts\/92815\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/nabfollower.com\/blog\/wp-json\/wp\/v2\/media\/92816"}],"wp:attachment":[{"href":"https:\/\/nabfollower.com\/blog\/wp-json\/wp\/v2\/media?parent=92815"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/nabfollower.com\/blog\/wp-json\/wp\/v2\/categories?post=92815"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/nabfollower.com\/blog\/wp-json\/wp\/v2\/tags?post=92815"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}