deployer: `dep ssh` does not work with fish shell on remote system

Q A
Issue Type Bug (or feature request?)
Deployer Version 6.0.3
Local Machine OS archlinux 2017-09
Remote Machine OS debian stretch

Description

dep ssh does not work with fish shell on the remote system:

hiciu@unknown ~/d/k/d/s/blog (feature/deployer)> dep ssh
Select host:
  [blog.xxxxxxxxx.dev] blog-xxxxxxxxx@blog.xxxxxxxxx.dev
  [blog.xxxxxxxxx    ] blog-xxxxxxxxx@blog.xxxxxxxxx
 > blog.xxxxxxxxx.dev
The authenticity of host 'blog.xxxxxxxxx.dev (192.168.150.59)' can't be established.
ECDSA key fingerprint is SHA256:+PjtDcpz+TZrYb9XcLMMVRE4uovxFYgsUBVMVsuPCiU.
Are you sure you want to continue connecting (yes/no)? yes
Warning: Permanently added 'blog.xxxxxxxxx.dev,192.168.150.59' (ECDSA) to the list of known hosts.
cd: The directory “/containers/blog-xxxxxxxxx/domains/blog.xxxxxxxxx/deployer/current” does not exist
/usr/share/fish/functions/cd.fish (line 30):     builtin cd $argv
                                                 ^
in function “cd”
        called on standard input
        with parameter list “/containers/blog-xxxxxxxxx/domains/blog.xxxxxxxxx/deployer/current”

Variables may not be used as commands. In fish, please define a function or use 'eval $SHELL'.
fish: cd /containers/blog-xxxxxxxxx/domains/blog.xxxxxxxxx/deployer/current; exec $SHELL -l
                                                                                  ^
Connection to blog.xxxxxxxxx.dev closed.

Steps to reproduce

  1. setup account with fish shell on the remote system: chsh -s /usr/bin/fish
  2. setup deploy.php which points to that host
  3. connect with dep ssh

Content of deploy.php

<?php

namespace Deployer;

require 'recipe/common.php';

define('CONTAINER', 'blog-xxxxxxxxx');
define('DOMAIN', 'blog.xxxxxxxxx');

host(sprintf('%s.dev', DOMAIN))
    ->stage('vagrant')
    ->user(CONTAINER)
    ->set('deploy_path', sprintf('/containers/%s/domains/%s/deployer', CONTAINER, DOMAIN));

Output log

With enabled option for verbose output -vvv.

hiciu@unknown ~/s/2/2/temp> dep -vvv ssh
cd: The directory “/containers/blog-xxxxxxxxx/domains/blog.xxxxxxxxx/deployer/current” does not exist
/usr/share/fish/functions/cd.fish (line 30):     builtin cd $argv
                                                 ^
in function “cd”
        called on standard input
        with parameter list “/containers/blog-xxxxxxxxx/domains/blog.xxxxxxxxx/deployer/current”
Variables may not be used as commands. In fish, please define a function or use 'eval $SHELL'.
fish: cd /containers/blog-xxxxxxxxx/domains/blog.xxxxxxxxx/deployer/current; exec $SHELL -l
                                                                                  ^
Connection to blog.xxxxxxxxx.dev closed.

Comments

For the simple tasks deployer works just fine with fish.

The offending line is here: https://github.com/deployphp/deployer/blob/master/src/Console/SshCommand.php#L87

About this issue

  • Original URL
  • State: closed
  • Created 7 years ago
  • Reactions: 1
  • Comments: 17 (7 by maintainers)

Most upvoted comments

Hello,

I have new patch for 6.2.0. It seems to be working fine on my system.

diff --git a/src/Ssh/Client.php b/src/Ssh/Client.php
index 04392b7..ee27ba0 100644
--- a/src/Ssh/Client.php
+++ b/src/Ssh/Client.php
@@ -66,6 +66,7 @@ class Client
             $this->output->write(''); // Notify OutputWatcher
             $sshArguments = $sshArguments->withFlag('-tt');
             $command = escapeshellarg($command);
+            $command = escapeshellarg("bash -c $command");
 
             $ssh = "ssh $sshArguments $host $command";
             $process = new Process($ssh);
@@ -83,7 +84,7 @@ class Client
 
         $shellCommand = $host->getShellCommand();
 
-        $ssh = "ssh $sshArguments $host $become '$shellCommand; printf \"[exit_code:%s]\" $?;'";
+        $ssh = "ssh $sshArguments $host $become bash -c \"'$shellCommand; printf \"[exit_code:%s]\" $?;'\"";
 
         $process = new Process($ssh);
         $process

after patching that on my local version dep deploy fails with:

  [Deployer\Exception\RuntimeException]
  The command "rm -f /containers/blog-xxxxxxxxx/domains/blog.xxxxxxxxx/deployer/.dep/deploy.lock" failed.
  Exit Code: -1 (Unknown error)
  Host Name: blog.xxxxxxxxx
  ================
  $? is not the exit status. In fish, please use $status.
  fish: bash -s; printf "[exit_code:%s]" $?;

I think deployer should explicitly call bash. This patch allows me to deploy stuff with fish on the remote system:

diff --git a/src/Ssh/Client.php b/src/Ssh/Client.php
index 250b8c0..621fb5b 100644
--- a/src/Ssh/Client.php
+++ b/src/Ssh/Client.php
@@ -80,7 +80,7 @@ class Client
             $sshArguments = $this->initMultiplexing($host);
         }

-        $ssh = "ssh $sshArguments $host $become 'bash -s; printf \"[exit_code:%s]\" $?;'";
+        $ssh = "ssh $sshArguments $host $become bash -c \"'bash -s; printf \"[exit_code:%s]\" $?;'\"";

         $process = new Process($ssh);
         $process

Now it’s fixed in https://github.com/deployphp/deployer/pull/2458

I checked in sith fish as default on the remote server and with zsh on the remote server. Works!