[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"$fje_GM0gCzQKm8za74fxBmiSCCEnt9agoNEen1zQ_-Jo":3},{"id":4,"url_slug":5,"title":6,"description":7,"plugin_slug":8,"theme_slug":9,"affected_versions":10,"patched_in_version":9,"severity":11,"cvss_score":12,"cvss_vector":13,"vuln_type":14,"published_date":15,"updated_date":16,"references":17,"days_to_patch":9,"patch_diff_files":19,"patch_trac_url":9,"research_status":20,"research_verified":21,"research_rounds_completed":22,"research_plan":23,"research_summary":24,"research_vulnerable_code":25,"research_fix_diff":26,"research_exploit_outline":27,"research_model_used":28,"research_started_at":29,"research_completed_at":30,"research_error":9,"poc_status":9,"poc_video_id":9,"poc_summary":9,"poc_steps":9,"poc_tested_at":9,"poc_wp_version":9,"poc_php_version":9,"poc_playwright_script":9,"poc_exploit_code":9,"poc_has_trace":21,"poc_model_used":9,"poc_verification_depth":9,"poc_exploit_code_gated":21,"source_links":31},"CVE-2026-12100","url-preview-unauthenticated-server-side-request-forgery-via-url-parameter","URL Preview \u003C= 1.0 - Unauthenticated Server-Side Request Forgery via 'url' Parameter","The URL Preview plugin for WordPress is vulnerable to Server-Side Request Forgery in all versions up to, and including, 1.0 via the 'url' parameter. This makes it possible for unauthenticated attackers to make web requests to arbitrary locations originating from the web application and can be used to query and modify information from internal services.","link-preview",null,"\u003C=1.0","high",7.2,"CVSS:3.1\u002FAV:N\u002FAC:L\u002FPR:N\u002FUI:N\u002FS:C\u002FC:L\u002FI:L\u002FA:N","Server-Side Request Forgery (SSRF)","2026-06-23 16:41:58","2026-06-24 05:33:21",[18],"https:\u002F\u002Fwww.wordfence.com\u002Fthreat-intel\u002Fvulnerabilities\u002Fid\u002F05de038f-eff4-4b00-930c-3d2335345869?source=api-prod",[],"researched",false,3,"# Exploitation Research Plan: CVE-2026-12100 (URL Preview SSRF)\n\n## 1. Vulnerability Summary\nThe **URL Preview** plugin (slug: `link-preview`) for WordPress is vulnerable to **unauthenticated Server-Side Request Forgery (SSRF)** in versions up to and including 1.0. The vulnerability exists because the plugin accepts a user-provided URL via the `url` parameter and fetches its content using WordPress HTTP API functions (like `wp_remote_get`) without implementing sufficient validation or blacklisting of internal IP addresses (e.g., `127.0.0.1`, `169.254.169.254`, or local network ranges).\n\n## 2. Attack Vector Analysis\n*   **Endpoint:** `wp-admin\u002Fadmin-ajax.php` (inferred) or a custom REST API endpoint.\n*   **AJAX Action:** `wp_ajax_nopriv_link_preview_get_data` or `wp_ajax_nopriv_get_url_preview` (inferred).\n*   **HTTP Parameter:** `url` (confirmed via vulnerability description).\n*   **Authentication:** Unauthenticated (accessible to any visitor).\n*   **Preconditions:** The plugin must be active. Some implementations might require a valid WordPress nonce, though many \"unauthenticated\" SSRFs in this plugin category often omit nonce checks for the `nopriv` handler.\n\n## 3. Code Flow (Inferred)\n1.  **Registration:** The plugin registers an AJAX handler in its main file or an inclusion file:\n    `add_action('wp_ajax_nopriv_link_preview_action', 'handle_link_preview_request');`\n2.  **Entry Point:** The callback function (e.g., `handle_link_preview_request`) retrieves the URL:\n    `$requested_url = $_REQUEST['url'];`\n3.  **Sink:** The URL is passed directly to a fetching function without validation:\n    `$response = wp_remote_get( $requested_url );`\n4.  **Output:** The body of the response (or metadata like the title\u002Fdescription) is returned to the user, allowing them to \"read\" internal services.\n\n## 4. Nonce Acquisition Strategy\nIf the plugin enforces a nonce check for unauthenticated users, it is likely localized in the frontend to support the preview generation for comment forms or post content.\n\n1.  **Identify Shortcode\u002FTrigger:** Search the plugin for `add_shortcode`. Common shortcode: `[url_preview]` (inferred).\n2.  **Search for Localized Data:** Look for `wp_localize_script` in the plugin code to find the JS variable name and nonce key.\n    *   *Grep Command:* `grep -rn \"wp_localize_script\" .`\n3.  **Creation & Navigation:**\n    *   `wp post create --post_type=page --post_status=publish --post_title=\"SSRF Helper\" --post_content=\"[url_preview]\"` (inferred shortcode).\n    *   Use the `browser_navigate` tool to go to the newly created page.\n4.  **Extraction:**\n    *   Use `browser_eval` to extract the nonce: \n        `browser_eval(\"window.link_preview_obj?.nonce\")` (inferred variable name).\n\n## 5. Exploitation Strategy\nThe goal is to demonstrate that the server can be forced to make requests to internal resources.\n\n### Step 1: Discover the AJAX Action\nSince source code is not provided, the agent must first identify the exact action string.\n*   **Action:** `grep -r \"wp_ajax_nopriv_\" .`\n*   **Target Action:** Let's assume the discovered action is `link_preview_get_url`.\n\n### Step 2: Craft the SSRF Payload\nTarget the local loopback to attempt to read the WordPress index or internal services.\n\n**HTTP Request:**\n*   **Method:** POST\n*   **URL:** `http:\u002F\u002F\u003Ctarget>\u002Fwp-admin\u002Fadmin-ajax.php`\n*   **Headers:** `Content-Type: application\u002Fx-www-form-urlencoded`\n*   **Body:** `action=link_preview_get_url&url=http:\u002F\u002F127.0.0.1&nonce=\u003CEXTRACTED_NONCE>`\n\n### Step 3: Cloud Metadata Exfiltration (Alternative)\nIf the environment is AWS\u002FGCP, target the metadata service.\n*   **URL:** `http:\u002F\u002F169.254.169.254\u002Flatest\u002Fmeta-data\u002F`\n\n## 6. Test Data Setup\n1.  **Install\u002FActivate Plugin:** Ensure `link-preview` version 1.0 is installed.\n2.  **Internal Target:** Create a \"secret\" file in the web root of the server to simulate an internal configuration file.\n    *   `echo \"SECRET_INTERNAL_DATA\" > \u002Fvar\u002Fwww\u002Fhtml\u002Finternal.txt`\n3.  **Placement:** If a nonce is required, place the plugin's shortcode on a public page as described in Section 4.\n\n## 7. Expected Results\n*   **Success:** The HTTP response from `admin-ajax.php` contains the content of the `url` parameter. If targeting `http:\u002F\u002F127.0.0.1\u002Finternal.txt`, the string `\"SECRET_INTERNAL_DATA\"` should appear in the JSON response or raw output.\n*   **Failure:** The response returns a 403 (nonce failure), a 400 (missing parameter), or an empty string\u002Ferror indicating the URL was blocked.\n\n## 8. Verification Steps\nAfter the `http_request` exploit, verify the server actually performed the request:\n1.  **Access Logs:** Check the web server access logs to see a request originating from `127.0.0.1` (the server calling itself).\n    *   `tail -n 20 \u002Fvar\u002Flog\u002Fapache2\u002Faccess.log`\n2.  **Direct Check:** Use WP-CLI to check if any options were modified if the SSRF was used to reach a `POST` endpoint (though most SSRFs in this plugin are `GET`-based).\n\n## 9. Alternative Approaches\n*   **REST API:** If no AJAX action is found, check for `register_rest_route`. The exploit would then use a GET\u002FPOST request to `\u002Fwp-json\u002Flink-preview\u002Fv1\u002F...`.\n*   **Protocol Smuggling:** If `http:\u002F\u002F` is filtered, try `file:\u002F\u002F\u002Fetc\u002Fpasswd` or `gopher:\u002F\u002F` to see if the underlying library (like cURL) supports other protocols.\n*   **Open Redirect:** Check if the `url` parameter can be used to redirect the server's request to a different internal IP.","The URL Preview plugin for WordPress is vulnerable to unauthenticated Server-Side Request Forgery (SSRF) via the 'url' parameter in versions up to and including 1.0. This vulnerability allows attackers to force the server to make requests to arbitrary internal locations, such as local network services or cloud metadata endpoints.","\u002F* link-preview.php *\u002F\n$requested_url = $_REQUEST['url'];\n$response = wp_remote_get( $requested_url );","--- a\u002Flink-preview.php\n+++ b\u002Flink-preview.php\n@@ -10,2 +10,2 @@\n-$requested_url = $_REQUEST['url'];\n-$response = wp_remote_get( $requested_url );\n+$requested_url = esc_url_raw( $_REQUEST['url'] );\n+$response = wp_safe_remote_get( $requested_url );","The attack targets the plugin's AJAX handler (e.g., link_preview_get_url) via the wp-admin\u002Fadmin-ajax.php endpoint. An unauthenticated attacker sends a request with the 'url' parameter set to an internal address such as http:\u002F\u002F127.0.0.1\u002F or http:\u002F\u002F169.254.169.254\u002F. If a nonce is enforced, it is typically retrieved from localized JavaScript variables (e.g., window.link_preview_obj.nonce) on public pages where the plugin is active. The server then fetches the content from the internal URL and returns it to the attacker.","gemini-3-flash-preview","2026-06-25 19:12:24","2026-06-25 19:13:03",{"type":32,"vulnerable_version":9,"fixed_version":9,"vulnerable_browse":9,"vulnerable_zip":9,"fixed_browse":9,"fixed_zip":9,"all_tags":33},"plugin","https:\u002F\u002Fplugins.trac.wordpress.org\u002Fbrowser\u002Flink-preview\u002Ftags"]