farming-code 2.2.6
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.
- package/LICENSE +21 -0
- package/README.md +287 -0
- package/README.zh_cn.md +329 -0
- package/SECURITY.md +29 -0
- package/THIRD_PARTY_NOTICES.md +106 -0
- package/backend/acp/client-services.js +312 -0
- package/backend/acp/patch-decisions.js +137 -0
- package/backend/acp/permission-security.js +108 -0
- package/backend/acp-runtime.js +1144 -0
- package/backend/acp-session-state.js +448 -0
- package/backend/acp-transcript.js +169 -0
- package/backend/agent-activity.js +186 -0
- package/backend/agent-env.js +250 -0
- package/backend/agent-json-stream.js +268 -0
- package/backend/agent-manager.js +4259 -0
- package/backend/agent-memory-report.js +583 -0
- package/backend/agent-order.js +162 -0
- package/backend/agent-provider-session.js +287 -0
- package/backend/agent-session-history.js +888 -0
- package/backend/app-server-api.js +917 -0
- package/backend/async-cache.js +94 -0
- package/backend/auth.js +178 -0
- package/backend/claude-settings.js +121 -0
- package/backend/cli-agents.js +484 -0
- package/backend/codex-app-server-home.js +39 -0
- package/backend/codex-app-server-runtime.js +901 -0
- package/backend/codex-context-window.js +189 -0
- package/backend/codex-models.js +229 -0
- package/backend/codex-rollout-follower.js +243 -0
- package/backend/codex-session-history.js +553 -0
- package/backend/codex-transcript-sanitizer.js +103 -0
- package/backend/codex-transcript.js +2341 -0
- package/backend/command-runner-child.js +67 -0
- package/backend/config-manager.js +815 -0
- package/backend/control-api.js +151 -0
- package/backend/data/chinese-poetic-words.json +8223 -0
- package/backend/data/poetic-word-sources/china.json +49209 -0
- package/backend/data/poetic-word-sources/india.json +9763 -0
- package/backend/data/poetic-word-sources/japan.json +8455 -0
- package/backend/executable-discovery.js +207 -0
- package/backend/farming-app-cli.js +790 -0
- package/backend/farming-cli.js +400 -0
- package/backend/farming-session-store.js +373 -0
- package/backend/haiku-token.js +772 -0
- package/backend/index-html.js +49 -0
- package/backend/input-parts.js +54 -0
- package/backend/input-routing.js +24 -0
- package/backend/json-cli-runtime.js +161 -0
- package/backend/local-session-engine.js +620 -0
- package/backend/main-agent-skills.js +292 -0
- package/backend/main-page-session.js +119 -0
- package/backend/native-pty-host-client.js +516 -0
- package/backend/native-pty-host-path.js +22 -0
- package/backend/native-pty-host.js +816 -0
- package/backend/native-session-engine.js +196 -0
- package/backend/network.js +23 -0
- package/backend/npm-update-helper.js +196 -0
- package/backend/packaged-node-pty.js +79 -0
- package/backend/provider-session-id.js +47 -0
- package/backend/qr-share-tickets.js +100 -0
- package/backend/review-diff-router.js +180 -0
- package/backend/review-diff-service.js +1270 -0
- package/backend/review-session-router.js +74 -0
- package/backend/review-session-service.js +432 -0
- package/backend/review-session-store.js +144 -0
- package/backend/review-state-router.js +116 -0
- package/backend/review-state-store.js +287 -0
- package/backend/run-history-store.js +70 -0
- package/backend/server.js +2446 -0
- package/backend/session-engine-bridge.js +110 -0
- package/backend/session-engine-router.js +66 -0
- package/backend/session-engine.js +39 -0
- package/backend/shell-busy-integration.js +472 -0
- package/backend/slash-command-discovery.js +296 -0
- package/backend/storage-layout.js +101 -0
- package/backend/system-monitor.js +77 -0
- package/backend/terminal-runtime-cleanup.js +80 -0
- package/backend/terminal-screen-state.js +240 -0
- package/backend/terminal-screen-worker-pool.js +165 -0
- package/backend/terminal-screen-worker-thread.js +161 -0
- package/backend/terminal-screen-worker.js +255 -0
- package/backend/terminal-status.js +356 -0
- package/backend/theme-manager.js +145 -0
- package/backend/update-service.js +1183 -0
- package/backend/usage-forecast.js +86 -0
- package/backend/usage-monitor.js +1357 -0
- package/backend/workspace-discovery.js +311 -0
- package/backend/workspace-file-router.js +431 -0
- package/backend/workspace-file-service.js +2765 -0
- package/bin/farming +5 -0
- package/config/farming.deploy.env.example +13 -0
- package/config/farming.install.env.example +17 -0
- package/dist/assets/App-BrP-ENHg.css +1 -0
- package/dist/assets/App-Dza5yEDe.js +124 -0
- package/dist/assets/FileEditorMarkdownPreview-DRDNQ8mX.css +1 -0
- package/dist/assets/FileEditorMarkdownPreview-elKWc8Im.js +404 -0
- package/dist/assets/FileEditorPane-BQLocXOp.js +5 -0
- package/dist/assets/IconGlyphs-RkMAdBXF.js +1 -0
- package/dist/assets/KaTeX_AMS-Regular-BQhdFMY1.woff2 +0 -0
- package/dist/assets/KaTeX_AMS-Regular-DMm9YOAa.woff +0 -0
- package/dist/assets/KaTeX_AMS-Regular-DRggAlZN.ttf +0 -0
- package/dist/assets/KaTeX_Caligraphic-Bold-ATXxdsX0.ttf +0 -0
- package/dist/assets/KaTeX_Caligraphic-Bold-BEiXGLvX.woff +0 -0
- package/dist/assets/KaTeX_Caligraphic-Bold-Dq_IR9rO.woff2 +0 -0
- package/dist/assets/KaTeX_Caligraphic-Regular-CTRA-rTL.woff +0 -0
- package/dist/assets/KaTeX_Caligraphic-Regular-Di6jR-x-.woff2 +0 -0
- package/dist/assets/KaTeX_Caligraphic-Regular-wX97UBjC.ttf +0 -0
- package/dist/assets/KaTeX_Fraktur-Bold-BdnERNNW.ttf +0 -0
- package/dist/assets/KaTeX_Fraktur-Bold-BsDP51OF.woff +0 -0
- package/dist/assets/KaTeX_Fraktur-Bold-CL6g_b3V.woff2 +0 -0
- package/dist/assets/KaTeX_Fraktur-Regular-CB_wures.ttf +0 -0
- package/dist/assets/KaTeX_Fraktur-Regular-CTYiF6lA.woff2 +0 -0
- package/dist/assets/KaTeX_Fraktur-Regular-Dxdc4cR9.woff +0 -0
- package/dist/assets/KaTeX_Main-Bold-Cx986IdX.woff2 +0 -0
- package/dist/assets/KaTeX_Main-Bold-Jm3AIy58.woff +0 -0
- package/dist/assets/KaTeX_Main-Bold-waoOVXN0.ttf +0 -0
- package/dist/assets/KaTeX_Main-BoldItalic-DxDJ3AOS.woff2 +0 -0
- package/dist/assets/KaTeX_Main-BoldItalic-DzxPMmG6.ttf +0 -0
- package/dist/assets/KaTeX_Main-BoldItalic-SpSLRI95.woff +0 -0
- package/dist/assets/KaTeX_Main-Italic-3WenGoN9.ttf +0 -0
- package/dist/assets/KaTeX_Main-Italic-BMLOBm91.woff +0 -0
- package/dist/assets/KaTeX_Main-Italic-NWA7e6Wa.woff2 +0 -0
- package/dist/assets/KaTeX_Main-Regular-B22Nviop.woff2 +0 -0
- package/dist/assets/KaTeX_Main-Regular-Dr94JaBh.woff +0 -0
- package/dist/assets/KaTeX_Main-Regular-ypZvNtVU.ttf +0 -0
- package/dist/assets/KaTeX_Math-BoldItalic-B3XSjfu4.ttf +0 -0
- package/dist/assets/KaTeX_Math-BoldItalic-CZnvNsCZ.woff2 +0 -0
- package/dist/assets/KaTeX_Math-BoldItalic-iY-2wyZ7.woff +0 -0
- package/dist/assets/KaTeX_Math-Italic-DA0__PXp.woff +0 -0
- package/dist/assets/KaTeX_Math-Italic-flOr_0UB.ttf +0 -0
- package/dist/assets/KaTeX_Math-Italic-t53AETM-.woff2 +0 -0
- package/dist/assets/KaTeX_SansSerif-Bold-CFMepnvq.ttf +0 -0
- package/dist/assets/KaTeX_SansSerif-Bold-D1sUS0GD.woff2 +0 -0
- package/dist/assets/KaTeX_SansSerif-Bold-DbIhKOiC.woff +0 -0
- package/dist/assets/KaTeX_SansSerif-Italic-C3H0VqGB.woff2 +0 -0
- package/dist/assets/KaTeX_SansSerif-Italic-DN2j7dab.woff +0 -0
- package/dist/assets/KaTeX_SansSerif-Italic-YYjJ1zSn.ttf +0 -0
- package/dist/assets/KaTeX_SansSerif-Regular-BNo7hRIc.ttf +0 -0
- package/dist/assets/KaTeX_SansSerif-Regular-CS6fqUqJ.woff +0 -0
- package/dist/assets/KaTeX_SansSerif-Regular-DDBCnlJ7.woff2 +0 -0
- package/dist/assets/KaTeX_Script-Regular-C5JkGWo-.ttf +0 -0
- package/dist/assets/KaTeX_Script-Regular-D3wIWfF6.woff2 +0 -0
- package/dist/assets/KaTeX_Script-Regular-D5yQViql.woff +0 -0
- package/dist/assets/KaTeX_Size1-Regular-C195tn64.woff +0 -0
- package/dist/assets/KaTeX_Size1-Regular-Dbsnue_I.ttf +0 -0
- package/dist/assets/KaTeX_Size1-Regular-mCD8mA8B.woff2 +0 -0
- package/dist/assets/KaTeX_Size2-Regular-B7gKUWhC.ttf +0 -0
- package/dist/assets/KaTeX_Size2-Regular-Dy4dx90m.woff2 +0 -0
- package/dist/assets/KaTeX_Size2-Regular-oD1tc_U0.woff +0 -0
- package/dist/assets/KaTeX_Size3-Regular-CTq5MqoE.woff +0 -0
- package/dist/assets/KaTeX_Size3-Regular-DgpXs0kz.ttf +0 -0
- package/dist/assets/KaTeX_Size4-Regular-BF-4gkZK.woff +0 -0
- package/dist/assets/KaTeX_Size4-Regular-DWFBv043.ttf +0 -0
- package/dist/assets/KaTeX_Size4-Regular-Dl5lxZxV.woff2 +0 -0
- package/dist/assets/KaTeX_Typewriter-Regular-C0xS9mPB.woff +0 -0
- package/dist/assets/KaTeX_Typewriter-Regular-CO6r4hn1.woff2 +0 -0
- package/dist/assets/KaTeX_Typewriter-Regular-D3Ib7_Hf.ttf +0 -0
- package/dist/assets/ProjectFilesSection-lS1azbgj.js +12 -0
- package/dist/assets/ReviewPage-DgnmgU2T.js +3 -0
- package/dist/assets/abap-Cc5D5h5i.js +1 -0
- package/dist/assets/abnfDiagram-VRR7QNED-BgawzDQT.js +1 -0
- package/dist/assets/apex-BKopwLmx.js +1 -0
- package/dist/assets/api-D1lyBYIQ.js +1 -0
- package/dist/assets/arc-CWoVlxJw.js +1 -0
- package/dist/assets/architecture-TIHT7OUA-CbJBFh3w.js +1 -0
- package/dist/assets/architectureDiagram-ZJ3FMSHR-DUShwPg0.js +36 -0
- package/dist/assets/array-HeX70jSN.js +1 -0
- package/dist/assets/azcli-DI-C34WA.js +1 -0
- package/dist/assets/bat-Cbp6u42z.js +1 -0
- package/dist/assets/bicep-4QA1jTCM.js +2 -0
- package/dist/assets/blockDiagram-677ZJIJ3-CeGZviXR.js +132 -0
- package/dist/assets/c4Diagram-LMCZKHZV-CLhYht6S.js +10 -0
- package/dist/assets/cameligo-Dda_adPs.js +1 -0
- package/dist/assets/channel-Uw90AO0b.js +1 -0
- package/dist/assets/chunk-2Q5K7J3B-d5WWh8jo.js +1 -0
- package/dist/assets/chunk-32BRIVSS-LFYpT-Cu.js +1 -0
- package/dist/assets/chunk-52WLFC77-BH6jDw9J.js +10 -0
- package/dist/assets/chunk-5FCAYU7R-C7AmIhYv.js +1 -0
- package/dist/assets/chunk-5HE753X5-C8cXaouP.js +1 -0
- package/dist/assets/chunk-5JV3BV7I-C1PtimcA.js +1 -0
- package/dist/assets/chunk-5TONJI2A-_81zUME8.js +2 -0
- package/dist/assets/chunk-5VM5RSS4-Dlw7AXWp.js +15 -0
- package/dist/assets/chunk-7BUUIJ7U-ZBRhjLOh.js +1 -0
- package/dist/assets/chunk-BIQX33UG-CWmzxeAw.js +1 -0
- package/dist/assets/chunk-C7G6YPKG-B_mIUlb7.js +1 -0
- package/dist/assets/chunk-CQNSW5MT-CMayolwI.js +1 -0
- package/dist/assets/chunk-CYSBUYHQ-lSPbrL3Z.js +1 -0
- package/dist/assets/chunk-DECur_0Z.js +1 -0
- package/dist/assets/chunk-EMLP6XTP-D9-jtCnM.js +1 -0
- package/dist/assets/chunk-EX3LRPZG-C63hVuAJ.js +231 -0
- package/dist/assets/chunk-FWX5IMBZ-CboX-WF_.js +2 -0
- package/dist/assets/chunk-HOUHSVGY-BOgSd6Un.js +1 -0
- package/dist/assets/chunk-ICXQ74PX-C0K-pgZt.js +2 -0
- package/dist/assets/chunk-JG7HCLWE-Cib606u_.js +2 -0
- package/dist/assets/chunk-JWPE2WC7-DSyBRaRG.js +1 -0
- package/dist/assets/chunk-KEIR6QF5-CNOHik0T.js +161 -0
- package/dist/assets/chunk-MOJQB5TN-CVMfwN_7.js +88 -0
- package/dist/assets/chunk-MOZMSUNE-D6JeZqmE.js +1 -0
- package/dist/assets/chunk-OGEWGWER-DLT3pxyw.js +1 -0
- package/dist/assets/chunk-OSBZ3O6U-C0W8KSeg.js +1 -0
- package/dist/assets/chunk-PUDLZKDR-Cd079yIQ.js +156 -0
- package/dist/assets/chunk-Q4XR5HBZ-D0jHa6SO.js +70 -0
- package/dist/assets/chunk-QBLGF6JB-p4omp7uO.js +1 -0
- package/dist/assets/chunk-R7FJI6CG-CZ_p9hSr.js +1 -0
- package/dist/assets/chunk-RYQCIY6F-CZA9pvFX.js +1 -0
- package/dist/assets/chunk-U6XO7XAA-CcXKsWxp.js +2 -0
- package/dist/assets/chunk-V7JOEXUC-CVDtR75H.js +206 -0
- package/dist/assets/chunk-VAUOI2AC-B-W2_9Ot.js +1 -0
- package/dist/assets/chunk-VR4S4FIN-FD3kWh32.js +1 -0
- package/dist/assets/chunk-WYO6CB5R-C2bGaS5r.js +127 -0
- package/dist/assets/chunk-XXDRQBXY-BBXwjhUx.js +1 -0
- package/dist/assets/chunk-Y2CYZVJY-Di0sYzi1.js +1 -0
- package/dist/assets/chunk-YOTPTUD7-BXHmEk89.js +1 -0
- package/dist/assets/chunk-ZGVPDNZ5-ymgts0zo.js +62 -0
- package/dist/assets/chunk-ZIRB5QZD-DncwlQQc.js +32 -0
- package/dist/assets/classDiagram-OUVF2IWQ-DKW_dtku.js +1 -0
- package/dist/assets/classDiagram-v2-EOCWNBFH-C8Fi7-yv.js +1 -0
- package/dist/assets/clojure-CvY8A83L.js +1 -0
- package/dist/assets/code-dark-Cjb1QGhu.css +1 -0
- package/dist/assets/code-mobile-3C2Rr-CN.css +1 -0
- package/dist/assets/codicon-ngg6Pgfi.ttf +0 -0
- package/dist/assets/coffee-4LX2Sv8A.js +1 -0
- package/dist/assets/core-ZlAPicox.js +3 -0
- package/dist/assets/cose-bilkent-JH36ORCC-BNIAz0nN.js +1 -0
- package/dist/assets/cpp-D4AzSV28.js +1 -0
- package/dist/assets/csharp-C4nWN4Yd.js +1 -0
- package/dist/assets/csp-CiEaaS5Z.js +1 -0
- package/dist/assets/css-DXxBRsbk.js +3 -0
- package/dist/assets/css.worker-DyDu5ynT.js +89 -0
- package/dist/assets/cssMode-DDWxTPm_.js +1 -0
- package/dist/assets/cynefin-VYW2F7L2-DgXGHlRt.js +1 -0
- package/dist/assets/cynefinDiagram-TSTJHNR4-CwpobXIl.js +62 -0
- package/dist/assets/cypher-DOMzqyFA.js +1 -0
- package/dist/assets/cytoscape.esm-Cl8iC3D7.js +321 -0
- package/dist/assets/dagre-DXlcHgr3.js +1 -0
- package/dist/assets/dagre-VKFMJZFB-Dkhlfjna.js +4 -0
- package/dist/assets/dart-BWS7MXt_.js +1 -0
- package/dist/assets/defaultLocale-GJwWH1Jr.js +1 -0
- package/dist/assets/diagram-FQU43EPY-hA8dicp6.js +3 -0
- package/dist/assets/diagram-G47NLZAW-BTY6JTzO.js +24 -0
- package/dist/assets/diagram-NH7WQ7WH-xkaHHX9M.js +24 -0
- package/dist/assets/diagram-OA4YK3LP-gk_fg9UU.js +30 -0
- package/dist/assets/diagram-WEI45ONY-BvC8xd6T.js +41 -0
- package/dist/assets/dist-ClAL-Tv5.js +1 -0
- package/dist/assets/dockerfile-Baf4U3xT.js +1 -0
- package/dist/assets/ebnfDiagram-CCIWWBDH-CR7RaNat.js +1 -0
- package/dist/assets/ecl-CT7udlkQ.js +1 -0
- package/dist/assets/editor-CtbFZlk0.css +1 -0
- package/dist/assets/editor.api2-B9h6iFPK.js +872 -0
- package/dist/assets/editor.worker-Dpt_xPrs.js +26 -0
- package/dist/assets/elixir-CIbAZw5l.js +1 -0
- package/dist/assets/erDiagram-Q63AITRT-_M-JFPbj.js +85 -0
- package/dist/assets/eventmodeling-45OFAUF4-DXYTQ2nt.js +1 -0
- package/dist/assets/file-icons-EFUGSSwf.js +1 -0
- package/dist/assets/flow9-Dqiw45WV.js +1 -0
- package/dist/assets/flowDiagram-23GEKE2U-DAiS5Y7G.js +1 -0
- package/dist/assets/freemarker2-QBsTERH-.js +3 -0
- package/dist/assets/fsharp-E8E2L9jU.js +1 -0
- package/dist/assets/ganttDiagram-NO4QXBWP-Bl8P1yf_.js +292 -0
- package/dist/assets/gitGraph-TEB2WS4Q-CzTBjEvV.js +1 -0
- package/dist/assets/gitGraphDiagram-IHSO6WYX-DoHa5ysz.js +106 -0
- package/dist/assets/go-CouVSN4D.js +1 -0
- package/dist/assets/graphlib-CbSvZcZU.js +1 -0
- package/dist/assets/graphql-a6h6h5-t.js +1 -0
- package/dist/assets/handlebars-CuoxPo5A.js +1 -0
- package/dist/assets/hcl-vso3e6N-.js +1 -0
- package/dist/assets/html-gX5PEu0Q.js +1 -0
- package/dist/assets/html.worker-IWNXhnIC.js +502 -0
- package/dist/assets/htmlMode-DIWUbUxd.js +1 -0
- package/dist/assets/index-BpHPeJf0.js +10 -0
- package/dist/assets/info-DKCQHKI2-DznP7j3s.js +1 -0
- package/dist/assets/infoDiagram-FWYZ7A6U-DSFcSuUs.js +2 -0
- package/dist/assets/ini-SwZZkotR.js +1 -0
- package/dist/assets/init-BPLPMQ3Y.js +1 -0
- package/dist/assets/ishikawaDiagram-FXEZZL3T-DdkqullI.js +70 -0
- package/dist/assets/java-CtRLC4_3.js +1 -0
- package/dist/assets/javascript-BYKGIUGs.js +1 -0
- package/dist/assets/journeyDiagram-5HDEW3XC-B4hRnQJr.js +139 -0
- package/dist/assets/json.worker-c4h5s80L.js +58 -0
- package/dist/assets/jsonMode-AFmQQP6u.js +7 -0
- package/dist/assets/jsx-runtime-BthL93pI.js +1 -0
- package/dist/assets/julia-CuJWFKQH.js +1 -0
- package/dist/assets/kanban-definition-HUTT4EX6-tm2FZB2E.js +89 -0
- package/dist/assets/katex-C8DPyI6s.js +257 -0
- package/dist/assets/kotlin-B_kBhsre.js +1 -0
- package/dist/assets/less-CtrHIfz3.js +2 -0
- package/dist/assets/lexon-yVt1pJLu.js +1 -0
- package/dist/assets/line-CmsjK4kn.js +1 -0
- package/dist/assets/linear-Dld3_ERu.js +1 -0
- package/dist/assets/liquid-DBIl-f0z.js +1 -0
- package/dist/assets/lspLanguageFeatures-DK6tqicV.js +4 -0
- package/dist/assets/lua-prOwgJ4U.js +1 -0
- package/dist/assets/m3-DhrdTQ84.js +1 -0
- package/dist/assets/main-DTJwH51M.css +1 -0
- package/dist/assets/map-LZWWoeWa.js +1 -0
- package/dist/assets/markdown-DoI5HwSM.js +1 -0
- package/dist/assets/mdx-DS-bVtZN.js +1 -0
- package/dist/assets/mermaid-parser.core-BQtepoLd.js +4 -0
- package/dist/assets/mermaid.core-C7UT_EEL.js +11 -0
- package/dist/assets/mindmap-definition-LN4V7U3C-DplfjGms.js +96 -0
- package/dist/assets/mips-Dye5jsBU.js +1 -0
- package/dist/assets/monaco.contribution-CyLosfZI.js +2 -0
- package/dist/assets/msdax-TkNOyIL8.js +1 -0
- package/dist/assets/mysql-CEc-RKZF.js +1 -0
- package/dist/assets/objective-c-CqqCsQz0.js +1 -0
- package/dist/assets/ordinal-BLrOss5K.js +1 -0
- package/dist/assets/packet-7NZHBO7P-BDEPOPha.js +1 -0
- package/dist/assets/pascal-DO_pj8yg.js +1 -0
- package/dist/assets/pascaligo-1cbdZdF3.js +1 -0
- package/dist/assets/path-YdFzr2W6.js +1 -0
- package/dist/assets/pegDiagram-2B236MQR-lu3SdkQs.js +1 -0
- package/dist/assets/perl-B_N3PYfC.js +1 -0
- package/dist/assets/pgsql-9iYk1FQ7.js +1 -0
- package/dist/assets/php-rO2sgoUM.js +1 -0
- package/dist/assets/pie-RZYD4A2V-DWIrwPJQ.js +1 -0
- package/dist/assets/pieDiagram-ENE6RG2P-3fHbmDf9.js +39 -0
- package/dist/assets/pla-Cbgv60kq.js +1 -0
- package/dist/assets/postiats-y6xrhy_M.js +1 -0
- package/dist/assets/powerquery-BaD8gWNE.js +1 -0
- package/dist/assets/powershell-BMhG4JVe.js +1 -0
- package/dist/assets/preload-helper-mJowh_hw.js +1 -0
- package/dist/assets/protobuf-CdOP5kN3.js +2 -0
- package/dist/assets/pug-Ck60hNF9.js +1 -0
- package/dist/assets/python-C93q3xXz.js +1 -0
- package/dist/assets/qoder-C9LmmOSf.svg +1 -0
- package/dist/assets/qoder-Cf9gl0Y5.svg +1 -0
- package/dist/assets/qoder-gHCinseV.svg +1 -0
- package/dist/assets/qrcode-DV-_rjU8.js +3 -0
- package/dist/assets/qsharp-BcaKFfP-.js +1 -0
- package/dist/assets/quadrantDiagram-ABIIQ3AL-a5qoWz-X.js +7 -0
- package/dist/assets/r-rFNes0iK.js +1 -0
- package/dist/assets/radar-I7S5WNFK-B7OaD8vp.js +1 -0
- package/dist/assets/railroad-3IZDKUUU-BXW2nuCA.js +1 -0
- package/dist/assets/railroad-abnf-AHOZXSZD-Buw9QG2r.js +1 -0
- package/dist/assets/railroad-ebnf-EBAXGLYW-BjSi4sWJ.js +1 -0
- package/dist/assets/railroad-peg-LSFZ7HO6-DN1wIVhS.js +1 -0
- package/dist/assets/railroadDiagram-RFXS5EU6-D2TOuXW9.js +1 -0
- package/dist/assets/razor-CBifNGXO.js +1 -0
- package/dist/assets/react-dom-gtU6X-Hj.js +1 -0
- package/dist/assets/redis-DkpQ3K6G.js +1 -0
- package/dist/assets/redshift-Di9N5TI3.js +1 -0
- package/dist/assets/requirementDiagram-TGXJPOKE-LQBWpUvd.js +84 -0
- package/dist/assets/restructuredtext-By5ZzLt6.js +1 -0
- package/dist/assets/review-BcnwQtJv.css +1 -0
- package/dist/assets/rough.esm-c4PR5shF.js +1 -0
- package/dist/assets/ruby-fF5zGiLp.js +1 -0
- package/dist/assets/rust-C5b3AYY6.js +1 -0
- package/dist/assets/sankeyDiagram-HTMAVEWB-B1ohYoyK.js +40 -0
- package/dist/assets/sb-CD07UNRs.js +1 -0
- package/dist/assets/scala-jtn1ip9G.js +1 -0
- package/dist/assets/scheme-C4vqMkn_.js +1 -0
- package/dist/assets/scss-I4Glxjbz.js +3 -0
- package/dist/assets/sequenceDiagram-DBY2YBRQ-C3vM-hMq.js +162 -0
- package/dist/assets/shell-DubUcuns.js +1 -0
- package/dist/assets/sizeCapture-X5ZJPWSS-daTB6OcF.js +1 -0
- package/dist/assets/solidity-CNy2KSl2.js +1 -0
- package/dist/assets/sophia-D9_URt84.js +1 -0
- package/dist/assets/sparql-DviXpm4C.js +1 -0
- package/dist/assets/sql-vDRbAZgK.js +1 -0
- package/dist/assets/src-WBW1QxJt.js +1 -0
- package/dist/assets/st-CnpnRqA7.js +1 -0
- package/dist/assets/stateDiagram-2N3HPSRC-BvFhOryI.js +1 -0
- package/dist/assets/stateDiagram-v2-6OUMAXLB-WMrz4PNo.js +1 -0
- package/dist/assets/swift-D_g8Ganz.js +1 -0
- package/dist/assets/swimlanes-5IMT3BWC-DKF_b-2s.js +2 -0
- package/dist/assets/swimlanesDiagram-G3AALYLV-BGswC9oC.js +8 -0
- package/dist/assets/systemverilog-OuZa5h1M.js +1 -0
- package/dist/assets/tcl-DBm9ucsV.js +1 -0
- package/dist/assets/timeline-definition-FHXFAJF6-vAs11ux_.js +120 -0
- package/dist/assets/tokens-BwenNn5Q.css +1 -0
- package/dist/assets/treeView-QDETBFTQ-BVfICaZQ.js +1 -0
- package/dist/assets/treemap-6X3UGDF4-oWHPqo17.js +1 -0
- package/dist/assets/ts.worker-BwM5Ha3L.js +67719 -0
- package/dist/assets/tsMode-DGZTlTj8.js +11 -0
- package/dist/assets/twig-BRzEqX5Y.js +1 -0
- package/dist/assets/typescript-KJKfYO7K.js +1 -0
- package/dist/assets/typespec-D4ZgGeX8.js +1 -0
- package/dist/assets/useWorkspaceMenuKeyboard-CneKAZUJ.js +1 -0
- package/dist/assets/vb-DcP4s6WS.js +1 -0
- package/dist/assets/vennDiagram-L72KCM5P-BybTX_9B.js +34 -0
- package/dist/assets/wardley-OPB4EBWU-Dg8t5y3s.js +1 -0
- package/dist/assets/wardleyDiagram-EHGQE667-CicUmMBR.js +78 -0
- package/dist/assets/wgsl-CnRJ_QUf.js +298 -0
- package/dist/assets/workers-BSQRIkqa.js +1 -0
- package/dist/assets/workspace-view-state-CTyDzk2D.js +1 -0
- package/dist/assets/xml-C8FAcN6j.js +1 -0
- package/dist/assets/xychartDiagram-FW5EYKEG-BhWDyCX-.js +7 -0
- package/dist/assets/yaml-BQ4NrRhG.js +1 -0
- package/dist/assets/zsh-CLpveKlF.svg +1 -0
- package/dist/assets/zsh-FxSpMPbz.svg +1 -0
- package/dist/farming-2/app-icon-v2-180.png +0 -0
- package/dist/farming-2/app-icon-v2-192.png +0 -0
- package/dist/farming-2/app-icon-v2-512.png +0 -0
- package/dist/farming-2/app-icon-v2-maskable-512.png +0 -0
- package/dist/farming-2/app-icon-v2-master.png +0 -0
- package/dist/farming-2/favicon-v2-16.png +0 -0
- package/dist/farming-2/favicon-v2-32.png +0 -0
- package/dist/farming-2/favicon-v2-48.png +0 -0
- package/dist/farming-2/favicon-v2-64.png +0 -0
- package/dist/farming-2/favicon-v2.ico +0 -0
- package/dist/farming-2/favicon.ico +0 -0
- package/dist/farming-2/github-social-preview.png +0 -0
- package/dist/farming-2/images/avatar-watercolor-v1-bee-garden.png +0 -0
- package/dist/farming-2/images/avatar-watercolor-v2.png +0 -0
- package/dist/farming-2/images/avatar-watercolor-v3.png +0 -0
- package/dist/farming-2/legacy-icons-v1/favicon.ico +1 -0
- package/dist/farming-2/legacy-icons-v1/logo-16.png +0 -0
- package/dist/farming-2/legacy-icons-v1/logo-180.png +0 -0
- package/dist/farming-2/legacy-icons-v1/logo-192.png +0 -0
- package/dist/farming-2/legacy-icons-v1/logo-32.png +0 -0
- package/dist/farming-2/legacy-icons-v1/logo-48.png +0 -0
- package/dist/farming-2/legacy-icons-v1/logo-512.png +0 -0
- package/dist/farming-2/legacy-icons-v1/logo-64.png +0 -0
- package/dist/farming-2/logo-16.png +0 -0
- package/dist/farming-2/logo-180.png +0 -0
- package/dist/farming-2/logo-192.png +0 -0
- package/dist/farming-2/logo-32.png +0 -0
- package/dist/farming-2/logo-48.png +0 -0
- package/dist/farming-2/logo-512.png +0 -0
- package/dist/farming-2/logo-64.png +0 -0
- package/dist/farming-2/site.webmanifest +27 -0
- package/dist/farming-2/style_capsules/watercolor-pastoral.json +94 -0
- package/dist/index.html +27 -0
- package/frontend/ghostty-loader.js +24 -0
- package/frontend/runtime-paths.js +28 -0
- package/frontend/session-bridge.js +82 -0
- package/frontend/session-modal-bridge.js +331 -0
- package/frontend/skin-bridge.js +25 -0
- package/frontend/skins/crt/app.js +6940 -0
- package/frontend/skins/crt/assets/branding/farming-crt-icon.svg +11 -0
- package/frontend/skins/crt/assets/branding/farming-crt-logo-v1.png +0 -0
- package/frontend/skins/crt/assets/effects/phosphor-noise.svg +11 -0
- package/frontend/skins/crt/assets/fonts/departure-mono/DepartureMonoNerdFontMono-Regular.otf +0 -0
- package/frontend/skins/crt/assets/fonts/departure-mono/LICENSE +93 -0
- package/frontend/skins/crt/effects.js +8 -0
- package/frontend/skins/crt/index.html +1712 -0
- package/frontend/skins/crt/styles/billing.css +1003 -0
- package/frontend/skins/crt/styles/effects.css +171 -0
- package/frontend/skins/crt/styles/history.css +215 -0
- package/frontend/skins/crt/styles/monochrome-green.css +509 -0
- package/frontend/skins/crt/styles/search.css +271 -0
- package/frontend/terminal-bridge.js +192 -0
- package/frontend/theme-loader.js +84 -0
- package/frontend/themes/terminal/theme.json +24 -0
- package/frontend/vendor/ghostty-web/LICENSE +21 -0
- package/frontend/vendor/ghostty-web/__vite-browser-external-2447137e.js +4 -0
- package/frontend/vendor/ghostty-web/ghostty-vt.wasm +0 -0
- package/frontend/vendor/ghostty-web/ghostty-web.js +2963 -0
- package/frontend/vendor/ghostty-web/ghostty-web.umd.cjs +13 -0
- package/frontend/vendor/ghostty-web/index.d.ts +1842 -0
- package/index.html +23 -0
- package/package.json +144 -0
- package/scripts/sync-ghostty-vendor.js +66 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Farming Code contributors
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,287 @@
|
|
|
1
|
+
# Farming
|
|
2
|
+
|
|
3
|
+
> Chinese version: [README.zh_cn.md](./README.zh_cn.md)
|
|
4
|
+
|
|
5
|
+
[](https://github.com/zhuwenzhuang/farming/actions/workflows/ci.yml)
|
|
6
|
+
[](https://github.com/zhuwenzhuang/farming/releases)
|
|
7
|
+
[](https://www.npmjs.com/package/farming-code)
|
|
8
|
+
[](./LICENSE)
|
|
9
|
+

|
|
10
|
+

|
|
11
|
+
|
|
12
|
+
Farming is a remote browser workspace for AI coding agents. The current public product line is **Farming 2**.
|
|
13
|
+
|
|
14
|
+
It brings remote terminal sessions, Codex / Claude Code, project-scoped agents, open editors, file search, lightweight editing, git review tools, usage signals, and machine status into one browser page. The goal is to reduce the context switching that usually happens between SSH, an IDE, browser tabs, monitoring pages, and separate agent panels.
|
|
15
|
+
|
|
16
|
+
Farming is designed around remote hosting. Agents, shells, project files, and git state keep running on the remote machine. A desktop browser is good for editing, reviewing, searching, and long follow-up sessions; a mobile browser is good for checking progress, switching sessions, and sending a short intervention while away from the desk.
|
|
17
|
+
|
|
18
|
+
The browser exposes two live interfaces over the same backend: Farming Code at `/farming/code/` and the original CRT interface at `/farming/crt/`. `/farming/` continues to open Farming Code. If Code cannot start or render, the failure view keeps the live CRT interface visible behind the bounded error details, without restarting running agents.
|
|
19
|
+
|
|
20
|
+
For a product-oriented introduction, screenshots, and the architecture diagram, see the [Farming 2 Wiki](https://github.com/zhuwenzhuang/farming/wiki/English).
|
|
21
|
+
|
|
22
|
+

|
|
23
|
+
|
|
24
|
+
> If you are an AI agent contributing to this repository, read [AGENTS.md](./AGENTS.md) first.
|
|
25
|
+
|
|
26
|
+
## Why Farming Exists
|
|
27
|
+
|
|
28
|
+
Current AI-agent interfaces are often chat-session lists. They are not great at showing which long-running task matters now, which agent is waiting, which one is stale, and where a human should intervene.
|
|
29
|
+
|
|
30
|
+
Farming first solves the practical workbench problem: put the tools needed to supervise coding agents into one remote UI. Longer term, it explores attention management through a Main Agent that can observe, coordinate, and summarize multiple child agents.
|
|
31
|
+
|
|
32
|
+
## Farming 2
|
|
33
|
+
|
|
34
|
+
Farming 2 turns the project into a remote coding workbench:
|
|
35
|
+
|
|
36
|
+
- start and manage Codex, Claude, OpenCode, Qoder, bash, and zsh sessions in the browser;
|
|
37
|
+
- discover and resume local Codex, Claude, OpenCode, and Qoder session history, then reconnect it to live Farming terminals;
|
|
38
|
+
- group agents by project;
|
|
39
|
+
- open Project Files with Open Editors, file tree, search, Monaco editing, Markdown/image preview, git changes, diff, and blame;
|
|
40
|
+
- click terminal `path:line` references and HTTP URLs;
|
|
41
|
+
- set Codex / Claude launch profiles for permissions, model, and speed where the underlying runtime supports them; App Server Codex updates permissions on its current thread, while terminal-owned sessions restart and resume when they already have a provider session id, or start fresh when no resumable id exists yet;
|
|
42
|
+
- attach text and images to composer messages;
|
|
43
|
+
- view lightweight usage, context, token-rate, quota, and CPU/MEM signals where available;
|
|
44
|
+
- access the same remote service from desktop and mobile browsers.
|
|
45
|
+
|
|
46
|
+
Screenshots, install details, and product notes are in [Farming 2 product guide](./docs/products/code/README.md).
|
|
47
|
+
|
|
48
|
+
## Quick Start
|
|
49
|
+
|
|
50
|
+
The easiest path is the npm package. Run Farming on the same development machine where `codex` or `claude` already works in a normal shell.
|
|
51
|
+
|
|
52
|
+
```bash
|
|
53
|
+
npm install --global farming-code
|
|
54
|
+
farming daemon
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
Farming defaults to port `6694`, base path `/farming`, config directory `~/.farming`, and token auth. The first authenticated start generates a random readable token and stores it in `~/.farming/.session-token`; later restarts and upgrades reuse that token unless `FARMING_TOKEN` is explicitly set. In Chinese time zones this is a Chinese haiku-style passphrase by default; Japanese time zones use Japanese haiku-style passphrases, and other time zones use English passphrases. The startup log prints a URL like:
|
|
58
|
+
|
|
59
|
+
```text
|
|
60
|
+
http://linux-host:6694/farming?token=<startup-token>
|
|
61
|
+
```
|
|
62
|
+
|
|
63
|
+
Open that URL in a desktop or mobile browser, click `New Agent`, choose `Codex`, `Claude Code`, `bash`, or `zsh`, select a workspace, and start working.
|
|
64
|
+
|
|
65
|
+
## Downloads
|
|
66
|
+
|
|
67
|
+
The npm package is the default distribution. GitHub release artifacts remain available for manual installation.
|
|
68
|
+
|
|
69
|
+
Farming uses these practical deployment shapes:
|
|
70
|
+
|
|
71
|
+
| Environment | Artifact | When to use it |
|
|
72
|
+
| --- | --- | --- |
|
|
73
|
+
| macOS and Linux | `npm install --global farming-code` | Default path. Requires Node.js 22 or newer and a system runtime that can load `node-pty`. |
|
|
74
|
+
| Standalone use | platform CLI from GitHub Releases | Manual installation for environments that do not want npm; upgrades remain manual. |
|
|
75
|
+
| Directory deployment | `farming-<version>-<platform>-<arch>.tar.gz` | App bundle with production dependencies and launcher scripts; it uses the target system runtime. |
|
|
76
|
+
| Legacy Linux x64 (glibc < 2.28) | `farming-<version>-linux-x64-legacy-glibc228.tar.gz` | First-install bootstrap with a pinned glibc 2.28 runtime. It installs Farming under `~/.farming/npm`; later one-click updates use npm like the default installation. A Node.js 22 executable and npm are still required. |
|
|
77
|
+
| Custom older Linux build | `farming-<version>-linux-x64-glibc217.tar.gz` | Separately built bundle that rebuilds `node-pty` against a glibc 2.17 baseline; it still needs a usable target Node.js runtime. |
|
|
78
|
+
|
|
79
|
+
If you want Farming to launch Codex or Claude Code, install and log in to those CLIs on the same machine first. Farming hosts their CLI sessions; it does not replace their installation or account setup.
|
|
80
|
+
|
|
81
|
+
## Architecture
|
|
82
|
+
|
|
83
|
+
```text
|
|
84
|
+
Browser skins
|
|
85
|
+
React + Vite + Monaco + terminal renderer
|
|
86
|
+
|
|
|
87
|
+
| HTTP / WebSocket
|
|
88
|
+
v
|
|
89
|
+
Farming core
|
|
90
|
+
Express server + token auth + agent manager + session providers
|
|
91
|
+
|
|
|
92
|
+
| native pty host + session engine
|
|
93
|
+
v
|
|
94
|
+
Execution environment
|
|
95
|
+
bash / zsh / Codex / Claude Code
|
|
96
|
+
```
|
|
97
|
+
|
|
98
|
+
The backend owns agent lifecycle, WebSocket state sync, session engines, workspace file APIs, session providers, model/profile discovery, usage collection, and configuration. Frontend skins organize those capabilities into different experiences. New interactive sessions use the native pty host by default, keeping node-pty agent processes outside the Farming server process so the server and browser can reconnect to live terminals. The native pty host persists across Farming server restarts unless `FARMING_NATIVE_PTY_HOST_PERSIST=0` is set, then exits after an idle grace period once no live sessions or clients remain. Set `FARMING_SESSION_ENGINE=local` only when debugging the in-process node-pty engine.
|
|
99
|
+
|
|
100
|
+
The browser terminal renderer defaults to xterm.js. The older Ghostty web renderer is still kept as an explicit debug path through `localStorage.farmingTerminalEngine = 'ghostty'`.
|
|
101
|
+
|
|
102
|
+
## Install And Run
|
|
103
|
+
|
|
104
|
+
### Install From npm
|
|
105
|
+
|
|
106
|
+
```bash
|
|
107
|
+
npm install --global farming-code
|
|
108
|
+
farming daemon
|
|
109
|
+
```
|
|
110
|
+
|
|
111
|
+
Open **Settings → Updates** to check and install a newer npm version in one click. Farming installs the new package while the current server is still running, restarts only after installation succeeds, and attempts to restore the previous version if the new server cannot start. The equivalent manual command is `npm install --global farming-code@latest`.
|
|
112
|
+
|
|
113
|
+
### Build From Source
|
|
114
|
+
|
|
115
|
+
```bash
|
|
116
|
+
npm install
|
|
117
|
+
npm run release:cli
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
To build an app bundle:
|
|
121
|
+
|
|
122
|
+
```bash
|
|
123
|
+
npm install
|
|
124
|
+
npm run release:app
|
|
125
|
+
```
|
|
126
|
+
|
|
127
|
+
The standard app bundle includes production dependencies and launcher scripts, and uses the target system runtime as installed.
|
|
128
|
+
|
|
129
|
+
For Linux x64 systems whose glibc is older than 2.28, build the release asset that carries the pinned legacy runtime:
|
|
130
|
+
|
|
131
|
+
```bash
|
|
132
|
+
npm run release:app:legacy-linux
|
|
133
|
+
```
|
|
134
|
+
|
|
135
|
+
The resulting `farming-<version>-linux-x64-legacy-glibc228.tar.gz` is a bootstrap package. It extracts the runtime to `~/.farming/glibc228`, installs the bundled Farming release into the private prefix `~/.farming/npm`, and writes a stable compatibility launcher at `~/.farming/bin/farming`. Later updates install `farming-code` into that same prefix through npm, then restart with the compatibility launcher; the tarball is not downloaded again for ordinary application updates.
|
|
136
|
+
|
|
137
|
+
For a separately built `node-pty` ABI baseline, run the following command inside a clean Linux x64 builder that has glibc 2.17, Node.js 22+, GCC/G++, Make, and Python 3:
|
|
138
|
+
|
|
139
|
+
```bash
|
|
140
|
+
npm run release:app:linux-compat
|
|
141
|
+
```
|
|
142
|
+
|
|
143
|
+
The command forces `node-pty` to build from source and rejects the archive unless its native module requires no newer than glibc 2.17. Install it remotely with `FARMING_REMOTE=user@host FARMING_RELEASE_TARBALL=<archive> npm run release:remote:linux-compat`. This ABI-focused bundle still uses the target machine's Node.js and libc.
|
|
144
|
+
|
|
145
|
+
When a clean source checkout is already present on a provisioned Linux x64 builder host, `scripts/build-linux-compat-release-on-builder.sh` automates the remaining container build, ABI verification, packaged bash-agent smoke, and artifact output. Set `FARMING_COMPAT_IMAGE` to an image that already exists on that host. The script uses `--pull=never` and disables container networking by default so release builds reuse existing images and caches instead of downloading infrastructure implicitly; set `FARMING_COMPAT_ALLOW_NETWORK=1` only when an intentional cache refresh is required.
|
|
146
|
+
|
|
147
|
+
### Run A Single-File CLI
|
|
148
|
+
|
|
149
|
+
```bash
|
|
150
|
+
chmod +x farming
|
|
151
|
+
./farming daemon
|
|
152
|
+
```
|
|
153
|
+
|
|
154
|
+
By default it listens on port `6694`, serves under `/farming`, creates `~/.farming`, enables token auth, and prints a browser URL containing the startup token.
|
|
155
|
+
|
|
156
|
+
Useful commands:
|
|
157
|
+
|
|
158
|
+
```bash
|
|
159
|
+
./farming status
|
|
160
|
+
./farming logs
|
|
161
|
+
./farming url
|
|
162
|
+
./farming stop
|
|
163
|
+
```
|
|
164
|
+
|
|
165
|
+
### Run An App Bundle
|
|
166
|
+
|
|
167
|
+
```bash
|
|
168
|
+
tar -xzf farming-<version>-linux-x64.tar.gz
|
|
169
|
+
cd farming-<version>-linux-x64
|
|
170
|
+
./farming
|
|
171
|
+
```
|
|
172
|
+
|
|
173
|
+
The standard bundle uses the target machine's ordinary Node.js and native runtime. On a legacy Linux x64 host, download the `-legacy-glibc228.tar.gz` bundle instead and run `./farming` once. After bootstrap, use `~/.farming/bin/farming`; that stable launcher keeps npm updates, server restarts, and PTY child processes on the bundled compatibility runtime.
|
|
174
|
+
|
|
175
|
+
## Development
|
|
176
|
+
|
|
177
|
+
```bash
|
|
178
|
+
npm install
|
|
179
|
+
npm start
|
|
180
|
+
```
|
|
181
|
+
|
|
182
|
+
For trusted local development only, token auth can be disabled:
|
|
183
|
+
|
|
184
|
+
```bash
|
|
185
|
+
npm run start:no-auth
|
|
186
|
+
```
|
|
187
|
+
|
|
188
|
+
## Configuration
|
|
189
|
+
|
|
190
|
+
Runtime settings are stored in `~/.farming/settings.json`.
|
|
191
|
+
Agent session metadata is stored separately in `~/.farming/sessions/`. Farming
|
|
192
|
+
uses stable `fsess_*` files for its own Agent records; live `agent-...` ids and
|
|
193
|
+
Codex / Claude provider session ids are stored as metadata on those records.
|
|
194
|
+
The main Projects page membership lives in `sessions/index.json` and is exposed
|
|
195
|
+
as `mainPageSessionKeys` only for API compatibility.
|
|
196
|
+
Archived run history is stored in `~/.farming/history/runs.json`, not in
|
|
197
|
+
`settings.json`.
|
|
198
|
+
Theme overrides, the startup token, server pid/state/log files, and native pty
|
|
199
|
+
host logs live under the same config directory.
|
|
200
|
+
|
|
201
|
+
Common settings:
|
|
202
|
+
|
|
203
|
+
- `defaultLaunchAgent`
|
|
204
|
+
- `agentLaunchProfiles.codex`
|
|
205
|
+
- `agentLaunchProfiles.claude`
|
|
206
|
+
- `agentHomes` (home metadata for Codex, Claude, OpenCode, and Qoder; each provider keeps a non-removable `default` home)
|
|
207
|
+
- `workspaceHistory`
|
|
208
|
+
- `dangerouslySkipAgentPermissionsByDefault` (launch supported coding agents such as Codex, Claude, OpenCode, Qoder, Qwen, Aider, GitHub Copilot CLI, and Amazon Q with their provider-specific dangerous permission-skip flags by default)
|
|
209
|
+
|
|
210
|
+
Native terminal sessions are owned by a Farming pty host reached through a local socket derived from `configDir`. By default the host is preserved during server shutdown so a restarted Farming server can recover live terminals; after the last live session and client disappear, the host shuts itself down after a short idle grace period. Set `FARMING_NATIVE_PTY_HOST_PERSIST=0` to tie the host lifetime to the server process. Terminal work should target the native pty host and xterm.js path.
|
|
211
|
+
|
|
212
|
+
Update behavior follows the installation method. npm installations and legacy Linux installations bootstrapped from `-legacy-glibc228.tar.gz` read versions from the npm registry and provide one-click upgrades in **Settings → Updates**. They install into their existing npm prefix while the old service remains alive, then restart and roll back on startup failure. Source checkouts update through Git, and standalone CLI artifacts are replaced manually. Standard app-bundle installations remain a directory-deployment path and may use a trusted HTTP(S) package directory or manifest URL stored as `settings.updateUrl`.
|
|
213
|
+
|
|
214
|
+
The simplest source is an HTTP(S) directory URL ending in `/` that lists platform-tagged `farming-<version>-<platform>-<arch>.tar.gz` app bundles and an adjacent `<bundle>.sha256` file for every bundle. Farming verifies the selected bundle's SHA-256 and archive layout before extraction, then runs its installer.
|
|
215
|
+
|
|
216
|
+
Example deployment templates:
|
|
217
|
+
|
|
218
|
+
- `config/farming.deploy.env.example`
|
|
219
|
+
- `config/farming.install.env.example`
|
|
220
|
+
|
|
221
|
+
Real `.env` files are ignored by git.
|
|
222
|
+
|
|
223
|
+
## Security
|
|
224
|
+
|
|
225
|
+
Farming controls real terminals and agent processes on the target machine. Run it on trusted development hosts and trusted networks. Do not expose it directly to the public internet without an additional layer such as VPN, SSH tunnel, HTTPS reverse proxy, or network ACLs.
|
|
226
|
+
|
|
227
|
+
The startup token protects both HTTP and WebSocket traffic. It is generated on first authenticated startup, persisted in `~/.farming/.session-token`, and reused across restarts and upgrades. The generated token is designed to be easier to copy than a long hexadecimal secret: Chinese time zones get a Chinese haiku-style passphrase by default, Japanese time zones get a Japanese haiku-style passphrase, and other time zones get an English passphrase. `FARMING_TOKEN_LOCALE=zh|ja|en|auto` can override generation behavior for a new token.
|
|
228
|
+
|
|
229
|
+
`FARMING_DISABLE_AUTH=1` is only for trusted local development. Terminal-owned Codex / Claude sessions apply a permission change by restarting with the selected CLI flags, resuming when a provider session id is available and starting fresh otherwise. App Server Codex applies the new approval and sandbox policy to its existing thread without a CLI restart.
|
|
230
|
+
|
|
231
|
+
See [SECURITY.md](./SECURITY.md) for the reporting policy and deployment notes.
|
|
232
|
+
|
|
233
|
+
## Troubleshooting
|
|
234
|
+
|
|
235
|
+
- **No `codex` or `claude` option works**: verify the CLI is installed, logged in, and runnable from a normal shell on the same host.
|
|
236
|
+
- **Native PTY cannot start**: verify the target system's Node.js and packaged `node-pty` runtime are compatible. On Linux x64 with glibc older than 2.28, use the `-legacy-glibc228` app bundle.
|
|
237
|
+
- **Port already in use**: pass `--port <port>` or let the default daemon mode choose the next available port when no explicit port is provided.
|
|
238
|
+
- **Phone cannot connect**: use the network URL printed by the server and make sure the phone can reach the target machine.
|
|
239
|
+
- **Lost the token URL**: run `./farming url`, or check `./farming logs`.
|
|
240
|
+
|
|
241
|
+
## Repository Layout
|
|
242
|
+
|
|
243
|
+
```text
|
|
244
|
+
farming/
|
|
245
|
+
├── .gitattributes # Source archive export rules
|
|
246
|
+
├── backend/ # Node.js server, session engines, and backend APIs
|
|
247
|
+
├── src/ # React + Vite frontend; Farming Code helpers live under src/components/code/
|
|
248
|
+
├── frontend/skins/crt/ # Independent live CRT entry, app, and visual effects
|
|
249
|
+
├── frontend/*.js # Shared terminal/session browser bridges
|
|
250
|
+
├── docs/products/code/ # Farming Code product docs and screenshots
|
|
251
|
+
├── docs/products/crt/ # CRT skin layout docs
|
|
252
|
+
├── config/ # deployment / install templates
|
|
253
|
+
├── scripts/ # release, deployment, screenshots, tests
|
|
254
|
+
├── tests/e2e/ # Playwright browser flows
|
|
255
|
+
├── pkg.config.cjs
|
|
256
|
+
└── bin/farming
|
|
257
|
+
```
|
|
258
|
+
|
|
259
|
+
`releases/` is a local packaging output directory and is not committed.
|
|
260
|
+
|
|
261
|
+
## Tests
|
|
262
|
+
|
|
263
|
+
```bash
|
|
264
|
+
npm run check
|
|
265
|
+
```
|
|
266
|
+
|
|
267
|
+
Common individual checks:
|
|
268
|
+
|
|
269
|
+
```bash
|
|
270
|
+
npm test
|
|
271
|
+
npm run typecheck
|
|
272
|
+
npm run lint
|
|
273
|
+
npm run test:e2e:playwright
|
|
274
|
+
```
|
|
275
|
+
|
|
276
|
+
## Authors
|
|
277
|
+
|
|
278
|
+
- [zhuwenzhuang](https://github.com/zhuwenzhuang)
|
|
279
|
+
- [l4wei](https://github.com/l4wei)
|
|
280
|
+
|
|
281
|
+
## Contributing
|
|
282
|
+
|
|
283
|
+
Issues and pull requests are welcome. Start with [CONTRIBUTING.md](./CONTRIBUTING.md), and keep user-facing docs updated when behavior or packaging changes.
|
|
284
|
+
|
|
285
|
+
## License
|
|
286
|
+
|
|
287
|
+
Farming is released under the MIT License. See [LICENSE](./LICENSE).
|
package/README.zh_cn.md
ADDED
|
@@ -0,0 +1,329 @@
|
|
|
1
|
+
# Farming
|
|
2
|
+
|
|
3
|
+
> English version: [README.md](./README.md)
|
|
4
|
+
|
|
5
|
+
[](https://github.com/zhuwenzhuang/farming/actions/workflows/ci.yml)
|
|
6
|
+
[](https://github.com/zhuwenzhuang/farming/releases)
|
|
7
|
+
[](https://www.npmjs.com/package/farming-code)
|
|
8
|
+
[](./LICENSE)
|
|
9
|
+

|
|
10
|
+

|
|
11
|
+
|
|
12
|
+
Farming 是一个面向 AI coding agent 的远程浏览器工作台。当前公开版本是 **Farming 2**。
|
|
13
|
+
|
|
14
|
+
它当前已经把远程 terminal、Codex / Claude Code、历史 session、项目级 agent、打开的编辑器、项目文件、搜索、轻量编辑、git review、usage 和机器状态收进同一个页面,减少人在 SSH、IDE、浏览器、监控页面和 agent 面板之间反复切换。
|
|
15
|
+
|
|
16
|
+
远程托管和多端浏览器接入是 Farming 的内核能力:agent、shell、项目文件和 git 状态都留在远程机器上持续运行;用户可以从电脑端浏览器做长时间操作,也可以从手机浏览器随时回到现场,看进度、切 session,或者做一次轻量介入。Farming 2 把这套能力组织成一个面向 Codex / Claude Code 的浏览器工作台,当前默认 UI 皮肤叫 Farming Code。
|
|
17
|
+
|
|
18
|
+
浏览器现在通过同一个后端提供两套实时 UI:`/farming/code/` 是 Farming Code,`/farming/crt/` 是原始 CRT 界面;`/farming/` 仍默认打开 Farming Code。当 Code 无法启动或渲染时,故障页面会在错误详情浮层后显示仍连接当前 Agent 的 CRT 界面,不会重启正在运行的 Agent。
|
|
19
|
+
|
|
20
|
+
产品介绍、截图和架构图见 [Farming 2 Wiki](https://github.com/zhuwenzhuang/farming/wiki)。
|
|
21
|
+
|
|
22
|
+

|
|
23
|
+
|
|
24
|
+
> 如果你是参与本仓库开发的 AI Agent,请先阅读 [`AGENTS.md`](./AGENTS.md),中文版本见 [`AGENTS.zh_cn.md`](./AGENTS.zh_cn.md)。
|
|
25
|
+
|
|
26
|
+
## 当前价值与长期目标
|
|
27
|
+
|
|
28
|
+
当前阶段,Farming 做的是一件很实在的事:把指挥 AI coding agent 时最常打开的工具能力放到一起。用户可以在同一个远程工作台里看 live terminal、恢复 Codex / Claude session、检查文件、搜索代码、做小修改、看 blame、看 usage 和 CPU/MEM 状态。它不是完整 IDE,也不是新的 agent 模型;它先把“观察现场”和“轻量介入”这两个高频动作变短。
|
|
29
|
+
|
|
30
|
+
远程托管是这里的关键价值。长任务可以继续跑在 Linux 开发机上,浏览器只是进入现场的入口;电脑端适合编辑、搜索、审查和长时间跟进,手机端适合离开电脑后查看状态、确认输出、发一句输入或启动一个简单 agent。这样用户不用把本地机器、远程 shell、agent session 和项目文件拆成几套上下文来回维护。
|
|
31
|
+
|
|
32
|
+
更长期的目标仍然是人的注意力管理。人类注意力有限,也没有真正的多线程处理能力;当多个 agent 同时工作时,真正消耗人的不是某一个终端,而是在不同页面、不同任务状态和不同上下文之间反复切换。
|
|
33
|
+
|
|
34
|
+
Farming 未来希望探索的是:让系统逐步判断哪些 agent 值得关注,哪些任务只是后台推进,哪些变化需要汇报,哪些地方需要人介入。Main Agent 是这个方向上的长期机制:它最终应该结合 Codex、Claude Code、shell agent 和更多工具型 agent,观察任务状态、组织子 agent、汇总进展,并减少人的上下文切换。
|
|
35
|
+
|
|
36
|
+
这部分仍在探索中,是 Farming 的终极目标;Farming 2 先把工具整合和远程工作台体验做好,作为后续 Main Agent 和多 agent 注意力管理能力的基础。
|
|
37
|
+
|
|
38
|
+
## Farming 2 带来的变化
|
|
39
|
+
|
|
40
|
+
Farming 2 是本仓库最近最大的一次产品变化。它把 Farming 从一个较轻的复古 agent monitor,推进成了更实用的远程 coding workbench,也为长期的 Main Agent 注意力管理目标补齐底座:
|
|
41
|
+
|
|
42
|
+
- 在浏览器里启动和管理 Codex、Claude、OpenCode、Qoder、bash 和 zsh session;
|
|
43
|
+
- 发现并恢复 Codex、Claude、OpenCode 和 Qoder 的本地历史 session,再重新接入 Farming 托管的实时 terminal;
|
|
44
|
+
- Codex / Claude 启动选项按 provider 收敛,不展示当前 agent 无法表达的控件;
|
|
45
|
+
- 在一个工作区里组织 project-scoped agents、pinned/unread sessions、Search、History 和 active terminals;
|
|
46
|
+
- 提供 Project Files:Open Editors、文件树、文件搜索、Monaco 编辑、Markdown/图片预览、git changes、git diff、行级 git blame;
|
|
47
|
+
- terminal 输出里的 `path:line` 可直接打开文件,`http(s)` URL 可直接在新标签页打开;
|
|
48
|
+
- Codex / Claude Composer 暴露底层运行时能表达的启动权限、模型和速度 profile;App Server Codex 会直接更新当前 thread 的权限,terminal-owned session 切换权限时才重启 CLI:已有 provider Session ID 时 resume,还没有可 resume 的 ID 时启动新会话;
|
|
49
|
+
- Composer 支持文本附件;粘贴或选择图片时会保存到 Farming 服务侧 `~/.farming/attachments`,并把图片路径插入消息,便于远端 Codex / Claude 读取;Farming 自动生成的图片附件默认保留 7 天后清理;
|
|
50
|
+
- 显示轻量 usage、context、token rate、quota 与机器状态,例如 CPU、MEM;
|
|
51
|
+
- 复用 Farming 的远程托管和多端浏览器接入能力,让桌面和手机访问同一套远程 Linux 服务。
|
|
52
|
+
|
|
53
|
+
具体截图、安装方式和产品说明见 [Farming 2 产品介绍](./docs/products/code/README.zh_cn.md)。
|
|
54
|
+
|
|
55
|
+
## 快速开始
|
|
56
|
+
|
|
57
|
+
默认推荐通过 npm 安装,把 Farming 运行在已经能正常执行 `codex` 或 `claude` 的开发机上。
|
|
58
|
+
|
|
59
|
+
```bash
|
|
60
|
+
npm install --global farming-code
|
|
61
|
+
farming daemon
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
默认端口是 `6694`,浏览器路径是 `/farming`,配置目录是 `~/.farming`,并默认启用 token auth。首次鉴权启动会生成一个随机但可读的口令,并保存到 `~/.farming/.session-token`;之后重启和升级都会复用这个 token,除非显式设置 `FARMING_TOKEN`。在中文时区默认是中文俳句式口令,日本时区默认是日文俳句式口令,其它时区默认是英文短语。启动日志会打印类似下面的 URL:
|
|
65
|
+
|
|
66
|
+
```text
|
|
67
|
+
http://linux-host:6694/farming?token=<startup-token>
|
|
68
|
+
```
|
|
69
|
+
|
|
70
|
+
把完整 URL 复制到桌面或手机浏览器中打开,点击 `New Agent`,选择 `Codex`、`Claude Code`、`bash` 或 `zsh`,填入 workspace,就可以进入远程工作台。
|
|
71
|
+
|
|
72
|
+
## 下载与部署形态
|
|
73
|
+
|
|
74
|
+
npm 包是默认发布形态;也可以从 [GitHub Releases](https://github.com/zhuwenzhuang/farming/releases) 下载手动安装产物。
|
|
75
|
+
|
|
76
|
+
Farming 2 当前有三种实际部署形态:
|
|
77
|
+
|
|
78
|
+
| 环境 | 产物 | 适用场景 |
|
|
79
|
+
| --- | --- | --- |
|
|
80
|
+
| macOS 与 Linux | `npm install --global farming-code` | 默认路径,需要 Node.js 22+,并且系统 runtime 能加载 `node-pty`。 |
|
|
81
|
+
| 不使用 npm 的环境 | GitHub Releases 平台 CLI | 手动安装,升级也需要手动替换。 |
|
|
82
|
+
| 目录部署 | `farming-<version>-<platform>-<arch>.tar.gz` | 包含 production dependencies 和 launcher 脚本的 App Bundle,直接使用目标系统 runtime。 |
|
|
83
|
+
| 老 Linux x64(glibc < 2.28) | `farming-<version>-linux-x64-legacy-glibc228.tar.gz` | 带固定 glibc 2.28 runtime 的首次安装引导包。它把 Farming 安装到 `~/.farming/npm`;后续与普通 npm 安装一样一键更新。目标机仍需 Node.js 22 和 npm。 |
|
|
84
|
+
| 自建老 Linux 包 | `farming-<version>-linux-x64-glibc217.tar.gz` | 独立构建的兼容包;基于 glibc 2.17 重新编译 `node-pty`,但仍要求目标机有可用的 Node.js runtime。 |
|
|
85
|
+
|
|
86
|
+
如果要通过 Farming 启动 Codex 或 Claude Code,同一台机器上仍然需要提前安装并登录对应 CLI。Farming 托管的是这些 CLI session,不替代它们自己的安装和账号流程。
|
|
87
|
+
|
|
88
|
+
## 架构
|
|
89
|
+
|
|
90
|
+
```text
|
|
91
|
+
浏览器皮肤
|
|
92
|
+
React + Vite + Monaco + terminal renderer
|
|
93
|
+
|
|
|
94
|
+
| HTTP / WebSocket
|
|
95
|
+
v
|
|
96
|
+
Farming 内核
|
|
97
|
+
Express server + token auth + agent manager + session providers
|
|
98
|
+
|
|
|
99
|
+
| native pty host + session engine
|
|
100
|
+
v
|
|
101
|
+
执行环境
|
|
102
|
+
bash / zsh / Codex / Claude Code
|
|
103
|
+
```
|
|
104
|
+
|
|
105
|
+
内核负责 agent 生命周期、WebSocket 状态同步、session engine、workspace 文件 API、历史 session provider、模型/profile 发现、usage 采集和配置管理。产品皮肤负责把这些能力组织成不同体验。新的交互 session 默认使用 native pty host:node-pty agent 进程放在独立 host 进程里,Farming server 和浏览器可以重新连回仍存活的 terminal。native pty host 默认会跨 Farming server 重启保留;当没有 live session 和 client 后会在空闲宽限期后退出。只有希望 host 跟随 server 一起退出时才设置 `FARMING_NATIVE_PTY_HOST_PERSIST=0`。只有调试进程内 node-pty engine 时才设置 `FARMING_SESSION_ENGINE=local`。
|
|
106
|
+
|
|
107
|
+
浏览器 terminal renderer 默认使用 xterm.js。旧的 Ghostty web renderer 仍保留为显式调试路径,可通过 `localStorage.farmingTerminalEngine = 'ghostty'` 切换。
|
|
108
|
+
|
|
109
|
+
## 安装与发布
|
|
110
|
+
|
|
111
|
+
Farming 2 最适合运行在一台 Linux 开发机上;这台机器里应当已经能在普通 SSH shell 中正常运行 Codex 或 Claude Code。
|
|
112
|
+
|
|
113
|
+
默认安装方式:
|
|
114
|
+
|
|
115
|
+
```bash
|
|
116
|
+
npm install --global farming-code
|
|
117
|
+
farming daemon
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
npm 安装后可在 **设置 → 更新** 一键升级。Farming 会先在旧服务仍运行时完成 npm 安装,安装成功后才重启;如果新服务无法启动,会尝试恢复旧版本。等价的手动命令是 `npm install --global farming-code@latest`。
|
|
121
|
+
|
|
122
|
+
兼容发布形态主要有两种:
|
|
123
|
+
|
|
124
|
+
- 单文件 CLI:适合现代 Linux 和 macOS,拿到一个 `farming` 可执行文件后直接运行。
|
|
125
|
+
- App bundle:适合目录式部署;包是一个 tarball,解压后通过根目录 `./farming` 脚本启动,脚本负责 Node heap 和运行环境。
|
|
126
|
+
|
|
127
|
+
源码远程部署脚本是开发团队把当前 checkout 部署到固定 Linux 机器的便捷路径。
|
|
128
|
+
|
|
129
|
+
如果要启动 Codex 或 Claude Code,目标机器上还需要提前安装并登录对应 CLI,确保在普通 SSH shell 中直接运行 `codex` 或 `claude` 能进入交互。
|
|
130
|
+
|
|
131
|
+
### 从源码打包
|
|
132
|
+
|
|
133
|
+
构建单文件 CLI:
|
|
134
|
+
|
|
135
|
+
```bash
|
|
136
|
+
npm install
|
|
137
|
+
npm run release:cli
|
|
138
|
+
```
|
|
139
|
+
|
|
140
|
+
构建可解压运行的 app bundle:
|
|
141
|
+
|
|
142
|
+
```bash
|
|
143
|
+
npm install
|
|
144
|
+
npm run release:app
|
|
145
|
+
```
|
|
146
|
+
|
|
147
|
+
`release:app` 会生成 `releases/<version>/farming-<version>-<platform>-<arch>.tar.gz`,包内包含已经构建好的前端、production dependencies 和根目录启动脚本,使用目标系统 runtime。
|
|
148
|
+
|
|
149
|
+
如果目标是 glibc 低于 2.28 的 Linux x64,构建带固定 glibc 2.28 runtime 的发布资产:
|
|
150
|
+
|
|
151
|
+
```bash
|
|
152
|
+
npm run release:app:legacy-linux
|
|
153
|
+
```
|
|
154
|
+
|
|
155
|
+
它会生成 `farming-<version>-linux-x64-legacy-glibc228.tar.gz`。这是首次安装引导包:安装器把 runtime 解压到 `~/.farming/glibc228`,把包内 Farming 版本放入私有 prefix `~/.farming/npm`,并生成稳定入口 `~/.farming/bin/farming`。后续普通版本更新直接通过 npm 安装到同一 prefix,再用兼容 launcher 重启;不需要反复下载兼容 tar。
|
|
156
|
+
|
|
157
|
+
如果只需要将 `node-pty` 编译到更低 ABI,仍可在干净的 Linux x64 构建环境中准备 glibc 2.17、Node.js 22+、GCC/G++、Make 和 Python 3,然后运行:
|
|
158
|
+
|
|
159
|
+
```bash
|
|
160
|
+
npm run release:app:linux-compat
|
|
161
|
+
```
|
|
162
|
+
|
|
163
|
+
该命令会强制从源码编译 `node-pty`,并在其 native module 依赖高于 glibc 2.17 时拒绝产物。远程安装使用 `FARMING_REMOTE=user@host FARMING_RELEASE_TARBALL=<archive> npm run release:remote:linux-compat`。这个 ABI 包仍使用目标机器自己的 Node.js 和 libc。
|
|
164
|
+
|
|
165
|
+
如果已经在配置好的 Linux x64 构建机上准备了干净源码,`scripts/build-linux-compat-release-on-builder.sh` 可以继续自动完成容器构建、ABI 校验、打包后 bash Agent 冒烟和产物输出。通过 `FARMING_COMPAT_IMAGE` 指定构建机上已经存在的镜像。脚本使用 `--pull=never`,并默认关闭容器网络,以复用已有镜像和缓存,避免发布时隐式下载构建环境;只有确实需要主动刷新缓存时才设置 `FARMING_COMPAT_ALLOW_NETWORK=1`。
|
|
166
|
+
|
|
167
|
+
### 启动单文件 CLI
|
|
168
|
+
|
|
169
|
+
拿到对应平台的单文件 `farming` 后:
|
|
170
|
+
|
|
171
|
+
```bash
|
|
172
|
+
chmod +x farming
|
|
173
|
+
./farming daemon
|
|
174
|
+
```
|
|
175
|
+
|
|
176
|
+
它会优先监听 `6694`、挂载到 `/farming`,并自动创建 `~/.farming/settings.json`、token 文件和必要运行目录;如果未显式指定端口且 `6694` 已占用,会自动上探选择可用端口。启动后终端会打印带 token 的浏览器 URL。前台运行可直接执行 `./farming` 或 `./farming start`;常用管理命令是 `./farming status`、`./farming logs`、`./farming stop`。
|
|
177
|
+
|
|
178
|
+
### 启动 app bundle
|
|
179
|
+
|
|
180
|
+
普通 Linux 上:
|
|
181
|
+
|
|
182
|
+
```bash
|
|
183
|
+
tar -xzf farming-<version>-linux-x64.tar.gz
|
|
184
|
+
cd farming-<version>-linux-x64
|
|
185
|
+
./farming
|
|
186
|
+
```
|
|
187
|
+
|
|
188
|
+
标准包的启动脚本直接使用目标机器的普通 Node.js 和 native runtime。glibc 低于 2.28 的 Linux x64 请改用 `-legacy-glibc228` 包并执行一次 `./farming` 完成引导;之后使用 `~/.farming/bin/farming`。这个稳定入口保证 npm 更新、server 重启和 PTY 子进程都继续经过兼容 runtime。
|
|
189
|
+
|
|
190
|
+
App bundle 常用命令:
|
|
191
|
+
|
|
192
|
+
```bash
|
|
193
|
+
./farming status
|
|
194
|
+
./farming logs
|
|
195
|
+
./farming stop
|
|
196
|
+
./farming start
|
|
197
|
+
./farming url
|
|
198
|
+
```
|
|
199
|
+
|
|
200
|
+
### 源码远程部署
|
|
201
|
+
|
|
202
|
+
如果本机可以 SSH 到目标 Linux,且已经配置 `config/farming.deploy.env`:
|
|
203
|
+
|
|
204
|
+
```bash
|
|
205
|
+
npm run release:remote
|
|
206
|
+
```
|
|
207
|
+
|
|
208
|
+
这条路径会从当前源码 checkout 构建 app bundle、上传到远端、安装并启动服务,适合团队开发和 dogfood。
|
|
209
|
+
|
|
210
|
+
### 开发调试
|
|
211
|
+
|
|
212
|
+
只在本地开发 Farming 本身时,才需要直接启动源码服务:
|
|
213
|
+
|
|
214
|
+
```bash
|
|
215
|
+
npm install
|
|
216
|
+
npm start
|
|
217
|
+
```
|
|
218
|
+
|
|
219
|
+
服务启动后会打印一个 token URL。仅在可信本地开发环境中,可以关闭 token 校验:
|
|
220
|
+
|
|
221
|
+
```bash
|
|
222
|
+
npm run start:no-auth
|
|
223
|
+
```
|
|
224
|
+
|
|
225
|
+
远程安装和 release 细节见 [`docs/products/code/README.zh_cn.md`](./docs/products/code/README.zh_cn.md)。
|
|
226
|
+
|
|
227
|
+
## 配置
|
|
228
|
+
|
|
229
|
+
运行时配置存储在 `~/.farming/settings.json`。
|
|
230
|
+
Agent session 元数据单独存储在 `~/.farming/sessions/`。Farming 使用稳定的
|
|
231
|
+
`fsess_*` 文件作为自己的 Agent 记录;live `agent-...` id 以及 Codex / Claude
|
|
232
|
+
provider session id 都作为这些记录上的元数据保存。主页面 Projects membership
|
|
233
|
+
存放在 `sessions/index.json`,`mainPageSessionKeys` 只是为兼容 API 暴露出来的投影。
|
|
234
|
+
归档 run/history 存储在 `~/.farming/history/runs.json`,不属于 `settings.json`。
|
|
235
|
+
主题覆盖配置、启动 token、server pid/state/log 文件和 native pty host 日志也都在同一个 config 目录下。
|
|
236
|
+
|
|
237
|
+
主要用户配置项:
|
|
238
|
+
|
|
239
|
+
- `defaultLaunchAgent`:New Agent 默认 provider,目前是 `codex` 或 `claude`;
|
|
240
|
+
- `agentLaunchProfiles.codex`:Codex 的启动权限、模型、reasoning、service tier profile;
|
|
241
|
+
- `agentLaunchProfiles.claude`:Claude 的启动 permission、model、effort profile;
|
|
242
|
+
- `agentHomes`:管理 Codex、Claude、OpenCode、Qoder 的 agent home 元数据,每项只包含 `id` 和 `path`;每个 provider 都保留不可删除的 `default` home;
|
|
243
|
+
- `workspaceHistory`:New Agent 启动时使用的最近 workspace;
|
|
244
|
+
- `dangerouslySkipAgentPermissionsByDefault`:是否默认让支持的 coding agent(如 Codex、Claude、OpenCode、Qoder、Qwen、Aider、GitHub Copilot CLI、Amazon Q)使用各自最激进的权限绕过启动 flag。
|
|
245
|
+
|
|
246
|
+
Native terminal session 由 Farming pty host 托管,通过从 `configDir` 派生的本地 socket 连接。默认保留 host 以支持 server 重启恢复;最后一个 live session 和 client 都消失后,host 会在短暂空闲宽限期后自退出。后续 terminal runtime 工作应面向 native pty host 和 xterm.js 链路。
|
|
247
|
+
|
|
248
|
+
更新行为跟随安装方式:普通 npm 安装和通过 `-legacy-glibc228.tar.gz` 引导的老 Linux 安装都读取 npm registry,并在 **设置 → 更新** 提供一键升级。更新先安装到原有 npm prefix,旧服务在安装期间继续运行;随后重启,新服务启动失败时回退。源码 checkout 通过 Git 更新,单文件 CLI 手动替换。标准 App bundle 仍作为目录部署路径,可使用保存在 `settings.updateUrl` 中的可信 HTTP(S) 包目录或 manifest URL。
|
|
249
|
+
|
|
250
|
+
最简单的更新源是一个以 `/` 结尾的 HTTP(S) 目录 URL,目录里列出带平台标记的 `farming-<version>-<platform>-<arch>.tar.gz` app bundle,并为每个 bundle 提供相邻的 `<bundle>.sha256` 文件。Farming 会在解压前校验所选 bundle 的 SHA-256 与归档路径,再运行 installer。
|
|
251
|
+
|
|
252
|
+
部署配置模板位于 `config/`:
|
|
253
|
+
|
|
254
|
+
- `config/farming.deploy.env.example`
|
|
255
|
+
- `config/farming.install.env.example`
|
|
256
|
+
|
|
257
|
+
真实 `.env` 配置文件会被 git 忽略。
|
|
258
|
+
|
|
259
|
+
## 安全
|
|
260
|
+
|
|
261
|
+
Farming 可以控制目标机器上的真实 terminal 和 agent 进程,适合运行在可信开发机和可信网络中。不要在没有 VPN、SSH tunnel、HTTPS 反向代理或网络 ACL 等额外安全层的情况下直接暴露到公网。
|
|
262
|
+
|
|
263
|
+
启动 token 会同时保护 HTTP 页面和 WebSocket 连接。它在首次鉴权启动时随机生成,持久保存到 `~/.farming/.session-token`,并在后续重启和升级中复用。生成的新 token 刻意做成比长十六进制串更容易复制的可读口令:中文时区默认生成中文俳句式口令,日本时区默认生成日文俳句式口令,其它时区默认生成英文短语;也可以用 `FARMING_TOKEN_LOCALE=zh|ja|en|auto` 显式指定新 token 的生成语言。
|
|
264
|
+
|
|
265
|
+
`FARMING_DISABLE_AUTH=1` 只应该用于可信本地开发环境。terminal-owned 的 Codex / Claude session 切换权限时会用所选 flag 重启 CLI:已有 provider Session ID 时会 resume,还没有可 resume 的 ID 时启动新会话。App Server Codex 则直接在当前 thread 上更新审批和 sandbox 策略,不启动 CLI。
|
|
266
|
+
|
|
267
|
+
安全上报和部署注意事项见 [SECURITY.md](./SECURITY.md)。
|
|
268
|
+
|
|
269
|
+
## 排错
|
|
270
|
+
|
|
271
|
+
- **Codex 或 Claude Code 无法启动**:先确认同一台机器上对应 CLI 已安装、已登录,并能在普通 shell 中直接运行。
|
|
272
|
+
- **Native PTY 无法启动**:检查目标系统的 Node.js 与打包的 `node-pty` runtime 是否兼容;glibc 低于 2.28 的 Linux x64 请使用 `-legacy-glibc228` 包。
|
|
273
|
+
- **端口占用**:可以传 `--port <port>`;如果没有显式指定端口,默认 daemon 启动会自动上探选择可用端口。
|
|
274
|
+
- **手机访问不了**:使用启动日志里打印的 Network URL,并确认手机能访问目标开发机。
|
|
275
|
+
- **找不到 token URL**:运行 `./farming url`,或查看 `./farming logs`。
|
|
276
|
+
|
|
277
|
+
## 目录结构
|
|
278
|
+
|
|
279
|
+
```text
|
|
280
|
+
farming/
|
|
281
|
+
├── .gitattributes # 源码归档 export-ignore 规则
|
|
282
|
+
├── backend/ # Node.js server、session engine、agent manager、session/history/usage/file/slash-command APIs
|
|
283
|
+
├── src/ # React + Vite 前端;Farming Code 皮肤与交互 helper 位于 src/components/code/
|
|
284
|
+
├── frontend/skins/crt/ # 独立的实时 CRT 入口、应用逻辑与视觉效果
|
|
285
|
+
├── frontend/*.js # 多皮肤共享的 terminal/session 浏览器 bridge
|
|
286
|
+
├── docs/
|
|
287
|
+
│ ├── products/code/ # Farming 2 产品介绍、Farming Code 皮肤截图、安装说明和验收 dogfood 方案
|
|
288
|
+
│ └── products/crt/ # CRT 皮肤 README 和布局说明
|
|
289
|
+
├── config/ # 部署 / 安装配置模板
|
|
290
|
+
├── scripts/ # 部署、release、测试、产品截图和辅助脚本
|
|
291
|
+
├── tests/e2e/ # Playwright 展示与浏览器流程测试
|
|
292
|
+
├── reference/ # 外部项目源码、工具链和调研 walkthrough;不作为 Farming 运行时依赖
|
|
293
|
+
├── pkg.config.cjs # 平台 CLI 应用打包配置(@yao-pkg/pkg + legacy pkg)
|
|
294
|
+
└── bin/farming # 开发态产品 CLI;发布后二进制也叫 farming
|
|
295
|
+
```
|
|
296
|
+
|
|
297
|
+
公开产品文档现在从根 README 和 `docs/products/` 下的皮肤 README 进入。`releases/` 是本地打包输出目录,不提交到源码仓库。
|
|
298
|
+
|
|
299
|
+
## 测试
|
|
300
|
+
|
|
301
|
+
运行主检查:
|
|
302
|
+
|
|
303
|
+
```bash
|
|
304
|
+
npm run check
|
|
305
|
+
```
|
|
306
|
+
|
|
307
|
+
常用单项命令:
|
|
308
|
+
|
|
309
|
+
```bash
|
|
310
|
+
npm test
|
|
311
|
+
npm run typecheck
|
|
312
|
+
npm run lint
|
|
313
|
+
npm run test:e2e:playwright
|
|
314
|
+
```
|
|
315
|
+
|
|
316
|
+
Playwright 测试会在合适位置使用 fake coding-agent executable,常规 UI 回归不会消耗真实 Codex / Claude 额度。
|
|
317
|
+
|
|
318
|
+
## 作者
|
|
319
|
+
|
|
320
|
+
- [zhuwenzhuang](https://github.com/zhuwenzhuang)
|
|
321
|
+
- [l4wei](https://github.com/l4wei)
|
|
322
|
+
|
|
323
|
+
## 贡献
|
|
324
|
+
|
|
325
|
+
欢迎提交 issue 和 pull request。开始前请阅读 [CONTRIBUTING.md](./CONTRIBUTING.md);如果改动影响用户可见行为、打包方式或部署方式,请同步更新 README、产品文档和相关验收说明。
|
|
326
|
+
|
|
327
|
+
## License
|
|
328
|
+
|
|
329
|
+
MIT
|