Run multiple websites using the same Laravel installation while keeping tenant specific data separated for fully independent multi-domain setups.

Overview

Tenancy logo Tenancy for Laravel

Enabling awesome Software as a Service with the Laravel framework.

This is the successor of hyn/multi-tenant. Feel free to show support by starring the project following progress via twitter and backing its development over at OpenCollective.

Tests Code Style Subsplit Code Coverage

Before you start, we highly recommend you to read the extensive online documentation.

Installation

To give this package a spin, install all components at once:

$ composer require tenancy/tenancy

Otherwise make sure to selectively install the components you need and at least the framework:

$ composer require tenancy/framework

After that you'll need to decide on and configure:

Contributions

This repository is used for developing all tenancy packages.

Contributors need to use this repository for implementing code. All other repositories are READ-ONLY and overwritten on each subsplit push.

Please read our Governance documentation in case you'd like to get involved.

Local Testing

Testing the ecosystem locally is possible when:

  • You have Docker (and docker-compose) installed
  • You have Bash installed

When you have those requirements, you can simply run ./test in order to run the test in Docker containers. By default they will run the most recent versions of all our dependencies

Comments
  • Shirt designs

    Shirt designs

    Hey there,

    We're looking on setting up an interesting collection of 🤓 **shirts related to Laravel Tenancy. We could use your help with getting some additional inspiration. Once we have shirts printed with your idea we will send you one for free which will include a personal thank you note.

    In addition the idea with the highest vote will receive 50 euro as price from me personally via PayPal!


    We're looking for ideas related to tenancy, tenants, renting etc which can be related back to web development and/or this package. If it's nerdy or funny, please share!

    Please also cast your vote on the ideas you like. You are allowed to upvote your own idea.

    • One idea per comment.
    • An idea has to be pretty clear about the intent and/or suggest implementations; clarify visuals and/or texts needed.
    • Use comments to post ideas, if you want to comment on an idea use Discord.
    • Post as many ideas as you like, but give some effort. Don't spam.
    • If a team member receives the highest votes, the second best receives the price.
    • By posting your idea you allow us to use it.
    type:org 
    opened by luceos 26
  • Quarterly roadmaps

    Quarterly roadmaps

    One of the organisational improvements I have been considering it to create a quarterly roadmap, in collaboration with @tenancy/team and the community. Aside from clear objectives for the package, it also allows for effort based payout which stimulates time investment into the package. Specifying goals per category well in advance allows team members (and even collaborators) to take ownership of their tasks.

    The first thing to decide on is what this process for Quarterly Roadmaps looks like.

    Some thoughts;

    • [ ] Have staff members compile their draft todos.
    • [ ] Discuss and improve the drafts as a team.
    • [ ] Open up the draft roadmap to the public with a deadline.
    • [ ] Once the deadline is reached, finalise and put them into separate issues.
    type:org 
    opened by luceos 19
  • Initial PR for L9 Support

    Initial PR for L9 Support

    Initial PR in order to support Laravel 9.

    Major change is the dropping of the Swift Mailer in favor of the Symphony Mailer and thus the change of: replaceSwiftMailer for replaceSymfonyTransport

    opened by sniper7kills 10
  • "Database connection [tenant] not configured" error and trait SerializesModels

    Hi. I use to use the Hyn/Tenancy one, and I switch to TT since it looks very promising! Thank so much for all your work and dedication.

    Description

    I have a problem creating an event with SerializesModels trait. If I remove it, I can workaround with the error, but I can't get the user to send the Notification.

    I define an event UserCreated when a user is created, which belongs to a Tenant.

    class User extends Authenticatable implements HasLocalePreference
    {
        use Notifiable;
        use OnTenant;
        ...
    
        protected $dispatchesEvents = [
            'created' => UserCreated::class,
        ];
        ...
    }
    
    class EventServiceProvider extends ServiceProvider
    {
        protected $listen = [
            ...
            UserCreated::class => [
                SendUserCreatedNotification::class,
            ],
        ];
    }
    
    class UserCreated
    {
        use Dispatchable, InteractsWithSockets, SerializesModels;
    
        public $user;
    
        public function __construct(User $user)
        {
            $this->user = $user;
        }
    }
    

    The SendUserCreatedNotification is a listener which listens to UserCreated event and is queued.

    class SendUserCreatedNotification implements ShouldQueue
    {
        use SerializesModels;
    
        protected $user;
    
        /** @var Customer $tenant */
        public $tenant;
    
        public function __construct(User $user)
        {
            logger('[SendUserCreatedNotification::__construct] 1 ' . $user);
            $this->user = $user;
        }
    
        public function handle()
        {
            logger('[SendUserCreatedNotification] 2 user: '.$this->user);
            $this->user->notifyNow(new UserCreation());
        }
    }
    

    But it looks there is an error in the deserializing the model. May it be is trying to access to the database in order to get the User before setting the Tenant?

    This is the queue identification function (just a copy from web):

        public function tenantIdentificationByQueue(Processing $event): ?Tenant
        {
            if ($event->tenant) {
                return $event->tenant;
            }
    
            if ($event->tenant_key && $event->tenant_identifier === $this->getTenantIdentifier()) {
                $tenant = $this->newQuery()
                    ->where($this->getTenantKeyName(), $event->tenant_key)
                    ->first();
                return $tenant;
            }
    
            return null;
        }
    

    I upgrade all packages to version 1.0.1 In my tests a write a log in the facade of the library to check if it is fired, and I confirm it.

    Actual behavior

    An exception Database connection [tenant] not configured is launched.

    Expected behavior

    Continue the work of the notification.


    Information

    • tenancy/tenancy version: 101
    • laravel version: 7.20.0
    • database driver and version: tenancy/db-driver-mysql v1.0.1
    • webserver software and version: nginx/1.17.6
    • php version: 7.3

    tenancy.php config

    I don't have.


    Error log

    [2020-07-15 15:50:17] local.DEBUG: [SendUserCreatedNotification::__construct] 1 []
    [2020-07-15 15:50:18] local.ERROR: Database connection [tenant] not configured. {"exception":"[object] (InvalidArgumentException(code: 0): Database connection [tenant] not configured. at /var/www/backend/vendor/laravel/framework/src/Illuminate/Database/DatabaseManager.php:152)
    [stacktrace]
    #0 /var/www/backend/vendor/laravel/framework/src/Illuminate/Database/DatabaseManager.php(115): Illuminate\\Database\\DatabaseManager->configuration('tenant')
    #1 /var/www/backend/vendor/laravel/framework/src/Illuminate/Database/DatabaseManager.php(86): Illuminate\\Database\\DatabaseManager->makeConnection('tenant')
    #2 /var/www/backend/vendor/laravel/framework/src/Illuminate/Database/Eloquent/Model.php(1342): Illuminate\\Database\\DatabaseManager->connection('tenant')
    #3 /var/www/backend/vendor/laravel/framework/src/Illuminate/Database/Eloquent/Model.php(1308): Illuminate\\Database\\Eloquent\\Model::resolveConnection('tenant')
    #4 /var/www/backend/vendor/laravel/framework/src/Illuminate/Database/Eloquent/Model.php(1114): Illuminate\\Database\\Eloquent\\Model->getConnection()
    #5 /var/www/backend/vendor/laravel/framework/src/Illuminate/Database/Eloquent/Model.php(1031): Illuminate\\Database\\Eloquent\\Model->newBaseQueryBuilder()
    #6 /var/www/backend/vendor/laravel/framework/src/Illuminate/Database/Eloquent/Model.php(1067): Illuminate\\Database\\Eloquent\\Model->newModelQuery()
    #7 /var/www/backend/vendor/laravel/framework/src/Illuminate/Database/Eloquent/Model.php(1093): Illuminate\\Database\\Eloquent\\Model->newQueryWithoutScopes()
    #8 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/SerializesAndRestoresModelIdentifiers.php(114): Illuminate\\Database\\Eloquent\\Model->newQueryForRestoration(46)
    #9 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/SerializesAndRestoresModelIdentifiers.php(101): App\\Events\\UserCreated->getQueryForModelRestoration(Object(App\\Models\\User), 46)
    #10 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/SerializesAndRestoresModelIdentifiers.php(57): App\\Events\\UserCreated->restoreModel(Object(Illuminate\\Contracts\\Database\\ModelIdentifier))
    #11 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/SerializesModels.php(45): App\\Events\\UserCreated->getRestoredPropertyValue(Object(Illuminate\\Contracts\\Database\\ModelIdentifier))
    #12 [internal function]: App\\Events\\UserCreated->__wakeup()
    #13 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/CallQueuedHandler.php(171): unserialize('O:36:\"Illuminat...')
    #14 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/Jobs/Job.php(213): Illuminate\\Queue\\CallQueuedHandler->failed(Array, Object(InvalidArgumentException))
    #15 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/Jobs/Job.php(192): Illuminate\\Queue\\Jobs\\Job->failed(Object(InvalidArgumentException))
    #16 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/Worker.php(499): Illuminate\\Queue\\Jobs\\Job->fail(Object(InvalidArgumentException))
    #17 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/Worker.php(459): Illuminate\\Queue\\Worker->failJob(Object(Illuminate\\Queue\\Jobs\\RedisJob), Object(InvalidArgumentException))
    #18 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/Worker.php(383): Illuminate\\Queue\\Worker->markJobAsFailedIfWillExceedMaxAttempts('redis', Object(Illuminate\\Queue\\Jobs\\RedisJob), 1, Object(InvalidArgumentException))
    #19 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/Worker.php(360): Illuminate\\Queue\\Worker->handleJobException('redis', Object(Illuminate\\Queue\\Jobs\\RedisJob), Object(Illuminate\\Queue\\WorkerOptions), Object(InvalidArgumentException))
    #20 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/Worker.php(306): Illuminate\\Queue\\Worker->process('redis', Object(Illuminate\\Queue\\Jobs\\RedisJob), Object(Illuminate\\Queue\\WorkerOptions))
    #21 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/Worker.php(132): Illuminate\\Queue\\Worker->runJob(Object(Illuminate\\Queue\\Jobs\\RedisJob), 'redis', Object(Illuminate\\Queue\\WorkerOptions))
    #22 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/Console/WorkCommand.php(112): Illuminate\\Queue\\Worker->daemon('redis', 'default', Object(Illuminate\\Queue\\WorkerOptions))
    #23 /var/www/backend/vendor/laravel/framework/src/Illuminate/Queue/Console/WorkCommand.php(96): Illuminate\\Queue\\Console\\WorkCommand->runWorker('redis', 'default')
    #24 /var/www/backend/vendor/laravel/horizon/src/Console/WorkCommand.php(46): Illuminate\\Queue\\Console\\WorkCommand->handle()
    #25 [internal function]: Laravel\\Horizon\\Console\\WorkCommand->handle()
    #26 /var/www/backend/vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php(33): call_user_func_array(Array, Array)
    #27 /var/www/backend/vendor/laravel/framework/src/Illuminate/Container/Util.php(37): Illuminate\\Container\\BoundMethod::Illuminate\\Container\\{closure}()
    #28 /var/www/backend/vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php(91): Illuminate\\Container\\Util::unwrapIfClosure(Object(Closure))
    #29 /var/www/backend/vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php(35): Illuminate\\Container\\BoundMethod::callBoundMethod(Object(Illuminate\\Foundation\\Application), Array, Object(Closure))
    #30 /var/www/backend/vendor/laravel/framework/src/Illuminate/Container/Container.php(592): Illuminate\\Container\\BoundMethod::call(Object(Illuminate\\Foundation\\Application), Array, Array, NULL)
    #31 /var/www/backend/vendor/laravel/framework/src/Illuminate/Console/Command.php(134): Illuminate\\Container\\Container->call(Array)
    #32 /var/www/backend/vendor/symfony/console/Command/Command.php(258): Illuminate\\Console\\Command->execute(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Illuminate\\Console\\OutputStyle))
    #33 /var/www/backend/vendor/laravel/framework/src/Illuminate/Console/Command.php(121): Symfony\\Component\\Console\\Command\\Command->run(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Illuminate\\Console\\OutputStyle))
    #34 /var/www/backend/vendor/symfony/console/Application.php(911): Illuminate\\Console\\Command->run(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
    #35 /var/www/backend/vendor/symfony/console/Application.php(264): Symfony\\Component\\Console\\Application->doRunCommand(Object(Laravel\\Horizon\\Console\\WorkCommand), Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
    #36 /var/www/backend/vendor/symfony/console/Application.php(140): Symfony\\Component\\Console\\Application->doRun(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
    #37 /var/www/backend/vendor/laravel/framework/src/Illuminate/Console/Application.php(93): Symfony\\Component\\Console\\Application->run(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
    #38 /var/www/backend/vendor/laravel/framework/src/Illuminate/Foundation/Console/Kernel.php(129): Illuminate\\Console\\Application->run(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
    #39 /var/www/backend/artisan(37): Illuminate\\Foundation\\Console\\Kernel->handle(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
    #40 {main}
    "} 
    
    type:support 
    opened by albertosgz 9
  • identification-driver-queue Is not connecting to the tenant database returning null for db keys.

    identification-driver-queue Is not connecting to the tenant database returning null for db keys.

    Description I am using tenancy dev for my project and I am facing issues with the queue handle function to connect to tenant DB. ..


    Actual behavior Is not resolving the db config for the tenant connection and returning config keys null.

    image

    ..

    Expected behavior It should be connected to the tenant database in the queue job. image

    ..


    Information

    • tenancy/tenancy version: 1.*
    • laravel version: ^7.0
    • database driver and version: Mysql, 5.6
    • webserver software and version: XAMPP
    • php version: 7.3

    tenancy.php config

    
    

    Error log

    #0 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Connectors\\ConnectionFactory.php(180): Illuminate\\Database\\Connectors\\ConnectionFactory->parseHosts(Array)
    #1 [internal function]: Illuminate\\Database\\Connectors\\ConnectionFactory->Illuminate\\Database\\Connectors\\{closure}()
    #2 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Connection.php(926): call_user_func(Object(Closure))
    #3 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Connection.php(961): Illuminate\\Database\\Connection->getPdo()
    #4 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Connection.php(405): Illuminate\\Database\\Connection->getReadPdo()
    #5 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Connection.php(331): Illuminate\\Database\\Connection->getPdoForSelect(true)
    #6 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Connection.php(664): Illuminate\\Database\\Connection->Illuminate\\Database\\{closure}('select * from `...', Array)
    #7 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Connection.php(631): Illuminate\\Database\\Connection->runQueryCallback('select * from `...', Array, Object(Closure))
    #8 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Connection.php(339): Illuminate\\Database\\Connection->run('select * from `...', Array, Object(Closure))
    #9 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Query\\Builder.php(2260): Illuminate\\Database\\Connection->select('select * from `...', Array, true)
    #10 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Query\\Builder.php(2248): Illuminate\\Database\\Query\\Builder->runSelect()
    #11 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Query\\Builder.php(2743): Illuminate\\Database\\Query\\Builder->Illuminate\\Database\\Query\\{closure}()
    #12 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Query\\Builder.php(2249): Illuminate\\Database\\Query\\Builder->onceWithColumns(Array, Object(Closure))
    #13 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Eloquent\\Builder.php(548): Illuminate\\Database\\Query\\Builder->get(Array)
    #14 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Eloquent\\Builder.php(532): Illuminate\\Database\\Eloquent\\Builder->getModels(Array)
    #15 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Database\\Concerns\\BuildsQueries.php(143): Illuminate\\Database\\Eloquent\\Builder->get(Array)
    #16 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\app\\Jobs\\Tenent\\DisburseAttendancePointJob.php(62): Illuminate\\Database\\Eloquent\\Builder->first()
    #17 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Container\\BoundMethod.php(36): App\\Jobs\\Tenent\\DisburseAttendancePointJob->handle()
    #18 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Container\\Util.php(37): Illuminate\\Container\\BoundMethod::Illuminate\\Container\\{closure}()
    #19 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Container\\BoundMethod.php(93): Illuminate\\Container\\Util::unwrapIfClosure(Object(Closure))
    #20 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Container\\BoundMethod.php(37): Illuminate\\Container\\BoundMethod::callBoundMethod(Object(Illuminate\\Foundation\\Application), Array, Object(Closure))
    #21 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Container\\Container.php(596): Illuminate\\Container\\BoundMethod::call(Object(Illuminate\\Foundation\\Application), Array, Array, NULL)
    #22 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Bus\\Dispatcher.php(94): Illuminate\\Container\\Container->call(Array)
    #23 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Pipeline\\Pipeline.php(128): Illuminate\\Bus\\Dispatcher->Illuminate\\Bus\\{closure}(Object(App\\Jobs\\Tenent\\DisburseAttendancePointJob))
    #24 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Pipeline\\Pipeline.php(103): Illuminate\\Pipeline\\Pipeline->Illuminate\\Pipeline\\{closure}(Object(App\\Jobs\\Tenent\\DisburseAttendancePointJob))
    #25 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Bus\\Dispatcher.php(98): Illuminate\\Pipeline\\Pipeline->then(Object(Closure))
    #26 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Queue\\CallQueuedHandler.php(83): Illuminate\\Bus\\Dispatcher->dispatchNow(Object(App\\Jobs\\Tenent\\DisburseAttendancePointJob), false)
    #27 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Pipeline\\Pipeline.php(128): Illuminate\\Queue\\CallQueuedHandler->Illuminate\\Queue\\{closure}(Object(App\\Jobs\\Tenent\\DisburseAttendancePointJob))
    #28 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Pipeline\\Pipeline.php(103): Illuminate\\Pipeline\\Pipeline->Illuminate\\Pipeline\\{closure}(Object(App\\Jobs\\Tenent\\DisburseAttendancePointJob))
    #29 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Queue\\CallQueuedHandler.php(85): Illuminate\\Pipeline\\Pipeline->then(Object(Closure))
    #30 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Queue\\CallQueuedHandler.php(59): Illuminate\\Queue\\CallQueuedHandler->dispatchThroughMiddleware(Object(Illuminate\\Queue\\Jobs\\DatabaseJob), Object(App\\Jobs\\Tenent\\DisburseAttendancePointJob))
    #31 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Queue\\Jobs\\Job.php(98): Illuminate\\Queue\\CallQueuedHandler->call(Object(Illuminate\\Queue\\Jobs\\DatabaseJob), Array)
    #32 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Queue\\Worker.php(356): Illuminate\\Queue\\Jobs\\Job->fire()
    #33 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Queue\\Worker.php(306): Illuminate\\Queue\\Worker->process('database', Object(Illuminate\\Queue\\Jobs\\DatabaseJob), Object(Illuminate\\Queue\\WorkerOptions))
    #34 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Queue\\Worker.php(132): Illuminate\\Queue\\Worker->runJob(Object(Illuminate\\Queue\\Jobs\\DatabaseJob), 'database', Object(Illuminate\\Queue\\WorkerOptions))
    #35 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Queue\\Console\\WorkCommand.php(112): Illuminate\\Queue\\Worker->daemon('database', 'default', Object(Illuminate\\Queue\\WorkerOptions))
    #36 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Queue\\Console\\WorkCommand.php(96): Illuminate\\Queue\\Console\\WorkCommand->runWorker('database', 'default')
    #37 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Container\\BoundMethod.php(36): Illuminate\\Queue\\Console\\WorkCommand->handle()
    #38 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Container\\Util.php(37): Illuminate\\Container\\BoundMethod::Illuminate\\Container\\{closure}()
    #39 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Container\\BoundMethod.php(93): Illuminate\\Container\\Util::unwrapIfClosure(Object(Closure))
    #40 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Container\\BoundMethod.php(37): Illuminate\\Container\\BoundMethod::callBoundMethod(Object(Illuminate\\Foundation\\Application), Array, Object(Closure))
    #41 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Container\\Container.php(596): Illuminate\\Container\\BoundMethod::call(Object(Illuminate\\Foundation\\Application), Array, Array, NULL)
    #42 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Console\\Command.php(134): Illuminate\\Container\\Container->call(Array)
    #43 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\symfony\\console\\Command\\Command.php(258): Illuminate\\Console\\Command->execute(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Illuminate\\Console\\OutputStyle))
    #44 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Console\\Command.php(121): Symfony\\Component\\Console\\Command\\Command->run(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Illuminate\\Console\\OutputStyle))
    #45 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\symfony\\console\\Application.php(920): Illuminate\\Console\\Command->run(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
    #46 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\symfony\\console\\Application.php(266): Symfony\\Component\\Console\\Application->doRunCommand(Object(Illuminate\\Queue\\Console\\WorkCommand), Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
    #47 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\symfony\\console\\Application.php(142): Symfony\\Component\\Console\\Application->doRun(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
    #48 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Console\\Application.php(93): Symfony\\Component\\Console\\Application->run(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
    #49 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\vendor\\laravel\\framework\\src\\Illuminate\\Foundation\\Console\\Kernel.php(129): Illuminate\\Console\\Application->run(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
    #50 M:\\hardwork\\htdocs\\mt-projects\\lms\\sms_lms_development\\artisan(37): Illuminate\\Foundation\\Console\\Kernel->handle(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
    #51 {main}
    "}
    
    opened by SaurabhDwi 8
  • Single connection pool

    Single connection pool

    Can I use tenancy for multi-tenant app uses a single connection pool? I don't want to create a connection pool per tenant (just want a single connection pool for multi-tenant) In PostgreSQL usually we use a schema per tenant which means the app uses a single database with multi schemas.

    type:question 
    opened by mbnoimi 8
  • Unable to grant permission to new user on new database

    Unable to grant permission to new user on new database

    Description

    I am using latest Laravel with sail, so mysql is in docker container. MYSQL_ROOT_HOST is % which I override using Configuring event hook. I also set extra PRIVILEGES (SELECT, CREATE, RELOAD, CREATE USER) for default user sail Please note that t24 is newly created database.


    Actual behavior   tenancy / tenancy / src / Database / Mysql / Driver / Mysql.php : 59 SQLSTATE[42000]: Syntax error or access violation: 1044 Access denied for user 'sail'@'%' to database 't24'

    Expected behavior

    Privileges are granted successfully.


    Information

    • tenancy/tenancy version: 2.x
    • laravel version: 9.24.x
    • database driver and version: mysql-server 8
    • webserver software and version:
    • php version: 8.1.8
    opened by yasirmturk 7
  • Ambiguous class resolution warning: duplicated interfaces

    Ambiguous class resolution warning: duplicated interfaces

    Following the doc to setup the project, it seems there is interface duplication between the main framework and the sub packages causing some warnings

    Warning: Ambiguous class resolution, "Tenancy\Identification\Drivers\Queue\Contracts\IdentifiesByQueue" was found in both "vendor/tenancy/identification-driver-queue/Contracts/IdentifiesByQueue.php" and "vendor/tenancy/tenancy/src/Identification/Queue/Contracts/IdentifiesByQueue.php", the first will be used.
    Warning: Ambiguous class resolution, "Tenancy\Identification\Drivers\Queue\Events\Processing" was found in both "vendor/tenancy/identification-driver-queue/Events/Processing.php" and "vendor/tenancy/tenancy/src/Identification/Queue/Events/Processing.php", the first will be used.
    Warning: Ambiguous class resolution, "Tenancy\Identification\Drivers\Queue\Middleware\ReadTenantFromQueuePayload" was found in both "vendor/tenancy/identification-driver-queue/Middleware/ReadTenantFromQueuePayload.php" and "vendor/tenancy/tenancy/src/Identification/Queue/Middleware/ReadTenantFromQueuePayload.php", the first will be used.
    Warning: Ambiguous class resolution, "Tenancy\Identification\Drivers\Queue\Middleware\SaveTenantOnQueuePayload" was found in both "vendor/tenancy/identification-driver-queue/Middleware/SaveTenantOnQueuePayload.php" and "vendor/tenancy/tenancy/src/Identification/Queue/Middleware/SaveTenantOnQueuePayload.php", the first will be used.
    Warning: Ambiguous class resolution, "Tenancy\Identification\Drivers\Queue\Providers\IdentificationProvider" was found in both "vendor/tenancy/identification-driver-queue/Providers/IdentificationProvider.php" and "vendor/tenancy/tenancy/src/Identification/Queue/Providers/IdentificationProvider.php", the first will be used.
    

    Here is my composer require config

        "require": {
            "php": "^7.3",
            "ext-json": "*",
            "laravel/framework": "^7",
            "tenancy/affects-configs": "^1.0",
            "tenancy/affects-connections": "^1.0",
            "tenancy/affects-filesystems": "^1.0",
            "tenancy/affects-logs": "^1.0",
            "tenancy/affects-mails": "^1.0",
            "tenancy/affects-urls": "^1.0",
            "tenancy/affects-views": "^1.0",
            "tenancy/db-driver-mysql": "^1.0",
            "tenancy/framework": "^1.0",
            "tenancy/hooks-database": "^1.0",
            "tenancy/identification-driver-http": "^1.0",
            "tenancy/identification-driver-queue": "^1.0"
        }
    

    Relevant composer lock.json

    
            {
                "name": "tenancy/identification-driver-queue",
                "version": "v1.0.1",
                "source": {
                    "type": "git",
                    "url": "https://github.com/tenancy/identification-driver-queue.git",
                    "reference": "d75d89dd2435da729e128d3976e5dc414d0fc065"
                },
                "dist": {
                    "type": "zip",
                    "url": "https://api.github.com/repos/tenancy/identification-driver-queue/zipball/d75d89dd2435da729e128d3976e5dc414d0fc065",
                    "reference": "d75d89dd2435da729e128d3976e5dc414d0fc065",
                    "shasum": ""
                },
                "require": {
                    "tenancy/framework": "*"
                },
                "type": "library",
                "extra": {
                    "laravel": {
                        "providers": [
                            "Tenancy\\Identification\\Drivers\\Queue\\Providers\\IdentificationProvider"
                        ]
                    }
                },
                "autoload": {
                    "psr-4": {
                        "Tenancy\\Identification\\Drivers\\Queue\\": ""
                    }
                },
                "notification-url": "https://packagist.org/downloads/",
                "license": [
                    "MIT"
                ],
                "authors": [
                    {
                        "name": "Arlon Antonius",
                        "email": "[email protected]",
                        "homepage": "https://arlon.dev"
                    }
                ],
                "description": "The tenancy/tenancy identification driver for queues",
                "keywords": [
                    "identification",
                    "queue",
                    "tenancy"
                ],
                "time": "2020-07-08T18:48:47+00:00"
            },
            {
                "name": "tenancy/tenancy",
                "version": "v1.0.1",
                "source": {
                    "type": "git",
                    "url": "https://github.com/tenancy/tenancy.git",
                    "reference": "be9dae407ad4f2600a3665b7abab31c5b8f1c6ba"
                },
                "dist": {
                    "type": "zip",
                    "url": "https://api.github.com/repos/tenancy/tenancy/zipball/be9dae407ad4f2600a3665b7abab31c5b8f1c6ba",
                    "reference": "be9dae407ad4f2600a3665b7abab31c5b8f1c6ba",
                    "shasum": ""
                },
                "require": {
                    "doctrine/dbal": "^2.9",
                    "laravel/framework": "^7.0"
                },
                "replace": {
                    "tenancy/affects-broadcasts": "self.version",
                    "tenancy/affects-cache": "self.version",
                    "tenancy/affects-configs": "self.version",
                    "tenancy/affects-connections": "self.version",
                    "tenancy/affects-filesystems": "self.version",
                    "tenancy/affects-logs": "self.version",
                    "tenancy/affects-mails": "self.version",
                    "tenancy/affects-models": "self.version",
                    "tenancy/affects-routes": "self.version",
                    "tenancy/affects-urls": "self.version",
                    "tenancy/affects-views": "self.version",
                    "tenancy/db-driver-mysql": "self.version",
                    "tenancy/db-driver-sqlite": "self.version",
                    "tenancy/framework": "self.version",
                    "tenancy/hooks-database": "self.version",
                    "tenancy/hooks-migration": "self.version",
                    "tenancy/identification-driver-console": "self.version",
                    "tenancy/identification-driver-environment": "self.version",
                    "tenancy/identification-driver-http": "self.version",
                    "tenancy/testing": "self.version"
                },
                "require-dev": {
                    "fzaninotto/faker": "^1.7",
                    "laminas/laminas-diactoros": "^1.0",
                    "laravel/laravel": "^7.0",
                    "mockery/mockery": "^1.0",
                    "phpunit/phpunit": "^8.0",
                    "psalm/plugin-laravel": "^1.1",
                    "squizlabs/php_codesniffer": "^3.3"
                },
                "type": "library",
                "extra": {
                    "laravel": {
                        "providers": [
                            "Tenancy\\Providers\\TenancyProvider",
                            "Tenancy\\Affects\\Broadcasts\\Provider",
                            "Tenancy\\Affects\\Cache\\Provider",
                            "Tenancy\\Affects\\Configs\\Provider",
                            "Tenancy\\Affects\\Connections\\Provider",
                            "Tenancy\\Affects\\Filesystems\\Provider",
                            "Tenancy\\Affects\\Logs\\Provider",
                            "Tenancy\\Affects\\Mails\\Provider",
                            "Tenancy\\Affects\\Models\\Provider",
                            "Tenancy\\Affects\\Routes\\Provider",
                            "Tenancy\\Affects\\URLs\\Provider",
                            "Tenancy\\Affects\\Views\\Provider",
                            "Tenancy\\Identification\\Drivers\\Console\\Providers\\IdentificationProvider",
                            "Tenancy\\Identification\\Drivers\\Environment\\Providers\\IdentificationProvider",
                            "Tenancy\\Identification\\Drivers\\Http\\Providers\\IdentificationProvider",
                            "Tenancy\\Identification\\Drivers\\Queue\\Providers\\IdentificationProvider"
                        ],
                        "aliases": {
                            "Tenancy": "Tenancy\\Facades\\Tenancy"
                        }
                    }
                },
                "autoload": {
                    "psr-4": {
                        "Tenancy\\": "src/Tenancy",
                        "Tenancy\\Affects\\": "src/Affects",
                        "Tenancy\\Database\\Drivers\\": "src/Database",
                        "Tenancy\\Hooks\\": "src/Hooks",
                        "Tenancy\\Identification\\Drivers\\": "src/Identification"
                    }
                },
                "notification-url": "https://packagist.org/downloads/",
                "license": [
                    "MIT"
                ],
                "authors": [
                    {
                        "name": "Arlon Antonius",
                        "email": "[email protected]",
                        "homepage": "https://arlon.dev"
                    }
                ],
                "description": "Creating multi tenant saas from your Laravel app with ease",
                "keywords": [
                    "aws",
                    "gce",
                    "laravel",
                    "multi-tenant",
                    "saas",
                    "tenancy"
                ],
                "time": "2020-07-10T13:47:59+00:00"
            },
    

    This issue arise after installing the package tenancy/identification-driver-queue that's not included in tenancy\tenancy (according to composer)

    Reproduction

    composer require tenancy/tenancy
    composer require tenancy/identification-driver-queue
    

    Warning will popup after the end of the second command (if you implement the interfaces in your models beforehand)

    opened by Tofandel 7
  • [Q1] Roadmap

    [Q1] Roadmap

    Roadmap

    Organisation

    • [X] Create Roadmap Draft
    • [x] Maintain roadmap
    • [x] Discuss Hyn/Multi-Tenant Migration
    • [x] Consider renaming of Tenancy / Tenancy and Tenancy / Framework
    • [x] Check advantages of disabling auto discovery

    Tenancy / Tenancy

    • [x] Start work on Beta Release
    • [x] Add Caching #20
    • [x] Code Coverage to 70+%
    • [x] Tenant Disk Package #19
    • [x] Tenant Config Package #2

    Tenancy / Docs

    • [x] Start Documentation on Tenancy Beta Release
    type:org 
    opened by ArlonAntonius 7
  • Landing Page Banner Concept

    Landing Page Banner Concept

    I need some help regarding the banner for the landing page, some thoughts and idea would be very helpful. Here's the current one i've been working on...

    screen shot 2018-05-15 at 9 27 34 am

    The given illustration isn't really fitting the product, so we're looking for some inspiration what to put in its place. We want the best result for the landing page so any suggestions would be very helpful.

    opened by paulotra 7
  • Not install with PHP 7.4.5

    Not install with PHP 7.4.5

    Description

    composer require tenancy/tenancy

    not work


    Actual behavior

    \Using version ^1.0 for tenancy/tenancy ./composer.json has been updated Loading composer repositories with package information Updating dependencies (including require-dev) Package operations: 1 install, 0 updates, 0 removals

    • Installing tenancy/tenancy (v1.0.0): Downloading (100%)
      Writing lock file Generating optimized autoload files

    Illuminate\Foundation\ComposerScripts::postAutoloadDump @php artisan package:discover --ansi

    In TenancyProvider.php line 71:

    Trying to access array offset on value of type null

    Script @php artisan package:discover --ansi handling the post-autoload-dump event returned with error code 1

    Installation failed, reverting ./composer.json to its original content.

    Expected behavior

    Package manifest generated successfully.


    Information

    • tenancy/tenancy version: 1.0
    • laravel version: 7.0
    • database driver and version: -
    • webserver software and version: -
    • php version: 7.4.5

    Error log

    In TenancyProvider.php line 71:
                                                           
      Trying to access array offset on value of type null  
    
    type:support 
    opened by xerron 6
  • Since moving to Laravel 9, this issue has returned with readyNow() method missing

    Since moving to Laravel 9, this issue has returned with readyNow() method missing

    Call to undefined method Illuminate\Queue\RedisQueue::readyNow() has popped up again for me since upgrading to Laravel 9. If we do a composer install --no-dev it errors. But if we include the dev dependencies it errors out.

    ..


    We use the following packages

        "tenancy/hooks-database": "^2.0",
        "tenancy/hooks-migration": "^2.0",
        "tenancy/identification-driver-console": "^2.0",
        "tenancy/identification-driver-http": "^2.0",
        "tenancy/identification-driver-queue": "^2.0",
    
    opened by bretto36 0
  • Allow users to specify the old database themselves using current default logic

    Allow users to specify the old database themselves using current default logic

    Fixes #212

    This is a possible solution, but I'm not completely sure yet if this is the best solution. It's sort of a breaking change; if people have custom logic and have not specified oldDatabase, but have specified oldUsername, than this is becoming an issue.

    opened by ArlonAntonius 1
  • Update GHA dependencies and add Dependabot

    Update GHA dependencies and add Dependabot

    • We're getting warnings on some builds due to old versions of a few actions
    • Dependabot is a great tool provided by GitHub that allows us to automatically get PRs for GitHub Actions
    opened by ArlonAntonius 1
  • Bug: Make sure the tenant connection is not used for moving tables

    Bug: Make sure the tenant connection is not used for moving tables

    Fixes #239

    Short explanation: In order to move the tables of the tenant to the right database (if the database was updated), we would instantiate a temporary connection on the specified TenantConnectionName. This would override the current tenant connection. Then we would empty that connection as we want to make sure we do not leave the connection open as it would form a security risk. Resulting in there not being a Tenant Connection anymore.

    This fix simply uses a completely random connection name.

    opened by ArlonAntonius 1
  • Test cases on a multi database tenants on sqlite memory fails in many ways.

    Test cases on a multi database tenants on sqlite memory fails in many ways.

    Description In a healthy and working tenant multi database system running tenancy with MySQL, when I tried to run unit test cases on sqlite :memory: I got all sort of erros. ..


    Actual behavior Trying directly to run test cases, it fails on migration since I create a default tenant when I migrate. It calls the mysql driver instead of the sqlite:

     SQLSTATE[HY000]: General error: 1 near "USER": syntax error (SQL: CREATE USER IF NOT EXISTS `erp_1`@'%' IDENTIFIED BY 'aaaaa')
    
     1   [internal]:0
          Tenancy\Hooks\Database\Support\QueryManager::Tenancy\Database\Drivers\Mysql\Driver\{closure}() 
    

    Changing the database resolver to check app.config to force sqlite pops error on the username:

    if(config('app.env') === 'testing') {
        $event->useConnection('sqlite', [
            'database' => ':memory:'
        ]);
    } else {
        $event->useConnection('mysql', $event->defaults($event->tenant));
    } 
    
    
       ErrorException
    
      Undefined index: username
    
      at C:\Users\Aislan\Work\eclipse\erp\vendor\tenancy\tenancy\src\Database\Mysql\Driver\Mysql.php:56
         52â–•         event(new Events\Creating($tenant, $config, $this));
         53â–•
         54â–•         $result = $this->queryManager->setConnection($this->system($tenant))
         55â–•             ->process(function () use ($config) {
      ➜  56▕                 $this->statement("CREATE USER IF NOT EXISTS `{$config['username']}`@'{$config['host']}' IDENTIFIED BY '{$config['password']}'");
         57â–•                 $this->statement("CREATE DATABASE `{$config['database']}`");
         58â–•                 $this->statement("GRANT ALL ON `{$config['database']}`.* TO `{$config['username']}`@'{$config['host']}'");
         59â–•             })
         60â–•             ->getStatus();
    
      1   C:\Users\Aislan\Work\eclipse\erp\vendor\tenancy\tenancy\src\Database\Mysql\Driver\Mysql.php:56
          Illuminate\Foundation\Bootstrap\HandleExceptions::handleError("Undefined index: username", "C:\Users\Aislan\Work\eclipse\erp\vendor\tenancy\tenancy\src\Database\Mysql\Driver\Mysql.php", [])
    
    

    Last, I tried to remove MySQL driver and keep only sqlite driver, but I got an error on database creation, since it tries to touch it:

      ErrorException
    
      touch(): Unable to create file :memory: because No such file or directory
    
      at C:\Users\Aislan\Work\eclipse\erp\vendor\tenancy\tenancy\src\Database\Sqlite\Driver\Sqlite.php:40
         36â–•         $config = $this->configure($tenant);
         37â–•
         38â–•         event(new Events\Creating($tenant, $config, $this));
         39â–•
      ➜  40▕         $result = touch($config['database']);
         41â–•
         42â–•         event(new Events\Created($tenant, $this, $result));
         43â–•
         44â–•         return $result;
    
      1   C:\Users\Aislan\Work\eclipse\erp\vendor\tenancy\tenancy\src\Database\Sqlite\Driver\Sqlite.php:40
          touch(":memory:")
    

    ..

    Expected behavior Expect to be able to run test cases without issues. ..


    Information

    • tenancy/tenancy version: 1.3.0
    • laravel version: 8.68.1
    • database driver and version: Mysql and Sqlite
    • webserver software and version: Apache
    • php version: 7.4

    driver:database 
    opened by aislanfoina 2
Releases(v1.3.0)
Owner
Tenancy
The SaaS multi-tenant toolkit for @laravel.
Tenancy
Run multiple websites using the same Laravel installation while keeping tenant specific data separated for fully independent multi-domain setups, previously

Run multiple websites using the same Laravel installation while keeping tenant specific data separated for fully independent multi-domain setups, previously

Tenancy 2.4k Jan 3, 2023
A Laravel package that allows you to use multiple ".env" files in a precedent manner. Use ".env" files per domain (multi-tentant)!

Laravel Multi ENVs Use multiple .envs files and have a chain of precedence for the environment variables in these different .envs files. Use the .env

Allyson Silva 48 Dec 29, 2022
Tiny hands is a Laravel multi-tenant boilerplate with SPA and i18n.

About Tiny Hands Tiny hands is a Laravel multi-tenant boilerplate with SPA and i18n using the following technology stack: Backend Laravel 8.0 API with

Bertrand Kintanar 12 Jun 23, 2022
Easily integrate single-database multi tenant features into your Laravel application

Laravel Tenant Aware Easily integrate single-database multi tenant features into your Laravel application. Installation You can install the package vi

H-FARM Innovation 9 Dec 21, 2022
Taskpm - Run multi tasks by PHP multi process

php-pkg-template Run multi tasks by PHP multi process Install composer composer require phppkg/taskpm Usage github: use the template for quick create

PHPPkg 2 Dec 20, 2021
A Laravel extension for using a laravel application on a multi domain setting

Laravel Multi Domain An extension for using Laravel in a multi domain setting Description This package allows a single Laravel installation to work wi

null 658 Jan 6, 2023
Simple project to send bulk comma-separated emails using laravel and messenger module from quick admin panel generator.

About Laravel Laravel is a web application framework with expressive, elegant syntax. We believe development must be an enjoyable and creative experie

Novath Thomas 1 Dec 1, 2021
Livewire component that provides you with a modal that supports multiple child modals while maintaining state.

About LivewireUI Modal LivewireUI Modal is a Livewire component that provides you with a modal that supports multiple child modals while maintaining s

Livewire UI 806 Jan 6, 2023
Livewire component that provides you with a modal that supports multiple child modals while maintaining state.

About Wire Elements Modal Wire Elements Modal is a Livewire component that provides you with a modal that supports multiple child modals while maintai

Wire Elements 806 Jan 6, 2023
An example of multi-domain/subdomain app in Laravel.

?? UPDATE A better example with online demo: https://github.com/laravel-101/multi-domain-laravel-app Multi-Domain Laravel App An example of multi-doma

DigitalWheat 204 Dec 27, 2022
This package enables you to create and run a fully functioning WebSocket server in your Laravel app.

This package enables you to create and run a fully functioning WebSocket server in your Laravel app. It can optionally receive messages broadcast over ZeroMQ.

Asked.io 181 Oct 6, 2022
Keeping Your Laravel Forms Awake.

Caffeine for Laravel Supporting This Package This is an MIT-licensed open source project with its ongoing development made possible by the support of

GeneaLabs, LLC 839 Dec 22, 2022
LaravelFly is a safe solution to speeds up new or old Laravel 5.5+ projects, with preloading and coroutine, while without data pollution or memory leak

Would you like php 7.4 Preloading? Would you like php coroutine? Today you can use them with Laravel because of Swoole. With LaravalFly, Laravel will

null 456 Dec 21, 2022
Chrome extension to generate Laravel integration tests while using your app.

Laravel TestTools Check out the introduction post about the chrome extension. Installation git clone [email protected]:mpociot/laravel-testtools.git # i

Marcel Pociot 473 Nov 1, 2022
Barcode generator in PHP that is easy to use, non-bloated and framework independent.

PHP Barcode Generator This is an easy to use, non-bloated, framework independent, barcode generator in PHP. It creates SVG, PNG, JPG and HTML images,

Picqer 1.4k Jan 6, 2023
Easy alignment of multiple selections and multi-line selections

Sublime Alignment A simple key-binding for aligning multi-line and multiple selections in Sublime Text 2. Please see http://wbond.net/sublime_packages

Will Bond 516 Dec 28, 2022
Hashtopolis is a multi-platform client-server tool for distributing hashcat tasks to multiple computers.

Hashtopolis is a multi-platform client-server tool for distributing hashcat tasks to multiple computers. The main goals for Hashtopolis's development are portability, robustness, multi-user support, and multiple groups management.

Hashtopolis 1.1k Jan 4, 2023
This Laravel package merges staudenmeir/eloquent-param-limit-fix and staudenmeir/laravel-adjacency-list to allow them being used in the same model.

This Laravel package merges staudenmeir/eloquent-param-limit-fix and staudenmeir/laravel-adjacency-list to allow them being used in the same model.

Jonas Staudenmeir 5 Jan 6, 2023
Renamify is a package for Laravel used to rename a file before uploaded to prevent replacing exists file which has the same name to this new uploaded file.

Renamify Laravel package for renaming file before uploaded on server. Renamify is a package for Laravel used to rename a file before uploaded to preve

MB'DUSENGE Callixte 2 Oct 11, 2022