Introduction
On my machine, I’ve a bundle folder. From right here I make a folder for every bundle.
I then load these into my initiatives utilizing composer.json
Within the require part load the bundle by its vendor identify adopted by the bundle identify then utilizing @dev
to load the principle model
"dcblogdev/laravel-module-generator": "@dev"
Subsequent with a purpose to load this, inform composer the place to seek out the information domestically utilizing a repository path:
"repositories": [
{
"type": "path",
"url": "../../packages/laravel-module-generator"
}
]
On this case, I would like composer to look two folders above the present Laravel venture.
Now run composer replace to put in the bundle into your venture.
Whats good about this method is you are able to do this with third-party packages. That is helpful as you possibly can run assessments and add options that you just plan to boost pull requests for.
Construct a bundle
You need to use bundle starter kits similar to https://github.com/spatie/package-skeleton-laravel
I have a tendency to construct packages from scratch or copy certainly one of my present packages and take away what I dont want.
On this submit, I am imagining constructing a bundle known as laravel-tags.
The folder construction shall be:
license.md
For the license, I exploit The MIT licence which permits customers to freely use, copy, modify, merge, publish, distribute, sublicense, and promote the software program and its related documentation.
this file comprises:
# The license
The MIT License (MIT)
Copyright (c) 2023 dcblogdev
Permission is hereby granted, freed from cost, to any particular person acquiring a duplicate
of this software program and related documentation information (the "Software program"), to deal
within the Software program with out restriction, together with with out limitation the rights
to make use of, copy, modify, merge, publish, distribute, sublicense, and/or promote
copies of the Software program, and to allow individuals to whom the Software program is
furnished to take action, topic to the next situations:
The above copyright discover and this permission discover shall be included in
all copies or substantial parts of the Software program.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
composer.json
I will begin by including a composer.json file that comprises:
{
"identify": "dcblogdev/laravel-tags",
"description": "A Laravel bundle for including tags to your content material",
"license": "MIT",
"authors": [
{
"name": "David Carr",
"email": "dave@dcblog.dev",
"homepage": "https://dcblog.dev"
}
],
"homepage": "https://github.com/dcblogdev/laravel-tags",
"key phrases": [
"Laravel",
"Tags"
],
"require-dev": {
"orchestra/testbench": "^8.0",
"pestphp/pest": "^v2.24.2",
"pestphp/pest-plugin-type-coverage": "^2.4",
"laravel/pint": "^1.13",
"mockery/mockery": "^1.6"
},
"autoload": {
"psr-4": {
"DcblogdevTags": "src/",
"DcblogdevTagsChecks": "assessments"
}
},
"autoload-dev": {
"classmap": [
"tests/TestCase.php"
]
},
"additional": {
"laravel": {
"suppliers": [
"DcblogdevTagsTagsServiceProvider"
],
"aliases": {
"Tags": "DcblogdevTagsFacadesTags"
}
}
},
"config": {
"allow-plugins": {
"pestphp/pest-plugin": true
}
},
"scripts": {
"pest": "vendor/bin/pest --parallel",
"pest-coverage": "vendor/bin/pest --coverage",
"pest-type": "vendor/bin/pest --type-coverage",
"pint": "vendor/bin/pint"
}
}
Breaking this down, first, the bundle wants a reputation within the conference of vendor identify and bundle identify dcblogdev/laravel-tags
in my case the seller identify is dcblogdev
and bundle identify is laravel-tags
Add a require part in case your bundle has dependencies
In a require-dev part, I import these third-party packages for improvement solely
testbench bundle lets you use Laravel conventions for testing.
pest is my testing framework of selection
pint to use styling conventions to my codebase.
"orchestra/testbench": "^8.0",
"pestphp/pest": "^v2.24.2",
"pestphp/pest-plugin-type-coverage": "^2.4",
"laravel/pint": "^1.13",
"mockery/mockery": "^1.6"
Inside autoload to any folders that you really want composer to autoload. I’ve a folder known as src which can comprise the courses and assessments for all of the assessments
One vital side of this bundle identify I will usually give the bundle a nickname to make use of so as a substitute of utilizing laravel-tags I will use tags
I will do that by utilizing Tags in any courses namespace and creating an alias:
"additional": {
"laravel": {
"suppliers": [
"DcblogdevTagsTagsServiceProvider"
],
"aliases": {
"Tags": "DcblogdevTagsFacadesTags"
}
}
}
Checks
Now I’ll create 2 folders:
-
src
-
assessments
Inside assessments I will create these information:
TestCase.php
<?php
namespace DcblogdevTagsTests;
use DcblogdevTagsTagsServiceProvider;
use OrchestraTestbenchTestCase as Orchestra;
class TestCase extends Orchestra
{
protected perform getPackageProviders($app)
{
return [
TagsServiceProvider::class,
];
}
protected perform getEnvironmentSetUp($app)
{
$app['config']->set('database.default', 'mysql');
$app['config']->set('database.connections.mysql', [
'driver' => 'sqlite',
'host' => '127.0.0.1',
'database' => ':memory:',
'prefix' => '',
]);
}
protected perform defineDatabaseMigrations()
{
$this->loadLaravelMigrations();
$this->loadMigrationsFrom(dirname( __DIR__ ).'/src/database/migrations');
}
}
The strategies getEnviromentSetup
and defineDatabaseMigrations
aren’t wanted by default. They’re solely required if you want to use a database and cargo migrations.
Inside getPackageProviders
the principle bundle service supplier is loaded.
Now create a file known as Pest.php
<?php
use DcblogdevTagsTestsTestCase;
makes use of(TestCase::class)->in( __DIR__ );
This file calls a makes use of() perform to load the assessments case I will use __DIR__
contained in the in() methodology to make Pest use the TestCase class within the root of this listing.
Contained in the bundle root create a phpunit.xml file containing:
<?xml model="1.0" encoding="UTF-8"?>
<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="vendor/phpunit/phpunit/phpunit.xsd"
bootstrap="vendor/autoload.php"
colours="true"
>
<supply>
<embrace>
<listing suffix=".php">src/</listing>
</embrace>
</supply>
<testsuites>
<testsuite identify="Take a look at">
<listing suffix="Take a look at.php">./assessments</listing>
</testsuite>
</testsuites>
<php>
<env identify="APP_KEY" worth="base64:2fl+Ktv64dkfl+Fuz4Qp/A75G2RTiWVA/ZoKZvp6fiiM10="/>
</php>
</phpunit>
This units the placement for assessments to learn from, it is uncommon this file will have to be modified from this default.
I set an APP_KEY
as normal for working assessments, its worth shouldn’t be vital.
Pint
To setup discover create a folder within the bundle root known as pint.json I exploit the Laravel preset:
{
"preset": "laravel"
}
ReadMe
contained in the venture root create a file known as readme.md to doc the venture, I sometimes use this format:
# Laravel Tags
Clarify what the bundle does.
# Documentation and set up directions
[https://dcblog.dev/docs/laravel-tags](https://dcblog.dev/docs/laravel-tags)
## Change log
Please see the [changelog][3] for extra info on what has modified not too long ago.
## Contributing
Contributions are welcome and shall be absolutely credited.
Contributions are accepted through Pull Requests on [Github][4].
## Pull Requests
- **Doc any change in behaviour** - Be sure that the `readme.md` and another related documentation are saved up-to-date.
- **Contemplate our launch cycle** - We attempt to observe [SemVer v2.0.0][5]. Randomly breaking public APIs shouldn't be an choice.
- **One pull request per function** - If you wish to do multiple factor, ship a number of pull requests.
## Safety
In the event you uncover any safety associated points, please electronic mail dave@dcblog.dev electronic mail as a substitute of utilizing the problem tracker.
## License
license. Please see the [license file][6] for extra info.
ServiceProvider
Inside src create the service supplier in my case TagsServiceProvider.php
<?php
namespace DcblogdevTags;
use IlluminateSupportServiceProvider;
class TagsServiceProvider extends ServiceProvider
{
public perform boot(): void
{
$this->configurePublishing();
}
public perform configurePublishing(): void
{
if (! $this->app->runningInConsole()) {
return;
}
$this->publishes([
__DIR__.'/../config/tags.php' => config_path('tags.php'),
], 'config');
}
public perform register(): void
{
$this->mergeConfigFrom( __DIR__.'/../config/tags.php', 'tags');
// Register the service the bundle offers.
$this->app->singleton('tags', perform () {
return new Tags;
});
}
public perform offers(): array
{
return ['tags'];
}
}
Contained in the boot perform set known as to different strategies, to start with I solely have one known as configurePublishing It will publish any information outlined on this web page and can solely run when the category is ran from a CLI
The register methodology permits a printed config file to be merged in with a neighborhood ./config/tags.php
config file
And arrange the principle class to be instantiated.
Facades
If you wish to make use of facade ie have static known as to a category that will usually be instantiated.
Inside src create a folder known as facades and your class similar to Tags.php
<?php
namespace DcblogdevTagsFacades;
use IlluminateSupportFacadesFacade;
class Tags extends Facade
{
protected static perform getFacadeAccessor(): string
{
return 'tags';
}
}
Assets
For extra particulars learn https://www.laravelpackage.com