@jackwener/opencli 1.7.11 → 1.7.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (1004) hide show
  1. package/README.md +8 -7
  2. package/README.zh-CN.md +11 -9
  3. package/cli-manifest.json +12952 -6208
  4. package/clis/1688/assets.js +1 -0
  5. package/clis/1688/download.js +1 -0
  6. package/clis/1688/item.js +1 -0
  7. package/clis/1688/search.js +2 -1
  8. package/clis/1688/store.js +1 -0
  9. package/clis/1point3acres/digest.js +35 -0
  10. package/clis/1point3acres/forum.js +51 -0
  11. package/clis/1point3acres/forums.js +44 -0
  12. package/clis/1point3acres/hot.js +35 -0
  13. package/clis/1point3acres/latest.js +35 -0
  14. package/clis/1point3acres/notifications.js +64 -0
  15. package/clis/1point3acres/search.js +71 -0
  16. package/clis/1point3acres/thread.js +117 -0
  17. package/clis/1point3acres/user.js +77 -0
  18. package/clis/1point3acres/utils.js +247 -0
  19. package/clis/36kr/article.js +1 -0
  20. package/clis/36kr/hot.js +1 -0
  21. package/clis/36kr/news.js +1 -0
  22. package/clis/36kr/search.js +1 -0
  23. package/clis/51job/company.js +1 -0
  24. package/clis/51job/detail.js +1 -0
  25. package/clis/51job/hot.js +1 -0
  26. package/clis/51job/search.js +1 -0
  27. package/clis/_shared/desktop-commands.js +4 -0
  28. package/clis/aibase/news.js +110 -0
  29. package/clis/aibase/news.test.js +59 -0
  30. package/clis/amazon/bestsellers.js +1 -0
  31. package/clis/amazon/discussion.js +1 -0
  32. package/clis/amazon/discussion.test.js +1 -28
  33. package/clis/amazon/movers-shakers.js +1 -0
  34. package/clis/amazon/new-releases.js +1 -0
  35. package/clis/amazon/offer.js +1 -0
  36. package/clis/amazon/product.js +1 -0
  37. package/clis/amazon/rankings.js +1 -0
  38. package/clis/amazon/search.js +1 -0
  39. package/clis/antigravity/dump.js +1 -0
  40. package/clis/antigravity/extract-code.js +1 -0
  41. package/clis/antigravity/model.js +1 -0
  42. package/clis/antigravity/new.js +1 -0
  43. package/clis/antigravity/read.js +1 -0
  44. package/clis/antigravity/send.js +1 -0
  45. package/clis/antigravity/status.js +1 -0
  46. package/clis/antigravity/watch.js +4 -2
  47. package/clis/apple-podcasts/episodes.js +1 -0
  48. package/clis/apple-podcasts/search.js +1 -0
  49. package/clis/apple-podcasts/top.js +1 -0
  50. package/clis/arxiv/arxiv.test.js +112 -0
  51. package/clis/arxiv/author.js +44 -0
  52. package/clis/arxiv/paper.js +4 -3
  53. package/clis/arxiv/recent.js +33 -0
  54. package/clis/arxiv/search.js +19 -7
  55. package/clis/arxiv/utils.js +68 -5
  56. package/clis/baidu-scholar/search.js +1 -1
  57. package/clis/band/bands.js +1 -0
  58. package/clis/band/mentions.js +1 -0
  59. package/clis/band/post.js +1 -0
  60. package/clis/band/posts.js +1 -0
  61. package/clis/barchart/flow.js +1 -0
  62. package/clis/barchart/greeks.js +1 -0
  63. package/clis/barchart/options.js +1 -0
  64. package/clis/barchart/quote.js +1 -0
  65. package/clis/bbc/news.js +1 -0
  66. package/clis/bbc/topic.js +57 -0
  67. package/clis/bbc/utils.js +79 -0
  68. package/clis/bilibili/comments.js +1 -0
  69. package/clis/bilibili/download.js +1 -0
  70. package/clis/bilibili/dynamic.js +1 -0
  71. package/clis/bilibili/favorite.js +1 -0
  72. package/clis/bilibili/feed.js +2 -0
  73. package/clis/bilibili/following.js +1 -0
  74. package/clis/bilibili/history.js +1 -0
  75. package/clis/bilibili/hot.js +6 -1
  76. package/clis/bilibili/hot.test.js +17 -0
  77. package/clis/bilibili/me.js +1 -1
  78. package/clis/bilibili/ranking.js +1 -0
  79. package/clis/bilibili/search.js +1 -1
  80. package/clis/bilibili/subtitle.js +1 -0
  81. package/clis/bilibili/user-videos.js +1 -0
  82. package/clis/bilibili/video.js +1 -0
  83. package/clis/binance/asks.js +1 -0
  84. package/clis/binance/depth.js +1 -0
  85. package/clis/binance/gainers.js +1 -0
  86. package/clis/binance/klines.js +1 -0
  87. package/clis/binance/losers.js +1 -0
  88. package/clis/binance/pairs.js +1 -0
  89. package/clis/binance/price.js +1 -0
  90. package/clis/binance/prices.js +1 -0
  91. package/clis/binance/ticker.js +1 -0
  92. package/clis/binance/top.js +1 -0
  93. package/clis/binance/trades.js +1 -0
  94. package/clis/bloomberg/businessweek.js +1 -0
  95. package/clis/bloomberg/economics.js +1 -0
  96. package/clis/bloomberg/feeds.js +1 -0
  97. package/clis/bloomberg/industries.js +1 -0
  98. package/clis/bloomberg/main.js +1 -0
  99. package/clis/bloomberg/markets.js +1 -0
  100. package/clis/bloomberg/news.js +1 -0
  101. package/clis/bloomberg/opinions.js +1 -0
  102. package/clis/bloomberg/politics.js +1 -0
  103. package/clis/bloomberg/tech.js +1 -0
  104. package/clis/bluesky/feeds.js +1 -0
  105. package/clis/bluesky/followers.js +1 -0
  106. package/clis/bluesky/following.js +1 -0
  107. package/clis/bluesky/profile.js +1 -0
  108. package/clis/bluesky/search.js +1 -0
  109. package/clis/bluesky/starter-packs.js +1 -0
  110. package/clis/bluesky/thread.js +1 -0
  111. package/clis/bluesky/trending.js +1 -0
  112. package/clis/bluesky/user.js +3 -1
  113. package/clis/boss/batchgreet.js +1 -0
  114. package/clis/boss/chatlist.js +1 -0
  115. package/clis/boss/chatmsg.js +1 -0
  116. package/clis/boss/detail.js +1 -0
  117. package/clis/boss/exchange.js +1 -0
  118. package/clis/boss/greet.js +1 -0
  119. package/clis/boss/invite.js +1 -0
  120. package/clis/boss/joblist.js +1 -0
  121. package/clis/boss/mark.js +1 -0
  122. package/clis/boss/recommend.js +1 -0
  123. package/clis/boss/resume.js +1 -0
  124. package/clis/boss/search.js +1 -0
  125. package/clis/boss/send.js +1 -0
  126. package/clis/boss/stats.js +1 -0
  127. package/clis/chaoxing/assignments.js +2 -1
  128. package/clis/chaoxing/exams.js +2 -1
  129. package/clis/chatgpt/ask.js +57 -0
  130. package/clis/chatgpt/commands.test.js +45 -0
  131. package/clis/chatgpt/detail.js +46 -0
  132. package/clis/chatgpt/history.js +39 -0
  133. package/clis/chatgpt/image.js +13 -11
  134. package/clis/chatgpt/image.test.js +23 -0
  135. package/clis/chatgpt/new.js +25 -0
  136. package/clis/chatgpt/read.js +43 -0
  137. package/clis/chatgpt/send.js +46 -0
  138. package/clis/chatgpt/status.js +29 -0
  139. package/clis/chatgpt/utils.js +294 -4
  140. package/clis/chatgpt/utils.test.js +13 -0
  141. package/clis/chatgpt-app/ask.js +7 -3
  142. package/clis/chatgpt-app/model.js +1 -0
  143. package/clis/chatgpt-app/new.js +1 -0
  144. package/clis/chatgpt-app/read.js +1 -0
  145. package/clis/chatgpt-app/send.js +1 -0
  146. package/clis/chatgpt-app/status.js +1 -0
  147. package/clis/chatwise/ask.js +17 -43
  148. package/clis/chatwise/composer.test.js +186 -0
  149. package/clis/chatwise/export.js +1 -0
  150. package/clis/chatwise/history.js +1 -0
  151. package/clis/chatwise/model.js +1 -0
  152. package/clis/chatwise/read.js +1 -0
  153. package/clis/chatwise/send.js +3 -24
  154. package/clis/chatwise/utils.js +143 -0
  155. package/clis/claude/ask.js +2 -1
  156. package/clis/claude/detail.js +2 -0
  157. package/clis/claude/history.js +2 -0
  158. package/clis/claude/new.js +2 -0
  159. package/clis/claude/read.js +2 -0
  160. package/clis/claude/send.js +2 -0
  161. package/clis/claude/status.js +2 -0
  162. package/clis/cnki/search.js +1 -0
  163. package/clis/codex/ask.js +16 -9
  164. package/clis/codex/export.js +1 -0
  165. package/clis/codex/extract-diff.js +1 -0
  166. package/clis/codex/history.js +17 -33
  167. package/clis/codex/model.js +1 -0
  168. package/clis/codex/projects.js +28 -0
  169. package/clis/codex/read.js +11 -4
  170. package/clis/codex/send.js +11 -3
  171. package/clis/codex/sidebar.js +356 -0
  172. package/clis/codex/sidebar.test.js +329 -0
  173. package/clis/coingecko/categories.js +75 -0
  174. package/clis/coingecko/coin.js +107 -0
  175. package/clis/coingecko/coingecko.test.js +109 -0
  176. package/clis/coingecko/derivatives.js +84 -0
  177. package/clis/coingecko/exchanges.js +74 -0
  178. package/clis/coingecko/global.js +71 -0
  179. package/clis/coingecko/top.js +64 -0
  180. package/clis/coingecko/trending.js +55 -0
  181. package/clis/coupang/add-to-cart.js +22 -13
  182. package/clis/coupang/coupang.test.js +159 -0
  183. package/clis/coupang/product.js +257 -0
  184. package/clis/coupang/search.js +39 -16
  185. package/clis/coupang/utils.js +55 -1
  186. package/clis/crates/crate.js +62 -0
  187. package/clis/crates/search.js +44 -0
  188. package/clis/crates/utils.js +72 -0
  189. package/clis/ctrip/ctrip.test.js +234 -0
  190. package/clis/ctrip/hotel-suggest.js +45 -0
  191. package/clis/ctrip/search.js +23 -68
  192. package/clis/ctrip/utils.js +175 -0
  193. package/clis/cursor/ask.js +7 -3
  194. package/clis/cursor/composer.js +1 -0
  195. package/clis/cursor/export.js +1 -0
  196. package/clis/cursor/extract-code.js +1 -0
  197. package/clis/cursor/history.js +1 -0
  198. package/clis/cursor/model.js +1 -0
  199. package/clis/cursor/read.js +1 -0
  200. package/clis/cursor/send.js +1 -0
  201. package/clis/dblp/author.js +133 -0
  202. package/clis/dblp/dblp.test.js +397 -0
  203. package/clis/dblp/paper.js +40 -0
  204. package/clis/dblp/search.js +45 -0
  205. package/clis/dblp/utils.js +290 -0
  206. package/clis/dblp/venue.js +64 -0
  207. package/clis/deepseek/ask.js +13 -7
  208. package/clis/deepseek/ask.test.js +13 -13
  209. package/clis/deepseek/detail.js +38 -0
  210. package/clis/deepseek/detail.test.js +81 -0
  211. package/clis/deepseek/history.js +2 -0
  212. package/clis/deepseek/new.js +2 -0
  213. package/clis/deepseek/read.js +2 -0
  214. package/clis/deepseek/send.js +140 -0
  215. package/clis/deepseek/send.test.js +107 -0
  216. package/clis/deepseek/status.js +2 -0
  217. package/clis/deepseek/utils.js +66 -0
  218. package/clis/deepseek/utils.test.js +107 -1
  219. package/clis/defillama/defillama.test.js +99 -0
  220. package/clis/defillama/protocol.js +84 -0
  221. package/clis/defillama/protocols.js +55 -0
  222. package/clis/defillama/utils.js +99 -0
  223. package/clis/devto/devto.test.js +236 -0
  224. package/clis/devto/latest.js +74 -0
  225. package/clis/devto/read.js +103 -0
  226. package/clis/devto/tag.js +5 -1
  227. package/clis/devto/top.js +5 -1
  228. package/clis/devto/user.js +5 -1
  229. package/clis/dianping/__fixtures__/search.html +168 -0
  230. package/clis/dianping/__fixtures__/shop.html +6 -0
  231. package/clis/dianping/dianping.test.js +424 -0
  232. package/clis/dianping/search.js +154 -0
  233. package/clis/dianping/shop.js +173 -0
  234. package/clis/dianping/utils.js +157 -0
  235. package/clis/dictionary/examples.js +1 -0
  236. package/clis/dictionary/search.js +1 -0
  237. package/clis/dictionary/synonyms.js +1 -0
  238. package/clis/discord-app/channels.js +1 -0
  239. package/clis/discord-app/delete.js +1 -0
  240. package/clis/discord-app/members.js +1 -0
  241. package/clis/discord-app/read.js +1 -0
  242. package/clis/discord-app/search.js +1 -0
  243. package/clis/discord-app/send.js +1 -0
  244. package/clis/discord-app/servers.js +1 -0
  245. package/clis/discord-app/status.js +1 -0
  246. package/clis/dockerhub/image.js +52 -0
  247. package/clis/dockerhub/search.js +47 -0
  248. package/clis/dockerhub/utils.js +100 -0
  249. package/clis/douban/book-hot.js +1 -0
  250. package/clis/douban/download.js +1 -0
  251. package/clis/douban/marks.js +1 -0
  252. package/clis/douban/movie-hot.js +2 -1
  253. package/clis/douban/movie-hot.test.js +14 -0
  254. package/clis/douban/photos.js +2 -1
  255. package/clis/douban/reviews.js +1 -0
  256. package/clis/douban/search.js +1 -0
  257. package/clis/douban/subject.js +1 -0
  258. package/clis/douban/top250.js +1 -0
  259. package/clis/douban/utils.js +11 -13
  260. package/clis/douban/utils.test.js +79 -0
  261. package/clis/doubao/ask.js +8 -3
  262. package/clis/doubao/detail.js +2 -0
  263. package/clis/doubao/history.js +2 -0
  264. package/clis/doubao/meeting-summary.js +2 -0
  265. package/clis/doubao/meeting-transcript.js +2 -0
  266. package/clis/doubao/new.js +2 -0
  267. package/clis/doubao/read.js +2 -0
  268. package/clis/doubao/send.js +2 -0
  269. package/clis/doubao/status.js +2 -0
  270. package/clis/doubao-app/ask.js +1 -0
  271. package/clis/doubao-app/dump.js +1 -0
  272. package/clis/doubao-app/new.js +1 -0
  273. package/clis/doubao-app/read.js +1 -0
  274. package/clis/doubao-app/screenshot.js +1 -0
  275. package/clis/doubao-app/send.js +1 -0
  276. package/clis/doubao-app/status.js +1 -0
  277. package/clis/douyin/activities.js +1 -0
  278. package/clis/douyin/collections.js +1 -0
  279. package/clis/douyin/delete.js +1 -0
  280. package/clis/douyin/draft.js +1 -0
  281. package/clis/douyin/draft.test.js +1 -30
  282. package/clis/douyin/drafts.js +1 -0
  283. package/clis/douyin/hashtag.js +1 -0
  284. package/clis/douyin/location.js +1 -0
  285. package/clis/douyin/profile.js +1 -0
  286. package/clis/douyin/publish.js +1 -0
  287. package/clis/douyin/stats.js +1 -0
  288. package/clis/douyin/update.js +1 -0
  289. package/clis/douyin/user-videos.js +1 -0
  290. package/clis/douyin/videos.js +1 -0
  291. package/clis/eastmoney/announcement.js +1 -0
  292. package/clis/eastmoney/convertible.js +1 -0
  293. package/clis/eastmoney/etf.js +1 -0
  294. package/clis/eastmoney/holders.js +1 -0
  295. package/clis/eastmoney/hot-rank.js +1 -0
  296. package/clis/eastmoney/index-board.js +1 -0
  297. package/clis/eastmoney/kline.js +1 -0
  298. package/clis/eastmoney/kuaixun.js +1 -0
  299. package/clis/eastmoney/longhu.js +1 -0
  300. package/clis/eastmoney/money-flow.js +1 -0
  301. package/clis/eastmoney/northbound.js +1 -0
  302. package/clis/eastmoney/quote.js +1 -0
  303. package/clis/eastmoney/rank.js +1 -0
  304. package/clis/eastmoney/sectors.js +1 -0
  305. package/clis/endoflife/endoflife.test.js +51 -0
  306. package/clis/endoflife/product.js +55 -0
  307. package/clis/endoflife/utils.js +89 -0
  308. package/clis/facebook/__fixtures__/notifications-page.html +13 -0
  309. package/clis/facebook/add-friend.js +1 -0
  310. package/clis/facebook/events.js +1 -0
  311. package/clis/facebook/feed.js +1 -0
  312. package/clis/facebook/friends.js +1 -0
  313. package/clis/facebook/groups.js +1 -0
  314. package/clis/facebook/join-group.js +1 -0
  315. package/clis/facebook/marketplace-inbox.js +1 -0
  316. package/clis/facebook/marketplace-listings.js +1 -0
  317. package/clis/facebook/memories.js +1 -0
  318. package/clis/facebook/notifications.js +327 -30
  319. package/clis/facebook/notifications.test.js +458 -0
  320. package/clis/facebook/profile.js +1 -0
  321. package/clis/facebook/search.js +1 -0
  322. package/clis/flathub/app.js +71 -0
  323. package/clis/flathub/flathub.test.js +90 -0
  324. package/clis/flathub/search.js +80 -0
  325. package/clis/flathub/utils.js +114 -0
  326. package/clis/gemini/ask.js +8 -3
  327. package/clis/gemini/ask.test.js +2 -2
  328. package/clis/gemini/deep-research-result.js +7 -2
  329. package/clis/gemini/deep-research-result.test.js +15 -14
  330. package/clis/gemini/deep-research.js +9 -4
  331. package/clis/gemini/deep-research.test.js +15 -18
  332. package/clis/gemini/image.js +8 -2
  333. package/clis/gemini/new.js +2 -0
  334. package/clis/gemini/utils.js +0 -4
  335. package/clis/gitee/search.js +1 -0
  336. package/clis/gitee/trending.js +1 -0
  337. package/clis/gitee/user.js +1 -0
  338. package/clis/google/news.js +1 -0
  339. package/clis/google/search.js +1 -0
  340. package/clis/google/suggest.js +1 -0
  341. package/clis/google/trends.js +1 -0
  342. package/clis/google-scholar/cite.js +1 -1
  343. package/clis/google-scholar/profile.js +1 -1
  344. package/clis/google-scholar/search.js +1 -1
  345. package/clis/goproxy/goproxy.test.js +103 -0
  346. package/clis/goproxy/module.js +47 -0
  347. package/clis/goproxy/utils.js +165 -0
  348. package/clis/goproxy/versions.js +59 -0
  349. package/clis/gov-law/recent.js +1 -1
  350. package/clis/gov-law/search.js +1 -1
  351. package/clis/gov-policy/__fixtures__/recent.html +16 -0
  352. package/clis/gov-policy/__fixtures__/search.html +41 -0
  353. package/clis/gov-policy/gov-policy.test.js +224 -0
  354. package/clis/gov-policy/recent.js +67 -24
  355. package/clis/gov-policy/search.js +66 -23
  356. package/clis/gov-policy/utils.js +54 -0
  357. package/clis/grok/ask.js +50 -265
  358. package/clis/grok/ask.test.js +21 -46
  359. package/clis/grok/detail.js +60 -0
  360. package/clis/grok/history.js +48 -0
  361. package/clis/grok/{image.ts → image.js} +57 -70
  362. package/clis/grok/image.test.ts +20 -0
  363. package/clis/grok/new.js +20 -0
  364. package/clis/grok/read.js +39 -0
  365. package/clis/grok/send.js +50 -0
  366. package/clis/grok/status.js +41 -0
  367. package/clis/grok/utils.js +326 -0
  368. package/clis/grok/utils.test.js +103 -0
  369. package/clis/hackernews/ask.js +3 -1
  370. package/clis/hackernews/best.js +3 -1
  371. package/clis/hackernews/hackernews.test.js +132 -0
  372. package/clis/hackernews/jobs.js +3 -1
  373. package/clis/hackernews/new.js +3 -1
  374. package/clis/hackernews/read.js +188 -0
  375. package/clis/hackernews/search.js +3 -1
  376. package/clis/hackernews/show.js +3 -1
  377. package/clis/hackernews/top.js +3 -1
  378. package/clis/hackernews/user.js +1 -0
  379. package/clis/hf/datasets.js +88 -0
  380. package/clis/hf/hf.test.js +16 -0
  381. package/clis/hf/models.js +91 -0
  382. package/clis/hf/paper.js +79 -0
  383. package/clis/hf/spaces.js +101 -0
  384. package/clis/hf/top.js +2 -0
  385. package/clis/homebrew/cask.js +39 -0
  386. package/clis/homebrew/formula.js +41 -0
  387. package/clis/homebrew/popular.js +54 -0
  388. package/clis/homebrew/utils.js +100 -0
  389. package/clis/hupu/__fixtures__/hot-home.html +64 -0
  390. package/clis/hupu/detail.js +1 -1
  391. package/clis/hupu/hot.js +157 -34
  392. package/clis/hupu/hot.test.js +224 -0
  393. package/clis/hupu/like.js +1 -0
  394. package/clis/hupu/mentions.js +2 -1
  395. package/clis/hupu/reply.js +1 -0
  396. package/clis/hupu/search.js +3 -2
  397. package/clis/hupu/unlike.js +1 -0
  398. package/clis/imdb/person.js +1 -0
  399. package/clis/imdb/reviews.js +1 -0
  400. package/clis/imdb/search.js +1 -0
  401. package/clis/imdb/title.js +1 -0
  402. package/clis/imdb/top.js +1 -0
  403. package/clis/imdb/trending.js +1 -0
  404. package/clis/indeed/indeed.test.js +375 -0
  405. package/clis/indeed/job.js +86 -0
  406. package/clis/indeed/search.js +110 -0
  407. package/clis/indeed/utils.js +152 -0
  408. package/clis/instagram/collection-create.js +1 -0
  409. package/clis/instagram/collection-delete.js +1 -0
  410. package/clis/instagram/comment.js +1 -0
  411. package/clis/instagram/download.js +1 -0
  412. package/clis/instagram/explore.js +1 -0
  413. package/clis/instagram/follow.js +1 -0
  414. package/clis/instagram/followers.js +1 -0
  415. package/clis/instagram/following.js +1 -0
  416. package/clis/instagram/like.js +1 -0
  417. package/clis/instagram/note.js +2 -1
  418. package/clis/instagram/note.test.js +1 -29
  419. package/clis/instagram/post.js +2 -1
  420. package/clis/instagram/post.test.js +1 -1
  421. package/clis/instagram/profile.js +1 -0
  422. package/clis/instagram/reel.js +2 -1
  423. package/clis/instagram/save.js +1 -0
  424. package/clis/instagram/saved.js +1 -0
  425. package/clis/instagram/search.js +1 -0
  426. package/clis/instagram/story.js +2 -1
  427. package/clis/instagram/story.test.js +1 -34
  428. package/clis/instagram/unfollow.js +1 -0
  429. package/clis/instagram/unlike.js +1 -0
  430. package/clis/instagram/unsave.js +1 -0
  431. package/clis/instagram/user.js +1 -0
  432. package/clis/jd/add-cart.js +1 -0
  433. package/clis/jd/cart.js +1 -0
  434. package/clis/jd/commands.test.js +1 -24
  435. package/clis/jd/detail.js +1 -0
  436. package/clis/jd/item.js +1 -0
  437. package/clis/jd/reviews.js +1 -0
  438. package/clis/jd/search.js +1 -0
  439. package/clis/jianyu/detail.js +1 -0
  440. package/clis/jianyu/search.js +1 -0
  441. package/clis/jike/comment.js +1 -0
  442. package/clis/jike/create.js +1 -0
  443. package/clis/jike/feed.js +3 -1
  444. package/clis/jike/like.js +1 -0
  445. package/clis/jike/notifications.js +1 -0
  446. package/clis/jike/post.js +1 -0
  447. package/clis/jike/repost.js +1 -0
  448. package/clis/jike/search.js +3 -1
  449. package/clis/jike/topic.js +1 -0
  450. package/clis/jike/user.js +3 -1
  451. package/clis/jimeng/generate.js +1 -0
  452. package/clis/jimeng/history.js +1 -0
  453. package/clis/jimeng/new.js +1 -0
  454. package/clis/jimeng/workspaces.js +1 -0
  455. package/clis/ke/chengjiao.js +1 -0
  456. package/clis/ke/ershoufang.js +1 -0
  457. package/clis/ke/xiaoqu.js +1 -0
  458. package/clis/ke/zufang.js +1 -0
  459. package/clis/lesswrong/comments.js +1 -0
  460. package/clis/lesswrong/curated.js +1 -0
  461. package/clis/lesswrong/frontpage.js +1 -0
  462. package/clis/lesswrong/new.js +1 -0
  463. package/clis/lesswrong/read.js +1 -0
  464. package/clis/lesswrong/sequences.js +1 -0
  465. package/clis/lesswrong/shortform.js +1 -0
  466. package/clis/lesswrong/tag.js +1 -0
  467. package/clis/lesswrong/tags.js +1 -0
  468. package/clis/lesswrong/top-month.js +1 -0
  469. package/clis/lesswrong/top-week.js +1 -0
  470. package/clis/lesswrong/top-year.js +1 -0
  471. package/clis/lesswrong/top.js +1 -0
  472. package/clis/lesswrong/user-posts.js +1 -0
  473. package/clis/lesswrong/user.js +1 -0
  474. package/clis/lichess/lichess.test.js +85 -0
  475. package/clis/lichess/top.js +46 -0
  476. package/clis/lichess/user.js +91 -0
  477. package/clis/lichess/utils.js +97 -0
  478. package/clis/linkedin/search.js +108 -10
  479. package/clis/linkedin/search.test.js +222 -0
  480. package/clis/linkedin/timeline.js +1 -0
  481. package/clis/linux-do/categories.js +1 -0
  482. package/clis/linux-do/feed.js +3 -5
  483. package/clis/linux-do/feed.test.js +35 -0
  484. package/clis/linux-do/search.js +1 -0
  485. package/clis/linux-do/tags.js +2 -1
  486. package/clis/linux-do/topic-content.js +1 -0
  487. package/clis/linux-do/topic.js +1 -0
  488. package/clis/linux-do/user-posts.js +1 -0
  489. package/clis/linux-do/user-topics.js +1 -0
  490. package/clis/lobsters/active.js +4 -1
  491. package/clis/lobsters/domain.js +92 -0
  492. package/clis/lobsters/hot.js +4 -1
  493. package/clis/lobsters/lobsters.test.js +169 -0
  494. package/clis/lobsters/newest.js +4 -1
  495. package/clis/lobsters/read.js +196 -0
  496. package/clis/lobsters/tag.js +4 -1
  497. package/clis/maimai/search-talents.js +1 -0
  498. package/clis/maven/artifact.js +49 -0
  499. package/clis/maven/search.js +51 -0
  500. package/clis/maven/utils.js +110 -0
  501. package/clis/mdn/search.js +97 -0
  502. package/clis/medium/feed.js +1 -0
  503. package/clis/medium/search.js +1 -0
  504. package/clis/medium/tag.js +135 -0
  505. package/clis/medium/user.js +1 -0
  506. package/clis/mubu/doc.js +1 -0
  507. package/clis/mubu/docs.js +1 -0
  508. package/clis/mubu/notes.js +1 -0
  509. package/clis/mubu/recent.js +1 -0
  510. package/clis/mubu/search.js +1 -0
  511. package/clis/notebooklm/current.js +1 -0
  512. package/clis/notebooklm/get.js +1 -0
  513. package/clis/notebooklm/history.js +1 -0
  514. package/clis/notebooklm/list.js +1 -0
  515. package/clis/notebooklm/note-list.js +1 -0
  516. package/clis/notebooklm/notes-get.js +1 -0
  517. package/clis/notebooklm/open.js +1 -0
  518. package/clis/notebooklm/source-fulltext.js +1 -0
  519. package/clis/notebooklm/source-get.js +1 -0
  520. package/clis/notebooklm/source-guide.js +1 -0
  521. package/clis/notebooklm/source-list.js +1 -0
  522. package/clis/notebooklm/status.js +1 -0
  523. package/clis/notebooklm/summary.js +1 -0
  524. package/clis/notion/export.js +1 -0
  525. package/clis/notion/favorites.js +1 -0
  526. package/clis/notion/new.js +1 -0
  527. package/clis/notion/read.js +1 -0
  528. package/clis/notion/search.js +1 -0
  529. package/clis/notion/sidebar.js +1 -0
  530. package/clis/notion/status.js +1 -0
  531. package/clis/notion/write.js +1 -0
  532. package/clis/nowcoder/companies.js +1 -0
  533. package/clis/nowcoder/creators.js +1 -0
  534. package/clis/nowcoder/detail.js +1 -0
  535. package/clis/nowcoder/experience.js +1 -0
  536. package/clis/nowcoder/hot.js +1 -0
  537. package/clis/nowcoder/jobs.js +1 -0
  538. package/clis/nowcoder/notifications.js +1 -0
  539. package/clis/nowcoder/papers.js +1 -0
  540. package/clis/nowcoder/practice.js +1 -0
  541. package/clis/nowcoder/recommend.js +1 -0
  542. package/clis/nowcoder/referral.js +1 -0
  543. package/clis/nowcoder/salary.js +1 -0
  544. package/clis/nowcoder/search.js +1 -0
  545. package/clis/nowcoder/suggest.js +1 -0
  546. package/clis/nowcoder/topics.js +1 -0
  547. package/clis/nowcoder/trending.js +1 -0
  548. package/clis/npm/downloads.js +59 -0
  549. package/clis/npm/package.js +70 -0
  550. package/clis/npm/search.js +49 -0
  551. package/clis/npm/utils.js +76 -0
  552. package/clis/nuget/nuget.test.js +111 -0
  553. package/clis/nuget/package.js +101 -0
  554. package/clis/nuget/search.js +69 -0
  555. package/clis/nuget/utils.js +87 -0
  556. package/clis/nvd/cve.js +121 -0
  557. package/clis/oeis/oeis.test.js +88 -0
  558. package/clis/oeis/search.js +63 -0
  559. package/clis/oeis/sequence.js +71 -0
  560. package/clis/oeis/utils.js +88 -0
  561. package/clis/ones/login.js +1 -0
  562. package/clis/ones/logout.js +1 -0
  563. package/clis/ones/me.js +1 -0
  564. package/clis/ones/my-tasks.js +1 -0
  565. package/clis/ones/task.js +1 -0
  566. package/clis/ones/tasks.js +1 -0
  567. package/clis/ones/token-info.js +1 -0
  568. package/clis/ones/worklog.js +1 -0
  569. package/clis/openalex/search.js +69 -0
  570. package/clis/openalex/utils.js +160 -0
  571. package/clis/openalex/work.js +65 -0
  572. package/clis/openfda/drug-label.js +74 -0
  573. package/clis/openfda/food-recall.js +65 -0
  574. package/clis/openfda/openfda.test.js +114 -0
  575. package/clis/openfda/utils.js +67 -0
  576. package/clis/openreview/openreview.test.js +345 -0
  577. package/clis/openreview/paper.js +43 -0
  578. package/clis/openreview/reviews.js +131 -0
  579. package/clis/openreview/search.js +46 -0
  580. package/clis/openreview/utils.js +158 -0
  581. package/clis/openreview/venue.js +63 -0
  582. package/clis/osv/osv.test.js +97 -0
  583. package/clis/osv/query.js +72 -0
  584. package/clis/osv/utils.js +169 -0
  585. package/clis/osv/vulnerability.js +54 -0
  586. package/clis/packagist/package.js +49 -0
  587. package/clis/packagist/search.js +43 -0
  588. package/clis/packagist/utils.js +113 -0
  589. package/clis/paperreview/feedback.js +2 -1
  590. package/clis/paperreview/review.js +2 -1
  591. package/clis/paperreview/submit.js +2 -1
  592. package/clis/pixiv/detail.js +1 -0
  593. package/clis/pixiv/download.js +1 -0
  594. package/clis/pixiv/download.test.js +1 -1
  595. package/clis/pixiv/illusts.js +2 -1
  596. package/clis/pixiv/illusts.test.js +1 -1
  597. package/clis/pixiv/ranking.js +2 -1
  598. package/clis/pixiv/search.js +2 -1
  599. package/clis/pixiv/search.test.js +1 -1
  600. package/clis/pixiv/user.js +2 -0
  601. package/clis/powerchina/search.js +1 -0
  602. package/clis/producthunt/browse.js +1 -0
  603. package/clis/producthunt/hot.js +1 -0
  604. package/clis/producthunt/posts.js +1 -0
  605. package/clis/producthunt/today.js +1 -0
  606. package/clis/pubmed/article.js +50 -0
  607. package/clis/pubmed/author.js +64 -0
  608. package/clis/pubmed/citations.js +36 -0
  609. package/clis/pubmed/pubmed.test.js +276 -0
  610. package/clis/pubmed/related.js +45 -0
  611. package/clis/pubmed/search.js +75 -0
  612. package/clis/pubmed/utils.js +309 -0
  613. package/clis/pypi/downloads.js +66 -0
  614. package/clis/pypi/package.js +79 -0
  615. package/clis/pypi/utils.js +55 -0
  616. package/clis/quark/ls.js +1 -0
  617. package/clis/quark/mkdir.js +1 -0
  618. package/clis/quark/mv.js +2 -1
  619. package/clis/quark/rename.js +1 -0
  620. package/clis/quark/rm.js +1 -0
  621. package/clis/quark/save.js +2 -1
  622. package/clis/quark/share-tree.js +1 -0
  623. package/clis/qwen/ask.js +85 -0
  624. package/clis/qwen/detail.js +62 -0
  625. package/clis/qwen/history.js +61 -0
  626. package/clis/qwen/image.js +179 -0
  627. package/clis/qwen/new.js +23 -0
  628. package/clis/qwen/read.js +41 -0
  629. package/clis/qwen/send.js +55 -0
  630. package/clis/qwen/status.js +37 -0
  631. package/clis/qwen/utils.js +409 -0
  632. package/clis/qwen/utils.test.js +45 -0
  633. package/clis/reddit/comment.js +1 -0
  634. package/clis/reddit/frontpage.js +1 -0
  635. package/clis/reddit/hot.js +6 -1
  636. package/clis/reddit/hot.test.js +18 -0
  637. package/clis/reddit/popular.js +1 -0
  638. package/clis/reddit/read.js +1 -0
  639. package/clis/reddit/save.js +1 -0
  640. package/clis/reddit/saved.js +1 -0
  641. package/clis/reddit/search.js +1 -0
  642. package/clis/reddit/subreddit.js +1 -0
  643. package/clis/reddit/subscribe.js +1 -0
  644. package/clis/reddit/upvote.js +1 -0
  645. package/clis/reddit/upvoted.js +1 -0
  646. package/clis/reddit/user-comments.js +1 -0
  647. package/clis/reddit/user-posts.js +1 -0
  648. package/clis/reddit/user.js +1 -0
  649. package/clis/rest-countries/country.js +65 -0
  650. package/clis/rest-countries/region.js +64 -0
  651. package/clis/rest-countries/rest-countries.test.js +83 -0
  652. package/clis/rest-countries/utils.js +126 -0
  653. package/clis/reuters/article-detail.js +53 -0
  654. package/clis/reuters/reuters.test.js +299 -0
  655. package/clis/reuters/search.js +46 -34
  656. package/clis/reuters/utils.js +159 -0
  657. package/clis/rfc/rfc.js +52 -0
  658. package/clis/rfc/rfc.test.js +74 -0
  659. package/clis/rfc/utils.js +72 -0
  660. package/clis/rubygems/gem.js +42 -0
  661. package/clis/rubygems/search.js +47 -0
  662. package/clis/rubygems/utils.js +86 -0
  663. package/clis/sinablog/article.js +1 -0
  664. package/clis/sinablog/hot.js +1 -0
  665. package/clis/sinablog/search.js +1 -0
  666. package/clis/sinablog/user.js +1 -0
  667. package/clis/sinafinance/news.js +1 -0
  668. package/clis/sinafinance/rolling-news.js +1 -0
  669. package/clis/sinafinance/stock-rank.js +1 -0
  670. package/clis/sinafinance/stock.js +1 -0
  671. package/clis/smzdm/search.js +1 -0
  672. package/clis/spotify/spotify.js +11 -0
  673. package/clis/stackoverflow/bounties.js +11 -3
  674. package/clis/stackoverflow/hot.js +10 -2
  675. package/clis/stackoverflow/read.js +314 -0
  676. package/clis/stackoverflow/related.js +66 -0
  677. package/clis/stackoverflow/search.js +10 -2
  678. package/clis/stackoverflow/stackoverflow.test.js +404 -0
  679. package/clis/stackoverflow/tag.js +60 -0
  680. package/clis/stackoverflow/unanswered.js +9 -2
  681. package/clis/stackoverflow/user.js +50 -0
  682. package/clis/stackoverflow/utils.js +118 -0
  683. package/clis/steam/app.js +67 -0
  684. package/clis/steam/search.js +58 -0
  685. package/clis/steam/steam.test.js +46 -0
  686. package/clis/steam/top-sellers.js +1 -0
  687. package/clis/steam/utils.js +107 -0
  688. package/clis/substack/feed.js +1 -0
  689. package/clis/substack/publication.js +1 -0
  690. package/clis/substack/search.js +1 -0
  691. package/clis/taobao/add-cart.js +1 -0
  692. package/clis/taobao/cart.js +1 -0
  693. package/clis/taobao/commands.test.js +1 -24
  694. package/clis/taobao/detail.js +1 -0
  695. package/clis/taobao/reviews.js +1 -0
  696. package/clis/taobao/search.js +1 -0
  697. package/clis/tdx/hot-rank.js +1 -0
  698. package/clis/test-utils.js +61 -0
  699. package/clis/ths/hot-rank.js +1 -0
  700. package/clis/tieba/hot.js +2 -2
  701. package/clis/tieba/posts.js +1 -0
  702. package/clis/tieba/read.js +1 -0
  703. package/clis/tieba/search.js +2 -1
  704. package/clis/tiktok/comment.js +128 -40
  705. package/clis/tiktok/creator-videos.js +270 -0
  706. package/clis/tiktok/creator-videos.test.js +113 -0
  707. package/clis/tiktok/explore.js +138 -29
  708. package/clis/tiktok/follow.js +116 -33
  709. package/clis/tiktok/following.js +157 -35
  710. package/clis/tiktok/friends.js +140 -37
  711. package/clis/tiktok/like.js +1 -0
  712. package/clis/tiktok/live.js +138 -41
  713. package/clis/tiktok/notifications.js +142 -38
  714. package/clis/tiktok/profile.js +1 -0
  715. package/clis/tiktok/refactor.test.js +389 -0
  716. package/clis/tiktok/save.js +1 -0
  717. package/clis/tiktok/search.js +1 -0
  718. package/clis/tiktok/unfollow.js +125 -38
  719. package/clis/tiktok/unlike.js +1 -0
  720. package/clis/tiktok/unsave.js +1 -0
  721. package/clis/tiktok/user.js +204 -29
  722. package/clis/tiktok/utils.js +505 -0
  723. package/clis/tiktok/write-refactor.test.js +370 -0
  724. package/clis/toutiao/articles.js +37 -62
  725. package/clis/toutiao/hot.js +63 -0
  726. package/clis/toutiao/toutiao.test.js +378 -0
  727. package/clis/toutiao/utils.js +161 -0
  728. package/clis/tvmaze/search.js +61 -0
  729. package/clis/tvmaze/show.js +60 -0
  730. package/clis/tvmaze/tvmaze.test.js +93 -0
  731. package/clis/tvmaze/utils.js +110 -0
  732. package/clis/twitter/accept.js +2 -1
  733. package/clis/twitter/article.js +1 -0
  734. package/clis/twitter/block.js +1 -0
  735. package/clis/twitter/bookmark.js +1 -0
  736. package/clis/twitter/bookmarks.js +2 -1
  737. package/clis/twitter/delete.js +1 -0
  738. package/clis/twitter/download.js +1 -0
  739. package/clis/twitter/follow.js +1 -0
  740. package/clis/twitter/followers.js +135 -69
  741. package/clis/twitter/following.js +1 -0
  742. package/clis/twitter/hide-reply.js +1 -0
  743. package/clis/twitter/like.js +1 -0
  744. package/clis/twitter/likes.js +2 -1
  745. package/clis/twitter/list-add.js +1 -0
  746. package/clis/twitter/list-remove.js +1 -0
  747. package/clis/twitter/list-tweets.js +1 -0
  748. package/clis/twitter/lists.js +1 -0
  749. package/clis/twitter/notifications.js +1 -0
  750. package/clis/twitter/post.js +1 -0
  751. package/clis/twitter/profile.js +1 -0
  752. package/clis/twitter/reply-dm.js +2 -1
  753. package/clis/twitter/reply.js +1 -0
  754. package/clis/twitter/reply.test.js +1 -29
  755. package/clis/twitter/search.js +1 -0
  756. package/clis/twitter/thread.js +1 -0
  757. package/clis/twitter/timeline.js +1 -0
  758. package/clis/twitter/trending.js +11 -12
  759. package/clis/twitter/trending.test.js +15 -0
  760. package/clis/twitter/tweets.js +2 -1
  761. package/clis/twitter/tweets.test.js +2 -2
  762. package/clis/twitter/unblock.js +1 -0
  763. package/clis/twitter/unbookmark.js +1 -0
  764. package/clis/twitter/unfollow.js +1 -0
  765. package/clis/uisdc/news.js +105 -0
  766. package/clis/uisdc/news.test.js +66 -0
  767. package/clis/uiverse/code.js +1 -0
  768. package/clis/uiverse/preview.js +1 -0
  769. package/clis/v2ex/daily.js +1 -0
  770. package/clis/v2ex/hot.js +1 -0
  771. package/clis/v2ex/latest.js +1 -0
  772. package/clis/v2ex/me.js +1 -0
  773. package/clis/v2ex/member.js +1 -0
  774. package/clis/v2ex/node.js +1 -0
  775. package/clis/v2ex/nodes.js +1 -0
  776. package/clis/v2ex/notifications.js +1 -0
  777. package/clis/v2ex/replies.js +1 -0
  778. package/clis/v2ex/topic.js +1 -0
  779. package/clis/v2ex/user.js +1 -0
  780. package/clis/wanfang/search.js +1 -1
  781. package/clis/web/read.js +48 -17
  782. package/clis/web/read.test.js +101 -1
  783. package/clis/weibo/comments.js +1 -0
  784. package/clis/weibo/favorites.js +1 -0
  785. package/clis/weibo/feed.js +3 -1
  786. package/clis/weibo/hot.js +1 -0
  787. package/clis/weibo/me.js +1 -0
  788. package/clis/weibo/post.js +1 -0
  789. package/clis/weibo/publish.js +1 -0
  790. package/clis/weibo/search.js +8 -2
  791. package/clis/weibo/user.js +1 -0
  792. package/clis/weixin/create-draft.js +2 -1
  793. package/clis/weixin/download.js +1 -0
  794. package/clis/weixin/drafts.js +2 -1
  795. package/clis/weixin/drafts.test.js +5 -1
  796. package/clis/weixin/search.js +157 -0
  797. package/clis/weixin/search.test.js +227 -0
  798. package/clis/weread/ai-outline.js +1 -0
  799. package/clis/weread/book.js +1 -0
  800. package/clis/weread/highlights.js +1 -0
  801. package/clis/weread/notebooks.js +1 -0
  802. package/clis/weread/notes.js +1 -0
  803. package/clis/weread/ranking.js +1 -0
  804. package/clis/weread/search.js +1 -0
  805. package/clis/weread/shelf.js +1 -0
  806. package/clis/wikidata/entity.js +60 -0
  807. package/clis/wikidata/search.js +50 -0
  808. package/clis/wikidata/utils.js +117 -0
  809. package/clis/wikidata/wikidata.test.js +83 -0
  810. package/clis/wikipedia/page.js +95 -0
  811. package/clis/wikipedia/random.js +1 -0
  812. package/clis/wikipedia/search.js +1 -0
  813. package/clis/wikipedia/summary.js +1 -0
  814. package/clis/wikipedia/trending.js +1 -0
  815. package/clis/wttr/current.js +63 -0
  816. package/clis/wttr/forecast.js +71 -0
  817. package/clis/wttr/utils.js +50 -0
  818. package/clis/wttr/wttr.test.js +84 -0
  819. package/clis/xianyu/chat.js +17 -4
  820. package/clis/xianyu/chat.test.js +64 -0
  821. package/clis/xianyu/item.js +1 -0
  822. package/clis/xianyu/publish.js +485 -0
  823. package/clis/xianyu/publish.test.js +220 -0
  824. package/clis/xianyu/search.js +1 -0
  825. package/clis/xiaoe/catalog.js +105 -39
  826. package/clis/xiaoe/content.js +165 -29
  827. package/clis/xiaoe/courses.js +86 -28
  828. package/clis/xiaoe/detail.js +1 -0
  829. package/clis/xiaoe/play-url.js +1 -0
  830. package/clis/xiaoe/xiaoe.test.js +486 -0
  831. package/clis/xiaohongshu/comments.js +1 -0
  832. package/clis/xiaohongshu/creator-note-detail.js +1 -0
  833. package/clis/xiaohongshu/creator-notes-summary.js +2 -1
  834. package/clis/xiaohongshu/creator-notes.js +1 -0
  835. package/clis/xiaohongshu/creator-profile.js +1 -0
  836. package/clis/xiaohongshu/creator-stats.js +1 -0
  837. package/clis/xiaohongshu/download.js +1 -0
  838. package/clis/xiaohongshu/feed.js +2 -1
  839. package/clis/xiaohongshu/note.js +1 -0
  840. package/clis/xiaohongshu/notifications.js +1 -0
  841. package/clis/xiaohongshu/publish.js +17 -3
  842. package/clis/xiaohongshu/publish.test.js +46 -1
  843. package/clis/xiaohongshu/search.js +1 -0
  844. package/clis/xiaohongshu/user.js +1 -0
  845. package/clis/xiaoyuzhou/download.js +1 -0
  846. package/clis/xiaoyuzhou/episode.js +1 -0
  847. package/clis/xiaoyuzhou/podcast-episodes.js +1 -0
  848. package/clis/xiaoyuzhou/podcast.js +1 -0
  849. package/clis/xiaoyuzhou/transcript.js +1 -0
  850. package/clis/xueqiu/comments.js +1 -0
  851. package/clis/xueqiu/earnings-date.js +1 -0
  852. package/clis/xueqiu/feed.js +1 -0
  853. package/clis/xueqiu/fund-holdings.js +1 -0
  854. package/clis/xueqiu/fund-snapshot.js +1 -0
  855. package/clis/xueqiu/groups.js +1 -0
  856. package/clis/xueqiu/hot-stock.js +1 -0
  857. package/clis/xueqiu/hot.js +1 -0
  858. package/clis/xueqiu/kline.js +1 -0
  859. package/clis/xueqiu/search.js +1 -0
  860. package/clis/xueqiu/stock.js +1 -0
  861. package/clis/xueqiu/watchlist.js +1 -0
  862. package/clis/yahoo-finance/quote.js +1 -0
  863. package/clis/yollomi/background.js +1 -0
  864. package/clis/yollomi/edit.js +1 -0
  865. package/clis/yollomi/face-swap.js +1 -0
  866. package/clis/yollomi/generate.js +1 -0
  867. package/clis/yollomi/models.js +1 -0
  868. package/clis/yollomi/object-remover.js +1 -0
  869. package/clis/yollomi/remove-bg.js +1 -0
  870. package/clis/yollomi/restore.js +1 -0
  871. package/clis/yollomi/try-on.js +1 -0
  872. package/clis/yollomi/upload.js +1 -0
  873. package/clis/yollomi/upscale.js +1 -0
  874. package/clis/yollomi/video.js +1 -0
  875. package/clis/youtube/channel.js +1 -0
  876. package/clis/youtube/comments.js +1 -0
  877. package/clis/youtube/feed.js +8 -7
  878. package/clis/youtube/feed.test.js +131 -0
  879. package/clis/youtube/history.js +1 -0
  880. package/clis/youtube/like.js +1 -0
  881. package/clis/youtube/playlist.js +1 -0
  882. package/clis/youtube/search.js +1 -0
  883. package/clis/youtube/subscribe.js +1 -0
  884. package/clis/youtube/subscriptions.js +1 -0
  885. package/clis/youtube/transcript.js +14 -19
  886. package/clis/youtube/transcript.test.js +17 -0
  887. package/clis/youtube/unlike.js +1 -0
  888. package/clis/youtube/unsubscribe.js +1 -0
  889. package/clis/youtube/video.js +1 -0
  890. package/clis/youtube/watch-later.js +1 -0
  891. package/clis/yuanbao/ask.js +18 -66
  892. package/clis/yuanbao/ask.test.js +5 -5
  893. package/clis/yuanbao/detail.js +65 -0
  894. package/clis/yuanbao/history.js +51 -0
  895. package/clis/yuanbao/new.js +2 -0
  896. package/clis/yuanbao/read.js +38 -0
  897. package/clis/yuanbao/send.js +57 -0
  898. package/clis/yuanbao/shared.js +297 -5
  899. package/clis/yuanbao/shared.test.js +80 -0
  900. package/clis/yuanbao/status.js +44 -0
  901. package/clis/zhihu/answer.js +1 -0
  902. package/clis/zhihu/collection.js +1 -0
  903. package/clis/zhihu/collections.js +1 -0
  904. package/clis/zhihu/comment.js +1 -0
  905. package/clis/zhihu/download.js +1 -0
  906. package/clis/zhihu/favorite.js +1 -0
  907. package/clis/zhihu/follow.js +1 -0
  908. package/clis/zhihu/hot.js +1 -0
  909. package/clis/zhihu/like.js +1 -0
  910. package/clis/zhihu/question.js +1 -0
  911. package/clis/zhihu/search.js +1 -0
  912. package/clis/zlibrary/commands.test.js +1 -11
  913. package/clis/zlibrary/info.js +1 -0
  914. package/clis/zlibrary/search.js +1 -0
  915. package/clis/zsxq/dynamics.js +1 -0
  916. package/clis/zsxq/groups.js +1 -0
  917. package/clis/zsxq/search.js +1 -0
  918. package/clis/zsxq/topic.js +1 -0
  919. package/clis/zsxq/topics.js +1 -0
  920. package/dist/src/adapter-source.test.js +1 -1
  921. package/dist/src/browser/analyze.test.js +2 -0
  922. package/dist/src/browser/base-page.d.ts +18 -0
  923. package/dist/src/browser/base-page.js +116 -4
  924. package/dist/src/browser/base-page.test.js +108 -0
  925. package/dist/src/browser/cdp.d.ts +1 -0
  926. package/dist/src/browser/cdp.js +57 -9
  927. package/dist/src/browser/cdp.test.js +3 -0
  928. package/dist/src/browser/daemon-client.d.ts +4 -0
  929. package/dist/src/browser/errors.js +1 -1
  930. package/dist/src/browser/page.d.ts +2 -1
  931. package/dist/src/browser/page.js +9 -1
  932. package/dist/src/browser/page.test.js +46 -0
  933. package/dist/src/browser/target-errors.d.ts +2 -1
  934. package/dist/src/browser/target-errors.js +1 -0
  935. package/dist/src/browser/target-resolver.d.ts +35 -3
  936. package/dist/src/browser/target-resolver.js +59 -10
  937. package/dist/src/browser/verify-fixture.d.ts +6 -1
  938. package/dist/src/browser/verify-fixture.js +87 -0
  939. package/dist/src/browser/verify-fixture.test.js +44 -1
  940. package/dist/src/build-manifest.js +12 -4
  941. package/dist/src/build-manifest.test.js +20 -20
  942. package/dist/src/capabilityRouting.d.ts +16 -1
  943. package/dist/src/capabilityRouting.js +24 -1
  944. package/dist/src/capabilityRouting.test.js +20 -2
  945. package/dist/src/cli.js +213 -12
  946. package/dist/src/cli.test.js +329 -0
  947. package/dist/src/commanderAdapter.d.ts +1 -1
  948. package/dist/src/commanderAdapter.js +17 -12
  949. package/dist/src/commanderAdapter.test.js +7 -7
  950. package/dist/src/convention-audit.d.ts +50 -0
  951. package/dist/src/convention-audit.js +546 -0
  952. package/dist/src/convention-audit.test.d.ts +1 -0
  953. package/dist/src/convention-audit.test.js +226 -0
  954. package/dist/src/discovery.js +4 -5
  955. package/dist/src/doctor.js +0 -1
  956. package/dist/src/doctor.test.js +1 -1
  957. package/dist/src/engine.test.js +10 -10
  958. package/dist/src/errors.js +1 -1
  959. package/dist/src/execution.d.ts +1 -1
  960. package/dist/src/execution.js +111 -27
  961. package/dist/src/execution.test.js +334 -25
  962. package/dist/src/help.d.ts +36 -0
  963. package/dist/src/help.js +171 -0
  964. package/dist/src/help.test.d.ts +1 -0
  965. package/dist/src/help.test.js +54 -0
  966. package/dist/src/main.js +27 -8
  967. package/dist/src/manifest-types.d.ts +7 -3
  968. package/dist/src/pipeline/executor.js +1 -1
  969. package/dist/src/pipeline/executor.test.js +8 -0
  970. package/dist/src/pipeline/registry.d.ts +9 -0
  971. package/dist/src/pipeline/registry.js +13 -1
  972. package/dist/src/pipeline/steps/browser.d.ts +1 -0
  973. package/dist/src/pipeline/steps/browser.js +10 -0
  974. package/dist/src/pipeline/steps/download.test.js +1 -0
  975. package/dist/src/plugin.test.js +26 -26
  976. package/dist/src/registry-api.d.ts +1 -1
  977. package/dist/src/registry.d.ts +17 -11
  978. package/dist/src/registry.js +24 -6
  979. package/dist/src/registry.test.js +29 -22
  980. package/dist/src/runtime.d.ts +2 -1
  981. package/dist/src/runtime.js +1 -1
  982. package/dist/src/serialization.d.ts +6 -2
  983. package/dist/src/serialization.js +31 -7
  984. package/dist/src/serialization.test.js +41 -2
  985. package/dist/src/types.d.ts +19 -0
  986. package/dist/src/validate.js +15 -11
  987. package/dist/src/validate.test.d.ts +9 -0
  988. package/dist/src/validate.test.js +90 -0
  989. package/package.json +4 -1
  990. package/scripts/check-listing-id-pairing.mjs +193 -0
  991. package/scripts/check-silent-column-drop.mjs +105 -0
  992. package/scripts/check-typed-error-lint.mjs +118 -0
  993. package/scripts/fetch-adapters.js +1 -1
  994. package/scripts/silent-column-drop-baseline.json +962 -0
  995. package/scripts/typed-error-lint-baseline.json +1514 -0
  996. package/clis/ctrip/search.test.js +0 -64
  997. package/clis/gov-policy/commands.test.js +0 -27
  998. package/clis/linux-do/category.js +0 -36
  999. package/clis/linux-do/hot.js +0 -25
  1000. package/clis/linux-do/latest.js +0 -18
  1001. package/clis/pixiv/test-utils.js +0 -23
  1002. package/clis/toutiao/articles.test.js +0 -30
  1003. package/dist/src/analysis.d.ts +0 -40
  1004. package/dist/src/analysis.js +0 -172
