diff --git a/src/Configuration/AbstractConfiguration.php b/src/Configuration/AbstractConfiguration.php index 4ac0e20..5810337 100644 --- a/src/Configuration/AbstractConfiguration.php +++ b/src/Configuration/AbstractConfiguration.php @@ -31,7 +31,7 @@ public function __construct() $this->servers = new ServerRepository(); } - public function server(string $sshDsn, array $roles = [Server::ROLE_APP], array $properties = []) + public function server(string $sshDsn, array $roles = [Server::ROLE_APP], array $properties = [], $system = null) { $reservedProperties = array_merge(self::RESERVED_SERVER_PROPERTIES, $this->getReservedServerProperties()); $reservedPropertiesUsed = array_intersect($reservedProperties, array_keys($properties)); @@ -39,7 +39,7 @@ public function server(string $sshDsn, array $roles = [Server::ROLE_APP], array throw new InvalidConfigurationException(sprintf('These properties set for the "%s" server are reserved: %s. Use different property names.', $sshDsn, implode(', ', $reservedPropertiesUsed))); } - $this->servers->add(new Server($sshDsn, $roles, $properties)); + $this->servers->add(new Server($sshDsn, $roles, $properties, $system)); } public function useSshAgentForwarding(bool $useIt) diff --git a/src/Configuration/CustomConfiguration.php b/src/Configuration/CustomConfiguration.php index 02d2f8b..a834c60 100644 --- a/src/Configuration/CustomConfiguration.php +++ b/src/Configuration/CustomConfiguration.php @@ -21,9 +21,9 @@ class CustomConfiguration extends AbstractConfiguration { // this proxy method is needed because the autocompletion breaks // if the parent method is used directly - public function server(string $sshDsn, array $roles = [Server::ROLE_APP], array $properties = []): self + public function server(string $sshDsn, array $roles = [Server::ROLE_APP], array $properties = [], $system = null): self { - parent::server($sshDsn, $roles, $properties); + parent::server($sshDsn, $roles, $properties, $system); return $this; } diff --git a/src/Configuration/DefaultConfiguration.php b/src/Configuration/DefaultConfiguration.php index 1abe5ac..951563e 100644 --- a/src/Configuration/DefaultConfiguration.php +++ b/src/Configuration/DefaultConfiguration.php @@ -70,9 +70,9 @@ public function __construct(string $localProjectDir) // this proxy method is needed because the autocompletion breaks // if the parent method is used directly - public function server(string $sshDsn, array $roles = [Server::ROLE_APP], array $properties = []): self + public function server(string $sshDsn, array $roles = [Server::ROLE_APP], array $properties = [], $system = null): self { - parent::server($sshDsn, $roles, $properties); + parent::server($sshDsn, $roles, $properties, $system); return $this; } diff --git a/src/Context.php b/src/Context.php index 28cd5b4..a319960 100644 --- a/src/Context.php +++ b/src/Context.php @@ -89,7 +89,7 @@ public function getOutput(): OutputInterface private function createLocalHost(): Server { - $localhost = new Server('localhost'); + $localhost = new Server('localhost', [], [], '\\' === DIRECTORY_SEPARATOR ? 'windows': null); $localhost->set(Property::project_dir, $this->projectDir); return $localhost; diff --git a/src/Deployer/DefaultDeployer.php b/src/Deployer/DefaultDeployer.php index fa28adc..443c3c7 100644 --- a/src/Deployer/DefaultDeployer.php +++ b/src/Deployer/DefaultDeployer.php @@ -18,6 +18,7 @@ use EasyCorp\Bundle\EasyDeployBundle\Requirement\CommandExists; use EasyCorp\Bundle\EasyDeployBundle\Server\Property; use EasyCorp\Bundle\EasyDeployBundle\Server\Server; +use EasyCorp\Bundle\EasyDeployBundle\Task\Task; use EasyCorp\Bundle\EasyDeployBundle\Task\TaskCompleted; abstract class DefaultDeployer extends AbstractDeployer @@ -45,7 +46,6 @@ public function getRequirements(): array if ('acl' === $this->getConfig(Option::permissionMethod)) { $requirements[] = new CommandExists($appServers, 'setfacl'); } - return $requirements; } @@ -161,14 +161,14 @@ private function doCheckPreviousReleases(): void private function doSymlinkToPreviousRelease(): void { $this->log('

Reverting the current symlink to the previous version'); - $this->runRemote('export _previous_release_dirname=$(ls -r1 {{ deploy_dir }}/releases | head -n 2 | tail -n 1) && rm -f {{ deploy_dir }}/current && ln -s {{ deploy_dir }}/releases/$_previous_release_dirname {{ deploy_dir }}/current'); + $this->runRemote('{{ _env_command export}} _previous_release_dirname=$(ls -r1 {{ deploy_dir }}/releases | head -n 2 | tail -n 1) && rm -f {{ deploy_dir }}/current && ln -s {{ deploy_dir }}/releases/$_previous_release_dirname {{ deploy_dir }}/current'); } private function doDeleteLastReleaseDirectory(): void { // this is needed to avoid rolling back in the future to this version $this->log('

Deleting the last release directory'); - $this->runRemote('export _last_release_dirname=$(ls -r1 {{ deploy_dir }}/releases | head -n 1) && rm -fr {{ deploy_dir }}/releases/$_last_release_dirname'); + $this->runRemote('{{ _env_command export}} _last_release_dirname=$(ls -r1 {{ deploy_dir }}/releases | head -n 1) && rm -fr {{ deploy_dir }}/releases/$_last_release_dirname'); } private function initializeServerOptions(): void @@ -232,7 +232,7 @@ private function createRemoteDirectoryLayout(): void $this->runRemote('mkdir -p {{ deploy_dir }} && mkdir -p {{ deploy_dir }}/releases && mkdir -p {{ deploy_dir }}/shared'); /** @var TaskCompleted[] $results */ - $results = $this->runRemote('export _release_path="{{ deploy_dir }}/releases/$(date +%Y%m%d%H%M%S)" && mkdir -p $_release_path && echo $_release_path'); + $results = $this->runRemote('{{ _env_command export}} _release_path={{ deploy_dir }}/releases/' . date('dmYHis') . ' && mkdir -p $_release_path && echo $_release_path'); foreach ($results as $result) { $remoteProjectDir = $this->getContext()->isDryRun() ? '(the remote project_dir)' : $result->getTrimmedOutput(); $result->getServer()->set(Property::project_dir, $remoteProjectDir); diff --git a/src/Requirement/CommandExists.php b/src/Requirement/CommandExists.php index d985eb4..73dff36 100644 --- a/src/Requirement/CommandExists.php +++ b/src/Requirement/CommandExists.php @@ -11,6 +11,7 @@ namespace EasyCorp\Bundle\EasyDeployBundle\Requirement; +use EasyCorp\Bundle\EasyDeployBundle\Server\Server; use EasyCorp\Bundle\EasyDeployBundle\Task\Task; class CommandExists extends AbstractRequirement @@ -30,13 +31,8 @@ public function getMessage(): string public function getChecker(): Task { - $shellCommand = sprintf('%s %s', $this->isWindows() ? 'where' : 'which', $this->commandName); + $shellCommand = sprintf('%s %s', '{{ _env_command which }}', $this->commandName); return new Task($this->getServers(), $shellCommand); } - - private function isWindows(): bool - { - return '\\' === DIRECTORY_SEPARATOR; - } } diff --git a/src/Server/Server.php b/src/Server/Server.php index 676a9a1..f3347b7 100644 --- a/src/Server/Server.php +++ b/src/Server/Server.php @@ -13,6 +13,8 @@ use EasyCorp\Bundle\EasyDeployBundle\Exception\ServerConfigurationException; use EasyCorp\Bundle\EasyDeployBundle\Helper\Str; +use EasyCorp\Bundle\EasyDeployBundle\System\AbstractSystem; +use EasyCorp\Bundle\EasyDeployBundle\System\DefaultSystem; use Symfony\Component\HttpFoundation\ParameterBag; class Server @@ -24,8 +26,9 @@ class Server private $host; private $port; private $properties; + private $system; - public function __construct(string $dsn, array $roles = [self::ROLE_APP], array $properties = []) + public function __construct(string $dsn, array $roles = [self::ROLE_APP], array $properties = [], string $system = null) { $this->roles = $roles; $this->properties = new ParameterBag($properties); @@ -41,6 +44,14 @@ public function __construct(string $dsn, array $roles = [self::ROLE_APP], array $this->host = $params['host']; $this->port = $params['port'] ?? null; + + $systemClassName = '\\EasyCorp\\Bundle\\EasyDeployBundle\\System\\' . ucfirst((string)$system) . 'System'; + if($system && class_exists($systemClassName)){ + $this->system = new $systemClassName(); + }else{ + $this->system = new DefaultSystem(); + } + } public function __toString(): string @@ -58,6 +69,13 @@ public function resolveProperties(string $expression): string $definedProperties = $this->properties; $resolved = preg_replace_callback('/(\{\{\s*(?.+)\s*\}\})/U', function (array $matches) use ($definedProperties, $expression) { $propertyName = trim($matches['propertyName']); + //Resolve special environment command + if(substr($propertyName,0, strlen('_env_command')) === '_env_command'){ + if(!isset(explode(' ', $propertyName)[1])){ + return ''; + } + return $this->system->getCommand(explode(' ', $propertyName)[1]); + } if (!$definedProperties->has($propertyName)) { throw new \InvalidArgumentException(sprintf('The "%s" property in "%s" expression is not a valid server property.', $propertyName, $expression)); } @@ -121,4 +139,10 @@ public function getPort(): ?int { return $this->port; } + + public function getSystem(): AbstractSystem + { + return $this->system; + } + } diff --git a/src/System/AbstractSystem.php b/src/System/AbstractSystem.php new file mode 100644 index 0000000..54e358d --- /dev/null +++ b/src/System/AbstractSystem.php @@ -0,0 +1,26 @@ +commands[$command])){ + return $this->commands[$command]; + } + + return $command; + } + + public function getSessionPrefix(){ + + } + +} \ No newline at end of file diff --git a/src/System/DefaultSystem.php b/src/System/DefaultSystem.php new file mode 100644 index 0000000..621418f --- /dev/null +++ b/src/System/DefaultSystem.php @@ -0,0 +1,10 @@ + 'set', + 'which' => 'where' + ]; +} \ No newline at end of file diff --git a/src/Task/TaskRunner.php b/src/Task/TaskRunner.php index ce53693..f0ca288 100644 --- a/src/Task/TaskRunner.php +++ b/src/Task/TaskRunner.php @@ -62,7 +62,11 @@ private function doRun(Server $server, string $shellCommand, array $envVars): Ta $envVarsAsString = http_build_query($envVars, '', ' '); // the ';' after the env vars makes them available to all commands, not only the first one // parenthesis create a sub-shell so the env vars don't affect to the parent shell - $shellCommand = sprintf('(export %s; %s)', $envVarsAsString, $shellCommand); + $shellCommand = sprintf('(' . $server->getSystem()->getCommand('export') . ' %s; %s)', $envVarsAsString, $shellCommand); + } + + if($server->getSystem()->getSessionPrefix()){ + $shellCommand = $server->getSystem()->getSessionPrefix() . $shellCommand; } $this->logger->log(sprintf('[%s] Executing command: %s', $server, $shellCommand));