0

I'm using paramiko's SSHClient to control a server via exec_command method. However, I'm failing to use python over there because it says python not found and I realized the entire conda enviroment is not there. On my local machine, I get around it with shell=True passed to subprocess. Question: how do I do this on paramiko, or, is there another command that I should run to get conda to be loaded up in server's shell.

EDIT: the exec_command offers environment optional keyword but I don't know how to leverage it if it is useful at all.

Alex Deft
  • 2,531
  • 1
  • 19
  • 34
  • 1
    sshd _always_ runs a shell. paramiko has no equivalent to `shell=False`, because there's no way to tell the remote server not to start one. – Charles Duffy Dec 19 '21 at 22:32
  • 1
    More likely what you're depending on is the remote shell being considered a _login_ shell, which influences which dotfiles it chooses to execute. – Charles Duffy Dec 19 '21 at 22:33
  • (when you pass a command, you don't get a login shell by default; that's not specific to paramiko; the regular command-line ssh client works the same way). – Charles Duffy Dec 19 '21 at 22:33
  • ...compare `ssh somehost` and then running `python` once it's in (which gets a login shell) to `ssh somehost python` (which starts Python from a noninteractive shell). There's still a shell in either case, but which dotfiles it runs is different. – Charles Duffy Dec 19 '21 at 22:34
  • ...once you've reproduced this from a command line, you can iterate more quickly on deciding what kind of solution you want. One ugly hack is just to source the files you want explicitly: `ssh somehost 'for f in .bashrc .profile .bash_profile; do [ -s "$f" ] && . "$f"; done; python'` -- if it works from your shell command line, it'll work from paramiko too. – Charles Duffy Dec 19 '21 at 22:35
  • (Does the above make sense? I'm going to wait until you've got follow-up questions before elaborating further). – Charles Duffy Dec 19 '21 at 22:37
  • makes a lot of sense, I'm reading it over and over, its just the gap between 250k points person with 1k person. @CharlesDuffy – Alex Deft Dec 19 '21 at 22:39
  • 1
    For some general background on which dotfiles are read during shell startup under which conditions, see the *Invocation* section of `man bash`. Once you've done that, and figured out which specific dotfiles are setting up what your Python environment needs, you should be in a better place to decide what kind of solution you want to implement. – Charles Duffy Dec 19 '21 at 22:43
  • @CharlesDuffy Solved! thanks for all the comments. See the answer. – Alex Deft Dec 20 '21 at 05:40

1 Answers1

1

Thanks to insightful comments by @CharesDuffy with "don't feed me teach me how to fish" style, I solved the problem as follows:

For conda/miniconda to be loaded, I prefaced my commands with source ~/miniconda3/bin/activate;.

Enriching points:

  • For a permanent solution, the preface can be added to .profile or .bash_profile or .bash_login which is what is loaded up by default when ssh'ing. If you have a fresh installation e.g. a virtual machine, those files don't exist in the first place.
  • sourcing that conda file is paramount (as opposed to executing it)

Ostensibly, shell=True kwarg of subprocess module is doing something like this behind the scenes.

Alex Deft
  • 2,531
  • 1
  • 19
  • 34