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

Oro Api Logger Laravel Package

25carat/oro-api-logger

Logs all OroCommerce REST API requests and responses for monitoring integrations. Adds a dedicated api_logger channel writing to api-logger-[env].log with configurable minimum level; headers at info, bodies at debug, client errors at error, server errors at critical.

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Steps

  1. Installation:
    composer require 25carat/oro-api-logger
    
  2. Configure Log Level: Add to config/packages/parameters.yml (or equivalent in OroCommerce):
    parameters:
        twenty5carat.api_logger.level: error  # Start with 'error' for production
    
  3. Clear Cache:
    php bin/console cache:clear
    
  4. Verify Logs: Check var/log/api-logger-[env].log for API request/response entries.

First Use Case

Debugging a Failed API Integration:

  • Enable debug level in staging:
    twenty5carat.api_logger.level: debug
    
  • Reproduce the failing API call (e.g., a third-party marketplace sync).
  • Inspect api-logger-staging.log for:
    • Exact request payload (headers + body).
    • Response status code and body.
    • Timestamps to identify latency issues.
  • Example log entry structure:
    [2025-06-27 12:34:56] api_logger.INFO: Request to /api/rest/v1/orders {"headers": {...}, "body": {...}}
    [2025-06-27 12:34:56] api_logger.ERROR: Response 400 {"headers": {...}, "body": "Invalid payload"}
    

Implementation Patterns

Core Workflow

  1. Decorator Pattern:

    • The package decorates OroCommerce’s RestApiController, intercepting all API requests/responses without modifying core logic.
    • Integration Tip: Extend the decorator to add custom logic (e.g., sanitize sensitive fields before logging) by overriding the logRequest/logResponse methods in the decorator service.
  2. Log Level Strategy:

    • Production: Start with error or critical to avoid log noise.
      twenty5carat.api_logger.level: error
      
    • Staging/Dev: Use debug for full payload inspection.
      twenty5carat.api_logger.level: debug
      
    • Dynamic Switching: Use environment variables or feature flags to toggle log levels dynamically (e.g., via env() in Symfony config).
  3. Log File Management:

    • Logs are written to var/log/api-logger-[env].log (e.g., api-logger-prod.log).
    • Best Practice: Implement log rotation using logrotate or Symfony’s Monolog handlers (e.g., RotatingFileHandler):
      # config/packages/monolog.yaml
      monolog:
          handlers:
              api_logger:
                  type: rotating_file
                  path: "%kernel.logs_dir%/api-logger-%kernel.environment%.log"
                  level: "%twenty5carat.api_logger.level%"
                  max_files: 30  # Keep 30 days of logs
      
  4. Pairing with Other Tools:

    • Centralized Logging: Forward logs to ELK/Splunk using Monolog’s SocketHandler or SyslogHandler.
      # config/packages/monolog.yaml
      monolog:
          handlers:
              api_logger:
                  type: socket
                  host: "logs.example.com"
                  port: 514
      
    • Alerting: Use tools like Sentry or Datadog to monitor for critical/error logs and trigger alerts.

Advanced Patterns

  1. Conditional Logging:

    • Filter logs by route or HTTP method using a custom formatter. Override the ApiLoggerFormatter service to exclude sensitive endpoints:
      // src/Service/ApiLoggerFormatter.php
      public function formatRequest(Request $request): string
      {
          if ($request->getPathInfo() === '/api/rest/v1/payments') {
              return "Request to [REDACTED]";
          }
          return parent::formatRequest($request);
      }
      
    • Register the custom formatter in services.yaml:
      services:
          App\Service\ApiLoggerFormatter:
              decorates: twenty5carat.api_logger.formatter
              arguments: ['@.inner']
      
  2. Performance Optimization:

    • For high-traffic APIs, offload logging to a queue (e.g., Symfony Messenger) to avoid blocking requests:
      // src/EventListener/ApiLoggerListener.php
      public function onKernelRequest(GetResponseEvent $event)
      {
          if ($event->isMasterRequest()) {
              $this->dispatcher->dispatch(new ApiLogEvent($event->getRequest()));
          }
      }
      
    • Process queued logs asynchronously with a worker.
  3. Structured Logging:

    • Extend the formatter to output JSON for better parsing in tools like ELK:
      public function formatResponse(Response $response): string
      {
          return json_encode([
              'timestamp' => (new \DateTime())->format('c'),
              'status_code' => $response->getStatusCode(),
              'headers' => $response->headers->all(),
              'body' => $response->getContent(),
          ]);
      }
      

