Skip to content

Instantly share code, notes, and snippets.

@graysonchao
Last active October 14, 2023 13:58
Show Gist options
  • Select an option

  • Save graysonchao/6fae927420431ec69e036b2b9333a090 to your computer and use it in GitHub Desktop.

Select an option

Save graysonchao/6fae927420431ec69e036b2b9333a090 to your computer and use it in GitHub Desktop.

Revisions

  1. graysonchao revised this gist Jul 15, 2016. 1 changed file with 1 addition and 1 deletion.
    2 changes: 1 addition & 1 deletion paramiko_yubikey.py
    Original file line number Diff line number Diff line change
    @@ -11,7 +11,7 @@

    try:
    client.connect(
    hostname=SyslogReviewer.BASTION_HOST,
    hostname="ssh.example.com",
    port=22,
    username=username,
    look_for_keys=True,
  2. graysonchao created this gist Jul 15, 2016.
    40 changes: 40 additions & 0 deletions paramiko_yubikey.py
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,40 @@
    username = raw_input("Enter SSH username:")
    yubikey_string = getpass.getpass('Enter YubiKey OTP:')

    client = paramiko.client.SSHClient()

    # Any means of getting the PKey will do. This code assumes you've only got one key loaded in your active ssh-agent.
    # See also:
    # - http://docs.paramiko.org/en/1.17/api/keys.html#paramiko.pkey.PKey
    # - http://docs.paramiko.org/en/1.17/api/client.html#paramiko.client.SSHClient.connect
    my_pkey = paramiko.agent.Agent().get_keys()[0]

    try:
    client.connect(
    hostname=SyslogReviewer.BASTION_HOST,
    port=22,
    username=username,
    look_for_keys=True,
    pkey=my_pkey
    )
    except paramiko.ssh_exception.SSHException:
    pass

    transport = client.get_transport()

    # Sometimes sshd is configured to use 'keyboard-interactive' instead of 'password' to implement the YubiKey challenge.
    # In that case, you can use something like this.
    # The code below assumes the server will only ask one question and expect the YubiKey OTP as an answer.
    # If there's more questions to answer, you should handle those per the docs at:
    # http://docs.paramiko.org/en/1.17/api/transport.html#paramiko.transport.Transport.auth_interactive
    #
    # def yubikey_handler(title, instructions, prompt_list):
    # return (yubikey_string)
    # transport.auth_interactive(username, yubikey_handler)

    transport.auth_password(username, self.yubikey_string)

    # You should now be able to use client as the authenticated user.
    client.exec_command("whatever")