Предисловие

В условиях отсутствия централизованной системы управления, такой как Active Directory и Group Policy Objects (GPO), администрирование парка принтеров становится нетривиальной задачей. Особенно остро это ощущается в гетерогенных средах, где совместно используются рабочие станции под управлением Windows, macOS и GNU/Linux. Стандартные решения вроде CUPS, идеально подходящие для *nix-систем, не всегда применимы для Windows-клиентов без потери функциональности.

В данной статье рассматривается метод автоматизированной установки сетевых принтеров на Windows с использованием оригинальных драйверов производителя. Это обеспечивает стабильность работы, доступ ко всем функциям оборудования и избегает проблем с совместимостью, характерных для универсальных драйверов.

Исходные условия и задачи

Инфраструктура: Офис ~300 пользователей; парк техники: Windows 10/11, macOS, GNU/Linux.

Парк принтеров:

  • Kyocera ECOSYS M3145dn (x3)

  • Kyocera ECOSYS M4132idn

  • HP PageWide 377dw MFP

  • HP LaserJet MFP M426fdn

  • Kyocera ECOSYS MA4000cix

Техническое задание (ТЗ):Автоматизация подключения сетевого принтера для пользователей Windows с минимальным их участием (идеально — в один клик).
Принтер должен отображаться с понятным именем (например, reception, accounting). Подключение по TCP/IP на стандартный порт 9100.

Обязательное использование оригинальных драйверов производителя для гарантии корректной работы и доступа ко всем настройкам.

Архитектура решения

Решение состоит из трех ключевых компонентов, упакованных в единый дистрибутив:

Реализация

1. Основной PowerShell-скрипт (InstallPrinter.ps1)

PowerShell-скрипт: Ядро системы, отвечающее за установку драйвера, создание TCP-порта и добавление принтера.
Пакет драйверов: Директория с распакованными оригинальными драйверами для конкретной модели принтера.
BAT-обертка: Вспомогательный скрипт, который временно изменяет политику выполнения PowerShell для работы основного скрипта и обеспечивает его запуск.

Скрипт использует встроенные административные инструменты Windows для печати.
powershell

