Ver código fonte

SSHVendor: password is independent of key_filename.

Jelmer Vernooij 7 anos atrás
pai
commit
4599ee4279
2 arquivos alterados com 36 adições e 14 exclusões
  1. 4 11
      dulwich/client.py
  2. 32 3
      dulwich/tests/test_client.py

+ 4 - 11
dulwich/client.py

@@ -1103,11 +1103,9 @@ class SubprocessSSHVendor(SSHVendor):
     def run_command(self, host, command, username=None, port=None,
                     password=None, key_filename=None):
 
-        if password:
+        if password is not None:
             raise NotImplementedError(
-                "You can't set password or passphrase for ssh key "
-                "with SubprocessSSHVendor, use ParamikoSSHVendor instead"
-            )
+                "Setting password not supported by SubprocessSSHVendor.")
 
         args = ['ssh', '-x']
 
@@ -1131,21 +1129,16 @@ class SubprocessSSHVendor(SSHVendor):
 
 class PLinkSSHVendor(SSHVendor):
     """SSH vendor that shells out to the local 'plink' command."""
+
     def run_command(self, host, command, username=None, port=None,
                     password=None, key_filename=None):
 
-        if password and key_filename:
-            raise NotImplementedError(
-                "You can't set passphrase for ssh key "
-                "with PLinkSSHVendor, use ParamikoSSHVendor instead"
-            )
-
         if sys.platform == 'win32':
             args = ['plink.exe', '-ssh']
         else:
             args = ['plink', '-ssh']
 
-        if password:
+        if password is not None:
             import warnings
             warnings.warn(
                 "Invoking PLink with a password exposes the password in the "

+ 32 - 3
dulwich/tests/test_client.py

@@ -1058,9 +1058,38 @@ class PLinkSSHVendorTests(TestCase):
 
     def test_run_command_password_and_privkey(self):
         vendor = PLinkSSHVendor()
-        self.assertRaises(NotImplementedError, vendor.run_command,
-                          'host', 'git-clone-url',
-                          password='12345', key_filename='/tmp/id_rsa')
+
+        warnings.simplefilter("always", UserWarning)
+        self.addCleanup(warnings.resetwarnings)
+        warnings_list, restore_warnings = setup_warning_catcher()
+        self.addCleanup(restore_warnings)
+
+        command = vendor.run_command(
+                'host', 'git-clone-url', password='12345',
+                key_filename='/tmp/id_rsa')
+
+        expected_warning = UserWarning(
+            'Invoking PLink with a password exposes the password in the '
+            'process list.')
+
+        for w in warnings_list:
+            if (type(w) == type(expected_warning) and
+                    w.args == expected_warning.args):
+                break
+        else:
+            raise AssertionError(
+                'Expected warning %r not in %r' %
+                (expected_warning, warnings_list))
+
+        args = command.proc.args
+
+        if sys.platform == 'win32':
+            binary = ['plink.exe', '-ssh']
+        else:
+            binary = ['plink', '-ssh']
+        expected = binary + [
+                '-pw', '12345', '-i', '/tmp/id_rsa', 'host', 'git-clone-url']
+        self.assertListEqual(expected, args[0])
 
     def test_run_command_password(self):
         if sys.platform == 'win32':