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

Sf Doctrine Prefix Bundle Laravel Package

avanzu/sf-doctrine-prefix-bundle

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Setup

  1. Installation

    composer require avanzu/sf-doctrine-prefix-bundle:dev-master
    

    (Note: Use a stable version if available; dev-master is unstable.)

  2. Enable the Bundle Add to config/bundles.php (Symfony 4+):

    return [
        // ...
        Avanzu\DoctrinePrefixBundle\AvanzuDoctrinePrefixBundle::class => ['all' => true],
    ];
    
  3. Configure Prefix Add to config/packages/avanzu_doctrine_prefix.yaml (Symfony 4+):

    avanzu_doctrine_prefix:
        prefix: "app_"  # Applies to all entity tables
    
  4. Verify Run migrations or inspect generated SQL to confirm tables are prefixed (e.g., app_users instead of users).


First Use Case: Multi-Tenant Isolation

Prefix tables by tenant ID dynamically:

# config/packages/avanzu_doctrine_prefix.yaml
avanzu_doctrine_prefix:
    prefix: "%tenant_id%"  # Use Symfony's parameter system

Inject TenantService to set %tenant_id% via dependency injection.


Implementation Patterns

1. Static vs. Dynamic Prefixes

  • Static: Hardcode prefixes in config.yml (e.g., app_).
  • Dynamic: Use Symfony parameters or environment variables:
    prefix: "%env(DB_PREFIX)%"  # .env: DB_PREFIX=tenant1_
    

2. Entity-Level Overrides

Exclude specific entities from prefixing by annotating:

/**
 * @ORM\Entity
 * @ORM\Table(name="users")  // Overrides prefix
 */
class User {}

3. Integration with Migrations

Use doctrine:migrations:execute after enabling the bundle. Prefixes apply retroactively to existing tables (if manually renamed).

4. Testing

Mock the prefix service in tests:

$prefixService = $this->createMock(PrefixService::class);
$prefixService->method('getPrefix')->willReturn('test_');
$container->set(PrefixService::class, $prefixService);

5. Custom Prefix Logic

Extend the bundle by creating a custom PrefixService:

class CustomPrefixService implements PrefixServiceInterface {
    public function getPrefix(): string {
        return 'custom_' . $this->getTenantId();
    }
}

Register as a service and override the bundle’s default.


Gotchas and Tips

Pitfalls

  1. Schema Mismatches

    • If tables already exist, manually rename them to match the prefix or drop/recreate them.
    • Fix: Use doctrine:schema:update --force cautiously.
  2. Case Sensitivity

    • Prefixes are case-sensitive in some databases (e.g., PostgreSQL). Ensure consistency:
      prefix: "APP_"  # Force uppercase if needed
      
  3. Foreign Key Constraints

    • Prefixing breaks FK references unless all related tables share the same prefix.
    • Workaround: Use a single prefix for all entities in a tenant.
  4. Legacy Code

    • Hardcoded table names in queries (e.g., SELECT * FROM users) will fail.
    • Solution: Use Doctrine’s EntityManager or DQL for queries.
  5. Dev vs. Prod Conflicts

    • Avoid mixing prefixed and non-prefixed tables in the same database.
    • Tip: Use separate databases for dev/prod or suffixes like _dev.

Debugging Tips

  1. Enable SQL Logging

    doctrine:
        dbal:
            logging: true
            logging_format: "%%timestamp%% %%sql%%"
    

    Check var/log/dev.log for generated SQL to verify prefixes.

  2. Inspect Metadata

    $metadata = $entityManager->getClassMetadata(User::class);
    echo $metadata->getTableName();  // Should show prefixed name
    
  3. Clear Cache After changing prefixes, run:

    php bin/console cache:clear
    

Extension Points

  1. Custom Prefix Generator Implement Avanzu\DoctrinePrefixBundle\Service\PrefixServiceInterface and bind it as a service.

  2. Exclude Namespaces Configure excluded entities in config.yml:

    avanzu_doctrine_prefix:
        prefix: "app_"
        exclude_namespaces: ["App\Entity\Admin"]  # Skip these entities
    
  3. Database-Specific Quirks Override the PrefixGenerator for edge cases (e.g., MySQL reserved words):

    class MySqlPrefixGenerator implements PrefixGeneratorInterface {
        public function generate(string $prefix, string $tableName): string {
            return str_replace(['_', '-'], '__', $prefix) . $tableName;
        }
    }
    

Pro Tips

  • Combine with Doctrine Extensions: Use with StofDoctrineExtensionsBundle for soft deletes while maintaining prefixes.
  • CI/CD Safety: Add a pre-deploy check to validate all queries use Doctrine’s ORM.
  • Documentation: Note the prefix scheme in your team’s database schema docs to avoid confusion.
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.
comsave/common
alecsammon/php-raml-parser
chrome-php/wrench
lendable/composer-license-checker
typhoon/reflection
mesilov/moneyphp-percentage
mike42/gfx-php
bookdown/themes
aura/view
aura/html
aura/cli
povils/phpmnd
nayjest/manipulator
omnipay/tests
psr-mock/http-message-implementation
psr-mock/http-factory-implementation
psr-mock/http-client-implementation
voku/email-check
voku/urlify
rtheunissen/guzzle-log-middleware