Weave 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

Flysystem Phpcr Laravel Package

league/flysystem-phpcr

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Setup

  1. Installation:

    composer require league/flysystem-phpcr
    

    Ensure you have a PHPCR-compatible repository (e.g., Jackrabbit, eZ Publish, or Doctrine PHPCR-ODM) configured.

  2. Basic Usage:

    use League\Flysystem\Filesystem;
    use League\Flysystem\Phpcr\PhpcrAdapter;
    
    $repository = new \Doctrine\ODM\PHPCR\DocumentManager(); // or your PHPCR repo
    $adapter = new PhpcrAdapter($repository, '/path/in/repo');
    $filesystem = new Filesystem($adapter);
    
    // Upload a file
    $filesystem->write('file.txt', 'Hello, PHPCR!');
    
    // Read a file
    $contents = $filesystem->read('file.txt');
    
  3. First Use Case:

    • Migrate existing files from a local filesystem to PHPCR:
      $localFilesystem = new Filesystem(new \League\Flysystem\Local\LocalFilesystemAdapter('/local/path'));
      $remoteFilesystem = new Filesystem($adapter);
      
      foreach ($localFilesystem->listContents('', true) as $file) {
          $remoteFilesystem->write($file['path'], $localFilesystem->read($file['path']));
      }
      

Implementation Patterns

Common Workflows

  1. File Operations:

    • Upload/Download:
      $filesystem->write('documents/report.pdf', file_get_contents('local.pdf'));
      $content = $filesystem->read('documents/report.pdf');
      file_put_contents('local_copy.pdf', $content);
      
    • Streaming Large Files:
      $filesystem->writeStream('large_file.zip', fopen('local.zip', 'r'));
      $stream = $filesystem->readStream('large_file.zip');
      
  2. Metadata Handling:

    • Set custom metadata (e.g., timestamps, custom properties):
      $filesystem->write('file.txt', 'Content', [
          'timestamp' => '2023-01-01T00:00:00+0000', // Custom timestamp
          'custom:property' => 'value', // PHPCR-specific metadata
      ]);
      
  3. Directory Operations:

    • Create/Delete:
      $filesystem->createDir('subfolder');
      $filesystem->deleteDir('subfolder');
      
    • List Contents:
      foreach ($filesystem->listContents('subfolder') as $item) {
          if ($item['type'] === 'file') {
              // Handle file
          }
      }
      
  4. Symlinks (if supported by PHPCR):

    $filesystem->createSymlink('target.txt', 'link.txt');
    

Integration Tips

  • Laravel Storage: Extend Laravel’s Filesystem class to support PHPCR:

    namespace App\Storage;
    
    use League\Flysystem\Filesystem;
    use League\Flysystem\Phpcr\PhpcrAdapter;
    use Illuminate\Contracts\Filesystem as FilesystemContract;
    
    class PhpcrStorage implements FilesystemContract {
        protected $filesystem;
    
        public function __construct($repository, $rootPath = '/') {
            $this->filesystem = new Filesystem(new PhpcrAdapter($repository, $rootPath));
        }
    
        // Delegate all methods to $this->filesystem
        public function write($path, $contents, $options = []) {
            return $this->filesystem->write($path, $contents, $options);
        }
        // ... other methods (read, delete, etc.)
    }
    

    Register in config/filesystems.php:

    'phpcr' => [
        'driver' => 'phpcr',
        'repository' => function () {
            return app('phpcr.document_manager');
        },
        'root' => '/laravel-storage',
    ],
    
  • Event Handling: Use PHPCR’s event system to trigger actions (e.g., logging, notifications) when files are modified:

    $repository->getEventDispatcher()->addListener(
        'prePersist',
        function ($event) {
            $document = $event->getDocument();
            if ($document instanceof \PHPCR\NodeInterface) {
                logger()->info("File created: {$document->getPath()}");
            }
        }
    );
    
  • Caching: Cache file metadata or contents if PHPCR operations are slow:

    $cache = new \Symfony\Component\Cache\Adapter\FilesystemAdapter();
    $filesystem->read('file.txt', function () use ($cache) {
        return $cache->get('file:file.txt', function () {
            return $filesystem->read('file.txt');
        });
    });
    

