Cкрипт для создания локальных пользователей с настройкой passwordless sudo.
Определяет дистрибутив через /etc/os-release. Для Astra Linux дополнительно выполняет pdpl-user -l 0:63 -i 63.
Проверяет наличие утилит, не пересоздаёт существующих пользователей и не изменяет их пароли. Конфигурация sudo проверяется через visudo. Поддерживает повторный запуск.
Запуск:
./create-users.sh user1 user2 user3#!/bin/bash
set -Eeuo pipefail
DEFAULT_USERS=(user1 user2 user3)
SUDOERS_DIR="/etc/sudoers.d"
SUDOERS_MODE="0440"
USER_SHELL="/bin/bash"
ASTRA_PDPL_LEVEL="0:63"
ASTRA_INTEGRITY="63"
TEMP_FILE=""
log() {
printf '[INFO] %s\n' "$*"
}
die() {
printf '[ERROR] %s\n' "$*" >&2
exit 1
}
cleanup() {
if [[ -n "$TEMP_FILE" && -f "$TEMP_FILE" ]]; then
rm -f -- "$TEMP_FILE"
fi
}
trap cleanup EXIT
# Проверка привилегий.
if [[ "$EUID" -ne 0 ]]; then
die "Скрипт необходимо запускать от root."
fi
# Определение дистрибутива.
OS_RELEASE="/etc/os-release"
if [[ ! -r "$OS_RELEASE" ]]; then
OS_RELEASE="/usr/lib/os-release"
fi
if [[ ! -r "$OS_RELEASE" ]]; then
die "Не найден файл os-release."
fi
unset ID PRETTY_NAME
. "$OS_RELEASE"
case "${ID:-}" in
debian)
OS_TYPE="debian"
;;
astra)
OS_TYPE="astra"
;;
*)
die "Неподдерживаемая ОС: ${ID:-unknown}"
;;
esac
log "ОС: ${PRETTY_NAME:-$OS_TYPE}"
log "Тип: $OS_TYPE"
# Проверка необходимых компонентов.
REQUIRED_COMMANDS=(
useradd
passwd
getent
mktemp
visudo
chmod
chown
mv
)
if [[ "$OS_TYPE" == "astra" ]]; then
REQUIRED_COMMANDS+=(pdpl-user)
fi
for cmd in "${REQUIRED_COMMANDS[@]}"; do
if ! command -v "$cmd" >/dev/null 2>&1; then
die "Не найдена команда: $cmd"
fi
done
if [[ ! -x "$USER_SHELL" ]]; then
die "Не найден shell: $USER_SHELL"
fi
if [[ ! -f /etc/sudoers || ! -d "$SUDOERS_DIR" ]]; then
die "Не найдена конфигурация sudo."
fi
# Проверка существующей конфигурации sudo.
if ! visudo -c >/dev/null; then
die "Обнаружена ошибка в существующей конфигурации sudo."
fi
# Выбор пользователей.
if [[ "$#" -gt 0 ]]; then
USERS=("$@")
else
USERS=("${DEFAULT_USERS[@]}")
fi
# Предварительная проверка имён.
for user in "${USERS[@]}"; do
if [[ ! "$user" =~ ^[a-z_][a-z0-9_-]*$ ]]; then
die "Некорректное имя пользователя: $user"
fi
done
# Создание и настройка пользователей.
for user in "${USERS[@]}"; do
log "Обработка пользователя: $user"
# Создание пользователя.
if getent passwd "$user" >/dev/null; then
log "Пользователь $user уже существует."
else
log "Создание пользователя $user"
useradd \
-m \
-s "$USER_SHELL" \
"$user" \
|| die "Не удалось создать пользователя $user"
# Пароль устанавливается только новому пользователю.
log "Установка пароля для $user"
if ! passwd "$user"; then
die "Ошибка установки пароля $user. Пользователь создан, задайте пароль вручную."
fi
fi
# Настройка мандатных атрибутов Astra Linux.
if [[ "$OS_TYPE" == "astra" ]]; then
log "Настройка мандатных атрибутов: $user"
pdpl-user \
-l "$ASTRA_PDPL_LEVEL" \
-i "$ASTRA_INTEGRITY" \
"$user" \
|| die "Ошибка pdpl-user для $user"
fi
# Создание временного файла sudoers.
SUDOERS_FILE="${SUDOERS_DIR}/${user}"
TEMP_FILE=$(mktemp "${SUDOERS_DIR}/.${user}.XXXXXX") \
|| die "Не удалось создать временный sudoers."
printf '%s ALL=(ALL) NOPASSWD: ALL\n' "$user" > "$TEMP_FILE"
chown root:root "$TEMP_FILE"
chmod "$SUDOERS_MODE" "$TEMP_FILE"
# Проверка синтаксиса перед установкой.
if ! visudo -cf "$TEMP_FILE" >/dev/null; then
die "Некорректная конфигурация sudo для $user"
fi
# Установка проверенной конфигурации.
mv -f -- "$TEMP_FILE" "$SUDOERS_FILE"
TEMP_FILE=""
log "Sudo настроен для $user"
done
# Финальная проверка.
visudo -c >/dev/null \
|| die "Ошибка итоговой проверки sudoers."
log "Все пользователи успешно обработаны."