Weave Code
Code Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Uri Laravel Package

sabre/uri

Lightweight PHP URI utility library compliant with RFC3986. Provides resolve, normalize, parse/build, and split helpers for working with URLs, including Windows-style path edge cases. Fully unit tested and inspired by Node.js URL handling.

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Steps

  1. Installation:

    composer require sabre/uri
    

    Ensure your composer.json specifies PHP 8.2+ for the latest features (or PHP 7.4+ for LTS support).

  2. First Use Case: Resolve a relative URL against a base URL in a Laravel route or controller:

    use Sabre\Uri\Uri;
    
    $baseUrl = Uri::resolve('https://example.com/base/path', '../relative/path');
    // Returns: 'https://example.com/relative/path'
    
  3. Where to Look First:


Implementation Patterns

Core Workflows

1. URL Resolution in Laravel Routes

Replace URL::to() or manual string concatenation with Uri::resolve():

use Sabre\Uri\Uri;

// In a route closure or controller
$absoluteUrl = Uri::resolve(
    request()->getSchemeAndHttpHost() . request()->path(),
    'subpath'
);

2. Normalizing URLs for Comparison

Ensure URLs are RFC-compliant before storage (e.g., in a database or cache):

$normalized = Uri::normalize('https://example.com/path?query=1#fragment');
// Returns: 'https://example.com/path?query=1'

3. Parsing and Rebuilding URIs

Use parse() and build() for dynamic URI manipulation (e.g., in API requests):

$parsed = Uri::parse('https://user:pass@example.com/path?query=1');
$rebuilt = Uri::build([
    'scheme' => 'https',
    'host'   => 'example.com',
    'path'   => '/new-path',
]);

4. Splitting Paths in File Uploads

Handle file paths safely (e.g., in Illuminate\Http\UploadedFile):

$uploadedFile = request()->file('file');
$dirname = Uri::split($uploadedFile->getPathname())['dirname'];

5. Integration with Laravel Facades

Create a custom facade for consistency:

// app/Providers/AppServiceProvider.php
public function boot()
{
    app()->bind('uri', function () {
        return new Sabre\Uri\Uri();
    });
}

Usage:

$resolved = app('uri')->resolve($base, $relative);

Laravel-Specific Patterns

1. Form Request Validation

Validate URIs in Illuminate\Foundation\Http\FormRequest:

use Sabre\Uri\Uri;

public function rules()
{
    return [
        'redirect_url' => [
            'required',
            function ($attribute, $value, $fail) {
                try {
                    Uri::parse($value); // Throws InvalidUriException on failure
                } catch (\Sabre\Uri\InvalidUriException $e) {
                    $fail('The :attribute must be a valid URI.');
                }
            },
        ],
    ];
}

2. Middleware for URI Sanitization

Strip or normalize URIs in incoming requests:

use Sabre\Uri\Uri;

public function handle($request, Closure $next)
{
    $request->merge([
        'sanitized_url' => Uri::normalize($request->input('url')),
    ]);
    return $next($request);
}

3. Queue Jobs with URI Resolution

Resolve relative paths in background jobs:

use Sabre\Uri\Uri;
use Illuminate\Bus\Queueable;

class ProcessUrlJob implements Queueable
{
    public function handle()
    {
        $absoluteUrl = Uri::resolve(
            config('app.url'),
            $this->relativePath
        );
        // Process $absoluteUrl...
    }
}

4. API Resource URI Handling

Override toArray() in Illuminate\Http\Resources\Json\JsonResource:

public function toArray($request)
{
    return [
        'url' => Uri::build([
            'scheme' => 'https',
            'host'   => $request->getHost(),
            'path'   => $this->path,
        ]),
    ];
}

5. Artisan Commands for URI Debugging

Add a custom command to inspect URIs:

use Sabre\Uri\Uri;
use Illuminate\Console\Command;