Gotchas and Tips

Pitfalls

  1. PHPCR-Specific Behavior:

    • Case Sensitivity: PHPCR paths are case-sensitive. Ensure consistency when listing or accessing files.
    • Node Types: PHPCR requires nodes to be of specific types (e.g., nt:file, nt:folder). The adapter handles this, but invalid operations (e.g., writing to a non-nt:file node) may fail silently or throw exceptions.
    • Transactions: PHPCR operations are transactional. Long-running operations may time out or require manual commit:
      $repository->beginTransaction();
      try {
          $filesystem->write('file.txt', 'Content');
          $repository->commit();
      } catch (\Exception $e) {
          $repository->rollback();
          throw $e;
      }
      
  2. Metadata Limitations:

    • Not all Flysystem metadata methods are supported. For example, lastModified() may return PHPCR’s internal timestamp unless configured otherwise (see release 1.1.0).
    • Custom metadata must use PHPCR’s property syntax (e.g., jcr:mixinTypes, custom:property).
  3. Performance:

    • PHPCR operations can be slow for large files or deep hierarchies. Batch operations where possible:
      $repository->getWorkspace()->getNode('/')->setProperty('batch:flag', true);
      
  4. Archived Package:

    • The package is archived (no updates since 2018). Test thoroughly in staging before production use. Consider forking or extending if new features are needed.

Debugging

  1. Enable PHPCR Logging: Configure Doctrine PHPCR-ODM or your PHPCR client to log queries:

    $repository->getConfiguration()->setQueryLogger(new \Doctrine\ODM\PHPCR\Logging\QueryLogger());
    

    Or use Monolog:

    $logger = new \Monolog\Logger('phpcr');
    $logger->pushHandler(new \Monolog\Handler\StreamHandler('phpcr.log'));
    $repository->getConfiguration()->setLogger($logger);
    
  2. Check Node Existence: Verify nodes exist before operations to avoid NodeNotFoundException:

    if (!$filesystem->has('file.txt')) {
        $filesystem->write('file.txt', 'Content');
    }
    
  3. Handle Encoding: PHPCR may return binary data or encoded strings. Use mb_convert_encoding if needed:

    $content = mb_convert_encoding($filesystem->read('file.txt'), 'UTF-8', 'auto');
    

Extension Points

  1. Custom Adapter Configuration: Extend PhpcrAdapter to add repository-specific logic:

    class CustomPhpcrAdapter extends PhpcrAdapter {
        public function write($path, $contents, array $options = []) {
            // Add custom logic (e.g., pre-process contents)
            $contents = $this->preProcess($contents);
            return parent::write($path, $contents, $options);
        }
    
        protected function preProcess($contents) {
            // Example: Compress contents
            return gzcompress($contents);
        }
    }
    
  2. Override Metadata: Modify how metadata is handled by overriding getMetadata or setMetadata:

    class CustomPhpcrAdapter extends PhpcrAdapter {
        public function getMetadata($path) {
            $metadata = parent::getMetadata($path);
            $metadata['custom'] = $this->getCustomMetadata($path);
            return $metadata;
        }
    }
    
  3. Add PHPCR-Specific Features: Expose PHPCR features not covered by Flysystem (e.g., versioning, access control):

    $adapter->getPhpcrNode('/path')->getProperty('jcr:created');
    
  4. Fallback for Missing Features: Implement fallback logic for unsupported Flysystem methods:

    public function createSymlink($target, $link) {
        throw new \League\Flysystem\FilesystemException("
    
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.
socialdept/atp-orm
cboxdk/laravel-assistant-client
socialdept/atp-resolver
socialdept/tenant-domains
tautvydasr/blade-class-names
socialdept/color-scales
maherelgamil/controller
coleus/widgets
coleus/table
coleus/users
coleus/music
coleus/health
coleus/calendar
coleus/notes
coleus/support
coleus/settings
coleus/apps
seampact/laravel
emmyconceptng/laravel-ng-postcode
jjsquady/round-robin