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

Dns Laravel Package

spatie/dns

Fetch DNS records in PHP using dig. Query domains for A, AAAA, CNAME, MX, TXT, SRV and more, filter by type(s), and get structured record objects with handy accessors for record details.

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Setup

  1. Installation:

    composer require spatie/dns
    

    No additional configuration is required for basic usage.

  2. First Use Case: Fetch all DNS records for a domain (e.g., google.com):

    use Spatie\Dns\Dns;
    
    $records = Dns::getRecords('google.com');
    dd($records); // Returns a collection of DNSRecord objects
    
  3. Key Classes:

    • Dns: Main facade for querying DNS records.
    • DNSRecord: Represents individual records (e.g., A, MX, TXT).
    • DnsException: Handle DNS-related errors.
  4. Where to Look First:

    • Documentation (official docs).
    • src/DnsServiceProvider.php (service provider setup).
    • src/Dns.php (core facade logic).

Implementation Patterns

Common Workflows

1. Fetching Specific Record Types

Filter records by type (e.g., MX, TXT, A):

$mxRecords = Dns::getRecords('example.com')->whereType('MX');
$txtRecords = Dns::getRecords('example.com')->whereType('TXT');

2. Caching DNS Responses

Avoid repeated DNS lookups by caching results (e.g., for rate-limited APIs or slow DNS providers):

$records = Cache::remember("dns_records_{$domain}", now()->addHours(1), function () use ($domain) {
    return Dns::getRecords($domain);
});

3. Handling DNS Failures Gracefully

Use try-catch blocks for DNS resolution errors:

try {
    $records = Dns::getRecords('nonexistent.example');
} catch (DnsException $e) {
    Log::error("DNS lookup failed for nonexistent.example: " . $e->getMessage());
    // Fallback logic (e.g., return cached data or default values)
}

4. Integration with Laravel Queues

Offload DNS lookups to background jobs (e.g., for bulk domain checks):

use Spatie\Dns\Jobs\GetRecords;

GetRecords::dispatch('example.com')
    ->afterCommit() // Optional: Run after DB commit
    ->onQueue('dns');

5. Custom DNS Providers

Extend the package to support custom DNS resolvers (e.g., internal DNS servers):

use Spatie\Dns\DnsProvider;

class CustomDnsProvider implements DnsProvider {
    public function getRecords(string $domain): array {
        // Implement custom logic (e.g., call internal API)
        return ['type' => 'A', 'data' => '192.0.2.1'];
    }
}

// Register in AppServiceProvider:
Dns::extend('custom', function () {
    return new CustomDnsProvider();
});

// Usage:
Dns::onProvider('custom')->getRecords('example.com');

6. Bulk DNS Lookups

Process multiple domains efficiently:

$domains = ['google.com', 'github.com', 'spatie.be'];
$results = collect($domains)->map(fn ($domain) => Dns::getRecords($domain));

7. Validation with DNS Records

Validate domain ownership via DNS (e.g., check for TXT records):

$txtRecords = Dns::getRecords($domain)->whereType('TXT');
$hasVerification = $txtRecords->contains(fn ($record) =>
    str_contains($record->data, 'verification-code=12345')
);

Integration Tips

Laravel Ecosystem

  • Laravel Scout: Use DNS records for custom search logic (e.g., prioritize domains with MX records).
  • Laravel Notifications: Validate sender domains via DNS before sending emails.
  • Laravel Policies: Restrict access based on DNS records (e.g., only allow domains with specific TXT entries).
  • Laravel Horizon: Monitor DNS job failures in real-time.

Testing

  • Mock Spatie\Dns\Dns in unit tests:
    $this->mock(Spatie\Dns\Dns::class, function ($mock) {
        $mock->shouldReceive('getRecords')
             ->with('example.com')
             ->andReturn(collect([new DNSRecord(['type' => 'A', 'data' => '1.1.1.1'])]));
    });
    

