A PHP 7.4+ package for managing IPP printers in Yii2 applications using the nateobray/IPP library.
composer require yourcompany/yii2-ipp-printer-managerAdd the component to your config/web.php:
'components' => [
'printerIPP' => [
'class' => 'app\components\PrinterIPP',
'autoConnect' => false,
'healthCheckInterval' => 300, // 5 minutes
'printers' => [
'office_hp_laser' => [
'type' => 'hp',
'host' => '192.168.1.100',
'port' => 631,
'username' => 'admin',
'password' => 'secure_password',
'timeout' => 30,
'encryption' => false
],
'warehouse_canon' => [
'type' => 'canon',
'host' => '192.168.1.101',
'port' => 631,
'pincode' => '1234',
'encryption' => true,
'timeout' => 45
],
'reception_generic' => [
'type' => 'generic',
'host' => '192.168.1.102',
'port' => 631,
'timeout' => 20
]
]
]
],// In your controller
public function actionPrint()
{
$printerIPP = \Yii::$app->printerIPP;
// Load document (PDF, PostScript, etc.)
$document = file_get_contents('/path/to/document.pdf');
// Print options
$options = [
'job-name' => 'Invoice #12345',
'copies' => 1,
'media' => 'iso_a4_210x297mm',
'sides' => 'one-sided',
'print-quality' => 'high'
];
try {
$result = $printerIPP->printBySlug('office_hp_laser', $document, $options);
if ($result['success']) {
return $this->asJson([
'status' => 'success',
'job_id' => $result['job-id'],
'message' => 'Document queued for printing'
]);
}
} catch (\Exception $e) {
return $this->asJson([
'status' => 'error',
'message' => $e->getMessage()
]);
}
}// Check all printers health
public function actionHealthDashboard()
{
$printerIPP = \Yii::$app->printerIPP;
$health = $printerIPP->getHealthStatus();
$summary = [];
foreach ($health as $name => $status) {
$summary[$name] = [
'online' => $status['online'],
'supplies' => $this->formatSupplies($status['supplies'] ?? []),
'last_check' => $status['last_check']
];
}
return $this->render('health', ['printers' => $summary]);
}
private function formatSupplies(array $supplies): array
{
$formatted = [];
foreach ($supplies as $supply) {
$formatted[] = [
'name' => $supply['name'],
'level' => $supply['level'],
'status' => $supply['status'],
'color' => $supply['color'] ?? 'unknown'
];
}
return $formatted;
}// Get printer jobs
public function actionJobs($printerName)
{
$printer = \Yii::$app->printerIPP->getPrinter($printerName);
if (!$printer) {
throw new NotFoundHttpException('Printer not found');
}
$jobs = $printer->getJobs();
return $this->asJson([
'printer' => $printerName,
'jobs' => $jobs
]);
}
// Cancel job
public function actionCancelJob($printerName, $jobId)
{
$printer = \Yii::$app->printerIPP->getPrinter($printerName);
$success = $printer->cancelJob((int)$jobId);
return $this->asJson([
'success' => $success,
'message' => $success ? 'Job cancelled' : 'Failed to cancel job'
]);
}// Add printer at runtime
public function actionAddPrinter()
{
$config = [
'type' => 'hp',
'host' => '192.168.1.200',
'port' => 631,
'username' => 'printer_admin',
'password' => 'printer_pass'
];
$printerIPP = \Yii::$app->printerIPP;
$printerIPP->addPrinter('new_printer', $config);
// Test connection
$printer = $printerIPP->getPrinter('new_printer');
$connected = $printer->connect();
return $this->asJson([
'added' => true,
'connected' => $connected
]);
}The package follows these design patterns:
Different printer types (HP, Canon, Generic) implement the same PrinterInterface but with specific behaviors.
PrinterFactory creates appropriate printer instances based on configuration.
printerIPP orchestrates multiple printers and provides unified access.
Yii2 integration through PrinterIPP for dependency injection.
use app\components\printer\BasePrinter;
class EpsonPrinter extends BasePrinter
{
protected function initializeIPP(): void
{
parent::initializeIPP();
// Epson-specific initialization
// Set specific attributes or connection parameters
}
public function getSuppliesStatus(): array
{
$data = parent::getSuppliesStatus();
// Epson-specific supply processing
return $this->processEpsonSupplies($data);
}
private function processEpsonSupplies(array $supplies): array
{
// Custom Epson supply level interpretation
foreach ($supplies as &$supply) {
if ($supply['type'] === 'ink-cartridge') {
// Epson ink cartridges might report differently
$supply['epson_specific_data'] = $this->getEpsonInkData($supply);
}
}
return $supplies;
}
}
// Register the new printer type
PrinterFactory::registerPrinterType('epson', EpsonPrinter::class);class CustomPrinter extends BasePrinter
{
public function printJob(string $document, array $options = []): array
{
// Add custom pre-processing
$document = $this->preprocessDocument($document, $options);
// Add custom IPP attributes
if (isset($options['custom_option'])) {
$this->ipp->addAttribute('custom-attribute', $options['custom_option']);
}
return parent::printJob($document, $options);
}
private function preprocessDocument(string $document, array $options): string
{
// Custom document processing
return $document;
}
}The package includes console commands for printer management:
# Check all printer health
php yii printer/health
# Test print to all printers
php yii printer/test-print
# Check specific printer status
php yii printer/status office_hp_laserThe package provides comprehensive error handling:
try {
$result = $printerIPP->printBySlug('printer_name', $document, $options);
} catch (\InvalidArgumentException $e) {
// Configuration or parameter errors
\Yii::error("Printer configuration error: " . $e->getMessage());
} catch (\Exception $e) {
// Network, IPP, or printer errors
\Yii::error("Printer communication error: " . $e->getMessage());
}// Basic printer connectivity test
$printer = \Yii::$app->printerIPP->getPrinter('test_printer');
$isOnline = $printer->isOnline();
// Health check test
$health = \Yii::$app->printerIPP->getHealthStatus(true);
foreach ($health as $name => $status) {
if (!$status['online']) {
\Yii::warning("Printer {$name} is offline");
}
}- Credentials Storage: Store printer credentials securely, consider using environment variables:
'printers' => [
'secure_printer' => [
'host' => getenv('PRINTER_HOST'),
'username' => getenv('PRINTER_USERNAME'),
'password' => getenv('PRINTER_PASSWORD'),
]
]- Network Security: Use encryption when available:
'encryption' => true,
'timeout' => 30,- Input Validation: Always validate print options and document content before sending to printers.
- Connection Pooling: Set
autoConnect => falseand connect only when needed. - Health Check Caching: Use the built-in caching with appropriate intervals.
- Async Processing: Consider using Yii2 queues for large print jobs.
- Connection Timeouts: Increase timeout values for slow networks
- Authentication Failures: Verify credentials and printer settings
- IPP Version Compatibility: Some older printers may need specific IPP versions
Enable debug logging in your Yii2 configuration:
'log' => [
'targets' => [
[
'class' => 'yii\log\FileTarget',
'categories' => ['app\components\printer\*'],
'logFile' => '@runtime/logs/printer.log',
],
],
],