@@ -0,0 +1,54 @@
1
+ import { describe, it, expect } from 'vitest';
2
+ import { classifyAdapter, formatRootAdapterHelpText } from './help.js';
3
+ describe('classifyAdapter', () => {
4
+ it('classifies DNS-style domains as site', () => {
5
+ expect(classifyAdapter('www.bilibili.com')).toBe('site');
6
+ expect(classifyAdapter('chatgpt.com')).toBe('site');
7
+ expect(classifyAdapter('claude.ai')).toBe('site');
8
+ expect(classifyAdapter('grok.com')).toBe('site');
9
+ });
10
+ it('classifies localhost as app (Electron / osascript desktop integrations)', () => {
11
+ expect(classifyAdapter('localhost')).toBe('app');
12
+ });
13
+ it('classifies non-DNS domain strings as app (e.g. literal "doubao-app")', () => {
14
+ expect(classifyAdapter('doubao-app')).toBe('app');
15
+ });
16
+ it('defaults missing domain to site (most adapters without explicit domain are public web scrapers)', () => {
17
+ expect(classifyAdapter(undefined)).toBe('site');
18
+ });
19
+ });
20
+ describe('formatRootAdapterHelpText', () => {
21
+ it('renders all three sections in External / App / Site order when populated', () => {
22
+ const text = formatRootAdapterHelpText({
23
+ external: ['gh', 'docker'],
24
+ apps: ['chatwise', 'codex'],
25
+ sites: ['bilibili'],
26
+ });
27
+ expect(text).toContain('External CLIs (2):');
28
+ expect(text).toContain('App adapters (2):');
29
+ expect(text).toContain('Site adapters (1):');
30
+ expect(text.indexOf('External CLIs')).toBeLessThan(text.indexOf('App adapters'));
31
+ expect(text.indexOf('App adapters')).toBeLessThan(text.indexOf('Site adapters'));
32
+ });
33
+ it('omits empty sections instead of rendering a (0) header', () => {
34
+ const text = formatRootAdapterHelpText({
35
+ external: [],
36
+ apps: [],
37
+ sites: ['bilibili'],
38
+ });
39
+ expect(text).not.toContain('External CLIs');
40
+ expect(text).not.toContain('App adapters');
41
+ expect(text).toContain('Site adapters (1):');
42
+ });
43
+ it('returns empty string when all groups are empty', () => {
44
+ expect(formatRootAdapterHelpText({ external: [], apps: [], sites: [] })).toBe('');
45
+ });
46
+ it('always renders the agent discovery hint when any section is populated', () => {
47
+ const text = formatRootAdapterHelpText({
48
+ external: [],
49
+ apps: [],
50
+ sites: ['bilibili'],
51
+ });
52
+ expect(text).toContain("'opencli <site> --help -f yaml'");
53
+ });
54
+ });
package/dist/src/main.js CHANGED
@@ -28,7 +28,7 @@ const __dirname = path.dirname(__filename);
28
28
  const BUILTIN_CLIS = path.join(findPackageRoot(__filename), 'clis');