Performance

  • Batch Processing: Use Laravel's chunk() or cursor() for large datasets.
  • Parallel Requests: Leverage Spatie\Async for concurrent DNS lookups:
    use Spatie\Async\Parallel;
    
    Parallel::make($domains)->each(function ($domain) {
        return Dns::getRecords($domain);
    });
    

Gotchas and Tips

Pitfalls

  1. Rate Limiting:

    • Some DNS providers (e.g., public resolvers like Google's 8.8.8.8) throttle requests.
    • Solution: Use a dedicated DNS service (e.g., Cloudflare API) or implement exponential backoff:
      use Symfony\Component\Process\Exception\ProcessTimedOutException;
      
      try {
          $records = Dns::getRecords($domain);
      } catch (ProcessTimedOutException $e) {
          sleep(2); // Wait before retry
          retry();
      }
      
  2. TTL (Time-to-Live) Caching:

    • DNS records are cached by resolvers. Changes may take time to propagate.
    • Solution: Use Dns::flushCache() (if supported) or implement local caching with short TTLs.
  3. DNSSEC Validation:

    • The package may not validate DNSSEC-signed records by default.
    • Solution: Use a library like rubensworks/dnssec-validator for additional checks.
  4. Non-Standard Record Types:

    • Some record types (e.g., CAA, SRV) may not be parsed correctly.
    • Solution: Extend DNSRecord or pre-process raw data:
      $rawRecords = Dns::getRecords($domain, true); // Get raw output
      
  5. Local Development:

    • DNS queries may fail if /etc/hosts or C:\Windows\System32\drivers\etc\hosts overrides are present.
    • Solution: Test with a public domain (e.g., google.com) or mock DNS responses.
  6. Case Sensitivity:

    • Domain names are case-insensitive, but some DNS providers may return inconsistent results.
    • Solution: Normalize domains to lowercase:
      $domain = strtolower($domain);
      

Debugging Tips

  1. Enable Verbose Output:

    Dns::enableVerboseOutput(); // Logs raw DNS queries/responses
    
  2. Check Underlying Process: The package uses exec() to call dig or nslookup. Verify these tools are installed:

    dig google.com
    nslookup google.com
    
  3. Inspect Raw Data: Access raw DNS output for debugging:

    $rawOutput = Dns::getRecords($domain, true);
    dd($rawOutput);
    
  4. Common Errors:

    • "Command not found": Ensure dig/nslookup is installed. Fix: Install via brew install bind (macOS) or apt-get install dnsutils (Linux).
    • Timeouts: Increase PHP's max_execution_time or use a faster DNS provider.
    • Permission Denied: Ensure the web server user has access to DNS tools.

Configuration Quirks

  1. Default DNS Provider: The package defaults to dig on Unix-like systems and nslookup on Windows. Override in config/dns.php:

    'provider' => 'custom', // Must match a registered provider
    
  2. Custom DNS Servers: Configure a specific DNS server (e.g., Cloudflare):

    Dns::setDnsServer('1.1.1.1'); // Cloudflare
    $records = Dns::getRecords('example.com');
    
  3. Environment-Specific Settings: Use Laravel's config caching to switch providers per environment:

    // config/dns.php
    'provider' => env('DNS_PROVIDER', 'dig'),
    

Extension Points

  1. Custom DNS Providers: Implement Spatie\Dns\DnsProvider for APIs (e.g., AWS Route 53, Cloudflare):
    class CloudflareDnsProvider implements DnsProvider {
        public function getRecords(string $domain): array {
            $response = Http::get("https://
    
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.
davejamesmiller/laravel-breadcrumbs
artisanry/parsedown
christhompsontldr/phpsdk
enqueue/dsn
bunny/bunny
enqueue/test
enqueue/null
enqueue/amqp-tools
milesj/emojibase
bower-asset/punycode
bower-asset/inputmask
bower-asset/jquery
bower-asset/yii2-pjax
laravel/nova
spatie/laravel-mailcoach
spatie/laravel-superseeder
laravel/liferaft
nst/json-test-suite
danielmiessler/sec-lists
jackalope/jackalope-transport