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

Cron Translator Laravel Package

lorisleiva/cron-translator

Translate CRON expressions into clear, human-readable schedules. Supports common patterns (ranges, steps, lists) and multiple locales, with optional 24-hour time formatting. Ideal for showing CRON schedules in UIs and logs.

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Steps

  1. Installation:

    composer require lorisleiva/cron-translator
    

    Add to composer.json under require or use require-dev if only for testing.

  2. First Use Case: Translate a cron expression in a Laravel controller or Blade view:

    use Lorisleiva\CronTranslator\CronTranslator;
    
    $translated = CronTranslator::translate('0 16 * * 1'); // "Every Monday at 4:00pm"
    return view('jobs.index', compact('translated'));
    
  3. Where to Look First:

    • README.md: For basic usage, locales, and examples.
    • src/CronTranslator.php: Core logic and supported cron syntax.
    • tests/: Edge cases and validation patterns.

Implementation Patterns

Core Workflows

  1. Admin Dashboards: Display human-readable cron schedules next to job listings:

    $jobs = Job::all();
    foreach ($jobs as $job) {
        $job->humanReadableCron = CronTranslator::translate($job->cron);
    }
    return view('jobs.index', compact('jobs'));
    
  2. API Documentation: Auto-generate cron descriptions for webhook endpoints:

    Route::get('/webhooks', function () {
        return [
            'webhooks' => [
                [
                    'name' => 'invoice_due',
                    'cron' => '0 0 1 * *',
                    'description' => CronTranslator::translate('0 0 1 * *'),
                ],
            ],
        ];
    });
    
  3. User-Facing Scheduling Tools: Localize cron descriptions for non-technical users:

    $locale = app()->getLocale(); // e.g., 'fr'
    $translated = CronTranslator::translate('30 18 * * *', $locale);
    // Output: "Chaque jour à 6:30pm" (French)
    

Integration Tips

  • Service Provider Binding: Bind the translator to Laravel’s container for dependency injection:

    $this->app->singleton(CronTranslator::class, function () {
        return new CronTranslator();
    });
    

    Then inject via constructor:

    public function __construct(private CronTranslator $translator) {}
    
  • Blade Directives: Create a custom Blade directive for reusable translations:

    Blade::directive('cron', function ($expression) {
        return "<?php echo Lorisleiva\CronTranslator\CronTranslator::translate({$expression}); ?>";
    });
    

    Usage:

    @cron('0 16 * * 1')
    
  • Form Validation Feedback: Use translations to explain cron syntax errors:

    $validator = Validator::make($request->all(), [
        'cron' => 'required|cron',
    ]);
    if ($validator->fails()) {
        return back()->withErrors([
            'cron' => 'Invalid cron. Example: ' . CronTranslator::translate('* * * * *'),
        ]);
    }
    
  • Testing: Mock translations in unit tests:

    $translator = Mockery::mock(CronTranslator::class);
    $translator->shouldReceive('translate')
               ->with('0 16 * * 1')
               ->andReturn('Every Monday at 4:00pm');
    $this->app->instance(CronTranslator::class, $translator);
    

Gotchas and Tips

Pitfalls

  1. Unsupported Cron Syntax:

    • The package does not support extended cron fields (e.g., @yearly, @monthly) or special characters like L (last day of month) or W (nearest weekday).
    • Workaround: Pre-process expressions or use a fallback message:
      if (str_contains($cron, '@') || str_contains($cron, 'L')) {
          return 'Custom cron syntax (not fully supported)';
      }
      
  2. Locale Fallback:

    • If a locale is unsupported, it defaults to English. Always validate locales:
      $supportedLocales = ['en', 'fr', 'de', 'es', 'pt', 'ru', 'zh', 'ar', 'nl'];
      $locale = in_array($request->locale, $supportedLocales) ? $request->locale : 'en';
      
  3. Time Format Ambiguity:

    • The use24h parameter defaults to false. Ensure consistency in your app’s time display settings.
  4. Performance:

    • The package is lightweight, but avoid translating the same cron repeatedly in loops. Cache results:
      $cacheKey = "cron_{$cron}_{$locale}";
      return Cache::remember($cacheKey, 60, function () use ($cron, $locale) {
          return CronTranslator::translate($cron, $locale);
      });
      

Debugging Tips

  1. Edge Cases:

    • Test with complex cron expressions like:
      '1,2 0 */2 1,2 *' // Twice an hour every 2 days 2 months a year at 12am
      '1-3/5 * * * *'   // 3 times every 5 minutes
      
    • Verify translations for all supported locales to catch inconsistencies.
  2. Logging:

    • Log untranslated cron expressions to identify unsupported patterns:
      try {
          $translation = CronTranslator::translate($cron);
      } catch (\Exception $e) {
          Log::warning("Unsupported cron: {$cron}", ['error' => $e->getMessage()]);
          $translation = 'Unsupported cron syntax';
      }
      
  3. Custom Extensions:

    • Extend the translator for unsupported syntax by subclassing:
      class ExtendedCronTranslator extends CronTranslator {
          public function translate($expression) {
              if (str_contains($expression, '@yearly')) {
                  return 'Yearly (custom)';
              }
              return parent::translate($expression);
          }
      }
      

Configuration Quirks

  1. Locale Prioritization:

    • Laravel’s app locale (config/app.php) does not automatically override the translator’s locale. Always pass the desired locale explicitly:
      // Wrong: Assumes app locale
      CronTranslator::translate('* * * * *');
      
      // Correct: Explicit locale
      CronTranslator::translate('* * * * *', app()->getLocale());
      
  2. Time Zone Handling:

    • The translator does not account for time zones. Ensure cron expressions are authored in the correct time zone or convert them before translation:
      $cronInUtc = CronExpression::factory($cron)->timezone('UTC')->getExpression();
      
  3. Testing Locales:

    • Use en for tests to avoid flakiness from locale-specific translations:
      $this->assertEquals('Every minute', CronTranslator::translate('* * * * *', 'en'));
      

Extension Points

  1. Add New Locales:

    • Contribute translations via PRs to the GitHub repo. Follow the existing structure in resources/lang/.
  2. Custom Translation Rules:

    • Override the translate() method or use a decorator pattern to modify logic:
      class CustomCronTranslator {
          public function translate($expression, $locale = 'en', $use24h = false) {
              $translation = CronTranslator::translate($expression, $locale, $use24h);
              return str_replace('Every', 'Scheduled', $translation); // Customize output
          }
      }
      
  3. Integration with Laravel Scheduler:

    • Combine with Laravel’s scheduler to display job descriptions:
      $schedule = app('schedule');
      $jobs = collect($schedule->commands())->map(function ($job) {
          return [
              'command' => $job,
              'description' => CronTranslator::translate($job->expression),
          ];
      });
      
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.
codraw/framework-extra-bundle
codraw/messenger
codraw/security
codraw/mailer
codraw/contracts
codraw/profiling
codraw/dependency-injection
codraw/tester
codraw/core
nexmo/api-specification
capell-app/block-library
axium/identity
cetria/laravel-dummy-models
cetria/reflection-helper
agropredict/sso-auth-bundle
evolvestudio/spam-protection
datacore/hub-sdk
develia/commons
cuci/prototurk-sdk
cuci/prototurk-sdk-symfony