Gotchas and Tips

Pitfalls

  1. Missing Configuration:

    • Error: Parameter "twenty5carat.api_logger.level" not found.
    • Fix: Ensure the parameter is added to parameters.yml (or equivalent). OroCommerce may use config/packages/parameters.yml or app/config/parameters.yml.
    • Tip: Add a validation check in a custom command or CI pipeline to catch missing configs early.
  2. Sensitive Data Leaks:

    • Risk: Logs may include PII (e.g., tokens, credit card numbers) in request/response bodies.
    • Fix:
      • Use debug level sparingly in production.
      • Sanitize logs by overriding the formatter (see Conditional Logging above).
      • Example: Redact fields like password, token, or cc_number.
    • Tip: Test with a sample payload containing sensitive data in staging before enabling in production.
  3. Performance Impact:

    • Issue: Logging large request/response bodies (e.g., file uploads, bulk APIs) at debug level can slow down API responses.
    • Fix:
      • Limit log levels to info or error in production.
      • Exclude large payloads by checking content length:
        public function formatRequest(Request $request): string
        {
            if ($request->getContentLength() > 1024 * 1024) { // 1MB
                return "Request to {$request->getPathInfo()} (large payload)";
            }
            return parent::formatRequest($request);
        }
        
    • Tip: Monitor API response times with Blackfire or New Relic when enabling verbose logging.
  4. Log File Permissions:

    • Issue: Log files may fail to write if permissions are incorrect (e.g., var/log not writable by the web server).
    • Fix:
      • Ensure var/log is writable:
        chmod -R 775 var/log
        
      • Configure Symfony’s kernel.logs_dir if using a custom path:
        # config/packages/framework.yaml
        framework:
            logs_dir: "%kernel.project_dir%/var/logs"
        
  5. OroCommerce Upgrades:

    • Risk: OroCommerce’s RestApiController may change in minor/patch updates, breaking the decorator.
    • Fix:
      • Test the package after every Oro upgrade in staging.
      • Monitor the OroCommerce changelog for API layer changes.
    • Tip: Subscribe to the package’s GitHub repo for compatibility updates (though activity is low).

Debugging Tips

  1. Logs Not Appearing:

    • Checklist:
      • Verify the log level is set (e.g., error).
      • Confirm the cache is cleared (php bin/console cache:clear).
      • Ensure the api_logger channel is enabled in Monolog (it should be by default).
      • Check file permissions on var/log.
    • Debug Command: Temporarily enable all log levels to test:
      php bin/console debug:config twenty5carat.api_logger.level
      
  2. Malformed Logs:

    • Cause: Custom formatters or decorators may output invalid data.
    • Fix: Enable Symfony’s debug mode to see exceptions:
      # config/packages/dev/monolog.yaml
      monolog:
          handlers:
              main:
                  level: debug
                  channels: ["!event"]
      
    • Tip: Use var_dump() in custom formatters to inspect data before logging.
  3. High Log Volume:

    • Solution: Implement log sampling or dynamic log levels based on request metadata (e.g., log only failed requests):
      public function logResponse(Response $response)
      {
          if ($response->getStatusCode() >=
      
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.
terminal42/code-quality-tools
codifyo/ts-generator-bundle
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