29
29
  const USER_CLIS = path.join(os.homedir(), '.opencli', 'clis');
30
30
  // ── Session lifecycle flags ──────────────────────────────────────────────
31
- // `--live` / `--focus` are top-level-ish toggles that tweak the automation
31
+ // `--live` / `--focus` / `--reuse` are top-level-ish toggles that tweak the automation
32
32
  // window's lifecycle. We strip them from argv before Commander runs so they
33
33
  // can be placed anywhere and work on any subcommand (adapter or browser).
34
34
  {
@@ -42,6 +42,19 @@ const USER_CLIS = path.join(os.homedir(), '.opencli', 'clis');
42
42
  process.env.OPENCLI_WINDOW_FOCUSED = '1';
43
43
  process.argv.splice(focusIdx, 1);
44
44
  }
45
+ const reuseIdx = process.argv.findIndex(arg => arg === '--reuse' || arg.startsWith('--reuse='));
46
+ if (reuseIdx !== -1) {
47
+ const arg = process.argv[reuseIdx];
48
+ const value = arg.startsWith('--reuse=')
49
+ ? arg.slice('--reuse='.length)
50
+ : process.argv[reuseIdx + 1];
51
+ if (value !== 'none' && value !== 'site') {
52
+ process.stderr.write(`--reuse must be one of: none, site. Received: "${value ?? ''}"\n`);
53
+ process.exit(EXIT_CODES.USAGE_ERROR);
54
+ }
55
+ process.env.OPENCLI_BROWSER_REUSE = value;
56
+ process.argv.splice(reuseIdx, arg.startsWith('--reuse=') ? 1 : 2);
57
+ }
45
58
  }
