打印客户端 SDK
@xihan-print/runtime/client 连接本地打印客户端:静默打印、写原始指令、导出 PDF、查打印机。这个子入口单独打包,不用客户端的页面不会加载它。
创建连接
createPrintClient()
declare function createPrintClient(options?: PrintClientOptions): PrintClient创建本地打印客户端的连接;不会立即连接,第一次调用时才连。
PrintClientOptions
createPrintClient 的选项。
| 属性 | 类型 | 说明 |
|---|---|---|
ports? | readonly number[] | 按顺序探测的端口,缺省 17620–17623。 |
timeoutMs? | number | 请求等响应的期限,缺省 10 秒。 |
connectTimeoutMs? | number | 每个端口建连的期限,缺省 3 秒。 |
consentTimeoutMs? | number | 客户端弹出授权窗口后等用户决定的期限,缺省 75 秒。 |
reconnect? | boolean | 断线后是否自动重连,缺省 true。 |
WebSocket? | WebSocketConstructor | WebSocket 构造函数,缺省为全局 WebSocket。 |
permissions? | PermissionsLike | null | 查本机网络权限的入口,缺省为 navigator.permissions;为 null 时不查。 |
secureContext? | boolean | 页面是否是安全上下文,缺省为全局 isSecureContext。 |
origin? | string | 页面的来源,缺省为全局 location.origin;页面本身在本机回环地址上时,连不上不按本机网络权限判定。 |
fetch? | typeof fetch | 打包文档时取资源用的 fetch,缺省为全局 fetch。 |
PrintClient
本地打印客户端的连接。
| 属性 | 类型 | 说明 |
|---|---|---|
state | PrintClientState | 连接状态。 |
welcome | ClientWelcome | undefined | 最近一次握手的结果;还没连上过时为 undefined。 |
| 方法 | 说明 |
|---|---|
connect(): Promise<ClientWelcome> | 连接并握手;已连着时直接返回握手结果。连不上抛 PrintClientError,码为 CLIENT_UNAVAILABLE、LOCAL_NETWORK_DENIED、PROTOCOL_UNSUPPORTED、CONSENT_DENIED、CONSENT_TIMEOUT 等。 |
close(): void | 断开连接,不再重连;未结束的任务以 CONNECTION_LOST 拒绝,客户端里的任务照常执行完。 |
printers(): Promise<PrinterInfo[]> | 列出打印机,不含能力明细。 |
printer(name: string): Promise<PrinterInfo> | 查一台打印机,含能力明细。 |
printDocument(schema: PrintDocument, data: unknown, options?: PrintClientDocumentOptions): PrintClientJob | 按数据排出模板并交给客户端打印。 |
printSheets(result: PaginationResult, options?: PrintClientDocumentOptions): PrintClientJob | 把排好的输出页交给客户端打印。 |
printRaw(printer: string, data: Uint8Array | ArrayBuffer | string, options?: PrintRawOptions): PrintClientJob | 把原始指令原样写给打印机;字符串按 UTF-8 编码,要别的编码时先转成字节。 |
exportPdf(schema: PrintDocument, data: unknown, options?: PrintClientDocumentOptions): Promise<Blob> | 按数据排出模板并导出为 PDF。 |
exportSheetsPdf(result: PaginationResult, options?: PrintClientDocumentOptions): Promise<Blob> | 把排好的输出页导出为 PDF。 |
job(jobId: string): Promise<JobStatus> | 查任务状态。 |
on<K extends keyof PrintClientEventMap>(type: K, listener: (detail: PrintClientEventMap[K]) => void): () => void | 订阅事件,返回退订函数。 |
PrintClientJob
一个交给客户端的任务。
| 属性 | 类型 | 说明 |
|---|---|---|
id | string | 任务标识,由 SDK 生成。 |
status | JobStatus | undefined | 最近一次的状态;还没交给客户端时为 undefined。 |
done | Promise<JobStatus> | completed 时兑现;failed 时以客户端给出的错误码拒绝,cancelled 时以 JOB_CANCELLED 拒绝,发送前出错时以对应错误拒绝。 |
| 方法 | 说明 |
|---|---|
onStatus(listener: (status: JobStatus) => void): () => void | 订阅状态变化,返回退订函数。 |
cancel(): Promise<boolean> | 取消任务:排队中的立即取消并返回 true;执行中的尽力取消并返回 false,结果以状态为准。 |
PrintClientEventMap
客户端派发的事件。
用 client.on(type, listener) 订阅。连接状态 PrintClientState 取 idle、connecting、open、reconnecting、closed。
| 属性 | 类型 | 说明 |
|---|---|---|
state | PrintClientState | 连接状态变化。 |
consentpending | { readonly origin: string } | 来源还没授权,客户端已弹出授权窗口。 |
退回浏览器打印
printWithFallback()
declare function printWithFallback(client: PrintClient, schema: PrintDocument, data: unknown, options?: PrintWithFallbackOptions): Promise<PrintWithFallbackOutcome>先交给本地打印客户端打印,等到交给打印池;只在连不上客户端(CLIENT_UNAVAILABLE、PROTOCOL_UNSUPPORTED)时退回浏览器的打印对话框。打印机报错、拒绝授权等其它错误照常抛出,免得用户以为已经静默打出来了。
PrintWithFallbackOptions
printWithFallback 的选项:客户端打印选项、分页注入项,退回浏览器打印时另用 title。
继承 PrintClientDocumentOptions、Pick<PrintOptions, 'title'>。
PrintWithFallbackOutcome
printWithFallback 的结果:走了哪条路,与送去打印的页数。
| 属性 | 类型 | 说明 |
|---|---|---|
via | 'client' | 'browser' | |
sheets | number |
shouldFallBack()
declare function shouldFallBack(error: unknown): boolean这个错误是否表示连不上客户端、应该退回浏览器打印;打印机报错、拒绝授权等一律不退回。
错误码
出错时抛出或以 PrintClientError 拒绝,code 为下表之一,details 带补充信息。「SDK」一栏的码在浏览器里产生,其余由客户端给出。
| 错误码 | 出自 | 说明 | 退回浏览器打印 |
|---|---|---|---|
CLIENT_UNAVAILABLE | SDK | 所有端口都连不上(客户端没装或没运行),details 带端口 ports 与浏览器报的「本机应用」权限状态 permission(查不到时不带) | 是 |
LOCAL_NETWORK_DENIED | SDK | 连接在浏览器里就被拦下:页面不在本机回环地址上、所有端口都在建连期限内失败,且「本机应用」权限被拒或页面不是安全上下文 | 否 |
CONNECTION_LOST | SDK | 等结果时断线,或断线后没能在期限内重连上 | 否 |
TOO_MANY_CONNECTIONS | SDK | 同一来源的连接数超过客户端上限 | 否 |
TIMEOUT | SDK | 请求没有在期限内得到响应 | 否 |
JOB_CANCELLED | SDK | 任务被取消 | 否 |
BAD_REQUEST | 客户端 | 消息格式或字段不合法 | 否 |
CONSENT_PENDING | 客户端 | 授权窗口还开着时又发了业务请求 | 否 |
CONSENT_DENIED | 客户端 | 用户拒绝,或来源在拒绝名单 | 否 |
CONSENT_TIMEOUT | 客户端 | 授权窗口在期限内没人处理 | 否 |
SESSION_EXPIRED | 客户端 | 重连令牌过期或不属于这个来源,已当作新会话 | 否 |
PROTOCOL_UNSUPPORTED | 客户端 | 协议主版本不匹配 | 是 |
NO_PRINTERS | 客户端 | 本机没有任何打印机 | 否 |
PRINTER_NOT_FOUND | 客户端 | 指定的打印机不存在 | 否 |
PRINTER_OFFLINE | 客户端 | 打印机脱机、暂停或出错 | 否 |
PAPER_UNSUPPORTED | 客户端 | 打印机没有任务需要的纸张,且驱动不接受自定义尺寸 | 否 |
DOCUMENT_TOO_LARGE | 客户端 | 超过消息上限或资源总量上限 | 否 |
RESOURCE_BLOCKED | 客户端 | 文档里引用了随任务带来的资源之外的地址 | 否 |
RENDER_FAILED | 客户端 | 渲染引擎载入或等待就绪失败 | 否 |
RENDER_TIMEOUT | 客户端 | 渲染超时 | 否 |
SPOOL_FAILED | 客户端 | 交给打印池失败 | 否 |
PDF_FAILED | 客户端 | 导出 PDF 失败 | 否 |
JOB_DUPLICATE | 客户端 | 任务标识重复 | 否 |
JOB_NOT_FOUND | 客户端 | 查无此任务 | 否 |
QUEUE_FULL | 客户端 | 同一会话排队的任务超过上限 | 否 |
CAPABILITY_UNSUPPORTED | 客户端 | 请求了客户端没有的能力 | 否 |
INTERNAL | 客户端 | 未预期的异常 | 否 |
提醒码
HTML 通道的任务照常完成、但有宿主应当知道的情况时,JobStatus 的 warnings 里带若干条提醒(ClientWarningPayload),code 为下表之一,details 带补充信息。
| 提醒码 | 说明 |
|---|---|
PAPER_UNCHECKED | 驱动没有报纸张能力,或读不出驱动会留下哪种纸,没有核对纸张就照常下发了 |
PAPER_FITTED | 按 fitToNearestPaper 把某组改用了最接近的纸张:比纸大的内容按 scale 等比缩小,比纸小的原大居中 |
打印选项与结果
ClientPrintOptions
交给客户端的打印选项。纸张不在选项里:每组输出页按模板里的纸张尺寸下发;原始指令的纸张由指令自己决定。
| 属性 | 类型 | 说明 |
|---|---|---|
printer? | string | 打印机名称,缺省为默认打印机。 |
copies? | number | 份数,1–999。 |
collate? | boolean | 多份时逐份打印,缺省 true。 |
duplex? | 'simplex' | 'long-edge' | 'short-edge' | |
color? | 'color' | 'grayscale' | |
pageRanges? | string | 页码范围,如 1-3,5。 |
dialog? | boolean | 弹系统打印对话框,缺省静默打印。 |
timeoutMs? | number | 交给打印池的期限,毫秒。 |
fitToNearestPaper? | boolean | 打印机没有某组的纸张、驱动也不接受这个尺寸时,改用最接近的纸张,比纸大的内容等比缩小到放得下,比纸小的原大居中;缺省 false,这时整个任务以 PAPER_UNSUPPORTED 失败。 |
PrintClientDocumentOptions
打印与导出的选项:客户端打印选项、分页注入项与打包文档的选项。
继承 ClientPrintOptions、PrintRenderOptions、Pick<ClientDocumentOptions, 'document'>。
PrintRawOptions
写原始指令的选项。
| 属性 | 类型 | 说明 |
|---|---|---|
docName? | string | 打印池里显示的文档名,缺省为任务标识。 |
JobStatus
任务的当前状态。
任务状态 JobState 取 queued、started、completed、failed、cancelled。
| 属性 | 类型 | 说明 |
|---|---|---|
jobId | string | |
state | JobState | |
position? | number | 排队时同一台打印机前面还有几个任务。 |
sheets? | number | HTML 通道交给打印池的页数。 |
bytes? | number | 原始通道写出的字节数,或导出的 PDF 大小。 |
error? | ClientErrorPayload | |
warnings? | readonly ClientWarningPayload[] | HTML 通道完成时的提醒,如没能核对纸张、按 fitToNearestPaper 换了纸;没有时缺省。 |
打印机与客户端信息
PrinterInfo
一台打印机。
打印机状态 PrinterState 取 ready、paused、offline、error、paperOut、paperJam、busy、unknown。
| 属性 | 类型 | 说明 |
|---|---|---|
name | string | |
isDefault | boolean | |
status | PrinterState | |
statusFlags | number | 系统给出的原始状态位。 |
location? | string | |
comment? | string | |
driver? | string | |
port? | string | |
isNetwork | boolean | |
capabilities? | PrinterCapabilities |
PrinterCapabilities
打印机能力,只在查单台打印机时给出。
| 属性 | 类型 | 说明 |
|---|---|---|
color | boolean | |
duplex | boolean | |
maxCopies | number | |
papers | readonly PaperInfo[] |
PaperInfo
打印机支持的一种纸张。
| 属性 | 类型 | 说明 |
|---|---|---|
id | number | |
name | string | |
widthMm | number | |
heightMm | number |
ClientWelcome
握手成功后客户端的回复。
| 属性 | 类型 | 说明 |
|---|---|---|
protocol | number | |
minor | number | |
client | ClientInfo | |
capabilities | ClientCapabilities | |
resumed | readonly string[] | 重连认回会话时仍未结束的任务。 |
ClientInfo
客户端信息。
| 属性 | 类型 | 说明 |
|---|---|---|
version | string | |
os | string | |
arch | string | |
renderer? | string | 渲染引擎版本;没有渲染引擎时缺省。 |
ClientCapabilities
客户端能力。
| 属性 | 类型 | 说明 |
|---|---|---|
html | boolean | |
raw | boolean | |
pdf | boolean | |
duplex | boolean | |
printerStatus | boolean |
交给客户端的文档
buildClientDocument()
declare function buildClientDocument(result: PaginationResult, options?: ClientDocumentOptions): Promise<ClientDocument>把分页结果打包成交给客户端的文档:输出页渲染进一份独立的 HTML(只在预览中显示的元素不画),图片、背景图与模板用到的字体取来随任务带去,地址改写成客户端里的资源地址。
ClientDocumentOptions
打包文档的选项。
| 属性 | 类型 | 说明 |
|---|---|---|
document? | Document | 发起打印的文档:从它的样式表里找模板用到的字体,相对地址也按它解析;缺省为全局 document。 |
fetch? | typeof fetch | 取资源用的 fetch,缺省为全局 fetch。 |
extensions? | readonly PrintRuntimeExtension[] | 扩展:扩展元素按它们给的渲染画出,与分页用同一份。 |
trace? | PrintTrace | 各环节的回调:报生成 DOM、取资源与合成文档三个环节的起止,见 PrintTrace。 |
ClientDocument
交给客户端的文档:自包含的输出页、资源与按出现顺序的纸张分组。
| 属性 | 类型 | 说明 |
|---|---|---|
html | string | |
resources | readonly ClientResource[] | |
sheets | readonly ClientSheetGroup[] |
ClientResource
随任务带去的一份资源,data 为 base64。
| 属性 | 类型 | 说明 |
|---|---|---|
id | string | |
type | string | |
data | string |
ClientSheetGroup
连续的若干张同尺寸输出页。
| 属性 | 类型 | 说明 |
|---|---|---|
widthMm | number | |
heightMm | number | |
count | number |
常量
| 名称 | 值 | 说明 |
|---|---|---|
DEFAULT_PORTS | [17620, 17621, 17622, 17623] | 客户端监听的端口,按顺序探测。 |
SUB_PROTOCOL | 'xihan-print.v1' | 带主版本的子协议。 |
PROTOCOL_VERSION | 1 | 协议主版本。 |
PROTOCOL_MINOR | 0 | 协议次版本:只加不减。 |
全部导出
client/client
| 名称 | 种类 | 说明 |
|---|---|---|
createPrintClient | 函数 | 创建本地打印客户端的连接;不会立即连接,第一次调用时才连。 |
PermissionsLike | 接口 | 查浏览器权限的入口,形同 navigator.permissions。 |
PrintClient | 接口 | 本地打印客户端的连接。 |
PrintClientDocumentOptions | 接口 | 打印与导出的选项:客户端打印选项、分页注入项与打包文档的选项。 |
PrintClientEventMap | 接口 | 客户端派发的事件。 |
PrintClientJob | 接口 | 一个交给客户端的任务。 |
PrintClientOptions | 接口 | createPrintClient 的选项。 |
PrintClientState | 类型 | 连接状态。 |
PrintRawOptions | 接口 | 写原始指令的选项。 |
WebSocketConstructor | 类型 | 能当 WebSocket 用的构造函数,单测可注入假实现。 |
client/document
| 名称 | 种类 | 说明 |
|---|---|---|
buildClientDocument | 函数 | 把分页结果打包成交给客户端的文档:输出页渲染进一份独立的 HTML(只在预览中显示的元素不画),图片、背景图与模板用到的字体取来随任务带去,地址改写成客户端里的资源地址。 |
ClientDocumentOptions | 接口 | 打包文档的选项。 |
client/errors
| 名称 | 种类 | 说明 |
|---|---|---|
FALLBACK_CODES | 常量 | 连不上客户端、可以退回浏览器打印的错误码:客户端没装或没运行,或协议主版本不对。 |
PrintClientError | 类 | 打印客户端相关的错误,code 与 details 供调用方判断与生成文案。 |
shouldFallBack | 函数 | 这个错误是否表示连不上客户端、应该退回浏览器打印;打印机报错、拒绝授权等一律不退回。 |
client/fallback
| 名称 | 种类 | 说明 |
|---|---|---|
printWithFallback | 函数 | 先交给本地打印客户端打印,等到交给打印池;只在连不上客户端(CLIENT_UNAVAILABLE、PROTOCOL_UNSUPPORTED)时退回浏览器的打印对话框。 |
PrintWithFallbackOptions | 接口 | printWithFallback 的选项:客户端打印选项、分页注入项,退回浏览器打印时另用 title。 |
PrintWithFallbackOutcome | 接口 | printWithFallback 的结果:走了哪条路,与送去打印的页数。 |
client/protocol
| 名称 | 种类 | 说明 |
|---|---|---|
ClientCapabilities | 接口 | 客户端能力。 |
ClientDocument | 接口 | 交给客户端的文档:自包含的输出页、资源与按出现顺序的纸张分组。 |
ClientErrorCode | 类型 | 客户端给出的错误码。 |
ClientErrorPayload | 接口 | 响应与任务事件里的错误。 |
ClientInfo | 接口 | 客户端信息。 |
ClientPrintOptions | 接口 | 交给客户端的打印选项。 |
ClientResource | 接口 | 随任务带去的一份资源,data 为 base64。 |
ClientSheetGroup | 接口 | 连续的若干张同尺寸输出页。 |
ClientWarningCode | 类型 | 客户端在完成的任务里给出的提醒码。 |
ClientWarningPayload | 接口 | 任务照常完成、但宿主应当知道的情况,code 取 ClientWarningCode。 |
ClientWelcome | 接口 | 握手成功后客户端的回复。 |
DEFAULT_PORTS | 常量 | 客户端监听的端口,按顺序探测。 |
JobState | 类型 | 任务状态。 |
JobStatus | 接口 | 任务的当前状态。 |
PaperInfo | 接口 | 打印机支持的一种纸张。 |
PrintClientErrorCode | 类型 | 打印客户端相关的全部错误码。 |
PrinterCapabilities | 接口 | 打印机能力,只在查单台打印机时给出。 |
PrinterInfo | 接口 | 一台打印机。 |
PrinterState | 类型 | 打印机状态。 |
PROTOCOL_MINOR | 常量 | 协议次版本:只加不减。 |
PROTOCOL_VERSION | 常量 | 协议主版本。 |
SdkErrorCode | 类型 | SDK 自己给出的错误码: |
SUB_PROTOCOL | 常量 | 带主版本的子协议。 |