class DebugUriCommand extends Command
{
    protected $signature = 'uri:debug {url}';
    public function handle()
    {
        $parsed = Uri::parse($this->argument('url'));
        $this->line(print_r($parsed, true));
    }
}

Gotchas and Tips

Pitfalls

  1. Windows Path Handling:

    • Issue: file:///C:/path may parse unexpectedly (see #81).
    • Fix: Use Uri::parse() with caution for Windows paths; prefer Uri::build() for reconstruction:
      $windowsPath = Uri::build([
          'scheme' => 'file',
          'host'   => '', // Empty host for Windows
          'path'   => 'C:/path/to/file.txt',
      ]);
      
  2. Fragment Handling:

    • Issue: Uri::resolve() may drop fragments (#) if not handled explicitly.
    • Fix: Manually preserve fragments:
      $base = Uri::parse('https://example.com#base');
      $relative = Uri::parse('subpath');
      $resolved = Uri::build([
          'scheme' => $base['scheme'],
          'host'   => $base['host'],
          'path'   => Uri::resolve($base['path'], $relative['path']),
          'fragment' => $base['fragment'],
      ]);
      
  3. Query String Normalization:

    • Issue: Uri::normalize() may not preserve query string order (RFC3986 is order-agnostic).
    • Fix: Use http_build_query() for ordered queries:
      $normalized = Uri::build([
          'scheme' => 'https',
          'host'   => 'example.com',
          'path'   => '/path',
          'query'  => http_build_query(['param' => 'value']),
      ]);
      
  4. Unicode Characters:

    • Issue: Non-ASCII characters (e.g., é, 中文) may not encode correctly.
    • Fix: Explicitly encode:
      $uri = Uri::build([
          'path' => Uri::encode('path/with/é/characters'),
      ]);
      
  5. Empty Components:

    • Issue: Uri::parse() may return null for empty components (e.g., scheme).
    • Fix: Validate parsed components:
      $parsed = Uri::parse($uri);
      if (empty($parsed['scheme'])) {
          throw new \InvalidArgumentException('URI must include a scheme.');
      }
      

Debugging Tips

  1. Use Uri::parse() for Inspection: Dump parsed URIs to debug issues:

    dd(Uri::parse('https://user:pass@example.com/path?query=1#frag'));
    
  2. Test Edge Cases: Run the library’s test suite locally to verify behavior:

    composer require --dev sabre/uri
    vendor/bin/phpunit vendor/sabre/uri/tests
    
  3. Leverage InvalidUriException: Catch parsing errors gracefully:

    try {
        Uri::parse($malformedUri);
    } catch (\Sabre\Uri\InvalidUriException $e) {
        Log::error('Invalid URI: ' . $e->getMessage());
    }
    

Configuration Quirks

  1. PHP Version Compatibility:

    • PHP 8.2+: Use 3.1.0+ for rector support and PHP 8.2 features.
    • PHP 7.4–8.1: Use 3.0.* for LTS compatibility.
    • PHP <7.4: Use 2.3.* (but avoid Windows path changes from 2.2.3).
  2. Custom URI Schemes:

    • The library supports non-standard schemes (e.g., s3://, mailto:), but validate them explicitly:
      if (!in_array($parsed['scheme'], ['http', 'https', 's3'])) {
          throw new \InvalidArgumentException("Unsupported
      
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
andydefer/laravel-cluster
testo/fiber
mintobit/jobqueue
a4sex/maintenance-bundle
a4sex/entity-date-update
a4sex/client-identifier
a4sex/base-utilites
a4sex/key-value-storage
a4sex/micro-status
chilldev/dependency-injection-extra
datinglibre/datinglibre-app-api
biberltd/corebundle
bricre/symfony-bundle-test
biberltd/logbundle
dominium/http-adapter-bundle
dominium/google-analytics
a4sex/auto-clean-entity
christhompsontldr/laravel-inky
spatie/mailcoach-vapor
spatie/laravel-javascript-views