QuickLauncher/插件目录
QUICKLAUNCHER / DEVELOPERS

开发者指南

用熟悉的语言,给 QuickLauncher 添加一个小功能。

脚本协议 v1
从一个目录开始

编写清单和脚本 → 本地导入测试 → 发布 GitHub Release → 申请展示站收录。文本参数、选中文字、复制结果和定时提醒由应用提供。

创建你的第一个插件

创建一个目录,放入以下两个文件。本例将输入的文本原样显示并复制;无参数时可使用前台应用中选中的文本。

manifest.json

{
  "id": "com.example.echo",
  "name": "文本示例",
  "description": "显示并复制文本",
  "keyword": "echo",
  "version": "1.0.0",
  "author": "Example",
  "runtime": "python",
  "entry": "main.py",
  "input": "arguments",
  "acceptsSelectedText": true
}

main.py

import json
import sys
import unicodedata

request = json.load(sys.stdin)
text = request.get("arguments", "").strip()
if request.get("version") != 1:
    result = {"version": 1, "action": "error", "text": "不支持的协议版本"}
elif not text or len(text) > 200 or any(unicodedata.category(c) == "Cc" for c in text):
    result = {"version": 1, "action": "error", "text": "请输入不超过 200 字的单行文本"}
else:
    result = {"version": 1, "action": "copyAndShow", "text": text}
print(json.dumps(result, ensure_ascii=False))

在该目录运行下面的命令,预期输出包含 copyAndShow 和 Hello 的 JSON。此命令只运行脚本,不会操作 QuickLauncher 或剪贴板。

printf '%s\n' '{"version":1,"arguments":"Hello"}' | python3 main.py

接着在 QuickLauncher 的“设置 → 脚本与插件 → 发现插件”点击“导入插件…”,选择这个目录。查看代码并启用后,输入 echo Hello,选择插件执行。Python 需要本机已有可用的 Python 3;可在“运行环境”中配置解释器。

示例声明了选区能力:只输入 echo 并执行时,应用会尝试读取唤起前的选中文字。没有这项需求时,请删除 acceptsSelectedText。

插件清单

manifest.json 是插件目录根部的 UTF-8 JSON 文件。以下字段除标注可选外均为字符串且必填。

字段说明
id唯一标识,最多 120 字符;以英文字母或数字开头,之后可用字母、数字、点、下划线、连字符。建议使用反向域名,发布后保持稳定。
name / description显示名称与功能说明;名称不能为空。
keyword触发词,1–32 个英文字母、数字、下划线或连字符,大小写不敏感。用户可修改;相同触发词的插件不能同时启用。
version / author版本与作者信息。建议发布版本与 Git 标签保持一致。
runtimeshell、python、ruby、applescript 或 executable。前四种可在应用中配置解释器绝对路径;executable 的入口需有执行权限。
entry入口文件的相对路径,必须存在;不使用绝对路径或 .. 路径段。应用以插件目录作为工作目录。
input(可选)arguments 接收触发词后的文本;passwordLength 接收密码长度;不声明时仅匹配触发词。
acceptsSelectedText(可选)布尔值。设为 true 时必须同时声明 input: "arguments";无参数执行时才尝试读取选区。
sourceURL(可选)插件源码地址。

标准输入与输出

仅在用户选择插件并执行时启动脚本。应用通过标准输入发送一个 JSON 请求;脚本向标准输出写一个完整 JSON 对象,并以成功退出码结束。不要在标准输出混入日志;标准错误不会展示或记录。

{"version":1}
{"version":1,"arguments":"Hello"}
{"version":1,"passwordLength":24}

请求始终包含协议 version: 1。arguments 是触发词后的原始文本,最多 1024 UTF-8 字节;passwordLength 为 8–128 的整数,用户未临时指定时使用应用设置的默认长度。按清单声明选择输入类型;仅声明 arguments 的插件可以接收选区。

返回 action行为与限制示例
copy复制 text;不在面板显示其内容,适合敏感结果。{"version":1,"action":"copy","text":"value"}
copyAndShow复制并显示 text,面板保持打开;不适合密码等敏感内容。{"version":1,"action":"copyAndShow","text":"9"}
message显示短暂提示。{"version":1,"action":"message","text":"完成"}
error显示错误并保持面板。{"version":1,"action":"error","text":"输入无效"}
scheduleReminder由应用安排一次系统通知;seconds 为 1–2,592,000 的整数(最长 30 天)。{"version":1,"action":"scheduleReminder","text":"喝水","seconds":600}