46
59
  // ── Ultra-fast path: lightweight commands bypass full discovery ──────────
47
60
  // These are high-frequency or trivial paths that must not pay the startup tax.
@@ -118,13 +131,19 @@ installNodeNetwork();
118
131
  // user-CLI discovery MUST run after built-in discovery to preserve the
119
132
  // intended override order (user adapters override built-in ones).
120
133
  // - discoverPlugins runs last: plugins may override both built-in and user CLIs.
121
- const [, ,] = await Promise.all([
122
- ensureUserCliCompatShims(),
123
- ensureUserAdapters(),
124
- discoverClis(BUILTIN_CLIS),
125
- ]);
126
- await discoverClis(USER_CLIS);
127
- await discoverPlugins();
134
+ const skipUserDiscovery = argv[0] === 'convention-audit';
135
+ if (skipUserDiscovery) {
136
+ await discoverClis(BUILTIN_CLIS);
137
+ }
138
+ else {
139
+ const [, ,] = await Promise.all([
140
+ ensureUserCliCompatShims(),
141
+ ensureUserAdapters(),
142
+ discoverClis(BUILTIN_CLIS),
143
+ ]);
144
+ await discoverClis(USER_CLIS);
145
+ await discoverPlugins();
146
+ }
128
147
  // Register exit hook: notice appears after command output (same as npm/gh/yarn)
