Skip to content

Instantly share code, notes, and snippets.

@yukithm
Created October 17, 2019 04:06
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save yukithm/5a850e12fa0138fbf2cfdbbaaadbc7e4 to your computer and use it in GitHub Desktop.
Save yukithm/5a850e12fa0138fbf2cfdbbaaadbc7e4 to your computer and use it in GitHub Desktop.
[ruby] LDAP password utility
# encoding: utf-8
require 'digest/md5'
require 'digest/sha1'
require 'base64'
module Example
class LDAP
# LDAPパスワード生成クラス
class Password
# LDAP用にハッシュ化されたパスワードを生成する
#
# @param [Symbol] type 種類(:cleartext, :crypt, :md5, :smd5, :sha, :ssha)
# @param [String] str 平文パスワード
# @param [String] salt salt
# @return [String] ハッシュ化されたパスワード
# @raise [RuntimeError] typeがサポートされていない種類の場合
# @see Net::LDAP::Password.generate
def self.generate(type, str, salt = nil)
unless salt
srand
salt = (rand * 1000).to_i.to_s
end
case type
when nil, :cleartext
attribute_value = str
when :crypt
attribute_value = '{CRYPT}' + str.crypt(salt)
when :md5
attribute_value = '{MD5}' + Base64.encode64(Digest::MD5.digest(str)).chomp!
when :smd5
attribute_value = '{SMD5}' + Base64.encode64(Digest::MD5.digest(str + salt) + salt).chomp!
when :sha
attribute_value = '{SHA}' + Base64.encode64(Digest::SHA1.digest(str)).chomp!
when :ssha
attribute_value = '{SSHA}' + Base64.encode64(Digest::SHA1.digest(str + salt) + salt).chomp!
else
fail "Unsupported password-hash type (#{type})"
end
attribute_value
end
# パスワードを照合する
#
# @param [String] password 平文パスワード
# @param [String] スキーム付きのハッシュ化されたパスワード
# @return [Boolean]
def self.verify(password, hash_with_scheme)
scheme, _, salt = split_hash(hash_with_scheme)
hash_with_scheme == generate(scheme, password, salt)
end
private
# スキーム付きのハッシュをスキーム、ハッシュ値、saltに分解する
def self.split_hash(hash_with_scheme)
if /\A\{([^}]+)\}(.*)\z/ =~ hash_with_scheme
scheme = Regexp.last_match[1].downcase.to_sym
scheme = nil if scheme == :cleartext
hash = Regexp.last_match[2]
salt = nil
case scheme
when :smd5
hash, salt = Base64.decode64(hash).unpack('a16a*')
when :ssha
hash, salt = Base64.decode64(hash).unpack('a20a*')
when :crypt
hash, salt = hash, hash
end
[scheme, hash, salt]
else
[nil, hash, nil]
end
end
end
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment