LDAPを使用したSSHキー認証


59

要するに:

LDAP経由でSSHキー認証を行う方法が必要です。

問題:

ディレクトリサービスにはLDAP(slapd)を使用しますが、最近、インスタンスの構築に独自のAMIを使用するようになりました。AMIビットが重要な理由は、理想的には、インスタンスが実行されるとすぐにキー認証を介してSSHでログインできるようにし、やや遅い構成管理ツールが追加するスクリプトを開始するのを待つ必要がないことですインスタンスへの正しいキー。

理想的なシナリオは、LDAPにユーザーを追加するときにキーも追加すると、すぐにログインできるようになることです。

パスワードベースのログインは安全性が低く面倒なため、キー認証は必須です。

この質問を読んで OpenSSHにこれを行うためのOpenSSH-lpkというパッチがあることを示唆していますが、これはOpenSSHサーバー> = 6.2ではもう必要ありません

sshd_config(5)オプションAuthorizedKeysCommandが追加され、ファイルシステムから(またはその代わりに)コマンドからauthorized_keysを取得できるようになりました。このコマンドは、AuthorizedKeysCommandUser sshd_config(5)オプションで指定されたアカウントで実行されます

これを実装するためにOpenSSHとLDAPを構成するにはどうすればよいですか?

回答:


64

LDAPを更新してOpenSSH-LPKスキーマを含める

まず、スキーマを使用してLDAPを更新し、sshPublicKeyユーザーの属性を追加する必要があります。

dn: cn=openssh-lpk,cn=schema,cn=config
objectClass: olcSchemaConfig
cn: openssh-lpk
olcAttributeTypes: ( 1.3.6.1.4.1.24552.500.1.1.1.13 NAME 'sshPublicKey'
    DESC 'MANDATORY: OpenSSH Public key'
    EQUALITY octetStringMatch
    SYNTAX 1.3.6.1.4.1.1466.115.121.1.40 )
olcObjectClasses: ( 1.3.6.1.4.1.24552.500.1.1.2.0 NAME 'ldapPublicKey' SUP top AUXILIARY
    DESC 'MANDATORY: OpenSSH LPK objectclass'
    MAY ( sshPublicKey $ uid )
    )

ユーザーの公開キーについてLDAPを照会するスクリプトを作成します。

スクリプトは、そのユーザーの公開鍵を出力する必要があります。例:

ldapsearch '(&(objectClass=posixAccount)(uid='"$1"'))' 'sshPublicKey' | sed -n '/^ /{H;d};/sshPublicKey:/x;$g;s/\n *//g;s/sshPublicKey: //gp'

sshd_config前のステップのスクリプトを指すように更新する

  • AuthorizedKeysCommand /path/to/script
  • AuthorizedKeysCommandUser nobody

ボーナスsshd_configこの質問に見られるように、内部RFC1918ネットワークからのパスワード認証を許可するように更新します。

内部ネットワークからSSHサーバーへのパスワード認証のみを許可する

便利なリンク:

編集:nobodyTRS-80の提案としてユーザーを追加


6
AuthorizedKeysCommandUser nobodyルートの代わりに提案しますが、これは素晴らしいです。
TRS-80

私のldapsearchコマンドまたはsedには、何かがあるはずです。なぜなら、出力をsed black magicコマンドにパイプすると、単純なldapsearchコマンドがデータを返しているにもかかわらず、出力が得られないからです。sedを使用する代わりに、出力をクリーンアップするスクリプトを作成する必要があります。
クリスL

1
以前のコメントは無視してください。私の問題は、sshPublicKeyプロパティに末尾の改行があるために発生しました。これにより、ldapsearchがすべてをbase64でエンコードします。私はsedコマンドを単純化しました:ldapsearch -u -LLL -o ldif-wrap=no '(&(objectClass=posixAccount)(uid='"$1"'))' 'sshPublicKey' | sed -n 's/^[ \t]*sshPublicKey:[ \t]*\(.*\)/\1/p'
クリスL

1
@クリスは確かに黒魔術が少ないが、sedはまだ1回だけの1方向ハッシュ関数です;)
Froyke

1
OpenSSHの私のバージョン(5.3p1-122.el6)にはAuthorizedKeysCommandRunAsAuthorizedKeysCommandUser
mveroone

5

ldapsearchの実行時にエラーが発生する場合:

sed: 1: "/^ /{H;d};": extra characters at the end of d command

私が(FreeBSD上で)そうだったように、修正は最初のsedコマンドを次のように変更することです:

/^ /{H;d;};

(「d」の後にセミコロンを追加します)。


4

私の「メソッド」を共有したかったのですが、クライアント側はDebian / Ubuntu固有ですが、サーバー側は基本的に上記と同じですが、「HowTo:」が少し増えています

サーバー:

公開キー属性を有効にする:

クレジット:

https://blog.shichao.io/2015/04/17/setup_openldap_server_with_openssh_lpk_on_ubuntu.html

cat << EOL >~/openssh-lpk.ldif
dn: cn=openssh-lpk,cn=schema,cn=config
objectClass: olcSchemaConfig
cn: openssh-lpk
olcAttributeTypes: ( 1.3.6.1.4.1.24552.500.1.1.1.13 NAME 'sshPublicKey'
  DESC 'MANDATORY: OpenSSH Public key'
  EQUALITY octetStringMatch
  SYNTAX 1.3.6.1.4.1.1466.115.121.1.40 )
olcObjectClasses: ( 1.3.6.1.4.1.24552.500.1.1.2.0 NAME 'ldapPublicKey' SUP top AUXILIARY
  DESC 'MANDATORY: OpenSSH LPK objectclass'
  MAY ( sshPublicKey $ uid )
  )
EOL

次に、これを使用してldifを追加します。

ldapadd -Y EXTERNAL -H ldapi:/// -f ~/openssh-lpk.ldif

phpLDAPadminでSSH公開キーを持つユーザーを追加する

最初に、「Generic:User Account」テンプレートでユーザーを作成します。次に、「objectClass」属性セクションに移動し、「値を追加」をクリックして、「ldapPublicKey」属性を選択します。送信後、ユーザー編集ページに戻り、上部の[新しい属性を追加]をクリックし、[sshPublicKey]を選択して、パブリックキーをテキスト領域に貼り付け、最後に[オブジェクトの更新]をクリックします。

sshPublicKey属性が表示されない-OpenLDAP PHPLDAP SSHキー認証

Ubuntuクライアント:

apt-get -y install python-pip python-ldap
pip install ssh-ldap-pubkey
sh -c 'echo "AuthorizedKeysCommand /usr/local/bin/ssh-ldap-pubkey-wrapper\nAuthorizedKeysCommandUser nobody" >> /etc/ssh/sshd_config' && service ssh restart

テストキーを作成します。

ssh-keygen -t rsa

3

これは完全な答えではなく、c4urselfの答えへの単なる追加です。これをコメントとして追加しますが、コメントするのに十分な評判がありません。

これはAuthorizedKeysCommand(c4urselfのバージョンに基づいて)私が使用しているスクリプトです。値がbase64エンコーディングで返されるかどうかに関係なく機能します。これは、複数の認証済みキーをLDAPに保存する場合に特に役立ちます。authorized_keysファイルと同様に、キーを改行文字で区切るだけです。

#!/bin/bash
set -eou pipefail
IFS=$'\n\t'

result=$(ldapsearch '(&(objectClass=posixAccount)(uid='"$1"'))' 'sshPublicKey')
attrLine=$(echo "$result" | sed -n '/^ /{H;d};/sshPublicKey:/x;$g;s/\n *//g;/sshPublicKey:/p')

if [[ "$attrLine" == sshPublicKey::* ]]; then
  echo "$attrLine" | sed 's/sshPublicKey:: //' | base64 -d
elif [[ "$attrLine" == sshPublicKey:* ]]; then
  echo "$attrLine" | sed 's/sshPublicKey: //'
else
  exit 1
fi
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.