{"id":15978178,"url":"https://github.com/brookshuihualee/mobo-ts","last_synced_at":"2025-03-18T00:31:05.675Z","repository":{"id":225253307,"uuid":"765474194","full_name":"BrookShuihuaLee/mobo-ts","owner":"BrookShuihuaLee","description":"A pluggable typescript library","archived":false,"fork":false,"pushed_at":"2024-09-09T14:07:34.000Z","size":83,"stargazers_count":2,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-03-16T16:11:22.711Z","etag":null,"topics":["aop","higher-kinded-types","hkt","mobo","pluggable","plugin","ts","typescript"],"latest_commit_sha":null,"homepage":"","language":"TypeScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/BrookShuihuaLee.png","metadata":{"files":{"readme":"readme-zh-cn.md","changelog":null,"contributing":null,"funding":null,"license":null,"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":"2024-03-01T01:40:18.000Z","updated_at":"2024-09-09T14:07:37.000Z","dependencies_parsed_at":"2024-03-01T08:46:45.717Z","dependency_job_id":"49733a12-93e2-4d23-97b6-29007957601f","html_url":"https://github.com/BrookShuihuaLee/mobo-ts","commit_stats":{"total_commits":3,"total_committers":1,"mean_commits":3.0,"dds":0.0,"last_synced_commit":"a500cea34e2c8c45f64a1c391f01c10e07532d79"},"previous_names":["brookshuihualee/mobo","brookshuihualee/mobo-ts"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/BrookShuihuaLee%2Fmobo-ts","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/BrookShuihuaLee%2Fmobo-ts/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/BrookShuihuaLee%2Fmobo-ts/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/BrookShuihuaLee%2Fmobo-ts/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/BrookShuihuaLee","download_url":"https://codeload.github.com/BrookShuihuaLee/mobo-ts/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":244133851,"owners_count":20403505,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","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":["aop","higher-kinded-types","hkt","mobo","pluggable","plugin","ts","typescript"],"created_at":"2024-10-07T23:06:32.129Z","updated_at":"2025-03-18T00:31:05.352Z","avatar_url":"https://github.com/BrookShuihuaLee.png","language":"TypeScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"[English (US)](./readme.md) | 中文（简体）\n\n# Mobo\n\nMobo (Motherboard), 一个插件化 TS 库。\n\n[![](https://s1.locimg.com/2024/09/09/ee0ba0dac1974.png)](https://stackblitz.com/edit/vitejs-vite-hyb4ts?file=src%2Ftest-mobo.ts)\n\n# 安装\n\n```sh\npnpm i @mobo-ts/mobo\n# or\nnpm i @mobo-ts/mobo\n```\n\n# 使用\n\n插件主要由三个部分组成：\n\n- 上下文类型：在 `MoboPlugin` 里通过扩展键值来声明，比如：`abc`。\n- 上下文初始化选项类型：在 `MoboPlugin` 里通过扩展键值拼接 `InitOptions` 来声明，比如：`abcInitOptions`。\n- 初始化函数：在插件对象里通过 `init` 拼接扩展键值来实现，比如：`initAbc`。\n\n在 `Mobo` 初始化和子上下文初始化时，可以得到准确的类型提示。然后，上下文初始化时，也会调用所有插件里的初始化函数，以分治的方式完成。\n\n```ts\nconst p: MoboPlugin\u003c{\n  mm: {\n    /**\n     * a 3234\n     */\n    a: number\n  }\n  mmInitOptions: {\n    /**\n     * bbbbbs\n     */\n    b: number\n  }\n  abcDd: {\n    /**\n     * 234\n     */\n    jjx: number[]\n  }\n  abcDdInitOptions: {\n    /**\n     * lkdjf\n     */\n    sdf: string[]\n  }\n}\u003e = {\n  id: '1',\n  initMm(ctx) {\n    ctx.a = ctx.initOptions.b + 1\n  },\n  initAbcDd(ctx) {\n    ctx.jjx = ctx.initOptions.sdf.map((s: string) =\u003e Number(s))\n  },\n}\n\nconst m = new Mobo([p], ['mm']).init({ b: 4 })\nconsole.log(m.a) // 5\nconst ctx = m.initSubcontext(['abcDd'], {\n  sdf: ['1', '2'],\n})\nconsole.log(ctx.jjx) // [1, 2]\n\nconst m2 = new Mobo([], ['mm']).use(p).init({ b: 43 })\nconsole.log(m2.a) // 44\n```\n\n## 自定义插件类型\n\n```ts\ninterface DodoPlugin\u003c\n  PropertiesExt extends MoboDefaultPropertiesExt,\n  DepPlugin extends AnyMoboPlugin = never,\n\u003e extends MoboPlugin\u003cPropertiesExt\u003e {\n  /**\n   * init Dodo\n   */\n  initDodo?: MoboPluginInitFnByPlugin\u003cthis | DepPlugin, 'dodo'\u003e\n}\n\nfunction createDodo\u003cPlugin extends AnyMoboPlugin\u003e(\n  plugins: readonly Plugin[],\n): Mobo\u003cPlugin, 'dodo'\u003e {\n  return new Mobo(plugins, ['dodo'])\n}\n\nconst p: DodoPlugin\u003c{\n  dodo: {\n    a: number\n  }\n  dodoInitOptions: {\n    b: number\n  }\n}\u003e = {\n  id: '1',\n  initDodo(ctx) {\n    ctx.a = ctx.initOptions.b + 1\n  },\n}\n\nconst dodo = createDodo([p]).init({ b: 4 })\nconsole.log(dodo.a) // 5\n```\n\n## 自定义插件高等类型\n\n感谢 [free-types](https://github.com/geoffreytools/free-types).\n\n```ts\ntype DodoDefaultPropertiesExt =\n  | MoboDefaultPropertiesExtObj\u003c'context' | 'dodo'\u003e\n  | MoboDefaultPropertiesExtHkt\n\ninterface DodoPlugin\u003c\n  PropertiesExt extends DodoDefaultPropertiesExt,\n  DepPlugin extends AnyMoboPlugin = never,\n\u003e extends MoboPlugin\u003cPropertiesExt\u003e {\n  /**\n   * init Context\n   */\n  initContext?: MoboPluginInitFnByPlugin\u003cthis | DepPlugin, 'context'\u003e\n  /**\n   * init Dodo\n   */\n  initDodo?: MoboPluginInitFnByPlugin\u003cthis | DepPlugin, 'context' | 'dodo'\u003e\n}\n\nfunction createDodo\u003cPlugin extends AnyMoboPlugin\u003e(\n  plugins: readonly Plugin[],\n): Mobo\u003cPlugin, 'context' | 'dodo'\u003e {\n  return new Mobo(plugins, ['context', 'dodo'])\n}\n\nconst p1: DodoPlugin\u003c{\n  dodo: {\n    a: number\n  }\n  dodoInitOptions: {\n    b: number\n  }\n}\u003e = {\n  id: '1',\n  initDodo(ctx) {\n    ctx.a = ctx.initOptions.b + 1\n  },\n}\nconst p2: DodoPlugin\u003c\n  {\n    context: {\n      co: number[]\n    }\n    contextInitOptions: {\n      ci: number\n    }\n  },\n  typeof p1\n\u003e = {\n  id: '2',\n  initContext(ctx) {\n    ctx.co = [ctx.initOptions.ci * 2]\n  },\n  initDodo(ctx) {\n    ctx.co.push(ctx.a++)\n  },\n}\ninterface MyPropertiesExtHkt\u003cPlugin extends AnyMoboPlugin\u003e {\n  context: {\n    /**\n     * asdf\n     */\n    parent?:\n      | MoboContext\u003cPlugin, 'context'\u003e\n      | MoboContext\u003cPlugin, 'context' | 'dodo'\u003e\n  }\n  contextInitOptions: {\n    /**\n     * in333\n     */\n    parent?:\n      | MoboContext\u003cPlugin, 'context'\u003e\n      | MoboContext\u003cPlugin, 'context' | 'dodo'\u003e\n  }\n}\ninterface $MyPropertiesExtHkt extends MoboDefaultPropertiesExtHkt {\n  type: MyPropertiesExtHkt\u003cMoboDefaultPropertiesExtHktPlugin\u003cthis\u003e\u003e\n}\nconst p3: DodoPlugin\u003c$MyPropertiesExtHkt\u003e = {\n  id: '3',\n  initContext(ctx) {\n    ctx.parent = ctx.initOptions.parent\n  },\n}\n\nconst m = createDodo([p1]).use(p2, p3).init({ b: 4, ci: 3 })\nconsole.log(m.a) // 6\nconsole.log(m.co) // [6, 5]\nconsole.log(m.parent) // undefined\nconst ctx = m.initSubcontext(['context'], {\n  ci: 7,\n  parent: m,\n})\nconsole.log(ctx.co) // [14]\nconsole.log(ctx.parent) // m\nconst ctx2 = ctx.initSubcontext(['context'], {\n  ci: 7,\n  parent: ctx,\n})\nconsole.log(ctx2.co) // [14]\nconsole.log(ctx2.parent) // ctx\n```\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbrookshuihualee%2Fmobo-ts","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fbrookshuihualee%2Fmobo-ts","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbrookshuihualee%2Fmobo-ts/lists"}