このパスワードジェネレータで1つの特殊文字のみを生成する方法

このパスワードジェネレータで1つの特殊文字のみを生成する方法

複数の特殊文字を含むパスワードを生成するコマンドがあります。特殊文字を1つだけ生成するにはどうすればよいですか?

# Generate a random password
#  $1 = number of characters; defaults to 32
#  $2 = include special characters; 1 = yes, 0 = no; defaults to 1
function randpass() {
  [ "$2" == "0" ] && CHAR="[:alnum:]" || CHAR="[:graph:]"
    cat /dev/urandom | tr -cd "$CHAR" | head -c ${1:-32}
    echo
}

答え1

これを行う方法はいくつかあります。

1. 「好きな」パスワードが得られるまで繰り返し続けます。

while true
do
    word=$(tr -cd "[:graph:]" < /dev/urandom | head -c ${1:-32})
    if [[ "$word" =~ [[:punct:]].*[[:punct:]] ]]
    then
        echo "$word has multiple special characters - reject."
        continue
    fi
    if [[ "$word" =~ [[:punct:]] ]]
    then
        echo "$word has one special character - accept."
        break
    fi
    echo "$word has no special characters - reject."
    continue
done

警告:文字数が多い場合(たとえば、16文字以上)、時間がかかることがあります。

2. 句読点を読んだ後停止

n=${1:-32}
if [ "$2" == "0" ]
then
    CHAR="[:alnum:]"
else
    CHAR="[:graph:]"
fi
word=
for ((i=0; i<n; i++))
do
    thischar=$(tr -cd "$CHAR" < /dev/urandom | head -c 1)
    if ! [[ "$thischar" =~ [[:alnum:]] ]]
                            # Probably equivalent to if [[ "$thischar" =~ [[:punct:]] ]]
    then
        # Got one special character – don’t allow any more.
        echo "$thischar is a special character."
        CHAR="[:alnum:]"
    fi
    word="$word$thischar"
done
echo "$word"

これは最初の3つの特殊文字(例ab!defghijklmnopqrstuvwxyz123456:)を取得します。非常に 頻繁に。また、この方法を使用すると、理論的に特殊文字が含まれていないパスワードを取得することも可能です。

答え2

[:alnum:]まず32文字を作成し、オプションで特殊文字を挿入すると思いました。

function randpass() {
  passwd=$( < /dev/urandom tr -cd "[:alnum:]" | head -c $1)
  if [ "$2" == "0" ]; then
    echo "$passwd"
  else
    spchar=$( < /dev/urandom tr -cd "[:punct:]" | head -c 1)
    pos=$((RANDOM%$1))
    echo "${passwd:0:pos}${spchar}${passwd:pos+1:$1}"
  fi
}

私は[:punct:]あなたが「特別」だと思うすべての文字が含まれていると仮定します。

構文は次のとおり$(( ))です。シェル算術拡張0から31までの乱数(または任意の数字$1)を生成します。

構文は次のとおり${var:offset:length}です。シェルパラメータ拡張文字列から部分文字列を返します。

答え3

headコマンドを次のように変更します-c 1

# Generate a random password
#  $1 = number of characters; defaults to 32
#  $2 = include special characters; 1 = yes, 0 = no; defaults to 1
function randpass() {
  [ "$2" == "0" ] && CHAR="[:alnum:]" || CHAR="[:graph:]"
    cat /dev/urandom | tr -cd "$CHAR" | head -c 1
    echo
}

関連情報