URL Security: Guide to Protection from XSS, Injection, and Attacks

Learn about URL-based vulnerabilities and attack vectors. Protection methods against XSS, SQL Injection, SSRF, and other threats.

URLs are fundamental building blocks of web applications, but they are also one of the most common attack vectors. In this guide, we examine URL-based security threats and protection methods.

URL Structure and Security Risks

URL Anatomy

https://user:pass@example.com:443/path/page?param=value#fragment
  │      │    │       │        │     │         │          │
  │      │    │       │        │     │         │          └─ Fragment
  │      │    │       │        │     │         └─ Query String
  │      │    │       │        │     └─ Path
  │      │    │       │        └─ Port
  │      │    │       └─ Host
  │      │    └─ Password
  │      └─ Username
  └─ Scheme

Risks in Each Component

Cross-Site Scripting (XSS)

URL-Based XSS Types

1. Reflected XSS

# Attack URL
https://example.com/search?q=<script>alert('XSS')</script>

# Vulnerable code
<p>Search results: <?= $_GET['q'] ?></p>

2. DOM-Based XSS

# Attack URL
https://example.com/page#<img src=x onerror=alert('XSS')>

# Vulnerable JavaScript
document.getElementById('content').innerHTML = location.hash.slice(1);

XSS Protection Methods

Output Encoding

// PHP
<?= htmlspecialchars($_GET['q'], ENT_QUOTES, 'UTF-8') ?>

// JavaScript
function escapeHtml(text) {
  const div = document.createElement('div');
  div.textContent = text;
  return div.innerHTML;
}

// React (automatic escaping)
<p>{searchQuery}</p>  // Safe

Content Security Policy

# HTTP Header
Content-Security-Policy: default-src 'self'; script-src 'self' 'nonce-abc123'

SQL Injection

SQL Injection from URL

# Attack URL
https://example.com/user?id=1' OR '1'='1
https://example.com/user?id=1; DROP TABLE users;--

# Vulnerable code
$query = "SELECT * FROM users WHERE id = " . $_GET['id'];

SQL Injection Protection

Prepared Statements

// PHP PDO
$stmt = $pdo->prepare('SELECT * FROM users WHERE id = ?');
$stmt->execute([$_GET['id']]);

// Node.js
const result = await db.query(
  'SELECT * FROM users WHERE id = $1',
  [req.query.id]
);

Server-Side Request Forgery (SSRF)

SSRF Attack

# Attack URL
https://example.com/fetch?url=http://localhost:8080/admin
https://example.com/fetch?url=http://169.254.169.254/metadata

SSRF Protection

function isUrlSafe(url) {
    const parsed = new URL(url);
    
    // Only allow HTTP/HTTPS
    if (!['http:', 'https:'].includes(parsed.protocol)) {
        return false;
    }
    
    // Block localhost and private IPs
    const privatePatterns = [
        /^localhost$/i,
        /^127\./,
        /^10\./,
        /^172\.(1[6-9]|2[0-9]|3[01])\./,
        /^192\.168\./
    ];
    
    return !privatePatterns.some(p => p.test(parsed.hostname));
}

Path Traversal

Directory Traversal Attack

# Attack URL
https://example.com/file?name=../../../etc/passwd

Path Traversal Protection

function getSafeFilePath(filename, baseDir) {
    const safeName = path.basename(filename);
    const fullPath = path.resolve(baseDir, safeName);
    
    if (!fullPath.startsWith(path.resolve(baseDir))) {
        throw new Error('Invalid file path');
    }
    
    return fullPath;
}

Open Redirect

Open Redirect Attack

# Attack URL
https://example.com/login?redirect=https://evil.com/phishing

Open Redirect Protection

function safeRedirect(url, allowedDomains) {
    try {
        const parsed = new URL(url, 'https://example.com');
        
        if (parsed.origin === 'https://example.com') {
            return url; // Relative URL, safe
        }
        
        if (allowedDomains.includes(parsed.hostname)) {
            return url;
        }
    } catch (e) {}
    
    return '/';
}

Security Checklist

Conclusion

URL security is a critical part of web application security. Treat every URL parameter as a potential attack vector and implement appropriate protection measures. Support URLs created with SlugURL with security best practices to create structures optimized for both SEO and security.