所有响应的 text 均不能为空;copyAndShow、error 和提醒文本最多 200 字符且不能含控制字符,提醒文本不能仅为空白。脚本执行超时为 5 秒,标准输出上限 65,536 字节;超限或 JSON 无效将被拒绝。

应用提供的能力

文本参数

声明 input: "arguments",执行 keyword 参数 时获得文本;应用不会把脚本查询写入使用历史。

读取选中文字

额外声明 acceptsSelectedText: true。只有用户无参数执行插件时才读取唤起前应用的选区,作为 arguments 传入。需用户授予辅助功能权限,目标应用也须提供选区;失败时用户可直接输入。不会模拟复制按键或读取剪贴板。

显示或复制结果

返回 copy、copyAndShow、message 或 error;由应用处理界面和剪贴板。剪贴板内容可能被有权限的其他应用读取。

定时提醒

返回 scheduleReminder,应用向系统申请一次性通知;首次使用时可能请求通知授权。显示受系统通知设置和专注模式影响,脚本无需后台等待。

权限与信任:脚本以当前用户身份运行,不受 QuickLauncher 沙箱限制,可自行访问文件、网络或其他应用;AppleScript 控制其他应用可能需要系统自动化权限。请在说明中明确数据用途,不上传敏感数据,不把凭证写入插件包。选区读取需由用户自行授权,标记为安全输入的控件不会读取。应用未提供任意插件访问书签、查询历史或密码的宿主 API。

本地安装与调试

  1. 在“设置 → 脚本与插件 → 发现插件”选择“导入插件…”,选包含清单的目录。
  2. 插件默认停用。在“已安装”检查文件后启用;若声明选区能力,启用时会说明。需要时在“设置 → 权限”自行管理系统授权。
  3. 输入完整触发词和可选参数,选中结果执行;也可在设置中调整触发词及 Python、Ruby、Shell 或 AppleScript 解释器路径。
  4. 导入时会复制文件,源目录改动不会自动同步;修改已安装副本后,需检查代码并重新启用。要重新导入相同 ID,需先删除旧副本;请留意保存自定义设置。请使用新版 QuickLauncher 以支持本页介绍的协议。

参考完整开源插件:计算器、定时提醒、密码生成。

发布到 GitHub

发布公开仓库与正式 Release 后,即可在应用内用 owner/repo 查找并审查安装。发布前确认插件文件不包含密钥或个人数据,并使用已经测试的 Git 提交打包。

如果已经通过本地导入安装了相同 ID,应用不会直接把该副本切换为 GitHub 来源。请先保存需要保留的自定义设置并删除本地副本,再从 GitHub 安装;也可以在隔离的测试环境中验证 GitHub 安装。
  1. 在 GitHub 创建一个空的公开仓库,将插件提交并配置 origin 指向它。新建仓库可在插件目录中执行以下命令,将 OWNER/REPO 替换成自己的仓库名;已有 Git 仓库可跳过初始化和添加已有 remote 的步骤。
git init -b main
git add manifest.json main.py
git commit -m "Add plugin"
git remote add origin https://github.com/OWNER/REPO.git

可添加 quicklauncher-plugin topic 作为仓库标记;应用内未收录仓库使用完整 owner/repo 查找。

  1. 下载 插件打包工具(MIT 协议,许可证;需要 Python 3.9+),创建并推送标签,从标签导出文件并打包。下面命令在插件 Git 仓库根目录执行:
git tag v1.0.0
git push origin main v1.0.0
WORK_DIR="$(mktemp -d "${TMPDIR:-/tmp}/quicklauncher-release.XXXXXX")"
mkdir "$WORK_DIR/source"
git archive v1.0.0 | tar -x -C "$WORK_DIR/source"
curl -fsSL https://plugin.quicklauncher.flyee.tech/tools/package_github_plugin.py -o "$WORK_DIR/package_github_plugin.py"
python3 "$WORK_DIR/package_github_plugin.py" "$WORK_DIR/source" "$WORK_DIR/my-plugin.quicklauncher.json"