129
148
  registerUpdateNoticeOnExit();
130
149
  // Kick off background fetch for next run (non-blocking)
@@ -11,6 +11,8 @@ export interface ManifestEntry {
11
11
  name: string;
12
12
  aliases?: string[];
13
13
  description: string;
14
+ access: 'read' | 'write';
15
+ example?: string;
14
16
  domain?: string;
15
17
  strategy: string;
16
18
  browser: boolean;
@@ -26,9 +28,7 @@ export interface ManifestEntry {
26
28
  }>;
27
29
  columns?: string[];
28
30
  pipeline?: Record<string, unknown>[];
29
- timeout?: number;
30
- deprecated?: boolean | string;
31
- replacedBy?: string;
31
+ defaultFormat?: 'table' | 'plain' | 'json' | 'yaml' | 'yml' | 'md' | 'markdown' | 'csv';
32
32
  type: 'js';
33
33
  /** Relative path from clis/ dir, e.g. 'bilibili/search.js' */
34
34
  modulePath?: string;
@@ -36,4 +36,8 @@ export interface ManifestEntry {
36
36
  sourceFile?: string;
37
37
  /** Pre-navigation control — see CliCommand.navigateBefore */
38
38
  navigateBefore?: boolean | string;
39
+ /** Browser session lifecycle defaults — see CliCommand.browserSession */
40
+ browserSession?: {
41
+ reuse?: 'none' | 'site';
42
+ };
39
43
  }
@@ -32,7 +32,7 @@ export async function executePipeline(page, pipeline, ctx = {}) {
32
32
  }
33
33
  }