# Скрипт для автоматической установки сетевого принтера с оригинальным драйвером.
# Параметры для подключения (должны быть адаптированы для каждого принтера)
$printerIP = "192.168.27.247"    # IP-адрес принтера в сети
$printerPort = "9100"            # Стандартный порт для печати (RAW)
$printerModel = "HP LaserJet Pro MFP M426f-M427f PCL-6" # Точное имя модели из INF-файла
$printerName = "reception"       # Удобное имя принтера для пользователя
# Определение путей
$scriptPath = $MyInvocation.MyCommand.Path
$scriptDir = Split-Path -Parent $scriptPath
# Предполагается, что драйверы находятся в единственной поддиректории
$driverFolder = Get-ChildItem -Path $scriptDir -Directory | Select-Object -First 1 -ExpandProperty Name
$driverDir = Join-Path -Path $scriptDir -ChildPath $driverFolder
# Вспомогательная функция для выполнения консольных команд
function Execute-Command {    param ([string]$Command)    Write-Output "Выполняется: $Command"    $exitCode = (cmd /c $Command 2>&1 | Out-String; $LastExitCode)    if ($LastExitCode -ne 0) {        Write-Error "Ошибка выполнения команды. Код выхода: $LastExitCode"        exit $LastExitCode    }
}
# Функция для рекурсивного поиска INF-файла, содержащего имя модели принтера
function Find-InfFile {    param (        [string]$driverDir,        [string]$printerModel    )    $infFiles = Get-ChildItem -Path $driverDir -Filter *.inf -Recurse    foreach ($infFile in $infFiles) {        $content = Get-Content $infFile.FullName -ErrorAction SilentlyContinue        if ($content -match [regex]::Escape($printerModel)) {            return $infFile.FullName        }    }    return $null
}
Write-Output "Поиск INF-файла для модели: $printerModel..."
$infPath = Find-InfFile -driverDir $driverDir -printerModel $printerModel
if (-Not $infPath) {    Write-Error "INF-файл для модели принтера '$printerModel' не найден в директории: $driverDir"    Write-Output "Убедитесь, что драйверы распакованы и модель указана точно."    exit 1
}
Write-Output "INF-файл найден: $infPath"
# Создание TCP-порта для принтера с помощью prnport.vbs
Write-Output "Создание порта принтера..."
$createPortCmd = "cscript C:\Windows\System32\Printing_Admin_Scripts\ru-RU\prnport.vbs -a -r `"$printerIP`" -h `"$printerIP`" -o RAW -n $printerPort"
Execute-Command $createPortCmd
# Установка драйвера в систему с помощью prndrvr.vbs
Write-Output "Установка драйвера..."
$installDriverCmd = "cscript C:\Windows\System32\Printing_Admin_Scripts\ru-RU\prndrvr.vbs -a -m `"$printerModel`" -v 3 -e 'Windows x64' -i `"$infPath`" -h `"$driverDir`""
Execute-Command $installDriverCmd
# Добавление принтера в систему с использованием printui.dll
Write-Output "Добавление принтера '$printerName'..."
$addPrinterCmd = "rundll32 printui.dll,PrintUIEntry /if /b `"$printerName`" /r `"$printerIP`" /m `"$printerModel`" /f `"$infPath`" /u /K /q /Gw"
Execute-Command $addPrinterCmd
Write-Output "Установка принтера '$printerName' успешно завершена."

2. BAT-обертка (Launcher.bat)

Решает проблему политики выполнения PowerShell, не требуя от пользователя ручных действий.

@echo off
setlocal
REM Сохранение текущей директории и поиск PS1-скрипта
set "scriptDir=%~dp0"
for %%f in ("%scriptDir%*.ps1") do set "scriptPath=%%f"
if not defined scriptPath (    echo Ошибка: В директории "%scriptDir%" не найден PowerShell-скрипт (.ps1).    pause    exit /b 1
)
REM Сохранение текущей политики выполнения
for /f "tokens=*" %%i in ('powershell -Command "Get-ExecutionPolicy -Scope LocalMachine"') do set "currPolicy=%%i"
REM Временное ослабление политики для установки
echo Настройка политики выполнения...
powershell -Command "Set-ExecutionPolicy Unrestricted -Scope LocalMachine -Force" >nul 2>&1
REM Запуск основного скрипта с обходом политики
echo Запуск скрипта установки...
powershell -ExecutionPolicy Bypass -File "%scriptPath%"
REM Восстановление исходной политики выполнения
echo Восстановление политики выполнения...
powershell -Command "Set-ExecutionPolicy %currPolicy% -Scope LocalMachine -Force" >nul 2>&1
echo -- Готово --
endlocal

3. Сборка дистрибутива

Для каждого принтера создается отдельная директория со следующей структурой:

Дистрибутив_Принтер_Reception/
│   InstallPrinter.ps1
│   Launcher.bat
│
└───HP_Drivers_M426fdn/        ├───...        └───*.inf, *.dll, ...

Порядок использования и дистрибуции

  1. Для каждого принтера готовится свой комплект файлов, где в скрипте InstallPrinter.ps1 изменены переменные $printerIP, $printerModel, $printerName и в поддиректорию HP_Drivers_... помещены соответствующие драйверы.

  2. Полученная директория упаковывается в самораспаковывающийся архив (SFX) с помощью архиваторов вроде WinRAR или 7-Zip.

    • В WinRAR: В SFX-настройках укажите Launcher.bat как "Файл для запуска после распаковки".

    • Установите опцию "Распаковать во временную папку" и "Выполнить скрытие".

    • Добавьте иконку для лучшего визуального восприятия.

Итоговый SFX-файл можно распространять среди пользователей. Им достаточно запустить его и подтвердить права администратора (если требуется). Все этапы установки пройдут автоматически.

Итоги и возможные пути улучшения

Представленное решение успешно решает задачу массовой установки принтеров в средах без AD. Оно обеспечивает использование оригинальных драйверов и минимальное участие пользователя.

Минусы текущей реализации:

Зависимость от сомнительного ПО (bat2exe) для конвертации BAT в EXE. Этого можно избежать, используя SFX-архивы, как описано выше.
Необходимость ручного приготовления отдельного дистрибутива для каждой модели принтера.

Возможные улучшения:

  • Параметризация: Можно сделать один главный скрипт, который принимает параметры (IP, модель, имя) из внешнего CSV-файла или конфигурационного INI-файла.

  • Централизованное хранилище драйверов: Драйверы можно разместить на файловом сервере, чтобы не включать их в каждый дистрибутив.

  • Графический интерфейс: Для менее технически подкованных пользователей можно разработать простой GUI на PowerShell или .NET, который будет запрашивать только локацию принтера.

  • Альтернативные инструменты упаковки: Использование MSI-пакетов (через WiX Toolset) или современных систем развертывания вроде Microsoft Intune предоставило бы больше контроля и лучшую интеграцию в корпоративную среду.

Несмотря на существование более элегантных методов, данное решение отличается простотой реализации, минимальными требованиями к инфраструктуре и эффективно решает поставленную задачу.

Буду рад услышать комментарии и предложения по оптимизации от сообщества.

Комментарии (10)


  1. DustCn
    18.10.2025 23:52

    Так, не понял, а где Катюша?


    1. nitro80
      18.10.2025 23:52

      В Корее, на складе пылится, ждёт, когда китайцы наклейку изготовят


  1. lamerAlex
    18.10.2025 23:52

    А зачем вы меняете политику выполнения powershell, если запускаете скрипт с -ExecutionPolicy Bypass ?

    парк техники: Windows 10/11:
    help Add-PrinterPort
    help Add-Printer

    Ну и заголовок не соответствует содержанию, не видно гетерогенной среды )


  1. Dupych
    18.10.2025 23:52

    Совсем не понятен механизм автоматической установки. ИИ смотрит, что Бухгалтер Сидорова в сети и подключает ей принтер...

    У меня в каждом офисе есть PRINT Server. В нем прописаны и расшарены все принтера.

    Набирая \\PRINT попадаешь на сервер. Далее таблица. Смотришь описание. Клацашь тот принтер который нужно и он сам ставится.

    Также через GPO. Автоматически ставился принтер.

    Вот тут я огреб.

    1. \\PRINT все принтеры подключенные через Принтсервер долго думают. Я румами ставлю принтер и он доступен всем пользователям данного пк. Не вижу проблемы прописать поинтер руками

    2. При дрменном входе политика цепляет принтер а он выключен. Вход в домен мучение. А когда это рабочмй сервер, то 200 пользователей долго входят особенно если 10 принтеры. на севере выключены

    Убрал всякие автоподкоючения принтеров.

    Прописываю руками и нет проблем.

    Только сетевые. Никаких USB.

    HP, Kyocera

    Проблем не знаю.

    ПРИНТ серверы в офисах оставил, чтобы если не смогу настроить например в дороге, то пользователь сам бы зашел и клацнул. Ну и для порядку. Смотрю какие принтеры на каких IP сидят.


    1. alexrus
      18.10.2025 23:52

      Автор имеет ввиду, что автоматически создается порт, принтер и выбирается драйвер. А пользователь (с правами админа) с шары сам запускает этот файлик. Страшно правда эту шару представить на 300 машин без домена))


  1. RoasterToaster
    18.10.2025 23:52

    Но суровые парни из Киосера для таких умников все продумали: в 1801, 4125 оригинальный драйвер по умолчанию выставляет какую то рандомную бумагу: пользовательская 5, картон и тд.

    То есть пользователь каждый раз бегает к аппарату нажать ок при печати, долго терпит а потом все таки зовёт айтишника.

    Причем эта фишка существует многие годы, это не баг, это фича. Наверное, чтобы техподдержка от Киосеры была востребована всегда.


    1. RoasterToaster
      18.10.2025 23:52


  1. CmpeJ1ok
    18.10.2025 23:52

    Хм, как в том анекдоте: «что будет кошка программист делать в цирке - не пойму», так и тут, только с точностью наоборот: чем CUPS не подходит? Или от админа в организации вы решили избавиться? Может каждый день пользователь подключает новый принтер в организации? Как экономика должна быть экономной, так и автоматизация должна упрощать работу, а пока вы дали возможность по клику ярлыка подключить принтер, но при этом не избавили админа потом идти к пользователю и настраивать его…


  1. Turbo_Demon
    18.10.2025 23:52

    Странное решение мне кажется. Сервер печати в полне удобное решение.

    У меня возник вопрос. Как управлять свойствами принтера в таком случае? Например если нужно изменить параметр печати пачке пользователей. Есть у кого подобное решение?


  1. Sosnin
    18.10.2025 23:52

    "с правами админа" .. кто бы им еще их давал ибо нефиг