VYPR
Moderate severityNVD Advisory· Published Mar 20, 2025· Updated Nov 3, 2025

Inconsistent CORS Matching Due to Handling of '+' in URL Path in corydolphin/flask-cors

CVE-2024-6844

Description

A vulnerability in corydolphin/flask-cors version 4.0.1 allows for inconsistent CORS matching due to the handling of the '+' character in URL paths. The request.path is passed through the unquote_plus function, which converts the '+' character to a space ' '. This behavior leads to incorrect path normalization, causing potential mismatches in CORS configuration. As a result, endpoints may not be matched correctly to their CORS settings, leading to unexpected CORS policy application. This can cause unauthorized cross-origin access or block valid requests, creating security vulnerabilities and usability issues.

Affected packages

Versions sourced from the GitHub Security Advisory.

PackageAffected versionsPatched versions
flask-corsPyPI
< 6.0.06.0.0

Affected products

1

Patches

1
35d875319621

[CVE-2024-6844] Replace use of (urllib) unquote_plus with unquote for paths (#389)

https://github.com/corydolphin/flask-corsAdriano Sela AvilesMay 17, 2025via ghsa
2 files changed · +58 2
  • flask_cors/extension.py+2 2 modified
    @@ -1,5 +1,5 @@
     import logging
    -from urllib.parse import unquote_plus
    +from urllib.parse import unquote
     
     from flask import request
     
    @@ -188,7 +188,7 @@ def cors_after_request(resp):
             if resp.headers is not None and resp.headers.get(ACL_ORIGIN):
                 LOG.debug("CORS have been already evaluated, skipping")
                 return resp
    -        normalized_path = unquote_plus(request.path)
    +        normalized_path = unquote(request.path)
             for res_regex, res_options in resources:
                 if try_match_pattern(normalized_path, res_regex, caseSensitive=True):
                     LOG.debug(
    
  • tests/extension/test_app_extension.py+56 0 modified
    @@ -378,5 +378,61 @@ def index():
                 self.assertEqual(resp.status_code, 200)
     
     
    +class AppExtensionPlusInPath(FlaskCorsTestCase):
    +    '''
    +        Regression test for CVE-2024-6844:
    +        Ensures that we correctly differentiate '+' from ' ' in URL paths.
    +    '''
    +
    +    def setUp(self):
    +        self.app = Flask(__name__)
    +        CORS(self.app, resources={
    +            r'/service\+path': {'origins': ['http://foo.com']},
    +            r'/service path': {'origins': ['http://bar.com']},
    +        })
    +
    +        @self.app.route('/service+path')
    +        def plus_path():
    +            return 'plus'
    +
    +        @self.app.route('/service path')
    +        def space_path():
    +            return 'space'
    +
    +        self.client = self.app.test_client()
    +
    +    def test_plus_path_origin_allowed(self):
    +        '''
    +        Ensure that CORS matches + literally and allows the correct origin
    +        '''
    +        response = self.client.get('/service+path', headers={'Origin': 'http://foo.com'})
    +        self.assertEqual(response.status_code, 200)
    +        self.assertEqual(response.headers.get(ACL_ORIGIN), 'http://foo.com')
    +
    +    def test_space_path_origin_allowed(self):
    +        '''
    +        Ensure that CORS treats /service path differently and allows correct origin
    +        '''
    +        response = self.client.get('/service%20path', headers={'Origin': 'http://bar.com'})
    +        self.assertEqual(response.status_code, 200)
    +        self.assertEqual(response.headers.get(ACL_ORIGIN), 'http://bar.com')
    +
    +    def test_plus_path_rejects_other_origin(self):
    +        '''
    +        Origin not allowed for + path should be rejected
    +        '''
    +        response = self.client.get('/service+path', headers={'Origin': 'http://bar.com'})
    +        self.assertEqual(response.status_code, 200)
    +        self.assertIsNone(response.headers.get(ACL_ORIGIN))
    +
    +    def test_space_path_rejects_other_origin(self):
    +        '''
    +        Origin not allowed for space path should be rejected
    +        '''
    +        response = self.client.get('/service%20path', headers={'Origin': 'http://foo.com'})
    +        self.assertEqual(response.status_code, 200)
    +        self.assertIsNone(response.headers.get(ACL_ORIGIN))
    +
    +
     if __name__ == "__main__":
         unittest.main()
    

Vulnerability mechanics

Generated by null/stub on May 9, 2026. Inputs: CWE entries + fix-commit diffs from this CVE's patches. Citations validated against bundle.

References

6

News mentions

0

No linked articles in our index yet.