如果标签已存在,请跳过创建标签的命令。替换 main 为仓库的实际分支名。工具拒绝 .git、符号链接、特殊文件、常见凭证文件、无效清单及超限内容,不会覆盖现有输出;插件最多 1000 个文件、原始内容总计不超过 10 MB、JSON 资产不超过 16 MB。自动检查不能识别所有敏感信息,请逐项检查它列出的文件。

在 GitHub 创建正式 Release 并上传唯一一个以 .quicklauncher.json 结尾的附件。例如,安装 GitHub CLI 并登录后:

gh release create v1.0.0 "$WORK_DIR/my-plugin.quicklauncher.json" \
  --repo OWNER/REPO --verify-tag --title v1.0.0 --notes "首个版本"

将 OWNER/REPO 替换为你的公开仓库。源码 ZIP 不能代替该附件。应用会显示仓库、标签、提交和资产摘要并在用户确认后安装;摘要一致不证明作者身份或资产确实由该提交构建。后续使用新标签发布更新,用户审核变更后确认。

想提供直接打开应用的链接,可使用 quicklauncher://install?repo=OWNER%2FREPO,将仓库名替换为你的值。链接只触发查找和审核,不能绕过用户确认。

申请目录收录

GitHub 仓库可先通过 owner/repo 安装;添加 topic 不会自动出现在展示站。要申请收录,请通过 官网仓库提交 Pull Request,插件源码和 Release 仍保留在你自己的 GitHub 仓库。

  1. 准备发布:按照发布到 GitHub创建公开仓库和正式 Release,上传唯一的 .quicklauncher.json 附件。确认清单、入口、版本和运行环境可用,并说明插件用途、触发词及需要的权限。
  2. Fork 并创建分支:在 GitHub Fork 官网仓库,从最新的 main 创建分支,将你的 OWNER/REPO 添加到官网仓库的 catalog-repositories.json。不要手动修改 catalog.json,它由同步任务生成。
  3. 添加网站卡片:在 index.html 的插件列表中添加卡片,填写唯一的卡片 ID、搜索关键词、插件名称、用途、运行环境、源码链接和安装链接;data-repository 必须与白名单中的仓库名一致。版本标签使用 版本待同步,不要写死版本号。
  4. 检查并提交:更新 tests/catalog.test.js 与 tests/catalog-versions.test.js 中的卡片、数量及版本期望,在官网仓库运行 node tests/catalog.test.js、node tests/catalog-versions.test.js 和 node tests/developer.test.js。向官网仓库的 main 发起 PR,说明仓库、Release、功能、测试方式和所需权限。

以下是卡片结构示例,将 OWNER/REPO 和说明替换为你的实际信息;安装链接中的斜杠使用 %2F:

<article class="plugin-card" id="example-plugin" data-search="示例 example" data-repository="OWNER/REPO">
  <div class="plugin-icon" aria-hidden="true">★</div>
  <div class="plugin-main">
    <div class="plugin-title-row">
      <h3>插件名称</h3><span class="version">版本待同步</span>
      <a class="plugin-source" href="https://github.com/OWNER/REPO"
         target="_blank" rel="noopener noreferrer">GitHub 源码</a>
    </div>
    <p class="plugin-summary">简要说明插件用途和触发词。</p>
    <div class="plugin-meta">作者 · 运行环境 · 许可证</div>
  </div>
  <div class="plugin-actions">
    <a class="plugin-action" href="quicklauncher://install?repo=OWNER%2FREPO">
      在 QuickLauncher 中打开 ↗
    </a>
  </div>
</article>

维护者会审核 PR 和插件内容;当前仓库没有专门针对插件 PR 的自动安全审查,提交不代表自动收录。合并后网站随主分支更新,GitHub Actions 约每四小时同步白名单中的最新正式 Release、标签提交和资产摘要,也可由维护者手动触发。同步或部署可能延迟或失败;目录更新前,新卡片的版本可能显示“版本暂不可用”。网站卡片从目录读取版本,名称和介绍仍需维护。

收录的标签须以英文字母或数字开头,后续仅使用字母、数字、点、下划线或连字符(总长最多 200);附件名也须以字母或数字开头、仅含上述字符,并以 .quicklauncher.json 结尾。目录快照超过 48 小时后,应用会暂停使用该目录安装或更新;目录不可用时,按仓库名查找也可能暂时不可用。

用户通过网站进入 QuickLauncher 后仍须审查并确认安装,安装后插件默认停用;审核和摘要匹配不代表作者身份或代码安全已获验证。