You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: README.md
+107-3Lines changed: 107 additions & 3 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -8,12 +8,116 @@ Base package that provides the very basic task interface, function abstraction a
8
8
9
9
## What is it?
10
10
11
-
This package is an extension to deployer that adds basic tasks and interfaces and abstracts the actual deployer API.
11
+
This package is an extension to deployer that adds basic tasks and interfaces and abstracts the actual deployer API. Deployer can still be used as usual but I
12
+
would recommend implementing your tasks as classes and write unit tests for them. If you have tasks you reuse across projects you should create your own
13
+
packages. There are already several codenamephp/deployer.* packages available to use.
12
14
13
-
## But ... why?
15
+
###But ... why?
14
16
15
17
I really like testable code and since the actual deploy.php is otherwise just a collection of callbacks that is hard to test I added basic interfaces and
16
18
classes that encapsulate the tasks and make them reusable.
17
19
18
20
Sure, you could make it work with lambdas but since PHP is not intended to be a functional programming language it's far easier to just throw some classes into
19
-
the mix.
21
+
the mix.
22
+
23
+
## Install
24
+
25
+
Just add the package to composer, ideally by executing `composer require codenamephp/deployer.base` which should install the latest version with semver range.
26
+
27
+
## Usage
28
+
29
+
Just create your `deploy.php` as usual. Then just add existing tasks or implement your own and add them using the package functions:
30
+
31
+
```php
32
+
const PROJECT_ROOT = __DIR__ . '/..'; // I have deployer in a seperate folder so this makes creating paths easier
33
+
34
+
$deployerFunctions = new All(); // Abstraction of deployer function and also has some additional methods
35
+
36
+
$deployerFunctions->registerTask(new UploadTransferables( // My version of deploying code in NEOS projects
37
+
new Simple(PROJECT_ROOT . '/Configuration', '{{release_path}}'),
38
+
new Simple(PROJECT_ROOT . '/DistributionPackages', '{{release_path}}', ['Tests/']),
39
+
new Simple(PROJECT_ROOT . '/Packages', '{{release_path}}'),
40
+
new Simple(PROJECT_ROOT . '/Web', '{{release_path}}', ['_Resources/']),
41
+
new Simple(PROJECT_ROOT . '/flow', '{{release_path}}'),
42
+
));
43
+
44
+
// additional tasks from other packages
45
+
$deployerFunctions->task('composer:install', new \de\codenamephp\deployer\composer\task\install\Production())->desc('Run composer install for production.');
46
+
$deployerFunctions->task('composer:install:development', new \de\codenamephp\deployer\composer\task\install\Development())->desc('Run composer install for production.');
47
+
48
+
(new ByTaskListAndMatchers(new AtLeastOne( // clean up the cli list
49
+
new ByRegexTaskName('/provision:?.*/'),
50
+
new ByRegexTaskName('/logs:caddy.*/'),
51
+
new ByRegexTaskName('/deploy:.*/')
52
+
)))->hide();
53
+
```
54
+
55
+
### Implementing tasks
56
+
57
+
Deployer just expects a callable as task so in theory this is everything a task needs. This package contains the
58
+
`\de\codenamephp\deployer\base\task\iTask` interface that enforces this so we can just add a new instance of the task.
59
+
60
+
There are also the `\de\codenamephp\deployer\base\task\iTaskWithName` and `\de\codenamephp\deployer\base\task\iTaskWithDescription` interfaces. These can be
61
+
used to set the description and name of the task directly in the class so we don't have to set the same strings in each project and clutter up our deployment
62
+
file. At the very least the `\de\codenamephp\deployer\base\task\iTaskWithName` has to be implemented so we can pass the task to
63
+
`\de\codenamephp\deployer\base\functions\iTask::registerTask` that takes care of the rest.
64
+
65
+
### Deployer Functions
66
+
67
+
The built in deployer functions require a running Deployer instance and are global so they are very hard to mock. In order for our tasks to be testable there
68
+
are several `\de\codenamephp\deployer\base\functions\*` interfaces, one for each method or method group. There is also an
69
+
`\de\codenamephp\deployer\base\functions\iAll` interface that combines them all as convenience if we need several methods. Likewise there's an
70
+
`\de\codenamephp\deployer\base\functions\All` implementation that acts mostly as a proxy for the global methods and also does some additional type checking.
71
+
72
+
The interfaces are mostly the same as the deployer built in methods but add some additional type hints and return hints for a cleaner API.
73
+
74
+
Use these interfaces in your tasks and either use the `\de\codenamephp\deployer\base\functions\All` implementation or write your own. In your tests you can then
75
+
easily mock these interfaces.
76
+
77
+
### Host Check
78
+
79
+
Some task should not be executed by accident, for example pushing a database from local to production. This can be easily achieved by adding
80
+
the `\de\codenamephp\deployer\base\hostCheck\iHostCheck` interface as dependency to your task and calling the
81
+
`\de\codenamephp\deployer\base\hostCheck\iHostCheck::check` method in your `__invoke()` method.
82
+
83
+
#### DoNotRunOnProduction
84
+
85
+
This implementation assumes the production host actually has the alias "production" (can be changed in constructor) and checks against the current host. If the
86
+
alias matches an `\de\codenamephp\deployer\base\UnsafeOperationException` is thrown which halts your deployer run. If you have things to clean up (e.g. a
87
+
database dump) you should add cleanup tasks to the failure step.
88
+
89
+
#### WithDisallowList
90
+
91
+
Similar to DoNotRunOnProduction but with a whole list of disallowed aliases.
92
+
93
+
#### SkippableByOption
94
+
95
+
This is a decorator for the adding the `\de\codenamephp\deployer\base\hostCheck\iHostCheck` that takes an existing host check but only executes it if the
96
+
`--cpd:skip-host-check` (or `-cpd:shc` as shorthand) are not set. This way we can skip the host check if we know what we are doing ... at your own risk of
97
+
course. ;)
98
+
99
+
### Task Hider / Task Matcher
100
+
101
+
Deployer comes with a whole set of default tasks, like the whole `provision` namespace. These are usually used once (if at all) and just clutter up the CLI
102
+
list. The `\de\codenamephp\deployer\base\taskHider\iTaskHider` can be used to hide those tasks you don't want. The default implementation The default
103
+
implementation `\de\codenamephp\deployer\base\taskHider\ByTaskListAndMatchers` uses a `\de\codenamephp\deployer\base\taskMatcher\iTaskMatcher` implementation to
104
+
find tasks to hide. There is also a collection that can be used to just add multiple matchers and hide all the matches.
105
+
106
+
An example could look like this:
107
+
108
+
```php
109
+
(new ByTaskListAndMatchers(new AtLeastOne( // clean up the cli list
110
+
new ByRegexTaskName('/provision:?.*/'),
111
+
new ByRegexTaskName('/logs:caddy.*/'),
112
+
new ByRegexTaskName('/deploy:.*/')
113
+
)))->hide();
114
+
```
115
+
116
+
### Transferables
117
+
118
+
There is a `\de\codenamephp\deployer\base\transferable\iTransferable` interface that makes file transfers more readable by clearly stating what is local and
119
+
remote.
120
+
121
+
### Tasks
122
+
123
+
Maybe I'm going to include an Open API generated manual at some point but for now just check the classes in the `\de\codenamephp\deployer\base\task` namespace.
0 commit comments