Skip to content

feat(service-catalog): split printer-device access and LAN discovery lane (closes #67)#201

Open
clubanderson wants to merge 1 commit into
projectbluefin:mainfrom
clubanderson:feat/service-catalog/print-device-discovery-lane
Open

feat(service-catalog): split printer-device access and LAN discovery lane (closes #67)#201
clubanderson wants to merge 1 commit into
projectbluefin:mainfrom
clubanderson:feat/service-catalog/print-device-discovery-lane

Conversation

@clubanderson

Copy link
Copy Markdown
Contributor

Summary

Defines the printer-device access and LAN mDNS discovery validation lane as a standalone split from the base print-service lane (#64). Closes #67.

Dependency chain (made explicit by this PR)

#54 substrate (USB device passthrough + LAN network policy on ghost)
    → #67 this lane (USB access + mDNS discovery contract proven)
    → #64 base print lane (already unblocked; this lane extends it)

Acceptance criteria check

What's in this PR

tests/service_catalog/print_device/test_print_device_discovery.py

Two independent test classes with separate skip gates:

TestPrinterDeviceAccessLane (gate: TEST_USB_PRINTER_DEVICE env var)

Test What it proves
test_usb_device_node_exists_in_container hostPath device node visible in CUPS container
test_usb_device_node_is_character_device node is a real character device, not a placeholder
test_cups_can_detect_local_usb_printer CUPS lpinfo -v reports USB URI
test_cups_accepts_test_print_job lp submits job without error (cancelled immediately)
test_usb_device_permissions_allow_cups_user CUPS user can r/w device node
test_kubevirt_usb_passthrough_is_out_of_scope pytest.skip#54

TestLanDiscoveryLane (gate: TEST_AVAHI_ENABLED=true)

Test What it proves
test_ipp_service_exposed_outside_cluster service type is NodePort or LoadBalancer
test_nodeport_is_reachable_on_node_ip NodePort reachable from inside cluster using host IP
test_avahi_sidecar_container_is_running avahi sidecar container is Ready
test_avahi_daemon_process_is_active avahi-daemon process is alive inside sidecar
test_avahi_daemon_advertises_ipp_service avahi-browse _ipp._tcp finds the record
test_avahi_service_file_is_present_in_config .service file present in /etc/avahi/services/
test_auth_gated_cups_ui_is_out_of_scope pytest.skip → deferred
test_split_horizon_dns_for_cups_is_out_of_scope pytest.skip → bluespeed

Both classes skip cleanly when their gate condition is not met — non-hardware CI is not broken.

argo/workflow-templates/homelab-print-device.yaml

WorkflowTemplate with parameterized hardware paths:

  • usb-device-path: if set, adds hostPath volume + enables USB tests
  • avahi-enabled: true: adds avahi sidecar + NodePort service + enables mDNS tests
  • check-prerequisites guard step emits informative epic: homelab cluster substrate and fleet-client model #54 instructions without failing the workflow
  • Fixture uses lscr.io/linuxserver/cups:latest (real CUPS, not nginx stub — USB tests need lpinfo/lp)
  • Avahi sidecar: ubuntu:22.04 + avahi-daemon + ConfigMap-mounted _ipp._tcp service file

docs/homelab-contracts.md

Dependencies

…lane (closes projectbluefin#67)

Defines the printer-device access and LAN mDNS discovery validation lane as
a standalone split from the base print-service lane (projectbluefin#64).  Makes the
substrate dependencies (projectbluefin#54) explicit and keeps them out of the base lane.

## Dependency chain

  projectbluefin#54 substrate (USB device passthrough + LAN network policy on ghost)
      → projectbluefin#67 this lane (USB access + mDNS discovery contract proven)
      → projectbluefin#64 base print lane (already unblocked; this lane extends it)

## New files

### tests/service_catalog/print_device/test_print_device_discovery.py
Two test classes with independent skip gates:

TestPrinterDeviceAccessLane (gate: TEST_USB_PRINTER_DEVICE env var)
- test_usb_device_node_exists_in_container
- test_usb_device_node_is_character_device
- test_cups_can_detect_local_usb_printer (lpinfo -v)
- test_cups_accepts_test_print_job (lp + cancel)
- test_usb_device_permissions_allow_cups_user
- test_kubevirt_usb_passthrough_is_out_of_scope → pytest.skip → projectbluefin#54

TestLanDiscoveryLane (gate: TEST_AVAHI_ENABLED=true)
- test_ipp_service_exposed_outside_cluster (NodePort/LB)
- test_nodeport_is_reachable_on_node_ip
- test_avahi_sidecar_container_is_running
- test_avahi_daemon_process_is_active
- test_avahi_daemon_advertises_ipp_service (avahi-browse _ipp._tcp)
- test_avahi_service_file_is_present_in_config
- test_auth_gated_cups_ui_is_out_of_scope → pytest.skip → deferred
- test_split_horizon_dns_for_cups_is_out_of_scope → pytest.skip → bluespeed

Both classes skip cleanly when their gate condition is not met so non-hardware
CI is not broken.

### argo/workflow-templates/homelab-print-device.yaml
WorkflowTemplate with three parameters controlling hardware paths:
- usb-device-path: set to /dev/usb/lp0 to enable USB tests (hostPath volume)
- avahi-enabled: set to 'true' to enable mDNS tests (NodePort svc + avahi sidecar)
- ipp-nodeport: default 30631

check-prerequisites guard step emits informative messages about projectbluefin#54 requirements
but does not fail — tests self-skip when conditions are absent.

Fixture uses lscr.io/linuxserver/cups:latest (real CUPS image, not nginx stub)
because USB tests require actual CUPS commands (lpinfo, lp, lpstat).

Avahi sidecar uses ubuntu:22.04 + avahi-daemon + ConfigMap service definition
for the _ipp._tcp record.

### argo/homelab-print-device.yaml
Workflow submit trigger.

## Updated files

### docs/homelab-contracts.md
- §6 known-blockers: projectbluefin#67 → ✅ defined
- §7 Printer-Device Access and LAN Discovery Lane added:
  boundary table (base vs this lane), substrate assumptions tables,
  behavior tables for both test classes, WorkflowTemplate parameters table

Closes projectbluefin#67
Child of projectbluefin#51
Depends on projectbluefin#54 (substrate), projectbluefin#64 (base print lane)

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>

@hanthor hanthor left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM — well-structured test/infra addition, clean code.

@hanthor hanthor left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Service-catalog lane addition. Merge after foundational #202. LGTM.

@hanthor hanthor left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Approved via org-wide review.

@hanthor hanthor left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Approved via org-wide review.

@hanthor hanthor left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Review: Approved ✅

Part of the structured service-catalog project build-up. Conventional Commits format, referenced issues, consistent with related PRs in the series.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

feat: split printer-device access and LAN discovery from the base non-media lane

3 participants