Skip to content

Commit 3bd3a66

Browse files
committed
add Composer and WPCLI tests, fix sudo prefix
1 parent de29f12 commit 3bd3a66

File tree

6 files changed

+400
-12
lines changed

6 files changed

+400
-12
lines changed

.gitignore

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,4 +3,5 @@
33
/.idea
44
.DS_STORE
55
.phpunit.cache
6-
.phpunit.result.cache
6+
.phpunit.result.cache
7+
/coverage

src/Composer.php

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -60,14 +60,13 @@ public static function install(
6060
string $binaryName = 'composer.phar',
6161
bool $sudo = false
6262
): string {
63-
$sudoCommand = $sudo ? 'sudo ' : '';
63+
$sudoPrefix = $sudo ? 'sudo ' : '';
6464

65-
run("mkdir -p $installPath");
66-
run("cd $installPath && curl -sS " . self::INSTALLER_DOWNLOAD . " | {{bin/php}}");
67-
run('mv {{deploy_path}}/composer.phar {{deploy_path}}/.dep/composer.phar');
65+
run($sudoPrefix . "mkdir -p $installPath");
66+
run($sudoPrefix . "cd $installPath && curl -sS " . self::INSTALLER_DOWNLOAD . " | {{bin/php}}");
6867

6968
if ($binaryName !== 'composer.phar') {
70-
run("$sudoCommand mv $installPath/composer.phar $installPath/$binaryName");
69+
run($sudoPrefix . "mv $installPath/composer.phar $installPath/$binaryName");
7170
}
7271

7372
return "$installPath/$binaryName";

src/WPCLI.php

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111
*/
1212
class WPCLI
1313
{
14-
private const INSTALLER_DOWNLOAD = 'https://raw.githubusercontent.com/wp-cli/builds/gh-pages/phar/wp-cli.phar';
14+
private const BINARY_DOWNLOAD = 'https://raw.githubusercontent.com/wp-cli/builds/gh-pages/phar/wp-cli.phar';
1515
private const DEFAULT_PATH = '{{release_or_current_path}}';
1616

1717
/**
@@ -64,11 +64,11 @@ public static function install(string $installPath, string $binaryName = 'wp-cli
6464
{
6565
$sudoPrefix = $sudo ? 'sudo ' : '';
6666

67-
run("mkdir -p $installPath");
68-
run("cd $installPath && curl -sS -O " . self::INSTALLER_DOWNLOAD);
67+
run($sudoPrefix . "mkdir -p $installPath");
68+
run($sudoPrefix . "cd $installPath && curl -sS " . self::BINARY_DOWNLOAD . " -o wp-cli.phar");
6969

7070
if ($binaryName !== 'wp-cli.phar') {
71-
run("$sudoPrefix mv $installPath/wp-cli.phar $installPath/$binaryName");
71+
run($sudoPrefix . "mv $installPath/wp-cli.phar $installPath/$binaryName");
7272
}
7373

7474
return "$installPath/$binaryName";
Lines changed: 229 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,229 @@
1+
<?php
2+
3+
namespace Gaambo\DeployerWordpress\Tests\Integration;
4+
5+
use Deployer\Component\ProcessRunner\ProcessRunner;
6+
use Deployer\Component\Ssh\Client;
7+
use Gaambo\DeployerWordpress\Composer;
8+
use PHPUnit\Framework\MockObject\MockObject;
9+
use Symfony\Component\Console\Output\OutputInterface;
10+
11+
class ComposerIntegrationTest extends IntegrationTestCase
12+
{
13+
private MockObject $processRunnerMock;
14+
private MockObject $sshClientMock;
15+
private MockObject $outputMock;
16+
17+
protected function setUp(): void
18+
{
19+
parent::setUp();
20+
21+
// Mock the processRunner and sshClient
22+
$this->processRunnerMock = $this->createMock(ProcessRunner::class);
23+
$this->sshClientMock = $this->createMock(Client::class);
24+
$this->outputMock = $this->createMock(OutputInterface::class);
25+
26+
// Set them in the Deployer container
27+
$this->deployer['processRunner'] = $this->processRunnerMock;
28+
$this->deployer['sshClient'] = $this->sshClientMock;
29+
$this->deployer['output'] = $this->outputMock;
30+
31+
// Set default composer configuration
32+
$this->deployer->config->set('composer_action', 'install');
33+
$this->deployer->config->set('composer_options', '--no-dev --no-interaction');
34+
$this->deployer->config->set('bin/composer', 'composer');
35+
$this->deployer->config->set('bin/php', 'php');
36+
$this->deployer->config->set('deploy_path', '/var/www');
37+
}
38+
39+
public function testRunDefault(): void
40+
{
41+
$path = '/var/www/html';
42+
$expectedCommand = "cd $path && composer install --no-dev --no-interaction ";
43+
44+
$this->processRunnerMock
45+
->expects($this->once())
46+
->method('run')
47+
->with($this->host, $expectedCommand)
48+
->willReturn('Composer output');
49+
50+
$result = Composer::runDefault($path);
51+
$this->assertEquals('Composer output', $result);
52+
}
53+
54+
public function testRunCommand(): void
55+
{
56+
$path = '/var/www/html';
57+
$command = 'require';
58+
$arguments = 'package/name:1.0.0';
59+
$expectedCommand = "cd $path && composer require package/name:1.0.0 ";
60+
61+
$this->processRunnerMock
62+
->expects($this->once())
63+
->method('run')
64+
->with($this->host, $expectedCommand)
65+
->willReturn('Composer output');
66+
67+
$result = Composer::runCommand($path, $command, $arguments);
68+
$this->assertEquals('Composer output', $result);
69+
}
70+
71+
public function testRunScript(): void
72+
{
73+
$path = '/var/www/html';
74+
$script = 'post-install-cmd';
75+
$arguments = '--env=prod';
76+
$expectedCommand = "cd $path && composer run-script post-install-cmd --env=prod ";
77+
78+
$this->processRunnerMock
79+
->expects($this->once())
80+
->method('run')
81+
->with($this->host, $expectedCommand)
82+
->willReturn('Script output');
83+
84+
$result = Composer::runScript($path, $script, $arguments);
85+
$this->assertEquals('Script output', $result);
86+
}
87+
88+
public function testInstall(): void
89+
{
90+
$installPath = '/usr/local/bin';
91+
$binaryName = 'composer';
92+
$expectedCommands = [
93+
"sudo mkdir -p $installPath",
94+
"sudo cd $installPath && curl -sS https://getcomposer.org/installer | php",
95+
"sudo mv $installPath/composer.phar $installPath/$binaryName"
96+
];
97+
98+
// Set up expectations for each command in sequence
99+
$this->processRunnerMock
100+
->expects($this->exactly(3))
101+
->method('run')
102+
->willReturnCallback(function ($host, $command) use ($expectedCommands) {
103+
static $index = 0;
104+
$this->assertEquals($expectedCommands[$index], $command);
105+
$index++;
106+
return 'Installation output';
107+
});
108+
109+
$result = Composer::install($installPath, $binaryName, true);
110+
$this->assertEquals("$installPath/$binaryName", $result);
111+
}
112+
113+
public function testInstallWithoutSudo(): void
114+
{
115+
$installPath = '/usr/local/bin';
116+
$binaryName = 'composer';
117+
$expectedCommands = [
118+
"mkdir -p $installPath",
119+
"cd $installPath && curl -sS https://getcomposer.org/installer | php",
120+
"mv $installPath/composer.phar $installPath/$binaryName"
121+
];
122+
123+
// Set up expectations for each command in sequence
124+
$this->processRunnerMock
125+
->expects($this->exactly(3))
126+
->method('run')
127+
->willReturnCallback(function ($host, $command) use ($expectedCommands) {
128+
static $index = 0;
129+
$this->assertEquals($expectedCommands[$index], $command);
130+
$index++;
131+
return 'Installation output';
132+
});
133+
134+
$result = Composer::install($installPath, $binaryName, false);
135+
$this->assertEquals("$installPath/$binaryName", $result);
136+
}
137+
138+
public function testInstallWithDefaultBinaryName(): void
139+
{
140+
$installPath = '/usr/local/bin';
141+
$expectedCommands = [
142+
"mkdir -p $installPath",
143+
"cd $installPath && curl -sS https://getcomposer.org/installer | php"
144+
];
145+
146+
// Set up expectations for each command in sequence
147+
$this->processRunnerMock
148+
->expects($this->exactly(2))
149+
->method('run')
150+
->willReturnCallback(function ($host, $command) use ($expectedCommands) {
151+
static $index = 0;
152+
$this->assertEquals($expectedCommands[$index], $command);
153+
$index++;
154+
return 'Installation output';
155+
});
156+
157+
$result = Composer::install($installPath);
158+
$this->assertEquals("$installPath/composer.phar", $result);
159+
}
160+
161+
public function testRunCommandWithVerbosity(): void
162+
{
163+
$path = '/var/www/html';
164+
$command = 'require';
165+
$arguments = 'package/name:1.0.0';
166+
167+
// Test with verbose output
168+
$this->outputMock->method('isVerbose')->willReturn(true);
169+
$this->outputMock->method('isVeryVerbose')->willReturn(false);
170+
$this->outputMock->method('isDebug')->willReturn(false);
171+
172+
$expectedCommand = "cd $path && composer require package/name:1.0.0 -v";
173+
174+
$this->processRunnerMock
175+
->expects($this->once())
176+
->method('run')
177+
->with($this->host, $expectedCommand)
178+
->willReturn('Composer output');
179+
180+
$result = Composer::runCommand($path, $command, $arguments);
181+
$this->assertEquals('Composer output', $result);
182+
}
183+
184+
public function testRunCommandWithVeryVerboseOutput(): void
185+
{
186+
$path = '/var/www/html';
187+
$command = 'require';
188+
$arguments = 'package/name:1.0.0';
189+
190+
// Test with very verbose output
191+
$this->outputMock->method('isVerbose')->willReturn(false);
192+
$this->outputMock->method('isVeryVerbose')->willReturn(true);
193+
$this->outputMock->method('isDebug')->willReturn(false);
194+
195+
$expectedCommand = "cd $path && composer require package/name:1.0.0 -vv";
196+
197+
$this->processRunnerMock
198+
->expects($this->once())
199+
->method('run')
200+
->with($this->host, $expectedCommand)
201+
->willReturn('Composer output');
202+
203+
$result = Composer::runCommand($path, $command, $arguments);
204+
$this->assertEquals('Composer output', $result);
205+
}
206+
207+
public function testRunCommandWithDebugOutput(): void
208+
{
209+
$path = '/var/www/html';
210+
$command = 'require';
211+
$arguments = 'package/name:1.0.0';
212+
213+
// Test with debug output
214+
$this->outputMock->method('isVerbose')->willReturn(false);
215+
$this->outputMock->method('isVeryVerbose')->willReturn(false);
216+
$this->outputMock->method('isDebug')->willReturn(true);
217+
218+
$expectedCommand = "cd $path && composer require package/name:1.0.0 -vvv";
219+
220+
$this->processRunnerMock
221+
->expects($this->once())
222+
->method('run')
223+
->with($this->host, $expectedCommand)
224+
->willReturn('Composer output');
225+
226+
$result = Composer::runCommand($path, $command, $arguments);
227+
$this->assertEquals('Composer output', $result);
228+
}
229+
}

tests/Integration/IntegrationTestCase.php

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
use Deployer\Host\Host;
77
use Deployer\Host\Localhost;
88
use Deployer\Task\Context;
9+
use PHPUnit\Framework\MockObject\MockObject;
910
use PHPUnit\Framework\TestCase;
1011
use Symfony\Component\Console\Application;
1112
use Symfony\Component\Console\Input\Input;
@@ -14,8 +15,8 @@
1415
abstract class IntegrationTestCase extends TestCase
1516
{
1617
protected Deployer $deployer;
17-
protected Input $input;
18-
protected Output $output;
18+
protected MockObject|Input $input;
19+
protected MockObject|Output $output;
1920
protected Host $host;
2021

2122
protected function setUp(): void
@@ -36,6 +37,10 @@ protected function setUp(): void
3637

3738
// Create a localhost instance for testing
3839
$this->host = new Localhost();
40+
$this->host->set('deploy_path', '/var/www');
41+
$this->host->set('bin/wp', 'wp');
42+
$this->host->set('release_or_current_path', '/var/www/current');
43+
$this->deployer->hosts->set('localhost', $this->host);
3944

4045
// Push a new context with our host
4146
Context::push(new Context($this->host));

0 commit comments

Comments
 (0)