From ca655ba10005f232336bbb431be3bba7e3133c2d Mon Sep 17 00:00:00 2001 From: Florian Klinger Date: Tue, 12 Mar 2024 10:53:14 +0100 Subject: [PATCH] fix: add check for app_api_system session flag to bypass rate limit Signed-off-by: Florian Klinger Signed-off-by: Andrey Borysenko --- .../AppFramework/DependencyInjection/DIContainer.php | 3 ++- .../Middleware/Security/RateLimitingMiddleware.php | 7 +++++++ .../Middleware/Security/RateLimitingMiddlewareTest.php | 6 +++++- 3 files changed, 14 insertions(+), 2 deletions(-) diff --git a/lib/private/AppFramework/DependencyInjection/DIContainer.php b/lib/private/AppFramework/DependencyInjection/DIContainer.php index c342ea236e2..a0951e75523 100644 --- a/lib/private/AppFramework/DependencyInjection/DIContainer.php +++ b/lib/private/AppFramework/DependencyInjection/DIContainer.php @@ -302,7 +302,8 @@ class DIContainer extends SimpleContainer implements IAppContainer { $c->get(IRequest::class), $c->get(IUserSession::class), $c->get(IControllerMethodReflector::class), - $c->get(OC\Security\RateLimiting\Limiter::class) + $c->get(OC\Security\RateLimiting\Limiter::class), + $c->get(ISession::class) ) ); $dispatcher->registerMiddleware( diff --git a/lib/private/AppFramework/Middleware/Security/RateLimitingMiddleware.php b/lib/private/AppFramework/Middleware/Security/RateLimitingMiddleware.php index 6f84a0c94d0..ffaa0cd19cb 100644 --- a/lib/private/AppFramework/Middleware/Security/RateLimitingMiddleware.php +++ b/lib/private/AppFramework/Middleware/Security/RateLimitingMiddleware.php @@ -40,6 +40,7 @@ use OCP\AppFramework\Http\Response; use OCP\AppFramework\Http\TemplateResponse; use OCP\AppFramework\Middleware; use OCP\IRequest; +use OCP\ISession; use OCP\IUserSession; use ReflectionMethod; @@ -70,6 +71,7 @@ class RateLimitingMiddleware extends Middleware { protected IUserSession $userSession, protected ControllerMethodReflector $reflector, protected Limiter $limiter, + protected ISession $session, ) { } @@ -81,6 +83,11 @@ class RateLimitingMiddleware extends Middleware { parent::beforeController($controller, $methodName); $rateLimitIdentifier = get_class($controller) . '::' . $methodName; + if ($this->session->exists('app_api_system')) { + // Bypass rate limiting for app_api + return; + } + if ($this->userSession->isLoggedIn()) { $rateLimit = $this->readLimitFromAnnotationOrAttribute($controller, $methodName, 'UserRateThrottle', UserRateLimit::class); diff --git a/tests/lib/AppFramework/Middleware/Security/RateLimitingMiddlewareTest.php b/tests/lib/AppFramework/Middleware/Security/RateLimitingMiddlewareTest.php index 47d479b18a1..c0988ff5a11 100644 --- a/tests/lib/AppFramework/Middleware/Security/RateLimitingMiddlewareTest.php +++ b/tests/lib/AppFramework/Middleware/Security/RateLimitingMiddlewareTest.php @@ -37,6 +37,7 @@ use OCP\AppFramework\Http\Attribute\UserRateLimit; use OCP\AppFramework\Http\DataResponse; use OCP\AppFramework\Http\TemplateResponse; use OCP\IRequest; +use OCP\ISession; use OCP\IUser; use OCP\IUserSession; use PHPUnit\Framework\MockObject\MockObject; @@ -77,6 +78,7 @@ class RateLimitingMiddlewareTest extends TestCase { private IUserSession|MockObject $userSession; private ControllerMethodReflector $reflector; private Limiter|MockObject $limiter; + private ISession|MockObject $session; private RateLimitingMiddleware $rateLimitingMiddleware; protected function setUp(): void { @@ -86,12 +88,14 @@ class RateLimitingMiddlewareTest extends TestCase { $this->userSession = $this->createMock(IUserSession::class); $this->reflector = new ControllerMethodReflector(); $this->limiter = $this->createMock(Limiter::class); + $this->session = $this->createMock(ISession::class); $this->rateLimitingMiddleware = new RateLimitingMiddleware( $this->request, $this->userSession, $this->reflector, - $this->limiter + $this->limiter, + $this->session ); }