{"id":40853456,"url":"https://github.com/ukatech/jsstp-lib","last_synced_at":"2026-01-21T23:43:02.696Z","repository":{"id":160385968,"uuid":"609855206","full_name":"ukatech/jsstp-lib","owner":"ukatech","description":"Use js to communicate with ukagaka in environments such as web pages or node.js in order to exchange information.","archived":false,"fork":false,"pushed_at":"2024-06-26T03:00:17.000Z","size":1389,"stargazers_count":5,"open_issues_count":0,"forks_count":2,"subscribers_count":2,"default_branch":"master","last_synced_at":"2025-10-24T16:29:02.491Z","etag":null,"topics":["js","ukagaka","web"],"latest_commit_sha":null,"homepage":"https://ukatech.github.io/jsstp-lib/","language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"other","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/ukatech.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2023-03-05T12:55:44.000Z","updated_at":"2024-06-26T03:00:21.000Z","dependencies_parsed_at":"2023-05-25T11:30:54.938Z","dependency_job_id":"cb42a657-0eea-4210-a189-46df56331339","html_url":"https://github.com/ukatech/jsstp-lib","commit_stats":null,"previous_names":[],"tags_count":34,"template":false,"template_full_name":null,"purl":"pkg:github/ukatech/jsstp-lib","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ukatech%2Fjsstp-lib","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ukatech%2Fjsstp-lib/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ukatech%2Fjsstp-lib/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ukatech%2Fjsstp-lib/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/ukatech","download_url":"https://codeload.github.com/ukatech/jsstp-lib/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ukatech%2Fjsstp-lib/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":28646954,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-01-21T21:29:11.980Z","status":"ssl_error","status_checked_at":"2026-01-21T21:24:31.872Z","response_time":86,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.5:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["js","ukagaka","web"],"created_at":"2026-01-21T23:43:02.605Z","updated_at":"2026-01-21T23:43:02.668Z","avatar_url":"https://github.com/ukatech.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"[![日本語](https://raw.githubusercontent.com/gosquared/flags/master/flags/flags/shiny/48/Japan.png)](./docs/README_JP.md)\n[![English](https://raw.githubusercontent.com/gosquared/flags/master/flags/flags/shiny/48/United-Kingdom.png)](./docs/README_EN.md)\n[![中文](https://raw.githubusercontent.com/gosquared/flags/master/flags/flags/shiny/48/China.png)](./docs/README_CN.md)\n\n# jsstp  \n\n[![jsDelivr hits](https://img.shields.io/jsdelivr/gh/hm/ukatech/jsstp-lib?color=green)](https://www.jsdelivr.com/package/gh/ukatech/jsstp-lib)\n[![npm下载量](https://img.shields.io/npm/dm/jsstp?label=npm%E4%B8%8B%E8%BD%BD%E9%87%8F)](https://www.npmjs.com/package/jsstp)\n[![npm bundle大小](https://img.shields.io/bundlephobia/min/jsstp?label=npm%20bundle%E5%A4%A7%E5%B0%8F)](./dist/jsstp.min.js)  \n\n用js在网页或node.js等环境中与伪春菜通信以实现信息交换。\n详情参考[伪春菜](https://zh.moegirl.org.cn/zh-hans/%E4%BC%AA%E6%98%A5%E8%8F%9C)与[SSTP](https://ssp.shillest.net/ukadoc/manual/spec_sstp.html)。\n\n## 用法\n\n### 1. 引入js\n\n#### npm\n\n如果你使用npm，你可以使用npm安装jsstp\n\n```shell\nnpm i jsstp\n```\n\n之后在js中使用`import`引入jsstp\n\n```javascript\nimport jsstp from \"jsstp\";\n//或者\nvar {jsstp}=await import(\"jsstp\");\n```\n\n在CommonJS中，你也可以使用`require`引入jsstp  \n\n```javascript\nvar {jsstp}=require('jsstp');\n```\n\n#### cdn\n\n或者你是怀旧党，你可以通过cdn访问jsstp的源码\n\n```html\n\u003cscript src=\"https://cdn.jsdelivr.net/gh/ukatech/jsstp-lib@v3.2.0.0/dist/jsstp.min.js\"\u003e\u003c/script\u003e\n```\n\n或者在js中动态载入jsstp\n\n```javascript\nvar {jsstp}=await import(\"https://cdn.jsdelivr.net/gh/ukatech/jsstp-lib@v3.2.0.0/dist/jsstp.mjs\");\n```\n\n##### 类型定义\n\n即使使用cdn并手把手编写js代码，你也可以在ide中使用jsstp的类型定义文件以获得代码提示\n\n首先确保你的ide可以访问jsstp，你或许可以全局安装它来在不干扰工作区文件的情况下使用它\n\n```shell\nnpm i -g jsstp\n```\n\n随后，在使用jsstp的文件头部添加类型导入，根据types约定，这个声明必须在任何正式代码之前\n\n```javascript\n/// \u003creference types=\"jsstp\" /\u003e\n```\n\n最后在jsstp的声明前用JSDoc注释声明其类型\n\n```javascript\n/** @type {typeof import(\"jsstp\").jsstp} */\nvar jsstp;\n```\n\n###### 类型定义：i18n\n\njsstp的类型定义提供了中日英三语的支持，正常情况下你可以这样指定加载的语言\n\n```javascript\n/// \u003creference types=\"jsstp/cn\" /\u003e\n// or\n/// \u003creference types=\"jsstp/jp\" /\u003e\n// or\n/// \u003creference types=\"jsstp/en\" /\u003e\n```\n\n不过如果你的ide在这样使用时出了错（或者你懒得每次都指定语言），你可以考虑手动修改`package.json`中的`types`字段来指定默认的语言\n\n```json\n{\n\t\"types\": \"dist/cn/jsstp.d.ts\"\n}\n```\n\n### 2. 使用\n\njsstp现在有专门的文档页面了！  \n你可以访问\u003chttps://ukatech.github.io/jsstp-lib/doc\u003e来获取更专业的信息  \n在观看文档的过程中，你可以在[jsstp playground](https://ukatech.github.io/jsstp-lib/playground)中尝试jsstp的各种功能  \n\n____\n\n你可能需要先在jsstp相关操作前检查ghost是否可用  \n\n```javascript\nif (!await jsstp.available())\n\tconsole.log(\"ghost不可用,请检查ghost是否启动\");\n```\n\njsstp2.0前曾经支持将回调函数作为参数传入，现在已经不再支持  \n如果你需要的话，可以使用`Promise`或者`async`/`await`来获取返回值  \n你可以使用`jsstp.SEND`来发送报文  \n\n```javascript\njsstp.SEND(\n\t{//事件信息\n\t\t\"Event\": \"OnTest\",\n\t\t\"Script\": \"\\\\0Hello, World!\\\\e\"\n\t}\n).then((data) =\u003e {\n\tconsole.log(\"head: \" + data.head);\n\tconsole.log(JSON.stringify(data));\n\tconsole.log(data[\"Script\"]);\n});\n```\n\njsstp支持所有的sstp基础操作，`jsstp.[SEND|NOTIFY|COMMUNICATE|EXECUTE|GIVE]`都可以被调用。  \n如果你喜欢怀旧，只想获得报文本身，你可以使用`jsstp.[SEND|NOTIFY|COMMUNICATE|EXECUTE|GIVE].get_raw`  \n\n如果你只是想触发事件，而不需要自定义发送较为复杂的报文，可以这样写\n\n```javascript\nlet data = await jsstp.OnTest(\"from jsstp.js!\", 123123);\n```\n\n这等价于：\n\n```javascript\nlet data = await jsstp.SEND({\n\t\"Event\": \"OnTest\",\n\t\"Reference0\": \"from jsstp.js!\",\n\t\"Reference1\": 123123\n});\n```\n\n对于所有事件你都可以这样写，不过如果事件不以`On`开头，你需要在事件名前加上`On_`来访问jsstp，这样它才能识别到你想要触发事件  \n你也可以使用`jsstp.event.事件名(参数)`来触发事件，这样你就不需要在事件名前加上`On_`了  \n\n在获取到返回内容后，其类型是`jsstp.sstp_info_t`，使用方法各种各样  \n\n- 以下是自`info_object`继承的方法\n\n```javascript\ndata.keys; //获取所有键\ndata.values; //获取所有值\ndata.entries; //获取所有键值对\ndata.length; //获取键值对数量\ndata.forEach((value, key) =\u003e console.log(key + \"=\" + value)); //遍历所有键值对：如果遍历函数有返回值，该值会被更新到此键值对中\n//省略key参数可以只遍历值\ndata.map((value, key) =\u003e value + \"1\"); //遍历所有键值对并返回一个由遍历函数返回值组成的数组\n//省略key参数可以只遍历值\n```\n\n- 以下是自`jsstp.base_sstp_info_t`继承的方法\n\n```javascript\ndata.status_code; //获取状态码\ndata.head; //获取报文头\ndata.Script; //获取报文中的Script键的值（其他键也可以这样获取）\ndata.status_code_text; //获取报文头中的状态码文本\n```\n\n- 以下是`jsstp.sstp_info_t`自有的方法\n\n```javascript\ndata.get_passthrough(\"Result\");\n//获取报文中`X-SSTP-PassThru`的某个键的值，和`data[\"X-SSTP-PassThru-Result\"]`等价\n//你也可以直接使用`data.Result`或者`data[\"Result\"]`来获取`X-SSTP-PassThru-Result`的值：这可能简洁一些\ndata.passthroughs; //获取所有`X-SSTP-PassThru`键值对\ndata.raw; //去除代理，访问原始对象\n```\n\n`sstp_info_t`自构造起便被一层代理包裹着，考虑到大多数情况开发者不需要访问非`X-SSTP-PassThru`键值对，此代理会在你访问某个键而该键存在`X-SSTP-PassThru`版本时优先返回`X-SSTP-PassThru-{key}`键的值。  \n换句话说，假若返回的报文有`Script`键和`X-SSTP-PassThru-Script`键，那么`data.Script`或`data[\"Script\"]`会返回`X-SSTP-PassThru-Script`的值，而`data.raw.Script`和`data.raw[\"Script\"]`会返回`Script`的值。  \n大多数情况下这个代理会减轻你的代码量，而在你需要访问非`X-SSTP-PassThru`键值对时，请一定记得使用`data.raw`来访问原始对象。  \n\n如果你想获取ghost是否支持某个事件，可以这样写\n\n```javascript\nlet result = await jsstp.has_event(\"OnTest\");//这和jsstp.event.Has_Event(event_name, security_level).then(({ Result }) =\u003e Result == \"1\")几乎一样！\nconsole.log(result);\n```\n\n如果你想大批量的查询事件（像ukadoc那样！），你可以使用`jsstp.new_event_queryer()`来获取一个queryer\n\n```javascript\nlet queryer = await jsstp.new_event_queryer();\n```\n\nqueryer的类型是`jsstp.ghost_events_queryer_t`，使用方法各种各样\n\n```javascript\nqueryer.check_event(\"OnTest\").then(result =\u003e console.log(result));\n```\n\nqueryer和`jsstp`一样，检查事件时有可选的参数指定事件的安全等级，默认的安全等级随着`jsstp`的运行环境而变化：  \n如果jsstp运行在node.js中，安全等级为`local`，如果jsstp运行在浏览器中，安全等级为`external`（因为浏览器中的jsstp只能触发外部事件！）  \n如果你想要固定查询local事件，你需要指定安全等级为`local`，像这样：  \n\n```javascript\nqueryer.check_event(\"OnBoot\", \"local\");\njsstp.has_event(\"OnBoot\", \"local\");//使用jsstp的话这样\n```\n\nqueryer还支持一些快速检测  \nqueryer与构造它的jsstp实例是绑定的，如果你想要让queryer指向特定的ghost，通过设置`jsstp.default_info`来修改默认的附加报文并使用`reset`清空缓存  \n\n```javascript\n//使用fmo中得到的hwnd，这可以避免重名导致的尴尬情况\njsstp.default_info.ReceiverGhostHWnd = fmo[uuid].hwnd;//fmo的获取方法见下文，这里只是举个例子\nawait queryer.reset();\n```\n\n如果你确定你的ghost名称足够独特，你也可以直接使用ghost名称，这两个方法只用其中一个就可以了\n\n```javascript\njsstp.default_info.ReceiverGhostName = \"橘花\";\nawait queryer.reset();\n```\n\nqueryer还支持一些快速检测用于检查queryer的可用性\n\n```javascript\nif (!queryer.available)\n\tconsole.info(\"无法获取支持的事件列表\");//queryer不可用，你需要提醒用户更新ghost或者向其作者反馈：jsstp和ghost terminal一样使用`Has_Event`事件来检查事件的可用情况。\nif (!queryer.fast_query_available)\n\tconsole.info(\"无法快速获取支持的事件列表\");//这不会影响使用，只是会导致查询未缓存的事件时会发出一次查询请求：如果ghost支持`Get_Supported_Events`事件的话queryer会使用它来获取事件列表（这样会快不少！）\nelse\n\tconsole.info(\"好哦\");\n```\n\n如果你想获取fmo信息，可以这样写\n\n```javascript\nlet fmo = await jsstp.get_fmo_infos();\nif (fmo.available)\n\tconsole.log(fmo);\n```\n\nfmo的类型是`jsstp.fmo_info_t`，使用方法各种各样  \n`fmo_info_t`是特化的`base_sstp_info_t`，所以你可以对其使用`base_sstp_info_t`的所有方法（也就是说，`sstp_info_t`的所有方法除了`get_passthrough`）  \n它还有一些特殊的方法  \n\n```javascript\nfmo.uuids; //获取所有uuid，和`fmo.keys`等价\nfmo.get_uuid_by(\"fullname\", \"Taromati2\"); //获取指定属性值与指定值相等的uuid\nfmo.get_list_of(\"fullname\"); //获取指定属性的所有值\nfmo.available; //获取fmo是否有内容\n```\n\nfmo的每个键值对都是`String:info_object`，键是uuid，值是该uuid对应的fmo信息  \n你仍然可以使用`info_object`的成员方法来操作fmo的中的fmo信息（参见上文中对于`sstp_info_t`的介绍）  \n如果你还是不太理解，可以在控制台查看fmo的结构或者查看jsstp的源码  \n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fukatech%2Fjsstp-lib","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fukatech%2Fjsstp-lib","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fukatech%2Fjsstp-lib/lists"}