34
34
  catch (err) {
35
- // Attempt cleanup: close automation window on pipeline failure
35
+ // Attempt cleanup: release automation tab lease on pipeline failure.
36
36
  if (page?.closeWindow) {
37
37
  try {
38
38
  await page.closeWindow();
@@ -14,6 +14,7 @@ function createMockPage(overrides = {}) {
14
14
  snapshot: vi.fn().mockResolvedValue(''),
15
15
  click: vi.fn(),
16
16
  typeText: vi.fn(),
17
+ fillText: vi.fn(),
17
18
  pressKey: vi.fn(),
18
19
  getFormState: vi.fn().mockResolvedValue({}),
19
20
  wait: vi.fn(),
@@ -159,6 +160,13 @@ describe('executePipeline', () => {
159
160
  ]);
160
161
  expect(page.click).toHaveBeenCalledWith('5');
161
162
  });
163
+ it('fill step calls page.fillText with raw rendered text', async () => {
164
+ const page = createMockPage();
165
+ await executePipeline(page, [
166
+ { fill: { ref: '@5', text: 'line1\\n/ / ${{ args.tail }}' } },
167
+ ], { args: { tail: 'raw' } });
168
+ expect(page.fillText).toHaveBeenCalledWith('5', 'line1\\n/ / raw');
169
+ });
162
170
  it('navigate preserves existing data through pipeline', async () => {
163
171
  const page = createMockPage({
164
172
  evaluate: vi.fn().mockResolvedValue([{ a: 1 }]),
@@ -13,6 +13,15 @@ export type StepHandler<TData = unknown, TResult = unknown, TParams = unknown> =
13
13
  * Get a registered step handler by name.
14
14
  */
15
15
  export declare function getStep(name: string): StepHandler | undefined;
16
+ /**
17
+ * List all currently registered step names. Used by `validate.ts` to allowlist
18
+ * step names without maintaining a parallel hand-coded list.
19
+ *
20
+ * Note: this depends on registerStep() side effects below already having run.
21
+ * Importing this module triggers all core registrations at the bottom of the
22
+ * file, so the returned array reflects every core + plugin step at call time.
23
+ */
24
+ export declare function getRegisteredStepNames(): string[];
16
25
  /**
17
26
  * Register a new custom step handler for the YAML pipeline.
18
27
  */
@@ -3,7 +3,7 @@
3
3
  * Allows core and third-party plugins to register custom YAML operations.
4
4
  */
5
5
  // Import core steps
6
- import { stepNavigate, stepClick, stepType, stepWait, stepPress, stepSnapshot, stepEvaluate } from './steps/browser.js';
6
+ import { stepNavigate, stepClick, stepType, stepFill, stepWait, stepPress, stepSnapshot, stepEvaluate } from './steps/browser.js';
7
7
  import { stepFetch } from './steps/fetch.js';
8
8
  import { stepSelect, stepMap, stepFilter, stepSort, stepLimit } from './steps/transform.js';
9
9
  import { stepIntercept } from './steps/intercept.js';
@@ -16,6 +16,17 @@ const _stepRegistry = new Map();
16
16
  export function getStep(name) {
17
17
  return _stepRegistry.get(name);
18
18
  }
19
+ /**
20
+ * List all currently registered step names. Used by `validate.ts` to allowlist
21
+ * step names without maintaining a parallel hand-coded list.
22
+ *
23
+ * Note: this depends on registerStep() side effects below already having run.
24
+ * Importing this module triggers all core registrations at the bottom of the
25
+ * file, so the returned array reflects every core + plugin step at call time.
26
+ */
27
+ export function getRegisteredStepNames() {
28
+ return [..._stepRegistry.keys()];
29
+ }
19
30
  /**
20
31
  * Register a new custom step handler for the YAML pipeline.
21
32
  */
@@ -32,6 +43,7 @@ registerStep('evaluate', stepEvaluate);
32
43
  registerStep('snapshot', stepSnapshot);
33
44
  registerStep('click', stepClick);
34
45
  registerStep('type', stepType);
46
+ registerStep('fill', stepFill);
35
47
  registerStep('wait', stepWait);
36
48
  registerStep('press', stepPress);
37
49
  registerStep('map', stepMap);
@@ -6,6 +6,7 @@ import type { IPage } from '../../types.js';
6
6
  export declare function stepNavigate(page: IPage | null, params: unknown, data: unknown, args: Record<string, unknown>): Promise<unknown>;
7
7
  export declare function stepClick(page: IPage | null, params: unknown, data: unknown, args: Record<string, unknown>): Promise<unknown>;
8
8
  export declare function stepType(page: IPage | null, params: unknown, data: unknown, args: Record<string, unknown>): Promise<unknown>;
9
+ export declare function stepFill(page: IPage | null, params: unknown, data: unknown, args: Record<string, unknown>): Promise<unknown>;
9
10
  export declare function stepWait(page: IPage | null, params: unknown, data: unknown, args: Record<string, unknown>): Promise<unknown>;
10
11
  export declare function stepPress(page: IPage | null, params: unknown, data: unknown, args: Record<string, unknown>): Promise<unknown>;
11
12
  export declare function stepSnapshot(page: IPage | null, params: unknown, _data: unknown, _args: Record<string, unknown>): Promise<unknown>;
@@ -29,6 +29,16 @@ export async function stepType(page, params, data, args) {
29
29
  }
30
30
  return data;
31
31
  }
32
+ export async function stepFill(page, params, data, args) {
33
+ if (isRecord(params)) {
34
+ const ref = String(render(params.ref ?? '', { args, data })).replace(/^@/, '');
35
+ const text = String(render(params.text ?? '', { args, data }));
36
+ await page.fillText(ref, text);
37
+ if (params.submit)
38
+ await page.pressKey('Enter');
39
+ }
40
+ return data;
41
+ }
32
42
  export async function stepWait(page, params, data, args) {
33
43
  if (typeof params === 'number')
34
44
  await page.wait(params);
@@ -25,6 +25,7 @@ function createMockPage(getCookies) {
25
25
  snapshot: vi.fn().mockResolvedValue(''),
26
26
  click: vi.fn(),
27
27
  typeText: vi.fn(),
28
+ fillText: vi.fn(),
28
29
  pressKey: vi.fn(),
29
30
  scrollTo: vi.fn(),
30
31
  getFormState: vi.fn().mockResolvedValue({}),
@@ -361,7 +361,7 @@ describe('listPlugins', () => {
361
361
  });
362
362
  it('lists installed plugins', () => {
363
363
  fs.mkdirSync(testDir, { recursive: true });
364
- fs.writeFileSync(path.join(testDir, 'hello.js'), 'cli({ site: "test", name: "hello" })');
364
+ fs.writeFileSync(path.join(testDir, 'hello.js'), 'cli({ site: "test", name: "hello", access: "read" })');
365
365
  const plugins = listPlugins();
366
366
  const found = plugins.find(p => p.name === '__test-list-plugin__');
367
367
  expect(found).toBeDefined();
@@ -369,7 +369,7 @@ describe('listPlugins', () => {
369
369
  });
370
370
  it('includes version metadata from the lock file', () => {
371
371
  fs.mkdirSync(testDir, { recursive: true });
372
- fs.writeFileSync(path.join(testDir, 'hello.js'), 'cli({ site: "test", name: "hello" })');
372
+ fs.writeFileSync(path.join(testDir, 'hello.js'), 'cli({ site: "test", name: "hello", access: "read" })');
373
373
  const lock = _readLockFile();
374
374
  lock['__test-list-plugin__'] = {
375
375
  source: { kind: 'git', url: 'https://github.com/user/repo.git' },
@@ -393,7 +393,7 @@ describe('listPlugins', () => {
393
393
  const localTarget = fs.mkdtempSync(path.join(os.tmpdir(), 'opencli-local-list-'));
394
394
  const linkPath = path.join(PLUGINS_DIR, '__test-list-plugin__');
395
395
  fs.mkdirSync(PLUGINS_DIR, { recursive: true });
396
- fs.writeFileSync(path.join(localTarget, 'hello.js'), 'cli({ site: "test", name: "hello" })');
396
+ fs.writeFileSync(path.join(localTarget, 'hello.js'), 'cli({ site: "test", name: "hello", access: "read" })');
397
397
  try {
398
398
  fs.unlinkSync(linkPath);
399
399
  }
@@ -435,13 +435,13 @@ describe('uninstallPlugin', () => {
435
435
  });
436
436
  it('removes plugin directory', () => {
437
437
  fs.mkdirSync(testDir, { recursive: true });
438
- fs.writeFileSync(path.join(testDir, 'test.js'), 'cli({ site: "test", name: "test" })');
438
+ fs.writeFileSync(path.join(testDir, 'test.js'), 'cli({ site: "test", name: "test", access: "read" })');
439
439
  uninstallPlugin('__test-uninstall__');
440
440
  expect(fs.existsSync(testDir)).toBe(false);
441
441
  });
442
442
  it('removes lock entry on uninstall', () => {
443
443
  fs.mkdirSync(testDir, { recursive: true });
444
- fs.writeFileSync(path.join(testDir, 'test.js'), 'cli({ site: "test", name: "test" })');
444
+ fs.writeFileSync(path.join(testDir, 'test.js'), 'cli({ site: "test", name: "test", access: "read" })');
445
445
  const lock = _readLockFile();
446
446
  lock['__test-uninstall__'] = {
447
447
  source: { kind: 'git', url: 'https://github.com/user/repo.git' },
@@ -464,7 +464,7 @@ describe('updatePlugin', () => {
464
464
  const localTarget = fs.mkdtempSync(path.join(os.tmpdir(), 'opencli-local-update-'));
465
465
  const linkPath = path.join(PLUGINS_DIR, '__test-local-update__');
466
466
  fs.mkdirSync(PLUGINS_DIR, { recursive: true });
467
- fs.writeFileSync(path.join(localTarget, 'hello.js'), 'cli({ site: "test", name: "hello" })');
467
+ fs.writeFileSync(path.join(localTarget, 'hello.js'), 'cli({ site: "test", name: "hello", access: "read" })');
468
468
  fs.symlinkSync(localTarget, linkPath, 'dir');
469
469
  const lock = _readLockFile();
470
470
  lock['__test-local-update__'] = {
@@ -540,7 +540,7 @@ describe('postInstallMonorepoLifecycle', () => {
540
540
  private: true,
541
541
  workspaces: ['packages/*'],
542
542
  }));
543
- fs.writeFileSync(path.join(subDir, 'hello.js'), 'cli({ site: "test", name: "hello" })');
543
+ fs.writeFileSync(path.join(subDir, 'hello.js'), 'cli({ site: "test", name: "hello", access: "read" })');
544
544
  });
545
545
  afterEach(() => {
546
546
  fs.rmSync(repoDir, { recursive: true, force: true });
@@ -575,9 +575,9 @@ describe('updateAllPlugins', () => {
575
575
  fs.mkdirSync(testDirA, { recursive: true });
576
576
  fs.mkdirSync(testDirB, { recursive: true });
577
577
  fs.mkdirSync(testDirC, { recursive: true });
578
- fs.writeFileSync(path.join(testDirA, 'cmd.js'), 'cli({ site: "a", name: "cmd" })');
579
- fs.writeFileSync(path.join(testDirB, 'cmd.js'), 'cli({ site: "b", name: "cmd" })');
580
- fs.writeFileSync(path.join(testDirC, 'cmd.js'), 'cli({ site: "c", name: "cmd" })');
578
+ fs.writeFileSync(path.join(testDirA, 'cmd.js'), 'cli({ site: "a", name: "cmd", access: "read" })');
579
+ fs.writeFileSync(path.join(testDirB, 'cmd.js'), 'cli({ site: "b", name: "cmd", access: "read" })');
580
+ fs.writeFileSync(path.join(testDirC, 'cmd.js'), 'cli({ site: "c", name: "cmd", access: "read" })');
581
581
  const lock = _readLockFile();
582
582
  lock['plugin-a'] = {
583
583
  source: { kind: 'git', url: 'https://github.com/user/plugin-a.git' },
@@ -622,7 +622,7 @@ describe('updateAllPlugins', () => {
622
622
  const cloneUrl = String(args[3]);
623
623
  const cloneDir = String(args[4]);
624
624
  fs.mkdirSync(cloneDir, { recursive: true });
625
- fs.writeFileSync(path.join(cloneDir, 'cmd.js'), 'cli({ site: "test", name: "hello" })');
625
+ fs.writeFileSync(path.join(cloneDir, 'cmd.js'), 'cli({ site: "test", name: "hello", access: "read" })');
626
626
  if (cloneUrl.includes('plugin-b')) {
627
627
  fs.writeFileSync(path.join(cloneDir, 'package.json'), JSON.stringify({ name: 'plugin-b' }));
628
628
  }
@@ -709,7 +709,7 @@ describe('monorepo uninstall with symlink', () => {
709
709
  monoDir = path.join(_getMonoreposDir(), '__test-mono__');
710
710
  const subDir = path.join(monoDir, 'packages', 'sub');
711
711
  fs.mkdirSync(subDir, { recursive: true });
712
- fs.writeFileSync(path.join(subDir, 'cmd.js'), 'cli({ site: "test", name: "cmd" })');
712
+ fs.writeFileSync(path.join(subDir, 'cmd.js'), 'cli({ site: "test", name: "cmd", access: "read" })');
713
713
  fs.mkdirSync(PLUGINS_DIR, { recursive: true });
714
714
  fs.symlinkSync(subDir, pluginDir, 'dir');
715
715
  const lock = _readLockFile();
@@ -776,7 +776,7 @@ describe('listPlugins with monorepo metadata', () => {
776
776
  const testLink = path.join(PLUGINS_DIR, '__test-mono-list__');
777
777
  beforeEach(() => {
778
778
  fs.mkdirSync(testSymlinkTarget, { recursive: true });
779
- fs.writeFileSync(path.join(testSymlinkTarget, 'hello.js'), 'cli({ site: "test", name: "hello" })');
779
+ fs.writeFileSync(path.join(testSymlinkTarget, 'hello.js'), 'cli({ site: "test", name: "hello", access: "read" })');
780
780
  fs.mkdirSync(PLUGINS_DIR, { recursive: true });
781
781
  try {
782
782
  fs.unlinkSync(testLink);
@@ -823,7 +823,7 @@ describe('installLocalPlugin', () => {
823
823
  const pluginName = '__test-local-plugin__';
824
824
  beforeEach(() => {
825
825
  tmpDir = fs.mkdtempSync(path.join(os.tmpdir(), 'opencli-local-install-'));
826
- fs.writeFileSync(path.join(tmpDir, 'hello.js'), 'cli({ site: "test", name: "hello" })');
826
+ fs.writeFileSync(path.join(tmpDir, 'hello.js'), 'cli({ site: "test", name: "hello", access: "read" })');
827
827
  });
828
828
  afterEach(() => {
829
829
  const linkPath = path.join(PLUGINS_DIR, pluginName);
@@ -963,7 +963,7 @@ describe('installPlugin transactional staging', () => {
963
963
  if (cmd === 'git' && Array.isArray(args) && args[0] === 'clone') {
964
964
  const cloneDir = String(args[args.length - 1]);
965
965
  fs.mkdirSync(cloneDir, { recursive: true });
966
- fs.writeFileSync(path.join(cloneDir, 'hello.js'), 'cli({ site: "test", name: "hello" })');
966
+ fs.writeFileSync(path.join(cloneDir, 'hello.js'), 'cli({ site: "test", name: "hello", access: "read" })');
967
967
  fs.writeFileSync(path.join(cloneDir, 'package.json'), JSON.stringify({ name: standaloneName }));
968
968
  return '';
969
969
  }
@@ -994,7 +994,7 @@ describe('installPlugin transactional staging', () => {
994
994
  alpha: { path: 'packages/alpha' },
995
995
  },
996
996
  }));
997
- fs.writeFileSync(path.join(alphaDir, 'hello.js'), 'cli({ site: "test", name: "hello" })');
997
+ fs.writeFileSync(path.join(alphaDir, 'hello.js'), 'cli({ site: "test", name: "hello", access: "read" })');
998
998
  return '';
999
999
  }
1000
1000
  if (cmd === 'npm' && Array.isArray(args) && args[0] === 'install') {
@@ -1051,7 +1051,7 @@ describe('installPlugin with existing monorepo', () => {
1051
1051
  [pluginName]: { path: `packages/${pluginName}` },
1052
1052
  },
1053
1053
  }));
1054
- fs.writeFileSync(path.join(subDir, 'hello.js'), 'cli({ site: "test", name: "hello" })');
1054
+ fs.writeFileSync(path.join(subDir, 'hello.js'), 'cli({ site: "test", name: "hello", access: "read" })');
1055
1055
  mockExecFileSync.mockImplementation((cmd, args) => {
1056
1056
  if (cmd === 'git' && Array.isArray(args) && args[0] === 'clone') {
1057
1057
  const cloneDir = String(args[4]);
@@ -1110,7 +1110,7 @@ describe('updatePlugin transactional staging', () => {
1110
1110
  });
1111
1111
  it('keeps the existing standalone plugin when staged update preparation fails', () => {
1112
1112
  fs.mkdirSync(standaloneDir, { recursive: true });
1113
- fs.writeFileSync(path.join(standaloneDir, 'old.js'), 'cli({ site: "old", name: "old" })');
1113
+ fs.writeFileSync(path.join(standaloneDir, 'old.js'), 'cli({ site: "old", name: "old", access: "read" })');
1114
1114
  const lock = _readLockFile();
1115
1115
  lock[standaloneName] = {
1116
1116
  source: {
@@ -1125,7 +1125,7 @@ describe('updatePlugin transactional staging', () => {
1125
1125
  if (cmd === 'git' && Array.isArray(args) && args[0] === 'clone') {
1126
1126
  const cloneDir = String(args[4]);
1127
1127
  fs.mkdirSync(cloneDir, { recursive: true });
1128
- fs.writeFileSync(path.join(cloneDir, 'hello.js'), 'cli({ site: "test", name: "hello" })');
1128
+ fs.writeFileSync(path.join(cloneDir, 'hello.js'), 'cli({ site: "test", name: "hello", access: "read" })');
1129
1129
  fs.writeFileSync(path.join(cloneDir, 'package.json'), JSON.stringify({ name: standaloneName }));
1130
1130
  return '';
1131
1131
  }
@@ -1145,7 +1145,7 @@ describe('updatePlugin transactional staging', () => {
1145
1145
  it('keeps the existing monorepo repo and link when staged update preparation fails', () => {
1146
1146
  const subDir = path.join(monorepoRepoDir, 'packages', monorepoPluginName);
1147
1147
  fs.mkdirSync(subDir, { recursive: true });
1148
- fs.writeFileSync(path.join(subDir, 'old.js'), 'cli({ site: "old", name: "old" })');
1148
+ fs.writeFileSync(path.join(subDir, 'old.js'), 'cli({ site: "old", name: "old", access: "read" })');
1149
1149
  fs.mkdirSync(PLUGINS_DIR, { recursive: true });
1150
1150
  fs.symlinkSync(subDir, monorepoLink, 'dir');
1151
1151
  const lock = _readLockFile();
@@ -1174,7 +1174,7 @@ describe('updatePlugin transactional staging', () => {
1174
1174
  [monorepoPluginName]: { path: `packages/${monorepoPluginName}` },
1175
1175
  },
1176
1176
  }));
1177
- fs.writeFileSync(path.join(alphaDir, 'hello.js'), 'cli({ site: "test", name: "hello" })');
1177
+ fs.writeFileSync(path.join(alphaDir, 'hello.js'), 'cli({ site: "test", name: "hello", access: "read" })');
1178
1178
  return '';
1179
1179
  }
1180
1180
  if (cmd === 'npm' && Array.isArray(args) && args[0] === 'install') {
@@ -1194,7 +1194,7 @@ describe('updatePlugin transactional staging', () => {
1194
1194
  it('relinks monorepo plugins when the updated manifest moves their subPath', () => {
1195
1195
  const oldSubDir = path.join(monorepoRepoDir, 'packages', 'old-alpha');
1196
1196
  fs.mkdirSync(oldSubDir, { recursive: true });
1197
- fs.writeFileSync(path.join(oldSubDir, 'old.js'), 'cli({ site: "old", name: "old" })');
1197
+ fs.writeFileSync(path.join(oldSubDir, 'old.js'), 'cli({ site: "old", name: "old", access: "read" })');
1198
1198
  fs.mkdirSync(PLUGINS_DIR, { recursive: true });
1199
1199
  fs.symlinkSync(oldSubDir, monorepoLink, 'dir');
1200
1200
  const lock = _readLockFile();
@@ -1219,7 +1219,7 @@ describe('updatePlugin transactional staging', () => {
1219
1219
  [monorepoPluginName]: { path: 'packages/moved-alpha' },
1220
1220
  },
1221
1221
  }));
1222
- fs.writeFileSync(path.join(movedDir, 'hello.js'), 'cli({ site: "test", name: "hello" })');
1222
+ fs.writeFileSync(path.join(movedDir, 'hello.js'), 'cli({ site: "test", name: "hello", access: "read" })');
1223
1223
  return '';
1224
1224
  }
1225
1225
  if (cmd === 'git' && Array.isArray(args) && args[0] === 'rev-parse' && args[1] === 'HEAD') {
@@ -1238,7 +1238,7 @@ describe('updatePlugin transactional staging', () => {
1238
1238
  it('rejects monorepo updates whose manifest path escapes the repo root', () => {
1239
1239
  const oldSubDir = path.join(monorepoRepoDir, 'packages', 'old-alpha');
1240
1240
  fs.mkdirSync(oldSubDir, { recursive: true });
1241
- fs.writeFileSync(path.join(oldSubDir, 'old.js'), 'cli({ site: "old", name: "old" })');
1241
+ fs.writeFileSync(path.join(oldSubDir, 'old.js'), 'cli({ site: "old", name: "old", access: "read" })');
1242
1242
  fs.mkdirSync(PLUGINS_DIR, { recursive: true });
1243
1243
  fs.symlinkSync(oldSubDir, monorepoLink, 'dir');
1244
1244
  const lock = _readLockFile();
@@ -1279,7 +1279,7 @@ describe('updatePlugin transactional staging', () => {
1279
1279
  it('rolls back the monorepo repo swap when relinking fails', () => {
1280
1280
  const oldSubDir = path.join(monorepoRepoDir, 'packages', 'old-alpha');
1281
1281
  fs.mkdirSync(oldSubDir, { recursive: true });
1282
- fs.writeFileSync(path.join(oldSubDir, 'old.js'), 'cli({ site: "old", name: "old" })');
1282
+ fs.writeFileSync(path.join(oldSubDir, 'old.js'), 'cli({ site: "old", name: "old", access: "read" })');
1283
1283
  fs.mkdirSync(monorepoLink, { recursive: true });
1284
1284
  fs.writeFileSync(path.join(monorepoLink, 'blocker.txt'), 'not a symlink');
1285
1285
  const lock = _readLockFile();
@@ -1304,7 +1304,7 @@ describe('updatePlugin transactional staging', () => {
1304
1304
  [monorepoPluginName]: { path: 'packages/moved-alpha' },
1305
1305
  },
1306
1306
  }));
1307
- fs.writeFileSync(path.join(movedDir, 'hello.js'), 'cli({ site: "test", name: "hello" })');
1307
+ fs.writeFileSync(path.join(movedDir, 'hello.js'), 'cli({ site: "test", name: "hello", access: "read" })');
1308
1308
  return '';
1309
1309
  }
1310
1310
  if (cmd === 'git' && Array.isArray(args) && args[0] === 'rev-parse' && args[1] === 'HEAD') {
@@ -7,7 +7,7 @@
7
7
  * plugins are dynamically imported during discoverPlugins().
8
8
  */
9
9
  export { cli, Strategy, getRegistry, fullName, registerCommand } from './registry.js';
10
- export type { CliCommand, Arg, CliOptions, CommandArgs } from './registry.js';
10
+ export type { CliCommand, Arg, CliOptions, CommandArgs, BrowserSessionOptions, BrowserSessionReuse } from './registry.js';
11
11
  export type { IPage } from './types.js';
12
12
  export { onStartup, onBeforeExecute, onAfterExecute } from './hooks.js';
13
13
  export type { HookFn, HookContext, HookName } from './hooks.js';
@@ -6,7 +6,6 @@ export declare enum Strategy {
6
6
  PUBLIC = "public",
7
7
  LOCAL = "local",
8
8
  COOKIE = "cookie",
9
- HEADER = "header",
10
9
  INTERCEPT = "intercept",
11
10
  UI = "ui"
12
11
  }
@@ -20,33 +19,37 @@ export interface Arg {
20
19
  help?: string;
21
20
  choices?: string[];
22
21
  }
23
- export interface RequiredEnv {
24
- name: string;
25
- help?: string;
26
- }
27
22
  export type CommandArgs = Record<string, any>;
28
23
  export type BrowserCommandFunc = (page: IPage, kwargs: CommandArgs, debug?: boolean) => Promise<unknown>;
29
24
  export type NonBrowserCommandFunc = (kwargs: CommandArgs, debug?: boolean) => Promise<unknown>;
25
+ export type CommandAccess = 'read' | 'write';
26
+ export type BrowserSessionReuse = 'none' | 'site';
27
+ export interface BrowserSessionOptions {
28
+ /**
29
+ * Control whether browser-backed adapter commands reuse a stable tab lease.
30
+ *
31
+ * - `none`: one-shot workspace per command execution (default)
32
+ * - `site`: all commands for this site share `site:<site>` until idle expiry
33
+ */
34
+ reuse?: BrowserSessionReuse;
35
+ }
30
36
  interface BaseCliCommand {
31
37
  site: string;
32
38
  name: string;
33
39
  aliases?: string[];
34
40
  description: string;
41
+ access: CommandAccess;
42
+ /** Canonical invocation shown in agent-facing help. Generated when omitted. */
43
+ example?: string;
35
44
  domain?: string;
36
45
  strategy?: Strategy;
37
46
  args: Arg[];
38
47
  columns?: string[];
39
48
  pipeline?: Record<string, unknown>[];
40
- timeoutSeconds?: number;
41
49
  /** Origin of this command: 'yaml', 'ts', or plugin name. */
42
50
  source?: string;
43
51
  footerExtra?: (kwargs: CommandArgs) => string | undefined;
44
- requiredEnv?: RequiredEnv[];
45
52
  validateArgs?: (kwargs: CommandArgs) => void;
46
- /** Deprecation note shown in help / execution warnings. */
47
- deprecated?: boolean | string;
48
- /** Preferred replacement command, if any. */
49
- replacedBy?: string;
50
53
  /**
51
54
  * Control pre-navigation and browser-session requirement.
52
55
  *
@@ -63,6 +66,8 @@ interface BaseCliCommand {
63
66
  * Adapter authors can set this explicitly to override the strategy-based default.
64
67
  */
65
68
  navigateBefore?: boolean | string;
69
+ /** Browser session lifecycle defaults for adapter commands. */
70
+ browserSession?: BrowserSessionOptions;
66
71
  /** Override the default CLI output format when the user does not pass -f/--format. */
67
72
  defaultFormat?: 'table' | 'plain' | 'json' | 'yaml' | 'yml' | 'md' | 'markdown' | 'csv';
68
73
  }
@@ -89,6 +94,7 @@ export type InternalCliCommand = CliCommand & {
89
94
  type RequiredCliOptions = {
90
95
  site: string;
91
96
  name: string;
97
+ access: CommandAccess;
92
98
  description?: string;
93
99
  args?: Arg[];
94
100
  };
@@ -6,7 +6,6 @@ export var Strategy;
6
6
  Strategy["PUBLIC"] = "public";
7
7
  Strategy["LOCAL"] = "local";
8
8
  Strategy["COOKIE"] = "cookie";
9
- Strategy["HEADER"] = "header";
10
9
  Strategy["INTERCEPT"] = "intercept";
11
10
  Strategy["UI"] = "ui";
12
11
  })(Strategy || (Strategy = {}));
@@ -17,6 +16,8 @@ export function cli(opts) {
17
16
  name: opts.name,
18
17
  aliases: opts.aliases,
19
18
  description: opts.description ?? '',
19
+ access: opts.access,
20
+ example: opts.example,
20
21
  domain: opts.domain,
21
22
  strategy: opts.strategy,
22
23
  browser: opts.browser,
@@ -24,12 +25,9 @@ export function cli(opts) {
24
25
  columns: opts.columns,
25
26
  func: opts.func,
26
27
  pipeline: opts.pipeline,
27
- timeoutSeconds: opts.timeoutSeconds,
28
28
  footerExtra: opts.footerExtra,
29
- requiredEnv: opts.requiredEnv,
30
- deprecated: opts.deprecated,
31
- replacedBy: opts.replacedBy,
32
29
  navigateBefore: opts.navigateBefore,
30
+ browserSession: opts.browserSession,
33
31
  defaultFormat: opts.defaultFormat,
34
32
  };
35
33
  registerCommand(cmd);
@@ -58,11 +56,13 @@ export function strategyLabel(cmd) {
58
56
  * 2. Derived from strategy + domain (the defaults below)
59
57
  */
60
58
  function normalizeCommand(cmd) {
59
+ assertCommandAccess(cmd);
60
+ assertBrowserSessionOptions(cmd);
61
61
  const strategy = cmd.strategy ?? (cmd.browser === false ? Strategy.PUBLIC : Strategy.COOKIE);
62
62
  const browser = cmd.browser ?? (strategy !== Strategy.PUBLIC && strategy !== Strategy.LOCAL);
63
63
  let navigateBefore = cmd.navigateBefore;
64
64
  if (navigateBefore === undefined) {
65
- if ((strategy === Strategy.COOKIE || strategy === Strategy.HEADER) && cmd.domain) {
65
+ if (strategy === Strategy.COOKIE && cmd.domain) {
66
66
  navigateBefore = `https://${cmd.domain}`;
67
67
  }
68
68
  else if (strategy !== Strategy.PUBLIC && strategy !== Strategy.LOCAL) {
@@ -76,6 +76,24 @@ function normalizeCommand(cmd) {
76
76
  ? { ...cmd, strategy, browser: true, navigateBefore }
77
77
  : { ...cmd, strategy, browser: false, navigateBefore };
78
78
  }
79
+ function assertCommandAccess(cmd) {
80
+ if (cmd.access === 'read' || cmd.access === 'write')
81
+ return;
82
+ const key = `${cmd.site}/${cmd.name}`;
83
+ throw new Error(`Command ${key} must declare access: 'read' | 'write'`);
84
+ }
85
+ function assertBrowserSessionOptions(cmd) {
86
+ if (cmd.browserSession === undefined)
87
+ return;
88
+ const key = `${cmd.site}/${cmd.name}`;
89
+ if (cmd.browserSession === null || typeof cmd.browserSession !== 'object' || Array.isArray(cmd.browserSession)) {
90
+ throw new Error(`Command ${key} browserSession must be an object`);
91
+ }
92
+ const reuse = cmd.browserSession.reuse;
93
+ if (reuse !== undefined && reuse !== 'none' && reuse !== 'site') {
94
+ throw new Error(`Command ${key} browserSession.reuse must be one of: none, site`);
95
+ }
96
+ }
79
97
  export function registerCommand(cmd) {
80
98
  const normalized = normalizeCommand(cmd);
81
99
  const canonicalKey = fullName(normalized);