From 142218cddf944a3420ae1e87bd74912dbeeeb113 Mon Sep 17 00:00:00 2001 From: Ethan Graf Date: Sun, 24 May 2026 00:26:42 -0400 Subject: [PATCH] Integrate subtext --- package-lock.json | 447 +- package.json | 5 +- src/App.tsx | 31 +- src/components/AppSidebar.tsx | 62 +- src/components/SettingsModal.tsx | 60 +- .../providers/subtextDocumentsProvider.ts | 178 + .../providers/subtextFilesystemProvider.ts | 59 + src/habitat/docSession.ts | 7 +- src/icons/index.tsx | 69 + src/index.css | 6 + src/main.ts | 31 + src/preload.ts | 14 + src/subtext/cache.ts | 93 + src/subtext/index.ts | 127 + src/subtext/proto.d.ts | 2004 +++++++ src/subtext/proto.js | 4783 +++++++++++++++++ src/subtext/tcpClient.ts | 296 + src/subtext/testClient.ts | 56 + src/vite-env.d.ts | 9 + 19 files changed, 8273 insertions(+), 64 deletions(-) create mode 100644 src/documents/providers/subtextDocumentsProvider.ts create mode 100644 src/filesystem/providers/subtextFilesystemProvider.ts create mode 100644 src/icons/index.tsx create mode 100644 src/subtext/cache.ts create mode 100644 src/subtext/index.ts create mode 100644 src/subtext/proto.d.ts create mode 100644 src/subtext/proto.js create mode 100644 src/subtext/tcpClient.ts create mode 100644 src/subtext/testClient.ts diff --git a/package-lock.json b/package-lock.json index e95b494..be66114 100644 --- a/package-lock.json +++ b/package-lock.json @@ -34,6 +34,7 @@ "lib0": "^0.2.117", "libp2p": "^2.8.0", "openid-client": "^6.8.4", + "protobufjs": "^8.4.1", "react": "^19.2.5", "react-dom": "^19.2.5", "react-router-dom": "^7.15.0", @@ -64,6 +65,7 @@ "eslint-plugin-import": "^2.32.0", "prettier": "^3.8.3", "prettier-plugin-tailwindcss": "^0.8.0", + "protobufjs-cli": "^2.4.1", "tailwindcss": "^4.2.4", "typescript": "~6.0.3", "vite": "^8.0.10", @@ -257,7 +259,6 @@ "resolved": "https://registry.npmjs.org/@babel/helper-string-parser/-/helper-string-parser-7.27.1.tgz", "integrity": "sha512-qMlSxKbpRlAridDExk92nSobyDdpPijUq2DW6oDnUqd0iOGxmQjyqhMIihI9+zv4LPyZdRje2cavWPbCbWm3eA==", "license": "MIT", - "peer": true, "engines": { "node": ">=6.9.0" } @@ -267,7 +268,6 @@ "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.28.5.tgz", "integrity": "sha512-qSs4ifwzKJSV39ucNjsvc6WVHs6b7S03sOh2OcHF9UHfVPqWWALUsNUVzhSBiItjRZoLHx7nIarVjqKVusUZ1Q==", "license": "MIT", - "peer": true, "engines": { "node": ">=6.9.0" } @@ -301,7 +301,6 @@ "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.29.3.tgz", "integrity": "sha512-b3ctpQwp+PROvU/cttc4OYl4MzfJUWy6FZg+PMXfzmt/+39iHVF0sDfqay8TQM3JA2EUOyKcFZt75jWriQijsA==", "license": "MIT", - "peer": true, "dependencies": { "@babel/types": "^7.29.0" }, @@ -361,7 +360,6 @@ "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.29.0.tgz", "integrity": "sha512-LwdZHpScM4Qz8Xw2iKSzS+cfglZzJGvofQICy7W7v4caru4EaAmyUuO6BGrbyQ2mYV11W0U8j5mBhd14dd3B0A==", "license": "MIT", - "peer": true, "dependencies": { "@babel/helper-string-parser": "^7.27.1", "@babel/helper-validator-identifier": "^7.28.5" @@ -2008,6 +2006,19 @@ "@jridgewell/sourcemap-codec": "^1.4.14" } }, + "node_modules/@jsdoc/salty": { + "version": "0.2.12", + "resolved": "https://registry.npmjs.org/@jsdoc/salty/-/salty-0.2.12.tgz", + "integrity": "sha512-TuB0x50EoAvEX/UEWITd8Mkn3WhiTjSvbTMCLj0BhsQEl5iUzjXdA0bETEVpTk+5TGTLR6QktI9H4hLviVeaAQ==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "lodash": "^4.18.1" + }, + "engines": { + "node": ">=v12.0.0" + } + }, "node_modules/@leichtgewicht/ip-codec": { "version": "2.0.5", "resolved": "https://registry.npmjs.org/@leichtgewicht/ip-codec/-/ip-codec-2.0.5.tgz", @@ -4563,6 +4574,31 @@ "@types/node": "*" } }, + "node_modules/@types/linkify-it": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/@types/linkify-it/-/linkify-it-5.0.0.tgz", + "integrity": "sha512-sVDA58zAw4eWAffKOaQH5/5j3XeayukzDk+ewSsnv3p4yJEZHCCzMDiZM8e0OUrRvmpGZ85jf4yDHkHsgBNr9Q==", + "dev": true, + "license": "MIT" + }, + "node_modules/@types/markdown-it": { + "version": "14.1.2", + "resolved": "https://registry.npmjs.org/@types/markdown-it/-/markdown-it-14.1.2.tgz", + "integrity": "sha512-promo4eFwuiW+TfGxhi+0x3czqTYJkG8qB17ZUJiVF10Xm7NLVRSLUsfRTU/6h1e24VvRnXCx+hG7li58lkzog==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/linkify-it": "^5", + "@types/mdurl": "^2" + } + }, + "node_modules/@types/mdurl": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@types/mdurl/-/mdurl-2.0.0.tgz", + "integrity": "sha512-RGdgjQUZba5p6QEFAVx2OGb8rQDL/cPRG7GiedRzMcJ1tYnUANBncjbSB1NRGwbvjcPeikRABz2nshyPk1bhWg==", + "dev": true, + "license": "MIT" + }, "node_modules/@types/mute-stream": { "version": "0.0.4", "resolved": "https://registry.npmjs.org/@types/mute-stream/-/mute-stream-0.0.4.tgz", @@ -6423,6 +6459,19 @@ ], "license": "CC-BY-4.0" }, + "node_modules/catharsis": { + "version": "0.9.0", + "resolved": "https://registry.npmjs.org/catharsis/-/catharsis-0.9.0.tgz", + "integrity": "sha512-prMTQVpcns/tzFgFVkVp6ak6RykZyWb3gu8ckUpd6YkTlacOd3DXGJjIpD4Q6zJirizvaiAjSSHlOsA+6sNh2A==", + "dev": true, + "license": "MIT", + "dependencies": { + "lodash": "^4.17.15" + }, + "engines": { + "node": ">= 10" + } + }, "node_modules/chai": { "version": "6.2.2", "resolved": "https://registry.npmjs.org/chai/-/chai-6.2.2.tgz", @@ -7775,6 +7824,19 @@ "node": ">=10.13.0" } }, + "node_modules/entities": { + "version": "4.5.0", + "resolved": "https://registry.npmjs.org/entities/-/entities-4.5.0.tgz", + "integrity": "sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==", + "dev": true, + "license": "BSD-2-Clause", + "engines": { + "node": ">=0.12" + }, + "funding": { + "url": "https://github.com/fb55/entities?sponsor=1" + } + }, "node_modules/env-paths": { "version": "2.2.1", "resolved": "https://registry.npmjs.org/env-paths/-/env-paths-2.2.1.tgz", @@ -8004,6 +8066,83 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/escodegen": { + "version": "1.14.3", + "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-1.14.3.tgz", + "integrity": "sha512-qFcX0XJkdg+PB3xjZZG/wKSuT1PnQWx57+TVSjIMmILd2yC/6ByYElPwJnslDsuWuSAp4AwJGumarAAmJch5Kw==", + "dev": true, + "license": "BSD-2-Clause", + "dependencies": { + "esprima": "^4.0.1", + "estraverse": "^4.2.0", + "esutils": "^2.0.2", + "optionator": "^0.8.1" + }, + "bin": { + "escodegen": "bin/escodegen.js", + "esgenerate": "bin/esgenerate.js" + }, + "engines": { + "node": ">=4.0" + }, + "optionalDependencies": { + "source-map": "~0.6.1" + } + }, + "node_modules/escodegen/node_modules/levn": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/levn/-/levn-0.3.0.tgz", + "integrity": "sha512-0OO4y2iOHix2W6ujICbKIaEQXvFQHue65vUG3pb5EUomzPI90z9hsA1VsO/dbIIpC53J8gxM9Q4Oho0jrCM/yA==", + "dev": true, + "license": "MIT", + "dependencies": { + "prelude-ls": "~1.1.2", + "type-check": "~0.3.2" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/escodegen/node_modules/optionator": { + "version": "0.8.3", + "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.8.3.tgz", + "integrity": "sha512-+IW9pACdk3XWmmTXG8m3upGUJst5XRGzxMRjXzAuJ1XnIFNvfhjjIuYkDvysnPQ7qzqVzLt78BCruntqRhWQbA==", + "dev": true, + "license": "MIT", + "dependencies": { + "deep-is": "~0.1.3", + "fast-levenshtein": "~2.0.6", + "levn": "~0.3.0", + "prelude-ls": "~1.1.2", + "type-check": "~0.3.2", + "word-wrap": "~1.2.3" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/escodegen/node_modules/prelude-ls": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.1.2.tgz", + "integrity": "sha512-ESF23V4SKG6lVSGZgYNpbsiaAkdab6ZgOxe52p7+Kid3W3u3bxR4Vfd/o21dmN7jSt0IwgZ4v5MUd26FEtXE9w==", + "dev": true, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/escodegen/node_modules/type-check": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.3.2.tgz", + "integrity": "sha512-ZCmOJdvOWDBYJlzAoFkC+Q0+bUyEOS1ltgp1MGU03fqHG+dbi9tBFU2Rd9QKiDZFAYrhPh2JUf7rZRIuHRKtOg==", + "dev": true, + "license": "MIT", + "dependencies": { + "prelude-ls": "~1.1.2" + }, + "engines": { + "node": ">= 0.8.0" + } + }, "node_modules/eslint": { "version": "8.57.1", "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.57.1.tgz", @@ -8350,6 +8489,20 @@ "url": "https://opencollective.com/eslint" } }, + "node_modules/esprima": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz", + "integrity": "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==", + "dev": true, + "license": "BSD-2-Clause", + "bin": { + "esparse": "bin/esparse.js", + "esvalidate": "bin/esvalidate.js" + }, + "engines": { + "node": ">=4" + } + }, "node_modules/esquery": { "version": "1.7.0", "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.7.0.tgz", @@ -10873,6 +11026,16 @@ "js-yaml": "bin/js-yaml.js" } }, + "node_modules/js2xmlparser": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/js2xmlparser/-/js2xmlparser-4.0.2.tgz", + "integrity": "sha512-6n4D8gLlLf1n5mNLQPRfViYzu9RATblzPEtm1SthMX1Pjao0r9YI9nw7ZIfRxQMERS87mcswrg+r/OYrPRX6jA==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "xmlcreate": "^2.0.4" + } + }, "node_modules/jsc-safe-url": { "version": "0.2.4", "resolved": "https://registry.npmjs.org/jsc-safe-url/-/jsc-safe-url-0.2.4.tgz", @@ -10880,6 +11043,59 @@ "license": "0BSD", "peer": true }, + "node_modules/jsdoc": { + "version": "4.0.5", + "resolved": "https://registry.npmjs.org/jsdoc/-/jsdoc-4.0.5.tgz", + "integrity": "sha512-P4C6MWP9yIlMiK8nwoZvxN84vb6MsnXcHuy7XzVOvQoCizWX5JFCBsWIIWKXBltpoRZXddUOVQmCTOZt9yDj9g==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@babel/parser": "^7.20.15", + "@jsdoc/salty": "^0.2.1", + "@types/markdown-it": "^14.1.1", + "bluebird": "^3.7.2", + "catharsis": "^0.9.0", + "escape-string-regexp": "^2.0.0", + "js2xmlparser": "^4.0.2", + "klaw": "^3.0.0", + "markdown-it": "^14.1.0", + "markdown-it-anchor": "^8.6.7", + "marked": "^4.0.10", + "mkdirp": "^1.0.4", + "requizzle": "^0.2.3", + "strip-json-comments": "^3.1.0", + "underscore": "~1.13.2" + }, + "bin": { + "jsdoc": "jsdoc.js" + }, + "engines": { + "node": ">=12.0.0" + } + }, + "node_modules/jsdoc/node_modules/escape-string-regexp": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-2.0.0.tgz", + "integrity": "sha512-UpzcLCXolUWcNu5HtVMHYdXJjArjsF9C0aNnquZYY4uW/Vu0miy5YoWvbV345HauVvcAUnpRuhMMcqTcGOY2+w==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=8" + } + }, + "node_modules/jsdoc/node_modules/marked": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/marked/-/marked-4.3.0.tgz", + "integrity": "sha512-PRsaiG84bK+AMvxziE/lCFss8juXjNaWzVbN5tXAm4XjeaS9NAHhop+PjQxz2A9h8Q4M/xGmzP8vqNwy6JeK0A==", + "dev": true, + "license": "MIT", + "bin": { + "marked": "bin/marked.js" + }, + "engines": { + "node": ">= 12" + } + }, "node_modules/jsesc": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-3.1.0.tgz", @@ -10968,6 +11184,16 @@ "json-buffer": "3.0.1" } }, + "node_modules/klaw": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/klaw/-/klaw-3.0.0.tgz", + "integrity": "sha512-0Fo5oir+O9jnXu5EefYbVK+mHMBeEVEy2cmctR1O1NECcCkPRreJKrS6Qt/j3KC2C148Dfo9i3pCmCMsdqGr0g==", + "dev": true, + "license": "MIT", + "dependencies": { + "graceful-fs": "^4.1.9" + } + }, "node_modules/leven": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/leven/-/leven-3.1.0.tgz", @@ -11382,6 +11608,16 @@ "url": "https://opencollective.com/parcel" } }, + "node_modules/linkify-it": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/linkify-it/-/linkify-it-5.0.0.tgz", + "integrity": "sha512-5aHCbzQRADcdP+ATqnDuhhJ/MRIqDkZX5pyjFHRRysS8vZ5AbqGEoFIb6pYHPZ+L/OC2Lc+xT8uHVVR5CAK/wQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "uc.micro": "^2.0.0" + } + }, "node_modules/linkifyjs": { "version": "4.3.3", "resolved": "https://registry.npmjs.org/linkifyjs/-/linkifyjs-4.3.3.tgz", @@ -11547,6 +11783,12 @@ "url": "https://github.com/chalk/strip-ansi?sponsor=1" } }, + "node_modules/long": { + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/long/-/long-5.3.2.tgz", + "integrity": "sha512-mNAgZ1GmyNhD7AuqnTG3/VQ26o760+ZYBPKjPvugO8+nLbYfX6TVpJPseBvopbdY+qpZ/lKUnmEc1LeZYS3QAA==", + "license": "Apache-2.0" + }, "node_modules/loose-envify": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz", @@ -11647,6 +11889,35 @@ "node": ">=6" } }, + "node_modules/markdown-it": { + "version": "14.1.1", + "resolved": "https://registry.npmjs.org/markdown-it/-/markdown-it-14.1.1.tgz", + "integrity": "sha512-BuU2qnTti9YKgK5N+IeMubp14ZUKUUw7yeJbkjtosvHiP0AZ5c8IAgEMk79D0eC8F23r4Ac/q8cAIFdm2FtyoA==", + "dev": true, + "license": "MIT", + "dependencies": { + "argparse": "^2.0.1", + "entities": "^4.4.0", + "linkify-it": "^5.0.0", + "mdurl": "^2.0.0", + "punycode.js": "^2.3.1", + "uc.micro": "^2.1.0" + }, + "bin": { + "markdown-it": "bin/markdown-it.mjs" + } + }, + "node_modules/markdown-it-anchor": { + "version": "8.6.7", + "resolved": "https://registry.npmjs.org/markdown-it-anchor/-/markdown-it-anchor-8.6.7.tgz", + "integrity": "sha512-FlCHFwNnutLgVTflOYHPW2pPcl2AACqVzExlkGQNsi4CJgqOHN7YTgDd4LuhgN1BFO3TS0vLAruV1Td6dwWPJA==", + "dev": true, + "license": "Unlicense", + "peerDependencies": { + "@types/markdown-it": "*", + "markdown-it": "*" + } + }, "node_modules/marked": { "version": "17.0.6", "resolved": "https://registry.npmjs.org/marked/-/marked-17.0.6.tgz", @@ -11690,6 +11961,13 @@ "node": ">= 0.4" } }, + "node_modules/mdurl": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/mdurl/-/mdurl-2.0.0.tgz", + "integrity": "sha512-Lf+9+2r+Tdp5wXDXC4PcIBjTDtq4UKjCPMQhKIuzpJNW0b96kVqSwW0bT7FhRSfmAiFYgP+SCRvdrDozfh0U5w==", + "dev": true, + "license": "MIT" + }, "node_modules/mem": { "version": "4.3.0", "resolved": "https://registry.npmjs.org/mem/-/mem-4.3.0.tgz", @@ -13808,6 +14086,113 @@ "prosemirror-transform": "^1.1.0" } }, + "node_modules/protobufjs": { + "version": "8.4.1", + "resolved": "https://registry.npmjs.org/protobufjs/-/protobufjs-8.4.1.tgz", + "integrity": "sha512-oXf2UgIty8jnwfN4yvL1x79VLhL5uiKjZJbSGXGCIUmHmItTP4eS/UIlWDCeNx3seg+ujfn9vDlPMSrsh7wO+Q==", + "hasInstallScript": true, + "license": "BSD-3-Clause", + "dependencies": { + "long": "^5.3.2" + }, + "engines": { + "node": ">=12.0.0" + } + }, + "node_modules/protobufjs-cli": { + "version": "2.4.1", + "resolved": "https://registry.npmjs.org/protobufjs-cli/-/protobufjs-cli-2.4.1.tgz", + "integrity": "sha512-qOMpejPoLUcYZkcuzCZRKPen2yiDfvHPiZqvGC4YzO2XWawOMg/HuLWk5vfhlisLTQkUXsZuPJfXnOkh0ZkAfQ==", + "dev": true, + "license": "BSD-3-Clause", + "dependencies": { + "chalk": "^4.0.0", + "escodegen": "^1.13.0", + "espree": "^9.0.0", + "estraverse": "^5.1.0", + "glob": "^8.0.0", + "jsdoc": "^4.0.0", + "minimist": "^1.2.8", + "semver": "^7.1.2", + "tmp": "^0.2.1", + "uglify-js": "^3.7.7" + }, + "bin": { + "pbjs": "bin/pbjs", + "pbts": "bin/pbts", + "protoc-gen-pbjs": "bin/protoc-gen-pbjs" + }, + "engines": { + "node": ">=12.0.0" + }, + "peerDependencies": { + "protobufjs": "^8.4.1" + } + }, + "node_modules/protobufjs-cli/node_modules/brace-expansion": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.1.0.tgz", + "integrity": "sha512-TN1kCZAgdgweJhWWpgKYrQaMNHcDULHkWwQIspdtjV4Y5aurRdZpjAqn6yX3FPqTA9ngHCc4hJxMAMgGfve85w==", + "dev": true, + "license": "MIT", + "dependencies": { + "balanced-match": "^1.0.0" + } + }, + "node_modules/protobufjs-cli/node_modules/estraverse": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", + "dev": true, + "license": "BSD-2-Clause", + "engines": { + "node": ">=4.0" + } + }, + "node_modules/protobufjs-cli/node_modules/glob": { + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/glob/-/glob-8.1.0.tgz", + "integrity": "sha512-r8hpEjiQEYlF2QU0df3dS+nxxSIreXQS1qRhMJM0Q5NDdR386C7jb7Hwwod8Fgiuex+k0GFjgft18yvxm5XoCQ==", + "deprecated": "Old versions of glob are not supported, and contain widely publicized security vulnerabilities, which have been fixed in the current version. Please update. Support for old versions may be purchased (at exorbitant rates) by contacting i@izs.me", + "dev": true, + "license": "ISC", + "dependencies": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^5.0.1", + "once": "^1.3.0" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/protobufjs-cli/node_modules/minimatch": { + "version": "5.1.9", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.9.tgz", + "integrity": "sha512-7o1wEA2RyMP7Iu7GNba9vc0RWWGACJOCZBJX2GJWip0ikV+wcOsgVuY9uE8CPiyQhkGFSlhuSkZPavN7u1c2Fw==", + "dev": true, + "license": "ISC", + "dependencies": { + "brace-expansion": "^2.0.1" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/protobufjs-cli/node_modules/tmp": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.2.5.tgz", + "integrity": "sha512-voyz6MApa1rQGUxT3E+BK7/ROe8itEx7vD8/HEvt4xwXucvQ5G5oeEiHkmHZJuBO21RpOf+YYm9MOivj709jow==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=14.14" + } + }, "node_modules/protons-runtime": { "version": "5.6.0", "resolved": "https://registry.npmjs.org/protons-runtime/-/protons-runtime-5.6.0.tgz", @@ -13839,6 +14224,16 @@ "node": ">=6" } }, + "node_modules/punycode.js": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/punycode.js/-/punycode.js-2.3.1.tgz", + "integrity": "sha512-uxFIHU0YlHYhDQtV4R9J6a52SLx28BCjT+4ieh7IGbgwVJWO+km431c4yRlREUAsAmt/uMjQUyQHNEPf0M39CA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=6" + } + }, "node_modules/pvtsutils": { "version": "1.3.6", "resolved": "https://registry.npmjs.org/pvtsutils/-/pvtsutils-1.3.6.tgz", @@ -14415,6 +14810,16 @@ "node": ">=0.10.0" } }, + "node_modules/requizzle": { + "version": "0.2.4", + "resolved": "https://registry.npmjs.org/requizzle/-/requizzle-0.2.4.tgz", + "integrity": "sha512-JRrFk1D4OQ4SqovXOgdav+K8EAhSB/LJZqCz8tbX0KObcdeM15Ss59ozWMBWmmINMagCwmqn4ZNryUGpBsl6Jw==", + "dev": true, + "license": "MIT", + "dependencies": { + "lodash": "^4.17.21" + } + }, "node_modules/resedit": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/resedit/-/resedit-2.0.3.tgz", @@ -16202,6 +16607,26 @@ "node": ">=14.17" } }, + "node_modules/uc.micro": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/uc.micro/-/uc.micro-2.1.0.tgz", + "integrity": "sha512-ARDJmphmdvUk6Glw7y9DQ2bFkKBHwQHLi2lsaH6PPmz/Ka9sFOBsBluozhDltWmnv9u/cF6Rt87znRTPV+yp/A==", + "dev": true, + "license": "MIT" + }, + "node_modules/uglify-js": { + "version": "3.19.3", + "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.19.3.tgz", + "integrity": "sha512-v3Xu+yuwBXisp6QYTcH4UbH+xYJXqnq2m/LtQVWKWzYc1iehYnLixoQDN9FH6/j9/oybfd6W9Ghwkl8+UMKTKQ==", + "dev": true, + "license": "BSD-2-Clause", + "bin": { + "uglifyjs": "bin/uglifyjs" + }, + "engines": { + "node": ">=0.8.0" + } + }, "node_modules/uint8-varint": { "version": "2.0.5", "resolved": "https://registry.npmjs.org/uint8-varint/-/uint8-varint-2.0.5.tgz", @@ -16249,6 +16674,13 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/underscore": { + "version": "1.13.8", + "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.13.8.tgz", + "integrity": "sha512-DXtD3ZtEQzc7M8m4cXotyHR+FAS18C64asBYY5vqZexfYryNNnDc02W4hKg3rdQuqOYas1jkseX0+nZXjTXnvQ==", + "dev": true, + "license": "MIT" + }, "node_modules/undici-types": { "version": "7.19.2", "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-7.19.2.tgz", @@ -17047,6 +17479,13 @@ "node": ">=8.0" } }, + "node_modules/xmlcreate": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/xmlcreate/-/xmlcreate-2.0.4.tgz", + "integrity": "sha512-nquOebG4sngPmGPICTS5EnxqhKbCmz5Ox5hsszI2T6U5qdrJizBc+0ilYSEjTSzU0yZcmvppztXe/5Al5fUwdg==", + "dev": true, + "license": "Apache-2.0" + }, "node_modules/y-protocols": { "version": "1.0.7", "resolved": "https://registry.npmjs.org/y-protocols/-/y-protocols-1.0.7.tgz", diff --git a/package.json b/package.json index 4b98491..aa13126 100644 --- a/package.json +++ b/package.json @@ -14,7 +14,8 @@ "format": "prettier --write .", "format:check": "prettier --check .", "test": "vitest run", - "test:watch": "vitest" + "test:watch": "vitest", + "proto:gen": "pbjs -t static-module -w es6 -o src/subtext/proto.js ../subtext/proto/subtext_handlers.proto && pbts -o src/subtext/proto.d.ts src/subtext/proto.js" }, "keywords": [], "author": "ethan", @@ -43,6 +44,7 @@ "eslint-plugin-import": "^2.32.0", "prettier": "^3.8.3", "prettier-plugin-tailwindcss": "^0.8.0", + "protobufjs-cli": "^2.4.1", "tailwindcss": "^4.2.4", "typescript": "~6.0.3", "vite": "^8.0.10", @@ -74,6 +76,7 @@ "lib0": "^0.2.117", "libp2p": "^2.8.0", "openid-client": "^6.8.4", + "protobufjs": "^8.4.1", "react": "^19.2.5", "react-dom": "^19.2.5", "react-router-dom": "^7.15.0", diff --git a/src/App.tsx b/src/App.tsx index f99132d..e8847fc 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -7,7 +7,10 @@ import { AppSidebar } from './components/AppSidebar'; import { AppTitleBar } from './components/AppTitleBar'; import { SettingsModal } from './components/SettingsModal'; import { HabitatDocumentsProvider } from './documents/providers/habitatDocumentsProvider'; +import { SubtextDocumentsProvider } from './documents/providers/subtextDocumentsProvider'; import { HabitatFilesystemProvider } from './filesystem/providers/habitatFilesystemProvider'; +import type { FileSystemProvider } from './filesystem/types'; +import { SubtextFilesystemProvider } from './filesystem/providers/subtextFilesystemProvider'; import { getRendererPlatform } from './lib/platform'; import { AboutPage } from './pages/AboutPage'; import { @@ -30,6 +33,16 @@ const queryClient = new QueryClient({ }); const WORKSPACE_KIND_STORAGE_KEY = 'textile.workspaceKind'; +const SUBTEXT_ENABLED_KEY = 'textile.subtext.enabled'; + +function isSubtextEnabled(): boolean { + if (typeof localStorage === 'undefined') return false; + try { + return localStorage.getItem(SUBTEXT_ENABLED_KEY) === 'true'; + } catch { + return false; + } +} function loadInitialWorkspaceKind(): WorkspaceKind { if (typeof localStorage === 'undefined') return DEFAULT_WORKSPACE_KIND; @@ -54,14 +67,24 @@ export default function App() { const [openRequest, setOpenRequest] = useState(null); const [openRequestId, setOpenRequestId] = useState(0); - const fileSystemProviders = useMemo(() => { - const habitatDocuments = new HabitatDocumentsProvider(); - return [ + const fileSystemProviders = useMemo(() => { + const providers: FileSystemProvider[] = [ new HabitatFilesystemProvider({ - documents: habitatDocuments, + documents: new HabitatDocumentsProvider(), defaultEditorKind: 'yjs', }), ]; + // TODO: When the Vault concept is introduced, each vault will choose its own + // source; this conditional registration will move to per-vault configuration. + if (isSubtextEnabled()) { + providers.push( + new SubtextFilesystemProvider({ + documents: new SubtextDocumentsProvider(), + defaultEditorKind: 'yjs', + }), + ); + } + return providers; }, []); const resolveProvider = useCallback( (providerId: string) => diff --git a/src/components/AppSidebar.tsx b/src/components/AppSidebar.tsx index 331cfb5..56f880c 100644 --- a/src/components/AppSidebar.tsx +++ b/src/components/AppSidebar.tsx @@ -1,6 +1,7 @@ import { useCallback, useEffect, useMemo, useState } from 'react'; import { useQuery, useQueryClient } from '@tanstack/react-query'; import type { FileSystemEntry, FileSystemProvider } from '../filesystem/types'; +import { DocFileIcon, SubtextIcon, NewDocumentIcon } from '../icons'; import type { OpenDocRequest } from '../workspaces/workspace'; type AppSidebarProps = { @@ -12,50 +13,6 @@ type AppSidebarProps = { type Selection = { providerId: string; entryId: string } | null; -function DocFileIcon({ className }: { className?: string }) { - return ( - - - - - ); -} - -/** File with pencil (lucide-style), for "new document". */ -function NewDocumentIcon({ className }: { className?: string }) { - return ( - - {/* Document with folded corner */} - - - {/* Pencil diagonal on the page: eraser upper-right, tip lower-left. - Axis runs from (15,12) to (9,18); perpendicular is (1,1)/√2. - Shaft half-width 1.5; tip 2.5 units before the point. */} - - {/* Ferrule line, perpendicular to axis, spanning shaft edge-to-edge */} - - - ); -} - function filesQueryKey(providerId: string) { return ['files', providerId] as const; } @@ -129,11 +86,11 @@ function ProviderSection({ 'Connect an account in Settings (⌘,) to see files here.'; return ( -
-

+
+

{provider.displayName}

-
+
{!provider.isReady() ? (

{idleCopy} @@ -151,10 +108,7 @@ function ProviderSection({ No files.

) : ( -
+
{entries.map((entry) => { const isSelected = selection?.providerId === provider.id && @@ -279,7 +233,11 @@ export function AppSidebar({ open, providers, onOpenEntry }: AppSidebarProps) { onClick={() => void handleCreate(provider)} className="text-foreground hover:bg-border/40 focus-visible:ring-accent/50 cursor-pointer rounded-md p-1.5 outline-none focus-visible:ring-2 disabled:opacity-50" > - + {provider.id === 'subtext' ? ( + + ) : ( + + )} ); })} diff --git a/src/components/SettingsModal.tsx b/src/components/SettingsModal.tsx index 8737da2..fe991c3 100644 --- a/src/components/SettingsModal.tsx +++ b/src/components/SettingsModal.tsx @@ -1,5 +1,6 @@ import { useState, type ReactNode } from 'react'; import { LOGIN_NAME, useHabitatAuth } from '../auth/habitatAuth'; +import { SubtextIcon } from '../icons'; import { WORKSPACE_DESCRIPTORS, type WorkspaceKind, @@ -16,7 +17,7 @@ type SettingsModalProps = { onWorkspaceKindChange: (kind: WorkspaceKind) => void; }; -type SettingsCategory = 'atmosphere' | 'appearance'; +type SettingsCategory = 'atmosphere' | 'appearance' | 'subtext'; function AtmosphereAccountPane() { const { authInfo, login, logout } = useHabitatAuth(); @@ -168,6 +169,56 @@ function MoonIcon() { ); } + + +function SubtextSettingsPane() { + const [enabled, setEnabled] = useState(() => { + if (typeof localStorage === 'undefined') return false; + return localStorage.getItem('textile.subtext.enabled') === 'true'; + }); + + const toggle = () => { + const next = !enabled; + setEnabled(next); + if (typeof localStorage !== 'undefined') { + localStorage.setItem('textile.subtext.enabled', String(next)); + } + }; + + return ( +
+
+

+ Experimental Feature +

+

+ Subtext is an experimental local-first cache. Files stored in Subtext + are read-only when opened with external editors. Edits made outside + Textile will not be saved. +

+
+ + + + + +

+ Subtext daemon address: 127.0.0.1:8081 +

+
+ ); +} + export function SettingsModal({ open, onClose, @@ -193,6 +244,11 @@ export function SettingsModal({ label: 'Appearance', icon: , }, + { + id: 'subtext', + label: 'Subtext', + icon: , + }, ]; return ( @@ -226,6 +282,8 @@ export function SettingsModal({ > {selectedCategory === 'atmosphere' ? ( + ) : selectedCategory === 'subtext' ? ( + ) : (
diff --git a/src/documents/providers/subtextDocumentsProvider.ts b/src/documents/providers/subtextDocumentsProvider.ts new file mode 100644 index 0000000..9083396 --- /dev/null +++ b/src/documents/providers/subtextDocumentsProvider.ts @@ -0,0 +1,178 @@ +import * as Y from 'yjs'; + +import { createYjsBinding } from '../../editors/yjs/yjsEditorBinding'; +import { getHeadingFromYdoc } from '../../habitat/habitatDoc'; +import type { DocumentHandle, DocumentProvider } from '../types'; +import { + seedYdocFromSubtext, + pushUpdateToSubtext, + createFileInSubtext, + renameFileInSubtext, + listCachedVaults, +} from '../../subtext/cache'; +import { + allocateId, + getPath, + updatePath, + emitSubtextTitle, +} from '../../subtext/index'; + +/** Sanitize a heading string for use as a filename. */ +function sanitizeFilename(name: string): string { + return name + .trim() + .replace(/[/\\?%*:|"<>]/g, '-') + .replace(/\s+/g, ' ') + .slice(0, 100); +} + +function makeVaultPath(name: string): string { + const safe = sanitizeFilename(name); + return `local/${safe}.md`; +} + +/** Find a non-conflicting vault path, appending (2), (3), etc. when needed. */ +async function findUniqueVaultPath( + desiredName: string, + excludePath?: string, +): Promise { + const basePath = makeVaultPath(desiredName); + const existing = new Set(await listCachedVaults()); + if (!existing.has(basePath) || basePath === excludePath) { + return basePath; + } + let n = 2; + while (true) { + const candidate = `local/${sanitizeFilename(desiredName)} (${n}).md`; + if (!existing.has(candidate) || candidate === excludePath) { + return candidate; + } + n += 1; + if (n > 999) break; + } + return `local/${Date.now()}.md`; +} + +/** + * Document provider for Subtext local vaults. + * + * - Files have stable opaque IDs (survive renames). + * - New files default to "Unknown" display name. + * - When a heading is added/changed, the file auto-renames on disk after a + * debounce and the sidebar title is patched live via subscribeEntryTitles. + */ +export class SubtextDocumentsProvider implements DocumentProvider { + readonly id = 'subtext'; + + async openDocument(entryId: string): Promise { + const vaultPath = getPath(entryId); + if (!vaultPath) { + throw new Error(`Unknown subtext document: ${entryId}`); + } + return this.openLocalDocument(entryId, vaultPath); + } + + private async openLocalDocument( + id: string, + vaultPath: string, + ): Promise { + const ydoc = new Y.Doc(); + + // Try to seed from an existing subtext vault; if absent we start empty. + await seedYdocFromSubtext(vaultPath, ydoc); + + let currentVaultPath = vaultPath; + let released = false; + let renameTimer: ReturnType | null = null; + + const getDisplayTitle = (): string => { + const heading = getHeadingFromYdoc(ydoc)?.trim(); + if (heading) return heading; + // Derive fallback from the filename (e.g. "Untitled" from "local/Untitled.md") + const filename = currentVaultPath.split('/').pop() ?? currentVaultPath; + return filename.replace(/\.md$/, ''); + }; + + const saveHandler = (_update: Uint8Array, _origin: unknown) => { + const update = Y.encodeStateAsUpdateV2(ydoc); + void pushUpdateToSubtext(currentVaultPath, update); + }; + ydoc.on('updateV2', saveHandler); + + // Auto-rename: when the user edits the first heading, we rename the vault + // file on disk to match. This is debounced (1.5 s trailing edge) so rapid + // keystrokes don't trigger many renames. The rename itself is async and + // fire-and-forget (`void tryRename()`); failures are logged, not thrown. + const tryRename = async () => { + if (released) return; + const heading = getHeadingFromYdoc(ydoc)?.trim(); + if (!heading) return; + + const desiredPath = await findUniqueVaultPath(heading, currentVaultPath); + if (desiredPath === currentVaultPath) return; + + try { + await renameFileInSubtext(currentVaultPath, desiredPath); + updatePath(id, desiredPath); + currentVaultPath = desiredPath; + emitSubtextTitle(id, getDisplayTitle()); + } catch (e) { + console.warn('[subtext] auto-rename failed:', e); + } + }; + + const scheduleRename = () => { + if (renameTimer) clearTimeout(renameTimer); + renameTimer = setTimeout(() => { + renameTimer = null; + void tryRename(); + }, 1500); + }; + + const titleWatcher = () => { + const heading = getHeadingFromYdoc(ydoc)?.trim(); + const nextTitle = heading ?? 'Unknown'; + emitSubtextTitle(id, nextTitle); + if (heading && makeVaultPath(heading) !== currentVaultPath) { + scheduleRename(); + } + }; + ydoc.on('update', titleWatcher); + // Emit initial title so the sidebar shows it immediately. + emitSubtextTitle(id, getDisplayTitle()); + + return { + id, + loadPromise: Promise.resolve(), + getTitle: getDisplayTitle, + subscribeTitle(listener: () => void) { + ydoc.on('update', listener); + return () => ydoc.off('update', listener); + }, + release() { + if (released) return; + released = true; + if (renameTimer) clearTimeout(renameTimer); + ydoc.off('updateV2', saveHandler); + ydoc.off('update', titleWatcher); + ydoc.destroy(); + }, + getEditorBinding: () => createYjsBinding({ ydoc, collabProvider: null }), + }; + } + + async createDocument(options?: { id?: string }): Promise { + const vaultPath = options?.id ?? (await findUniqueVaultPath('Untitled')); + const id = allocateId(vaultPath); + + const ydoc = new Y.Doc(); + const initialState = Y.encodeStateAsUpdateV2(ydoc); + try { + await createFileInSubtext(vaultPath, initialState); + } catch (e) { + console.warn('[subtext] failed to create local file in daemon:', e); + } + + return this.openLocalDocument(id, vaultPath); + } +} diff --git a/src/filesystem/providers/subtextFilesystemProvider.ts b/src/filesystem/providers/subtextFilesystemProvider.ts new file mode 100644 index 0000000..26a1ec6 --- /dev/null +++ b/src/filesystem/providers/subtextFilesystemProvider.ts @@ -0,0 +1,59 @@ +import type { DocumentProvider } from '../../documents/types'; +import type { EditorKind } from '../../editors/types'; +import { listCachedVaults } from '../../subtext/cache'; +import { scanPaths, subscribeSubtextTitleChanges } from '../../subtext/index'; +import type { FileSystemEntry, FileSystemProvider } from '../types'; + +export type SubtextFilesystemProviderOptions = { + documents: DocumentProvider; + defaultEditorKind?: EditorKind; +}; + +/** + * FileSystemProvider for Subtext local vaults. + * + * Uses stable IDs so sidebar selection survives renames. Listing scans the + * daemon store and reconciles paths with a persistent registry. + */ +export class SubtextFilesystemProvider implements FileSystemProvider { + readonly id = 'subtext'; + readonly displayName = 'Subtext'; + readonly idleHint = 'Subtext daemon not reachable. Ensure it is running on 127.0.0.1:8081.'; + readonly documents: DocumentProvider; + readonly defaultEditorKind: EditorKind; + + constructor(options: SubtextFilesystemProviderOptions) { + this.documents = options.documents; + this.defaultEditorKind = options.defaultEditorKind ?? 'yjs'; + } + + isReady(): boolean { + return true; + } + + subscribeReady(_listener: () => void): () => void { + return () => {}; + } + + async listFiles(): Promise { + const paths = await listCachedVaults(); + console.log('[subtext] daemon listed', paths.length, 'files'); + const entries = scanPaths(paths); + console.log('[subtext] registry has', entries.length, 'entries'); + return entries.map(({ id, path }) => ({ + id, + name: (path.split('/').pop() ?? path).replace(/\.md$/, ''), + })); + } + + subscribeEntryTitles( + listener: (entryId: string, name: string) => void, + ): () => void { + return subscribeSubtextTitleChanges(listener); + } + + async createFile(): Promise { + const handle = await this.documents.createDocument(); + return { id: handle.id, name: handle.getTitle() }; + } +} diff --git a/src/habitat/docSession.ts b/src/habitat/docSession.ts index 93c3f31..1d6496a 100644 --- a/src/habitat/docSession.ts +++ b/src/habitat/docSession.ts @@ -233,11 +233,14 @@ function detachSaveHandler(entry: RegistryEntry) { * with a `DocSession` whose `ydoc` is the canonical instance for `uri`; the * first load resolves in the background and updates the ydoc in place. */ -export function acquireDocSession(uri: string): DocSession { +export function acquireDocSession( + uri: string, + options?: { initialYdoc?: Y.Doc }, +): DocSession { ensureVisibilityListener(); let entry = ydocRegistry.get(uri); if (!entry) { - const ydoc = new Y.Doc(); + const ydoc = options?.initialYdoc ?? new Y.Doc(); entry = { uri, ydoc, diff --git a/src/icons/index.tsx b/src/icons/index.tsx new file mode 100644 index 0000000..c1f54b1 --- /dev/null +++ b/src/icons/index.tsx @@ -0,0 +1,69 @@ +/** + * Shared SVG icons used across the app. + * + * All icons accept `className` for sizing/coloring via Tailwind and use + * `currentColor` for stroke so they inherit the parent's text color. + */ + +type IconProps = { className?: string }; + +/** Generic document icon (lucide file). */ +export function DocFileIcon({ className }: IconProps) { + return ( + + + + + ); +} + +/** Document with pencil (lucide-style), for "new document" actions. */ +export function NewDocumentIcon({ className }: IconProps) { + return ( + + + + + + + ); +} + +/** Subtext logo: document with upward arrow (file-upload style). */ +export function SubtextIcon({ className }: IconProps) { + return ( + + + + + + + ); +} diff --git a/src/index.css b/src/index.css index 5589740..fbea801 100644 --- a/src/index.css +++ b/src/index.css @@ -10,6 +10,8 @@ --semantic-accent: oklch(0.52 0.17 260); --semantic-border: oklch(0.9 0 0); --semantic-destructive: oklch(0.52 0.2 27); + --semantic-warning: oklch(0.55 0.16 70); + --semantic-warning-bg: oklch(0.95 0.04 90); } :root[data-theme='dark'] { @@ -20,6 +22,8 @@ --semantic-accent: oklch(0.72 0.14 260); --semantic-border: oklch(0.32 0.02 260); --semantic-destructive: oklch(0.7 0.16 27); + --semantic-warning: oklch(0.78 0.12 70); + --semantic-warning-bg: oklch(0.25 0.03 70); } @theme { @@ -30,6 +34,8 @@ --color-accent: var(--semantic-accent); --color-border: var(--semantic-border); --color-destructive: var(--semantic-destructive); + --color-warning: var(--semantic-warning); + --color-warning-bg: var(--semantic-warning-bg); } @layer base { diff --git a/src/main.ts b/src/main.ts index cadba62..d7283a3 100644 --- a/src/main.ts +++ b/src/main.ts @@ -1,4 +1,5 @@ import { app, BrowserWindow, Menu, ipcMain } from 'electron'; +import { SubtextTCPClient } from './subtext/tcpClient'; import path from 'node:path'; import started from 'electron-squirrel-startup'; @@ -269,6 +270,36 @@ app.on('ready', () => { createWindow(); }); +const subtextClient = new SubtextTCPClient(); + +ipcMain.handle('subtext:get-full-state', async (_event, { vaultPath }) => { + return subtextClient.getFullState(vaultPath); +}); + +ipcMain.handle('subtext:apply-update', async (_event, { vaultPath, update }) => { + return subtextClient.applyUpdate(vaultPath, update); +}); + +ipcMain.handle('subtext:list-files', async () => { + return subtextClient.listFiles(); +}); + +ipcMain.handle('subtext:file-exists', async (_event, { vaultPath }) => { + return subtextClient.fileExists(vaultPath); +}); + +ipcMain.handle('subtext:create-file', async (_event, { vaultPath, initialState }) => { + return subtextClient.createFile(vaultPath, initialState); +}); + +ipcMain.handle('subtext:rename-file', async (_event, { oldVaultPath, newVaultPath }) => { + return subtextClient.renameFile(oldVaultPath, newVaultPath); +}); + +ipcMain.handle('subtext:status', async () => { + return { connected: subtextClient.isConnected }; +}); + ipcMain.handle( 'auth:start-habitat-login', async (_event, payload: { redirectUri: string; url: string }) => { diff --git a/src/preload.ts b/src/preload.ts index 196c058..3c7c210 100644 --- a/src/preload.ts +++ b/src/preload.ts @@ -9,4 +9,18 @@ contextBridge.exposeInMainWorld('textile', { }, startHabitatLogin: (url: string, redirectUri: string) => ipcRenderer.invoke('auth:start-habitat-login', { redirectUri, url }), + subtext: { + getFullState: (vaultPath: string) => + ipcRenderer.invoke('subtext:get-full-state', { vaultPath }), + applyUpdate: (vaultPath: string, update: Uint8Array) => + ipcRenderer.invoke('subtext:apply-update', { vaultPath, update }), + listFiles: () => ipcRenderer.invoke('subtext:list-files'), + fileExists: (vaultPath: string) => + ipcRenderer.invoke('subtext:file-exists', { vaultPath }), + createFile: (vaultPath: string, initialState: Uint8Array) => + ipcRenderer.invoke('subtext:create-file', { vaultPath, initialState }), + renameFile: (oldVaultPath: string, newVaultPath: string) => + ipcRenderer.invoke('subtext:rename-file', { oldVaultPath, newVaultPath }), + status: () => ipcRenderer.invoke('subtext:status'), + }, }); diff --git a/src/subtext/cache.ts b/src/subtext/cache.ts new file mode 100644 index 0000000..d5bc606 --- /dev/null +++ b/src/subtext/cache.ts @@ -0,0 +1,93 @@ +/** + * Subtext cache operations (renderer-side). + * + * Bridges the renderer's Yjs documents with the Subtext local CRDT store via + * the IPC-exposed TCP client. + * + * All functions below accept a `vaultPath` directly; there is no URI→vaultPath + * mapping layer at this time. + */ + +import * as Y from 'yjs'; + +const IPC_TIMEOUT_MS = 5000; + +async function ipcCall(method: string, ...args: unknown[]): Promise { + if (!window.textile?.subtext) { + throw new Error('subtext IPC not available'); + } + const fn = window.textile.subtext[method as keyof typeof window.textile.subtext]; + if (typeof fn !== 'function') { + throw new Error(`unknown subtext IPC method: ${method}`); + } + return Promise.race([ + (fn as (...args: unknown[]) => Promise)(...args), + new Promise((_, reject) => + setTimeout(() => reject(new Error('subtext IPC timeout')), IPC_TIMEOUT_MS), + ), + ]); +} + +/** Try to seed an existing Y.Doc from Subtext's local cache. Returns true if seeded. */ +export async function seedYdocFromSubtext(vaultPath: string, ydoc: Y.Doc): Promise { + try { + const bytes = (await ipcCall('getFullState', vaultPath)) as Uint8Array | null; + if (bytes && bytes.length > 0) { + Y.applyUpdateV2(ydoc, bytes); + return true; + } + } catch (e) { + console.warn('[subtext] seed failed for', vaultPath, e); + } + return false; +} + +/** Push the full Yjs state of a document to Subtext (overwrite local cache). */ +export async function pushYdocToSubtext(vaultPath: string, ydoc: Y.Doc): Promise { + const bytes = Y.encodeStateAsUpdateV2(ydoc); + try { + await ipcCall('applyUpdate', vaultPath, bytes); + } catch (e) { + console.warn('[subtext] push failed for', vaultPath, e); + throw e; + } +} + +/** Push a single update diff to Subtext (lightweight, used on every local edit). */ +export async function pushUpdateToSubtext(vaultPath: string, update: Uint8Array): Promise { + try { + await ipcCall('applyUpdate', vaultPath, update); + } catch (e) { + console.warn('[subtext] push update failed for', vaultPath, e); + } +} + +/** Create a new vault file in Subtext with the given initial Yjs state. */ +export async function createFileInSubtext( + vaultPath: string, + initialState: Uint8Array, +): Promise { + await ipcCall('createFile', vaultPath, initialState); +} + +/** Rename a vault file in Subtext. */ +export async function renameFileInSubtext( + oldVaultPath: string, + newVaultPath: string, +): Promise { + await ipcCall('renameFile', oldVaultPath, newVaultPath); +} + +/** Check whether Subtext has a local file at the given vault path. */ +export async function fileExists(vaultPath: string): Promise { + try { + return await ipcCall('fileExists', vaultPath); + } catch { + return false; + } +} + +/** List all local vault paths from Subtext. */ +export async function listCachedVaults(): Promise { + return await ipcCall('listFiles'); +} diff --git a/src/subtext/index.ts b/src/subtext/index.ts new file mode 100644 index 0000000..c3d10bf --- /dev/null +++ b/src/subtext/index.ts @@ -0,0 +1,127 @@ +/** + * Subtext stable file registry (renderer-side). + * + * Maps opaque stable IDs to current vault paths so the sidebar selection survives + * renames. Persisted in localStorage so IDs are stable across app restarts. + */ + +const REGISTRY_KEY = 'textile.subtext.registry'; + +type Registry = { + version: number; + entries: Record; // id -> vaultPath +}; + +function readRegistry(): Registry { + if (typeof localStorage === 'undefined') { + return { version: 1, entries: {} }; + } + try { + const raw = localStorage.getItem(REGISTRY_KEY); + if (raw) { + const parsed = JSON.parse(raw) as Registry; + if (parsed.version === 1) return parsed; + } + } catch { + // corrupt storage + } + return { version: 1, entries: {} }; +} + +function writeRegistry(registry: Registry): void { + if (typeof localStorage === 'undefined') return; + localStorage.setItem(REGISTRY_KEY, JSON.stringify(registry)); +} + +function generateId(): string { + if (typeof crypto !== 'undefined' && 'randomUUID' in crypto) { + return crypto.randomUUID(); + } + // Fallback for environments without crypto.randomUUID() + return `${Date.now()}-${Math.random().toString(36).slice(2, 11)}`; +} + +/** Allocate a new stable ID mapped to the given vault path. */ +export function allocateId(vaultPath: string): string { + const registry = readRegistry(); + const id = generateId(); + registry.entries[id] = vaultPath; + writeRegistry(registry); + return id; +} + +/** Look up the current vault path for a stable ID. */ +export function getPath(id: string): string | null { + return readRegistry().entries[id] ?? null; +} + +/** Update the vault path for an existing stable ID (e.g. after a rename). */ +export function updatePath(id: string, newPath: string): void { + const registry = readRegistry(); + if (registry.entries[id]) { + registry.entries[id] = newPath; + writeRegistry(registry); + } +} + +/** Find an existing ID for a vault path, or return null. */ +export function findIdByPath(vaultPath: string): string | null { + const registry = readRegistry(); + for (const [id, path] of Object.entries(registry.entries)) { + if (path === vaultPath) return id; + } + return null; +} + +/** + * Scan a list of paths from the daemon and reconcile them with the registry. + * Returns `{ id, path }` pairs with stable IDs. Unknown paths get new IDs. + * Stale entries (paths that no longer exist) are cleaned up. + */ +export function scanPaths(paths: string[]): Array<{ id: string; path: string }> { + const registry = readRegistry(); + const reverse = new Map(); + for (const [id, path] of Object.entries(registry.entries)) { + reverse.set(path, id); + } + + const result: Array<{ id: string; path: string }> = []; + const seenPaths = new Set(); + + for (const path of paths) { + seenPaths.add(path); + let id = reverse.get(path); + if (!id) { + id = generateId(); + registry.entries[id] = path; + } + result.push({ id, path }); + } + + // Remove stale entries whose paths no longer exist on disk. + for (const [id, path] of Object.entries(registry.entries)) { + if (!seenPaths.has(path)) { + delete registry.entries[id]; + } + } + + writeRegistry(registry); + return result; +} + +// --- Title-change pub/sub (mirrors habitat/docSession.ts pattern) --------- + +const titleListeners = new Set<(id: string, name: string) => void>(); + +export function subscribeSubtextTitleChanges( + listener: (id: string, name: string) => void, +): () => void { + titleListeners.add(listener); + return () => titleListeners.delete(listener); +} + +export function emitSubtextTitle(id: string, name: string): void { + for (const listener of titleListeners) { + listener(id, name); + } +} diff --git a/src/subtext/proto.d.ts b/src/subtext/proto.d.ts new file mode 100644 index 0000000..ebc7ffc --- /dev/null +++ b/src/subtext/proto.d.ts @@ -0,0 +1,2004 @@ +import * as $protobuf from "protobufjs"; +import Long = require("long"); + +/** Namespace subtext_handlers. */ +export namespace subtext_handlers { + + /** + * Properties of a Request. + * @deprecated Use subtext_handlers.Request.$Properties instead. + */ + interface IRequest extends subtext_handlers.Request.$Properties { + } + + /** Represents a Request. */ + class Request { + + /** + * Constructs a new Request. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.Request.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** Request id. */ + id: (number|Long); + + /** Request ping. */ + ping?: (subtext_handlers.Ping.$Properties|null); + + /** Request applyUpdateV2. */ + applyUpdateV2?: (subtext_handlers.ApplyUpdateV2.$Properties|null); + + /** Request getStateVector. */ + getStateVector?: (subtext_handlers.GetStateVector.$Properties|null); + + /** Request getFullState. */ + getFullState?: (subtext_handlers.GetFullState.$Properties|null); + + /** Request listFiles. */ + listFiles?: (subtext_handlers.ListFiles.$Properties|null); + + /** Request fileExists. */ + fileExists?: (subtext_handlers.FileExists.$Properties|null); + + /** Request createFile. */ + createFile?: (subtext_handlers.CreateFile.$Properties|null); + + /** Request renameFile. */ + renameFile?: (subtext_handlers.RenameFile.$Properties|null); + + /** Request content. */ + content?: ("ping"|"applyUpdateV2"|"getStateVector"|"getFullState"|"listFiles"|"fileExists"|"createFile"|"renameFile"); + + /** + * Creates a new Request instance using the specified properties. + * @param [properties] Properties to set + * @returns Request instance + */ + static create(properties: subtext_handlers.Request.$Shape): subtext_handlers.Request & subtext_handlers.Request.$Shape; + static create(properties?: subtext_handlers.Request.$Properties): subtext_handlers.Request; + + /** + * Encodes the specified Request message. Does not implicitly {@link subtext_handlers.Request.verify|verify} messages. + * @param message Request message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.Request.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified Request message, length delimited. Does not implicitly {@link subtext_handlers.Request.verify|verify} messages. + * @param message Request message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.Request.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes a Request message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.Request & subtext_handlers.Request.$Shape} Request + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.Request & subtext_handlers.Request.$Shape; + + /** + * Decodes a Request message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.Request & subtext_handlers.Request.$Shape} Request + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.Request & subtext_handlers.Request.$Shape; + + /** + * Verifies a Request message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates a Request message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns Request + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.Request; + + /** + * Creates a plain object from a Request message. Also converts values to other types if specified. + * @param message Request + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.Request, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this Request to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for Request + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace Request { + + /** Properties of a Request. */ + interface $Properties { + + /** Request id */ + id?: (number|Long|null); + + /** Request ping */ + ping?: (subtext_handlers.Ping.$Properties|null); + + /** Request applyUpdateV2 */ + applyUpdateV2?: (subtext_handlers.ApplyUpdateV2.$Properties|null); + + /** Request getStateVector */ + getStateVector?: (subtext_handlers.GetStateVector.$Properties|null); + + /** Request getFullState */ + getFullState?: (subtext_handlers.GetFullState.$Properties|null); + + /** Request listFiles */ + listFiles?: (subtext_handlers.ListFiles.$Properties|null); + + /** Request fileExists */ + fileExists?: (subtext_handlers.FileExists.$Properties|null); + + /** Request createFile */ + createFile?: (subtext_handlers.CreateFile.$Properties|null); + + /** Request renameFile */ + renameFile?: (subtext_handlers.RenameFile.$Properties|null); + + /** Request content */ + content?: ("ping"|"applyUpdateV2"|"getStateVector"|"getFullState"|"listFiles"|"fileExists"|"createFile"|"renameFile"); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Narrowed shape of a Request. */ + type $Shape = { + id?: number|Long|null; + ping?: subtext_handlers.Ping.$Shape|null; + applyUpdateV2?: subtext_handlers.ApplyUpdateV2.$Shape|null; + getStateVector?: subtext_handlers.GetStateVector.$Shape|null; + getFullState?: subtext_handlers.GetFullState.$Shape|null; + listFiles?: subtext_handlers.ListFiles.$Shape|null; + fileExists?: subtext_handlers.FileExists.$Shape|null; + createFile?: subtext_handlers.CreateFile.$Shape|null; + renameFile?: subtext_handlers.RenameFile.$Shape|null; + $unknowns?: Uint8Array[]; +} & ( + ({ content?: undefined; ping?: null; applyUpdateV2?: null; getStateVector?: null; getFullState?: null; listFiles?: null; fileExists?: null; createFile?: null; renameFile?: null }|{ content?: "ping"; ping: subtext_handlers.Ping.$Shape; applyUpdateV2?: null; getStateVector?: null; getFullState?: null; listFiles?: null; fileExists?: null; createFile?: null; renameFile?: null }|{ content?: "applyUpdateV2"; ping?: null; applyUpdateV2: subtext_handlers.ApplyUpdateV2.$Shape; getStateVector?: null; getFullState?: null; listFiles?: null; fileExists?: null; createFile?: null; renameFile?: null }|{ content?: "getStateVector"; ping?: null; applyUpdateV2?: null; getStateVector: subtext_handlers.GetStateVector.$Shape; getFullState?: null; listFiles?: null; fileExists?: null; createFile?: null; renameFile?: null }|{ content?: "getFullState"; ping?: null; applyUpdateV2?: null; getStateVector?: null; getFullState: subtext_handlers.GetFullState.$Shape; listFiles?: null; fileExists?: null; createFile?: null; renameFile?: null }|{ content?: "listFiles"; ping?: null; applyUpdateV2?: null; getStateVector?: null; getFullState?: null; listFiles: subtext_handlers.ListFiles.$Shape; fileExists?: null; createFile?: null; renameFile?: null }|{ content?: "fileExists"; ping?: null; applyUpdateV2?: null; getStateVector?: null; getFullState?: null; listFiles?: null; fileExists: subtext_handlers.FileExists.$Shape; createFile?: null; renameFile?: null }|{ content?: "createFile"; ping?: null; applyUpdateV2?: null; getStateVector?: null; getFullState?: null; listFiles?: null; fileExists?: null; createFile: subtext_handlers.CreateFile.$Shape; renameFile?: null }|{ content?: "renameFile"; ping?: null; applyUpdateV2?: null; getStateVector?: null; getFullState?: null; listFiles?: null; fileExists?: null; createFile?: null; renameFile: subtext_handlers.RenameFile.$Shape }) +); + } + + /** + * Properties of a Ping. + * @deprecated Use subtext_handlers.Ping.$Properties instead. + */ + interface IPing extends subtext_handlers.Ping.$Properties { + } + + /** Represents a Ping. */ + class Ping { + + /** + * Constructs a new Ping. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.Ping.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** + * Creates a new Ping instance using the specified properties. + * @param [properties] Properties to set + * @returns Ping instance + */ + static create(properties: subtext_handlers.Ping.$Shape): subtext_handlers.Ping & subtext_handlers.Ping.$Shape; + static create(properties?: subtext_handlers.Ping.$Properties): subtext_handlers.Ping; + + /** + * Encodes the specified Ping message. Does not implicitly {@link subtext_handlers.Ping.verify|verify} messages. + * @param message Ping message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.Ping.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified Ping message, length delimited. Does not implicitly {@link subtext_handlers.Ping.verify|verify} messages. + * @param message Ping message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.Ping.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes a Ping message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.Ping & subtext_handlers.Ping.$Shape} Ping + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.Ping & subtext_handlers.Ping.$Shape; + + /** + * Decodes a Ping message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.Ping & subtext_handlers.Ping.$Shape} Ping + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.Ping & subtext_handlers.Ping.$Shape; + + /** + * Verifies a Ping message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates a Ping message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns Ping + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.Ping; + + /** + * Creates a plain object from a Ping message. Also converts values to other types if specified. + * @param message Ping + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.Ping, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this Ping to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for Ping + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace Ping { + + /** Properties of a Ping. */ + interface $Properties { + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Shape of a Ping. */ + type $Shape = subtext_handlers.Ping.$Properties; + } + + /** + * Properties of an ApplyUpdateV2. + * @deprecated Use subtext_handlers.ApplyUpdateV2.$Properties instead. + */ + interface IApplyUpdateV2 extends subtext_handlers.ApplyUpdateV2.$Properties { + } + + /** Represents an ApplyUpdateV2. */ + class ApplyUpdateV2 { + + /** + * Constructs a new ApplyUpdateV2. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.ApplyUpdateV2.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** ApplyUpdateV2 vaultPath. */ + vaultPath: string; + + /** ApplyUpdateV2 update. */ + update: Uint8Array; + + /** + * Creates a new ApplyUpdateV2 instance using the specified properties. + * @param [properties] Properties to set + * @returns ApplyUpdateV2 instance + */ + static create(properties: subtext_handlers.ApplyUpdateV2.$Shape): subtext_handlers.ApplyUpdateV2 & subtext_handlers.ApplyUpdateV2.$Shape; + static create(properties?: subtext_handlers.ApplyUpdateV2.$Properties): subtext_handlers.ApplyUpdateV2; + + /** + * Encodes the specified ApplyUpdateV2 message. Does not implicitly {@link subtext_handlers.ApplyUpdateV2.verify|verify} messages. + * @param message ApplyUpdateV2 message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.ApplyUpdateV2.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified ApplyUpdateV2 message, length delimited. Does not implicitly {@link subtext_handlers.ApplyUpdateV2.verify|verify} messages. + * @param message ApplyUpdateV2 message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.ApplyUpdateV2.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes an ApplyUpdateV2 message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.ApplyUpdateV2 & subtext_handlers.ApplyUpdateV2.$Shape} ApplyUpdateV2 + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.ApplyUpdateV2 & subtext_handlers.ApplyUpdateV2.$Shape; + + /** + * Decodes an ApplyUpdateV2 message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.ApplyUpdateV2 & subtext_handlers.ApplyUpdateV2.$Shape} ApplyUpdateV2 + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.ApplyUpdateV2 & subtext_handlers.ApplyUpdateV2.$Shape; + + /** + * Verifies an ApplyUpdateV2 message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates an ApplyUpdateV2 message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns ApplyUpdateV2 + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.ApplyUpdateV2; + + /** + * Creates a plain object from an ApplyUpdateV2 message. Also converts values to other types if specified. + * @param message ApplyUpdateV2 + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.ApplyUpdateV2, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this ApplyUpdateV2 to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for ApplyUpdateV2 + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace ApplyUpdateV2 { + + /** Properties of an ApplyUpdateV2. */ + interface $Properties { + + /** ApplyUpdateV2 vaultPath */ + vaultPath?: (string|null); + + /** ApplyUpdateV2 update */ + update?: (Uint8Array|null); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Shape of an ApplyUpdateV2. */ + type $Shape = subtext_handlers.ApplyUpdateV2.$Properties; + } + + /** + * Properties of a GetStateVector. + * @deprecated Use subtext_handlers.GetStateVector.$Properties instead. + */ + interface IGetStateVector extends subtext_handlers.GetStateVector.$Properties { + } + + /** Represents a GetStateVector. */ + class GetStateVector { + + /** + * Constructs a new GetStateVector. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.GetStateVector.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** GetStateVector vaultPath. */ + vaultPath: string; + + /** + * Creates a new GetStateVector instance using the specified properties. + * @param [properties] Properties to set + * @returns GetStateVector instance + */ + static create(properties: subtext_handlers.GetStateVector.$Shape): subtext_handlers.GetStateVector & subtext_handlers.GetStateVector.$Shape; + static create(properties?: subtext_handlers.GetStateVector.$Properties): subtext_handlers.GetStateVector; + + /** + * Encodes the specified GetStateVector message. Does not implicitly {@link subtext_handlers.GetStateVector.verify|verify} messages. + * @param message GetStateVector message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.GetStateVector.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified GetStateVector message, length delimited. Does not implicitly {@link subtext_handlers.GetStateVector.verify|verify} messages. + * @param message GetStateVector message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.GetStateVector.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes a GetStateVector message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.GetStateVector & subtext_handlers.GetStateVector.$Shape} GetStateVector + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.GetStateVector & subtext_handlers.GetStateVector.$Shape; + + /** + * Decodes a GetStateVector message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.GetStateVector & subtext_handlers.GetStateVector.$Shape} GetStateVector + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.GetStateVector & subtext_handlers.GetStateVector.$Shape; + + /** + * Verifies a GetStateVector message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates a GetStateVector message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns GetStateVector + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.GetStateVector; + + /** + * Creates a plain object from a GetStateVector message. Also converts values to other types if specified. + * @param message GetStateVector + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.GetStateVector, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this GetStateVector to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for GetStateVector + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace GetStateVector { + + /** Properties of a GetStateVector. */ + interface $Properties { + + /** GetStateVector vaultPath */ + vaultPath?: (string|null); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Shape of a GetStateVector. */ + type $Shape = subtext_handlers.GetStateVector.$Properties; + } + + /** + * Properties of a GetFullState. + * @deprecated Use subtext_handlers.GetFullState.$Properties instead. + */ + interface IGetFullState extends subtext_handlers.GetFullState.$Properties { + } + + /** Represents a GetFullState. */ + class GetFullState { + + /** + * Constructs a new GetFullState. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.GetFullState.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** GetFullState vaultPath. */ + vaultPath: string; + + /** + * Creates a new GetFullState instance using the specified properties. + * @param [properties] Properties to set + * @returns GetFullState instance + */ + static create(properties: subtext_handlers.GetFullState.$Shape): subtext_handlers.GetFullState & subtext_handlers.GetFullState.$Shape; + static create(properties?: subtext_handlers.GetFullState.$Properties): subtext_handlers.GetFullState; + + /** + * Encodes the specified GetFullState message. Does not implicitly {@link subtext_handlers.GetFullState.verify|verify} messages. + * @param message GetFullState message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.GetFullState.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified GetFullState message, length delimited. Does not implicitly {@link subtext_handlers.GetFullState.verify|verify} messages. + * @param message GetFullState message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.GetFullState.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes a GetFullState message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.GetFullState & subtext_handlers.GetFullState.$Shape} GetFullState + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.GetFullState & subtext_handlers.GetFullState.$Shape; + + /** + * Decodes a GetFullState message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.GetFullState & subtext_handlers.GetFullState.$Shape} GetFullState + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.GetFullState & subtext_handlers.GetFullState.$Shape; + + /** + * Verifies a GetFullState message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates a GetFullState message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns GetFullState + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.GetFullState; + + /** + * Creates a plain object from a GetFullState message. Also converts values to other types if specified. + * @param message GetFullState + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.GetFullState, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this GetFullState to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for GetFullState + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace GetFullState { + + /** Properties of a GetFullState. */ + interface $Properties { + + /** GetFullState vaultPath */ + vaultPath?: (string|null); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Shape of a GetFullState. */ + type $Shape = subtext_handlers.GetFullState.$Properties; + } + + /** + * Properties of a ListFiles. + * @deprecated Use subtext_handlers.ListFiles.$Properties instead. + */ + interface IListFiles extends subtext_handlers.ListFiles.$Properties { + } + + /** Represents a ListFiles. */ + class ListFiles { + + /** + * Constructs a new ListFiles. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.ListFiles.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** ListFiles prefix. */ + prefix: string; + + /** + * Creates a new ListFiles instance using the specified properties. + * @param [properties] Properties to set + * @returns ListFiles instance + */ + static create(properties: subtext_handlers.ListFiles.$Shape): subtext_handlers.ListFiles & subtext_handlers.ListFiles.$Shape; + static create(properties?: subtext_handlers.ListFiles.$Properties): subtext_handlers.ListFiles; + + /** + * Encodes the specified ListFiles message. Does not implicitly {@link subtext_handlers.ListFiles.verify|verify} messages. + * @param message ListFiles message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.ListFiles.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified ListFiles message, length delimited. Does not implicitly {@link subtext_handlers.ListFiles.verify|verify} messages. + * @param message ListFiles message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.ListFiles.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes a ListFiles message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.ListFiles & subtext_handlers.ListFiles.$Shape} ListFiles + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.ListFiles & subtext_handlers.ListFiles.$Shape; + + /** + * Decodes a ListFiles message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.ListFiles & subtext_handlers.ListFiles.$Shape} ListFiles + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.ListFiles & subtext_handlers.ListFiles.$Shape; + + /** + * Verifies a ListFiles message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates a ListFiles message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns ListFiles + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.ListFiles; + + /** + * Creates a plain object from a ListFiles message. Also converts values to other types if specified. + * @param message ListFiles + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.ListFiles, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this ListFiles to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for ListFiles + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace ListFiles { + + /** Properties of a ListFiles. */ + interface $Properties { + + /** ListFiles prefix */ + prefix?: (string|null); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Shape of a ListFiles. */ + type $Shape = subtext_handlers.ListFiles.$Properties; + } + + /** + * Properties of a FileExists. + * @deprecated Use subtext_handlers.FileExists.$Properties instead. + */ + interface IFileExists extends subtext_handlers.FileExists.$Properties { + } + + /** Represents a FileExists. */ + class FileExists { + + /** + * Constructs a new FileExists. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.FileExists.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** FileExists vaultPath. */ + vaultPath: string; + + /** + * Creates a new FileExists instance using the specified properties. + * @param [properties] Properties to set + * @returns FileExists instance + */ + static create(properties: subtext_handlers.FileExists.$Shape): subtext_handlers.FileExists & subtext_handlers.FileExists.$Shape; + static create(properties?: subtext_handlers.FileExists.$Properties): subtext_handlers.FileExists; + + /** + * Encodes the specified FileExists message. Does not implicitly {@link subtext_handlers.FileExists.verify|verify} messages. + * @param message FileExists message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.FileExists.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified FileExists message, length delimited. Does not implicitly {@link subtext_handlers.FileExists.verify|verify} messages. + * @param message FileExists message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.FileExists.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes a FileExists message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.FileExists & subtext_handlers.FileExists.$Shape} FileExists + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.FileExists & subtext_handlers.FileExists.$Shape; + + /** + * Decodes a FileExists message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.FileExists & subtext_handlers.FileExists.$Shape} FileExists + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.FileExists & subtext_handlers.FileExists.$Shape; + + /** + * Verifies a FileExists message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates a FileExists message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns FileExists + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.FileExists; + + /** + * Creates a plain object from a FileExists message. Also converts values to other types if specified. + * @param message FileExists + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.FileExists, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this FileExists to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for FileExists + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace FileExists { + + /** Properties of a FileExists. */ + interface $Properties { + + /** FileExists vaultPath */ + vaultPath?: (string|null); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Shape of a FileExists. */ + type $Shape = subtext_handlers.FileExists.$Properties; + } + + /** + * Properties of a CreateFile. + * @deprecated Use subtext_handlers.CreateFile.$Properties instead. + */ + interface ICreateFile extends subtext_handlers.CreateFile.$Properties { + } + + /** Represents a CreateFile. */ + class CreateFile { + + /** + * Constructs a new CreateFile. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.CreateFile.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** CreateFile vaultPath. */ + vaultPath: string; + + /** CreateFile initialState. */ + initialState: Uint8Array; + + /** + * Creates a new CreateFile instance using the specified properties. + * @param [properties] Properties to set + * @returns CreateFile instance + */ + static create(properties: subtext_handlers.CreateFile.$Shape): subtext_handlers.CreateFile & subtext_handlers.CreateFile.$Shape; + static create(properties?: subtext_handlers.CreateFile.$Properties): subtext_handlers.CreateFile; + + /** + * Encodes the specified CreateFile message. Does not implicitly {@link subtext_handlers.CreateFile.verify|verify} messages. + * @param message CreateFile message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.CreateFile.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified CreateFile message, length delimited. Does not implicitly {@link subtext_handlers.CreateFile.verify|verify} messages. + * @param message CreateFile message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.CreateFile.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes a CreateFile message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.CreateFile & subtext_handlers.CreateFile.$Shape} CreateFile + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.CreateFile & subtext_handlers.CreateFile.$Shape; + + /** + * Decodes a CreateFile message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.CreateFile & subtext_handlers.CreateFile.$Shape} CreateFile + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.CreateFile & subtext_handlers.CreateFile.$Shape; + + /** + * Verifies a CreateFile message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates a CreateFile message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns CreateFile + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.CreateFile; + + /** + * Creates a plain object from a CreateFile message. Also converts values to other types if specified. + * @param message CreateFile + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.CreateFile, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this CreateFile to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for CreateFile + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace CreateFile { + + /** Properties of a CreateFile. */ + interface $Properties { + + /** CreateFile vaultPath */ + vaultPath?: (string|null); + + /** CreateFile initialState */ + initialState?: (Uint8Array|null); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Shape of a CreateFile. */ + type $Shape = subtext_handlers.CreateFile.$Properties; + } + + /** + * Properties of a RenameFile. + * @deprecated Use subtext_handlers.RenameFile.$Properties instead. + */ + interface IRenameFile extends subtext_handlers.RenameFile.$Properties { + } + + /** Represents a RenameFile. */ + class RenameFile { + + /** + * Constructs a new RenameFile. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.RenameFile.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** RenameFile oldVaultPath. */ + oldVaultPath: string; + + /** RenameFile newVaultPath. */ + newVaultPath: string; + + /** + * Creates a new RenameFile instance using the specified properties. + * @param [properties] Properties to set + * @returns RenameFile instance + */ + static create(properties: subtext_handlers.RenameFile.$Shape): subtext_handlers.RenameFile & subtext_handlers.RenameFile.$Shape; + static create(properties?: subtext_handlers.RenameFile.$Properties): subtext_handlers.RenameFile; + + /** + * Encodes the specified RenameFile message. Does not implicitly {@link subtext_handlers.RenameFile.verify|verify} messages. + * @param message RenameFile message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.RenameFile.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified RenameFile message, length delimited. Does not implicitly {@link subtext_handlers.RenameFile.verify|verify} messages. + * @param message RenameFile message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.RenameFile.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes a RenameFile message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.RenameFile & subtext_handlers.RenameFile.$Shape} RenameFile + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.RenameFile & subtext_handlers.RenameFile.$Shape; + + /** + * Decodes a RenameFile message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.RenameFile & subtext_handlers.RenameFile.$Shape} RenameFile + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.RenameFile & subtext_handlers.RenameFile.$Shape; + + /** + * Verifies a RenameFile message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates a RenameFile message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns RenameFile + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.RenameFile; + + /** + * Creates a plain object from a RenameFile message. Also converts values to other types if specified. + * @param message RenameFile + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.RenameFile, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this RenameFile to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for RenameFile + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace RenameFile { + + /** Properties of a RenameFile. */ + interface $Properties { + + /** RenameFile oldVaultPath */ + oldVaultPath?: (string|null); + + /** RenameFile newVaultPath */ + newVaultPath?: (string|null); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Shape of a RenameFile. */ + type $Shape = subtext_handlers.RenameFile.$Properties; + } + + /** + * Properties of a Response. + * @deprecated Use subtext_handlers.Response.$Properties instead. + */ + interface IResponse extends subtext_handlers.Response.$Properties { + } + + /** Represents a Response. */ + class Response { + + /** + * Constructs a new Response. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.Response.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** Response requestId. */ + requestId: (number|Long); + + /** Response pong. */ + pong?: (subtext_handlers.Pong.$Properties|null); + + /** Response ack. */ + ack?: (subtext_handlers.Ack.$Properties|null); + + /** Response error. */ + error?: (subtext_handlers.Error.$Properties|null); + + /** Response bytesPayload. */ + bytesPayload?: (subtext_handlers.BytesPayload.$Properties|null); + + /** Response fileList. */ + fileList?: (subtext_handlers.FileList.$Properties|null); + + /** Response fileExistsResult. */ + fileExistsResult?: (subtext_handlers.FileExistsResult.$Properties|null); + + /** Response content. */ + content?: ("pong"|"ack"|"error"|"bytesPayload"|"fileList"|"fileExistsResult"); + + /** + * Creates a new Response instance using the specified properties. + * @param [properties] Properties to set + * @returns Response instance + */ + static create(properties: subtext_handlers.Response.$Shape): subtext_handlers.Response & subtext_handlers.Response.$Shape; + static create(properties?: subtext_handlers.Response.$Properties): subtext_handlers.Response; + + /** + * Encodes the specified Response message. Does not implicitly {@link subtext_handlers.Response.verify|verify} messages. + * @param message Response message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.Response.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified Response message, length delimited. Does not implicitly {@link subtext_handlers.Response.verify|verify} messages. + * @param message Response message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.Response.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes a Response message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.Response & subtext_handlers.Response.$Shape} Response + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.Response & subtext_handlers.Response.$Shape; + + /** + * Decodes a Response message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.Response & subtext_handlers.Response.$Shape} Response + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.Response & subtext_handlers.Response.$Shape; + + /** + * Verifies a Response message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates a Response message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns Response + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.Response; + + /** + * Creates a plain object from a Response message. Also converts values to other types if specified. + * @param message Response + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.Response, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this Response to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for Response + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace Response { + + /** Properties of a Response. */ + interface $Properties { + + /** Response requestId */ + requestId?: (number|Long|null); + + /** Response pong */ + pong?: (subtext_handlers.Pong.$Properties|null); + + /** Response ack */ + ack?: (subtext_handlers.Ack.$Properties|null); + + /** Response error */ + error?: (subtext_handlers.Error.$Properties|null); + + /** Response bytesPayload */ + bytesPayload?: (subtext_handlers.BytesPayload.$Properties|null); + + /** Response fileList */ + fileList?: (subtext_handlers.FileList.$Properties|null); + + /** Response fileExistsResult */ + fileExistsResult?: (subtext_handlers.FileExistsResult.$Properties|null); + + /** Response content */ + content?: ("pong"|"ack"|"error"|"bytesPayload"|"fileList"|"fileExistsResult"); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Narrowed shape of a Response. */ + type $Shape = { + requestId?: number|Long|null; + pong?: subtext_handlers.Pong.$Shape|null; + ack?: subtext_handlers.Ack.$Shape|null; + error?: subtext_handlers.Error.$Shape|null; + bytesPayload?: subtext_handlers.BytesPayload.$Shape|null; + fileList?: subtext_handlers.FileList.$Shape|null; + fileExistsResult?: subtext_handlers.FileExistsResult.$Shape|null; + $unknowns?: Uint8Array[]; +} & ( + ({ content?: undefined; pong?: null; ack?: null; error?: null; bytesPayload?: null; fileList?: null; fileExistsResult?: null }|{ content?: "pong"; pong: subtext_handlers.Pong.$Shape; ack?: null; error?: null; bytesPayload?: null; fileList?: null; fileExistsResult?: null }|{ content?: "ack"; pong?: null; ack: subtext_handlers.Ack.$Shape; error?: null; bytesPayload?: null; fileList?: null; fileExistsResult?: null }|{ content?: "error"; pong?: null; ack?: null; error: subtext_handlers.Error.$Shape; bytesPayload?: null; fileList?: null; fileExistsResult?: null }|{ content?: "bytesPayload"; pong?: null; ack?: null; error?: null; bytesPayload: subtext_handlers.BytesPayload.$Shape; fileList?: null; fileExistsResult?: null }|{ content?: "fileList"; pong?: null; ack?: null; error?: null; bytesPayload?: null; fileList: subtext_handlers.FileList.$Shape; fileExistsResult?: null }|{ content?: "fileExistsResult"; pong?: null; ack?: null; error?: null; bytesPayload?: null; fileList?: null; fileExistsResult: subtext_handlers.FileExistsResult.$Shape }) +); + } + + /** + * Properties of a Pong. + * @deprecated Use subtext_handlers.Pong.$Properties instead. + */ + interface IPong extends subtext_handlers.Pong.$Properties { + } + + /** Represents a Pong. */ + class Pong { + + /** + * Constructs a new Pong. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.Pong.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** + * Creates a new Pong instance using the specified properties. + * @param [properties] Properties to set + * @returns Pong instance + */ + static create(properties: subtext_handlers.Pong.$Shape): subtext_handlers.Pong & subtext_handlers.Pong.$Shape; + static create(properties?: subtext_handlers.Pong.$Properties): subtext_handlers.Pong; + + /** + * Encodes the specified Pong message. Does not implicitly {@link subtext_handlers.Pong.verify|verify} messages. + * @param message Pong message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.Pong.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified Pong message, length delimited. Does not implicitly {@link subtext_handlers.Pong.verify|verify} messages. + * @param message Pong message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.Pong.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes a Pong message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.Pong & subtext_handlers.Pong.$Shape} Pong + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.Pong & subtext_handlers.Pong.$Shape; + + /** + * Decodes a Pong message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.Pong & subtext_handlers.Pong.$Shape} Pong + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.Pong & subtext_handlers.Pong.$Shape; + + /** + * Verifies a Pong message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates a Pong message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns Pong + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.Pong; + + /** + * Creates a plain object from a Pong message. Also converts values to other types if specified. + * @param message Pong + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.Pong, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this Pong to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for Pong + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace Pong { + + /** Properties of a Pong. */ + interface $Properties { + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Shape of a Pong. */ + type $Shape = subtext_handlers.Pong.$Properties; + } + + /** + * Properties of an Ack. + * @deprecated Use subtext_handlers.Ack.$Properties instead. + */ + interface IAck extends subtext_handlers.Ack.$Properties { + } + + /** Represents an Ack. */ + class Ack { + + /** + * Constructs a new Ack. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.Ack.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** Ack message. */ + message: string; + + /** + * Creates a new Ack instance using the specified properties. + * @param [properties] Properties to set + * @returns Ack instance + */ + static create(properties: subtext_handlers.Ack.$Shape): subtext_handlers.Ack & subtext_handlers.Ack.$Shape; + static create(properties?: subtext_handlers.Ack.$Properties): subtext_handlers.Ack; + + /** + * Encodes the specified Ack message. Does not implicitly {@link subtext_handlers.Ack.verify|verify} messages. + * @param message Ack message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.Ack.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified Ack message, length delimited. Does not implicitly {@link subtext_handlers.Ack.verify|verify} messages. + * @param message Ack message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.Ack.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes an Ack message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.Ack & subtext_handlers.Ack.$Shape} Ack + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.Ack & subtext_handlers.Ack.$Shape; + + /** + * Decodes an Ack message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.Ack & subtext_handlers.Ack.$Shape} Ack + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.Ack & subtext_handlers.Ack.$Shape; + + /** + * Verifies an Ack message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates an Ack message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns Ack + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.Ack; + + /** + * Creates a plain object from an Ack message. Also converts values to other types if specified. + * @param message Ack + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.Ack, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this Ack to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for Ack + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace Ack { + + /** Properties of an Ack. */ + interface $Properties { + + /** Ack message */ + message?: (string|null); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Shape of an Ack. */ + type $Shape = subtext_handlers.Ack.$Properties; + } + + /** + * Properties of an Error. + * @deprecated Use subtext_handlers.Error.$Properties instead. + */ + interface IError extends subtext_handlers.Error.$Properties { + } + + /** Represents an Error. */ + class Error { + + /** + * Constructs a new Error. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.Error.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** Error message. */ + message: string; + + /** + * Creates a new Error instance using the specified properties. + * @param [properties] Properties to set + * @returns Error instance + */ + static create(properties: subtext_handlers.Error.$Shape): subtext_handlers.Error & subtext_handlers.Error.$Shape; + static create(properties?: subtext_handlers.Error.$Properties): subtext_handlers.Error; + + /** + * Encodes the specified Error message. Does not implicitly {@link subtext_handlers.Error.verify|verify} messages. + * @param message Error message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.Error.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified Error message, length delimited. Does not implicitly {@link subtext_handlers.Error.verify|verify} messages. + * @param message Error message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.Error.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes an Error message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.Error & subtext_handlers.Error.$Shape} Error + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.Error & subtext_handlers.Error.$Shape; + + /** + * Decodes an Error message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.Error & subtext_handlers.Error.$Shape} Error + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.Error & subtext_handlers.Error.$Shape; + + /** + * Verifies an Error message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates an Error message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns Error + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.Error; + + /** + * Creates a plain object from an Error message. Also converts values to other types if specified. + * @param message Error + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.Error, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this Error to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for Error + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace Error { + + /** Properties of an Error. */ + interface $Properties { + + /** Error message */ + message?: (string|null); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Shape of an Error. */ + type $Shape = subtext_handlers.Error.$Properties; + } + + /** + * Properties of a BytesPayload. + * @deprecated Use subtext_handlers.BytesPayload.$Properties instead. + */ + interface IBytesPayload extends subtext_handlers.BytesPayload.$Properties { + } + + /** Represents a BytesPayload. */ + class BytesPayload { + + /** + * Constructs a new BytesPayload. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.BytesPayload.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** BytesPayload data. */ + data: Uint8Array; + + /** + * Creates a new BytesPayload instance using the specified properties. + * @param [properties] Properties to set + * @returns BytesPayload instance + */ + static create(properties: subtext_handlers.BytesPayload.$Shape): subtext_handlers.BytesPayload & subtext_handlers.BytesPayload.$Shape; + static create(properties?: subtext_handlers.BytesPayload.$Properties): subtext_handlers.BytesPayload; + + /** + * Encodes the specified BytesPayload message. Does not implicitly {@link subtext_handlers.BytesPayload.verify|verify} messages. + * @param message BytesPayload message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.BytesPayload.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified BytesPayload message, length delimited. Does not implicitly {@link subtext_handlers.BytesPayload.verify|verify} messages. + * @param message BytesPayload message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.BytesPayload.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes a BytesPayload message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.BytesPayload & subtext_handlers.BytesPayload.$Shape} BytesPayload + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.BytesPayload & subtext_handlers.BytesPayload.$Shape; + + /** + * Decodes a BytesPayload message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.BytesPayload & subtext_handlers.BytesPayload.$Shape} BytesPayload + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.BytesPayload & subtext_handlers.BytesPayload.$Shape; + + /** + * Verifies a BytesPayload message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates a BytesPayload message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns BytesPayload + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.BytesPayload; + + /** + * Creates a plain object from a BytesPayload message. Also converts values to other types if specified. + * @param message BytesPayload + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.BytesPayload, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this BytesPayload to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for BytesPayload + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace BytesPayload { + + /** Properties of a BytesPayload. */ + interface $Properties { + + /** BytesPayload data */ + data?: (Uint8Array|null); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Shape of a BytesPayload. */ + type $Shape = subtext_handlers.BytesPayload.$Properties; + } + + /** + * Properties of a FileList. + * @deprecated Use subtext_handlers.FileList.$Properties instead. + */ + interface IFileList extends subtext_handlers.FileList.$Properties { + } + + /** Represents a FileList. */ + class FileList { + + /** + * Constructs a new FileList. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.FileList.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** FileList paths. */ + paths: string[]; + + /** + * Creates a new FileList instance using the specified properties. + * @param [properties] Properties to set + * @returns FileList instance + */ + static create(properties: subtext_handlers.FileList.$Shape): subtext_handlers.FileList & subtext_handlers.FileList.$Shape; + static create(properties?: subtext_handlers.FileList.$Properties): subtext_handlers.FileList; + + /** + * Encodes the specified FileList message. Does not implicitly {@link subtext_handlers.FileList.verify|verify} messages. + * @param message FileList message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.FileList.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified FileList message, length delimited. Does not implicitly {@link subtext_handlers.FileList.verify|verify} messages. + * @param message FileList message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.FileList.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes a FileList message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.FileList & subtext_handlers.FileList.$Shape} FileList + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.FileList & subtext_handlers.FileList.$Shape; + + /** + * Decodes a FileList message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.FileList & subtext_handlers.FileList.$Shape} FileList + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.FileList & subtext_handlers.FileList.$Shape; + + /** + * Verifies a FileList message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates a FileList message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns FileList + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.FileList; + + /** + * Creates a plain object from a FileList message. Also converts values to other types if specified. + * @param message FileList + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.FileList, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this FileList to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for FileList + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace FileList { + + /** Properties of a FileList. */ + interface $Properties { + + /** FileList paths */ + paths?: (string[]|null); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Shape of a FileList. */ + type $Shape = subtext_handlers.FileList.$Properties; + } + + /** + * Properties of a FileExistsResult. + * @deprecated Use subtext_handlers.FileExistsResult.$Properties instead. + */ + interface IFileExistsResult extends subtext_handlers.FileExistsResult.$Properties { + } + + /** Represents a FileExistsResult. */ + class FileExistsResult { + + /** + * Constructs a new FileExistsResult. + * @param [properties] Properties to set + */ + constructor(properties?: subtext_handlers.FileExistsResult.$Properties); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + + /** FileExistsResult exists. */ + exists: boolean; + + /** + * Creates a new FileExistsResult instance using the specified properties. + * @param [properties] Properties to set + * @returns FileExistsResult instance + */ + static create(properties: subtext_handlers.FileExistsResult.$Shape): subtext_handlers.FileExistsResult & subtext_handlers.FileExistsResult.$Shape; + static create(properties?: subtext_handlers.FileExistsResult.$Properties): subtext_handlers.FileExistsResult; + + /** + * Encodes the specified FileExistsResult message. Does not implicitly {@link subtext_handlers.FileExistsResult.verify|verify} messages. + * @param message FileExistsResult message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encode(message: subtext_handlers.FileExistsResult.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Encodes the specified FileExistsResult message, length delimited. Does not implicitly {@link subtext_handlers.FileExistsResult.verify|verify} messages. + * @param message FileExistsResult message or plain object to encode + * @param [writer] Writer to encode to + * @returns Writer + */ + static encodeDelimited(message: subtext_handlers.FileExistsResult.$Properties, writer?: $protobuf.Writer): $protobuf.Writer; + + /** + * Decodes a FileExistsResult message from the specified reader or buffer. + * @param reader Reader or buffer to decode from + * @param [length] Message length if known beforehand + * @returns {subtext_handlers.FileExistsResult & subtext_handlers.FileExistsResult.$Shape} FileExistsResult + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decode(reader: ($protobuf.Reader|Uint8Array), length?: number): subtext_handlers.FileExistsResult & subtext_handlers.FileExistsResult.$Shape; + + /** + * Decodes a FileExistsResult message from the specified reader or buffer, length delimited. + * @param reader Reader or buffer to decode from + * @returns {subtext_handlers.FileExistsResult & subtext_handlers.FileExistsResult.$Shape} FileExistsResult + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + static decodeDelimited(reader: ($protobuf.Reader|Uint8Array)): subtext_handlers.FileExistsResult & subtext_handlers.FileExistsResult.$Shape; + + /** + * Verifies a FileExistsResult message. + * @param message Plain object to verify + * @returns `null` if valid, otherwise the reason why it is not + */ + static verify(message: { [k: string]: any }): (string|null); + + /** + * Creates a FileExistsResult message from a plain object. Also converts values to their respective internal types. + * @param object Plain object + * @returns FileExistsResult + */ + static fromObject(object: { [k: string]: any }): subtext_handlers.FileExistsResult; + + /** + * Creates a plain object from a FileExistsResult message. Also converts values to other types if specified. + * @param message FileExistsResult + * @param [options] Conversion options + * @returns Plain object + */ + static toObject(message: subtext_handlers.FileExistsResult, options?: $protobuf.IConversionOptions): { [k: string]: any }; + + /** + * Converts this FileExistsResult to JSON. + * @returns JSON object + */ + toJSON(): { [k: string]: any }; + + /** + * Gets the type url for FileExistsResult + * @param [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns The type url + */ + static getTypeUrl(prefix?: string): string; + } + + namespace FileExistsResult { + + /** Properties of a FileExistsResult. */ + interface $Properties { + + /** FileExistsResult exists */ + exists?: (boolean|null); + + /** Unknown fields preserved while decoding */ + $unknowns?: Uint8Array[]; + } + + /** Shape of a FileExistsResult. */ + type $Shape = subtext_handlers.FileExistsResult.$Properties; + } +} diff --git a/src/subtext/proto.js b/src/subtext/proto.js new file mode 100644 index 0000000..e699c71 --- /dev/null +++ b/src/subtext/proto.js @@ -0,0 +1,4783 @@ +/*eslint-disable block-scoped-var, id-length, no-control-regex, no-magic-numbers, no-mixed-operators, no-prototype-builtins, no-redeclare, no-shadow, no-var, sort-vars, default-case, jsdoc/require-param*/ +import $protobuf from "protobufjs/minimal.js"; + +// Common aliases +const $Reader = $protobuf.Reader, $Writer = $protobuf.Writer, $util = $protobuf.util; + +// Exported root namespace +const $root = $protobuf.roots["default"] || ($protobuf.roots["default"] = {}); + +export const subtext_handlers = $root.subtext_handlers = (() => { + + /** + * Namespace subtext_handlers. + * @exports subtext_handlers + * @namespace + */ + const subtext_handlers = {}; + + subtext_handlers.Request = (function() { + + /** + * Properties of a Request. + * @typedef {Object} subtext_handlers.Request.$Properties + * @property {number|Long|null} [id] Request id + * @property {subtext_handlers.Ping.$Properties|null} [ping] Request ping + * @property {subtext_handlers.ApplyUpdateV2.$Properties|null} [applyUpdateV2] Request applyUpdateV2 + * @property {subtext_handlers.GetStateVector.$Properties|null} [getStateVector] Request getStateVector + * @property {subtext_handlers.GetFullState.$Properties|null} [getFullState] Request getFullState + * @property {subtext_handlers.ListFiles.$Properties|null} [listFiles] Request listFiles + * @property {subtext_handlers.FileExists.$Properties|null} [fileExists] Request fileExists + * @property {subtext_handlers.CreateFile.$Properties|null} [createFile] Request createFile + * @property {subtext_handlers.RenameFile.$Properties|null} [renameFile] Request renameFile + * @property {"ping"|"applyUpdateV2"|"getStateVector"|"getFullState"|"listFiles"|"fileExists"|"createFile"|"renameFile"} [content] Request content + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of a Request. + * @memberof subtext_handlers + * @interface IRequest + * @augments subtext_handlers.Request.$Properties + * @deprecated Use subtext_handlers.Request.$Properties instead. + */ + + /** + * Narrowed shape of a Request. + * @typedef {{ + * id?: number|Long|null; + * ping?: subtext_handlers.Ping.$Shape|null; + * applyUpdateV2?: subtext_handlers.ApplyUpdateV2.$Shape|null; + * getStateVector?: subtext_handlers.GetStateVector.$Shape|null; + * getFullState?: subtext_handlers.GetFullState.$Shape|null; + * listFiles?: subtext_handlers.ListFiles.$Shape|null; + * fileExists?: subtext_handlers.FileExists.$Shape|null; + * createFile?: subtext_handlers.CreateFile.$Shape|null; + * renameFile?: subtext_handlers.RenameFile.$Shape|null; + * $unknowns?: Array.; + * } & ( + * ({ content?: undefined; ping?: null; applyUpdateV2?: null; getStateVector?: null; getFullState?: null; listFiles?: null; fileExists?: null; createFile?: null; renameFile?: null }|{ content?: "ping"; ping: subtext_handlers.Ping.$Shape; applyUpdateV2?: null; getStateVector?: null; getFullState?: null; listFiles?: null; fileExists?: null; createFile?: null; renameFile?: null }|{ content?: "applyUpdateV2"; ping?: null; applyUpdateV2: subtext_handlers.ApplyUpdateV2.$Shape; getStateVector?: null; getFullState?: null; listFiles?: null; fileExists?: null; createFile?: null; renameFile?: null }|{ content?: "getStateVector"; ping?: null; applyUpdateV2?: null; getStateVector: subtext_handlers.GetStateVector.$Shape; getFullState?: null; listFiles?: null; fileExists?: null; createFile?: null; renameFile?: null }|{ content?: "getFullState"; ping?: null; applyUpdateV2?: null; getStateVector?: null; getFullState: subtext_handlers.GetFullState.$Shape; listFiles?: null; fileExists?: null; createFile?: null; renameFile?: null }|{ content?: "listFiles"; ping?: null; applyUpdateV2?: null; getStateVector?: null; getFullState?: null; listFiles: subtext_handlers.ListFiles.$Shape; fileExists?: null; createFile?: null; renameFile?: null }|{ content?: "fileExists"; ping?: null; applyUpdateV2?: null; getStateVector?: null; getFullState?: null; listFiles?: null; fileExists: subtext_handlers.FileExists.$Shape; createFile?: null; renameFile?: null }|{ content?: "createFile"; ping?: null; applyUpdateV2?: null; getStateVector?: null; getFullState?: null; listFiles?: null; fileExists?: null; createFile: subtext_handlers.CreateFile.$Shape; renameFile?: null }|{ content?: "renameFile"; ping?: null; applyUpdateV2?: null; getStateVector?: null; getFullState?: null; listFiles?: null; fileExists?: null; createFile?: null; renameFile: subtext_handlers.RenameFile.$Shape }) + * )} subtext_handlers.Request.$Shape + */ + + /** + * Constructs a new Request. + * @memberof subtext_handlers + * @classdesc Represents a Request. + * @constructor + * @param {subtext_handlers.Request.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function Request(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * Request id. + * @member {number|Long} id + * @memberof subtext_handlers.Request + * @instance + */ + Request.prototype.id = $util.Long ? $util.Long.fromBits(0,0,true) : 0; + + /** + * Request ping. + * @member {subtext_handlers.Ping.$Properties|null|undefined} ping + * @memberof subtext_handlers.Request + * @instance + */ + Request.prototype.ping = null; + + /** + * Request applyUpdateV2. + * @member {subtext_handlers.ApplyUpdateV2.$Properties|null|undefined} applyUpdateV2 + * @memberof subtext_handlers.Request + * @instance + */ + Request.prototype.applyUpdateV2 = null; + + /** + * Request getStateVector. + * @member {subtext_handlers.GetStateVector.$Properties|null|undefined} getStateVector + * @memberof subtext_handlers.Request + * @instance + */ + Request.prototype.getStateVector = null; + + /** + * Request getFullState. + * @member {subtext_handlers.GetFullState.$Properties|null|undefined} getFullState + * @memberof subtext_handlers.Request + * @instance + */ + Request.prototype.getFullState = null; + + /** + * Request listFiles. + * @member {subtext_handlers.ListFiles.$Properties|null|undefined} listFiles + * @memberof subtext_handlers.Request + * @instance + */ + Request.prototype.listFiles = null; + + /** + * Request fileExists. + * @member {subtext_handlers.FileExists.$Properties|null|undefined} fileExists + * @memberof subtext_handlers.Request + * @instance + */ + Request.prototype.fileExists = null; + + /** + * Request createFile. + * @member {subtext_handlers.CreateFile.$Properties|null|undefined} createFile + * @memberof subtext_handlers.Request + * @instance + */ + Request.prototype.createFile = null; + + /** + * Request renameFile. + * @member {subtext_handlers.RenameFile.$Properties|null|undefined} renameFile + * @memberof subtext_handlers.Request + * @instance + */ + Request.prototype.renameFile = null; + + // OneOf field names bound to virtual getters and setters + let $oneOfFields; + + /** + * Request content. + * @member {"ping"|"applyUpdateV2"|"getStateVector"|"getFullState"|"listFiles"|"fileExists"|"createFile"|"renameFile"|undefined} content + * @memberof subtext_handlers.Request + * @instance + */ + Object.defineProperty(Request.prototype, "content", { + get: $util.oneOfGetter($oneOfFields = ["ping", "applyUpdateV2", "getStateVector", "getFullState", "listFiles", "fileExists", "createFile", "renameFile"]), + set: $util.oneOfSetter($oneOfFields) + }); + + /** + * Creates a new Request instance using the specified properties. + * @function create + * @memberof subtext_handlers.Request + * @static + * @param {subtext_handlers.Request.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.Request} Request instance + * @type {{ + * (properties: subtext_handlers.Request.$Shape): subtext_handlers.Request & subtext_handlers.Request.$Shape; + * (properties?: subtext_handlers.Request.$Properties): subtext_handlers.Request; + * }} + */ + Request.create = function create(properties) { + return new Request(properties); + }; + + /** + * Encodes the specified Request message. Does not implicitly {@link subtext_handlers.Request.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.Request + * @static + * @param {subtext_handlers.Request.$Properties} message Request message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + Request.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.id != null && Object.hasOwnProperty.call(message, "id")) + writer.uint32(/* id 1, wireType 0 =*/8).uint64(message.id); + if (message.ping != null && Object.hasOwnProperty.call(message, "ping")) + $root.subtext_handlers.Ping.encode(message.ping, writer.uint32(/* id 2, wireType 2 =*/18).fork(), _depth + 1).ldelim(); + if (message.applyUpdateV2 != null && Object.hasOwnProperty.call(message, "applyUpdateV2")) + $root.subtext_handlers.ApplyUpdateV2.encode(message.applyUpdateV2, writer.uint32(/* id 3, wireType 2 =*/26).fork(), _depth + 1).ldelim(); + if (message.getStateVector != null && Object.hasOwnProperty.call(message, "getStateVector")) + $root.subtext_handlers.GetStateVector.encode(message.getStateVector, writer.uint32(/* id 4, wireType 2 =*/34).fork(), _depth + 1).ldelim(); + if (message.getFullState != null && Object.hasOwnProperty.call(message, "getFullState")) + $root.subtext_handlers.GetFullState.encode(message.getFullState, writer.uint32(/* id 5, wireType 2 =*/42).fork(), _depth + 1).ldelim(); + if (message.listFiles != null && Object.hasOwnProperty.call(message, "listFiles")) + $root.subtext_handlers.ListFiles.encode(message.listFiles, writer.uint32(/* id 6, wireType 2 =*/50).fork(), _depth + 1).ldelim(); + if (message.fileExists != null && Object.hasOwnProperty.call(message, "fileExists")) + $root.subtext_handlers.FileExists.encode(message.fileExists, writer.uint32(/* id 7, wireType 2 =*/58).fork(), _depth + 1).ldelim(); + if (message.createFile != null && Object.hasOwnProperty.call(message, "createFile")) + $root.subtext_handlers.CreateFile.encode(message.createFile, writer.uint32(/* id 8, wireType 2 =*/66).fork(), _depth + 1).ldelim(); + if (message.renameFile != null && Object.hasOwnProperty.call(message, "renameFile")) + $root.subtext_handlers.RenameFile.encode(message.renameFile, writer.uint32(/* id 9, wireType 2 =*/74).fork(), _depth + 1).ldelim(); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified Request message, length delimited. Does not implicitly {@link subtext_handlers.Request.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.Request + * @static + * @param {subtext_handlers.Request.$Properties} message Request message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + Request.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes a Request message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.Request + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.Request & subtext_handlers.Request.$Shape} Request + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + Request.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.Request(), value; + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + let wireType = tag & 7; + switch (tag >>>= 3) { + case 1: { + if (wireType !== 0) + break; + if (typeof (value = reader.uint64()) === "object" ? value.low || value.high : value !== 0) + message.id = value; + else + delete message.id; + continue; + } + case 2: { + if (wireType !== 2) + break; + message.ping = $root.subtext_handlers.Ping.decode(reader, reader.uint32(), undefined, _depth + 1, message.ping); + message.content = "ping"; + continue; + } + case 3: { + if (wireType !== 2) + break; + message.applyUpdateV2 = $root.subtext_handlers.ApplyUpdateV2.decode(reader, reader.uint32(), undefined, _depth + 1, message.applyUpdateV2); + message.content = "applyUpdateV2"; + continue; + } + case 4: { + if (wireType !== 2) + break; + message.getStateVector = $root.subtext_handlers.GetStateVector.decode(reader, reader.uint32(), undefined, _depth + 1, message.getStateVector); + message.content = "getStateVector"; + continue; + } + case 5: { + if (wireType !== 2) + break; + message.getFullState = $root.subtext_handlers.GetFullState.decode(reader, reader.uint32(), undefined, _depth + 1, message.getFullState); + message.content = "getFullState"; + continue; + } + case 6: { + if (wireType !== 2) + break; + message.listFiles = $root.subtext_handlers.ListFiles.decode(reader, reader.uint32(), undefined, _depth + 1, message.listFiles); + message.content = "listFiles"; + continue; + } + case 7: { + if (wireType !== 2) + break; + message.fileExists = $root.subtext_handlers.FileExists.decode(reader, reader.uint32(), undefined, _depth + 1, message.fileExists); + message.content = "fileExists"; + continue; + } + case 8: { + if (wireType !== 2) + break; + message.createFile = $root.subtext_handlers.CreateFile.decode(reader, reader.uint32(), undefined, _depth + 1, message.createFile); + message.content = "createFile"; + continue; + } + case 9: { + if (wireType !== 2) + break; + message.renameFile = $root.subtext_handlers.RenameFile.decode(reader, reader.uint32(), undefined, _depth + 1, message.renameFile); + message.content = "renameFile"; + continue; + } + } + reader.skipType(wireType, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes a Request message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.Request + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.Request & subtext_handlers.Request.$Shape} Request + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + Request.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies a Request message. + * @function verify + * @memberof subtext_handlers.Request + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + Request.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + let properties = {}; + if (message.id != null && message.hasOwnProperty("id")) + if (!$util.isInteger(message.id) && !(message.id && $util.isInteger(message.id.low) && $util.isInteger(message.id.high))) + return "id: integer|Long expected"; + if (message.ping != null && message.hasOwnProperty("ping")) { + properties.content = 1; + { + let error = $root.subtext_handlers.Ping.verify(message.ping, _depth + 1); + if (error) + return "ping." + error; + } + } + if (message.applyUpdateV2 != null && message.hasOwnProperty("applyUpdateV2")) { + if (properties.content === 1) + return "content: multiple values"; + properties.content = 1; + { + let error = $root.subtext_handlers.ApplyUpdateV2.verify(message.applyUpdateV2, _depth + 1); + if (error) + return "applyUpdateV2." + error; + } + } + if (message.getStateVector != null && message.hasOwnProperty("getStateVector")) { + if (properties.content === 1) + return "content: multiple values"; + properties.content = 1; + { + let error = $root.subtext_handlers.GetStateVector.verify(message.getStateVector, _depth + 1); + if (error) + return "getStateVector." + error; + } + } + if (message.getFullState != null && message.hasOwnProperty("getFullState")) { + if (properties.content === 1) + return "content: multiple values"; + properties.content = 1; + { + let error = $root.subtext_handlers.GetFullState.verify(message.getFullState, _depth + 1); + if (error) + return "getFullState." + error; + } + } + if (message.listFiles != null && message.hasOwnProperty("listFiles")) { + if (properties.content === 1) + return "content: multiple values"; + properties.content = 1; + { + let error = $root.subtext_handlers.ListFiles.verify(message.listFiles, _depth + 1); + if (error) + return "listFiles." + error; + } + } + if (message.fileExists != null && message.hasOwnProperty("fileExists")) { + if (properties.content === 1) + return "content: multiple values"; + properties.content = 1; + { + let error = $root.subtext_handlers.FileExists.verify(message.fileExists, _depth + 1); + if (error) + return "fileExists." + error; + } + } + if (message.createFile != null && message.hasOwnProperty("createFile")) { + if (properties.content === 1) + return "content: multiple values"; + properties.content = 1; + { + let error = $root.subtext_handlers.CreateFile.verify(message.createFile, _depth + 1); + if (error) + return "createFile." + error; + } + } + if (message.renameFile != null && message.hasOwnProperty("renameFile")) { + if (properties.content === 1) + return "content: multiple values"; + properties.content = 1; + { + let error = $root.subtext_handlers.RenameFile.verify(message.renameFile, _depth + 1); + if (error) + return "renameFile." + error; + } + } + return null; + }; + + /** + * Creates a Request message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.Request + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.Request} Request + */ + Request.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.Request) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let message = new $root.subtext_handlers.Request(); + if (object.id != null) + if (typeof object.id === "object" ? object.id.low || object.id.high : Number(object.id) !== 0) + if ($util.Long) + message.id = $util.Long.fromValue(object.id, true); + else if (typeof object.id === "string") + message.id = parseInt(object.id, 10); + else if (typeof object.id === "number") + message.id = object.id; + else if (typeof object.id === "object") + message.id = new $util.LongBits(object.id.low >>> 0, object.id.high >>> 0).toNumber(true); + if (object.ping != null) { + if (typeof object.ping !== "object") + throw TypeError(".subtext_handlers.Request.ping: object expected"); + message.ping = $root.subtext_handlers.Ping.fromObject(object.ping, _depth + 1); + } + if (object.applyUpdateV2 != null) { + if (typeof object.applyUpdateV2 !== "object") + throw TypeError(".subtext_handlers.Request.applyUpdateV2: object expected"); + message.applyUpdateV2 = $root.subtext_handlers.ApplyUpdateV2.fromObject(object.applyUpdateV2, _depth + 1); + } + if (object.getStateVector != null) { + if (typeof object.getStateVector !== "object") + throw TypeError(".subtext_handlers.Request.getStateVector: object expected"); + message.getStateVector = $root.subtext_handlers.GetStateVector.fromObject(object.getStateVector, _depth + 1); + } + if (object.getFullState != null) { + if (typeof object.getFullState !== "object") + throw TypeError(".subtext_handlers.Request.getFullState: object expected"); + message.getFullState = $root.subtext_handlers.GetFullState.fromObject(object.getFullState, _depth + 1); + } + if (object.listFiles != null) { + if (typeof object.listFiles !== "object") + throw TypeError(".subtext_handlers.Request.listFiles: object expected"); + message.listFiles = $root.subtext_handlers.ListFiles.fromObject(object.listFiles, _depth + 1); + } + if (object.fileExists != null) { + if (typeof object.fileExists !== "object") + throw TypeError(".subtext_handlers.Request.fileExists: object expected"); + message.fileExists = $root.subtext_handlers.FileExists.fromObject(object.fileExists, _depth + 1); + } + if (object.createFile != null) { + if (typeof object.createFile !== "object") + throw TypeError(".subtext_handlers.Request.createFile: object expected"); + message.createFile = $root.subtext_handlers.CreateFile.fromObject(object.createFile, _depth + 1); + } + if (object.renameFile != null) { + if (typeof object.renameFile !== "object") + throw TypeError(".subtext_handlers.Request.renameFile: object expected"); + message.renameFile = $root.subtext_handlers.RenameFile.fromObject(object.renameFile, _depth + 1); + } + return message; + }; + + /** + * Creates a plain object from a Request message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.Request + * @static + * @param {subtext_handlers.Request} message Request + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + Request.toObject = function toObject(message, options, _depth) { + if (!options) + options = {}; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let object = {}; + if (options.defaults) + if ($util.Long) { + let long = new $util.Long(0, 0, true); + object.id = options.longs === String ? long.toString() : options.longs === Number ? long.toNumber() : typeof BigInt !== "undefined" && options.longs === BigInt ? long.toBigInt() : long; + } else + object.id = options.longs === String ? "0" : typeof BigInt !== "undefined" && options.longs === BigInt ? BigInt("0") : 0; + if (message.id != null && message.hasOwnProperty("id")) + if (typeof BigInt !== "undefined" && options.longs === BigInt) + object.id = typeof message.id === "number" ? BigInt(message.id) : $util.Long.fromBits(message.id.low >>> 0, message.id.high >>> 0, true).toBigInt(); + else if (typeof message.id === "number") + object.id = options.longs === String ? String(message.id) : message.id; + else + object.id = options.longs === String ? $util.Long.prototype.toString.call(message.id) : options.longs === Number ? new $util.LongBits(message.id.low >>> 0, message.id.high >>> 0).toNumber(true) : message.id; + if (message.ping != null && message.hasOwnProperty("ping")) { + object.ping = $root.subtext_handlers.Ping.toObject(message.ping, options, _depth + 1); + if (options.oneofs) + object.content = "ping"; + } + if (message.applyUpdateV2 != null && message.hasOwnProperty("applyUpdateV2")) { + object.applyUpdateV2 = $root.subtext_handlers.ApplyUpdateV2.toObject(message.applyUpdateV2, options, _depth + 1); + if (options.oneofs) + object.content = "applyUpdateV2"; + } + if (message.getStateVector != null && message.hasOwnProperty("getStateVector")) { + object.getStateVector = $root.subtext_handlers.GetStateVector.toObject(message.getStateVector, options, _depth + 1); + if (options.oneofs) + object.content = "getStateVector"; + } + if (message.getFullState != null && message.hasOwnProperty("getFullState")) { + object.getFullState = $root.subtext_handlers.GetFullState.toObject(message.getFullState, options, _depth + 1); + if (options.oneofs) + object.content = "getFullState"; + } + if (message.listFiles != null && message.hasOwnProperty("listFiles")) { + object.listFiles = $root.subtext_handlers.ListFiles.toObject(message.listFiles, options, _depth + 1); + if (options.oneofs) + object.content = "listFiles"; + } + if (message.fileExists != null && message.hasOwnProperty("fileExists")) { + object.fileExists = $root.subtext_handlers.FileExists.toObject(message.fileExists, options, _depth + 1); + if (options.oneofs) + object.content = "fileExists"; + } + if (message.createFile != null && message.hasOwnProperty("createFile")) { + object.createFile = $root.subtext_handlers.CreateFile.toObject(message.createFile, options, _depth + 1); + if (options.oneofs) + object.content = "createFile"; + } + if (message.renameFile != null && message.hasOwnProperty("renameFile")) { + object.renameFile = $root.subtext_handlers.RenameFile.toObject(message.renameFile, options, _depth + 1); + if (options.oneofs) + object.content = "renameFile"; + } + return object; + }; + + /** + * Converts this Request to JSON. + * @function toJSON + * @memberof subtext_handlers.Request + * @instance + * @returns {Object.} JSON object + */ + Request.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for Request + * @function getTypeUrl + * @memberof subtext_handlers.Request + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + Request.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.Request"; + }; + + return Request; + })(); + + subtext_handlers.Ping = (function() { + + /** + * Properties of a Ping. + * @typedef {Object} subtext_handlers.Ping.$Properties + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of a Ping. + * @memberof subtext_handlers + * @interface IPing + * @augments subtext_handlers.Ping.$Properties + * @deprecated Use subtext_handlers.Ping.$Properties instead. + */ + + /** + * Shape of a Ping. + * @typedef {subtext_handlers.Ping.$Properties} subtext_handlers.Ping.$Shape + */ + + /** + * Constructs a new Ping. + * @memberof subtext_handlers + * @classdesc Represents a Ping. + * @constructor + * @param {subtext_handlers.Ping.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function Ping(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * Creates a new Ping instance using the specified properties. + * @function create + * @memberof subtext_handlers.Ping + * @static + * @param {subtext_handlers.Ping.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.Ping} Ping instance + * @type {{ + * (properties: subtext_handlers.Ping.$Shape): subtext_handlers.Ping & subtext_handlers.Ping.$Shape; + * (properties?: subtext_handlers.Ping.$Properties): subtext_handlers.Ping; + * }} + */ + Ping.create = function create(properties) { + return new Ping(properties); + }; + + /** + * Encodes the specified Ping message. Does not implicitly {@link subtext_handlers.Ping.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.Ping + * @static + * @param {subtext_handlers.Ping.$Properties} message Ping message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + Ping.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified Ping message, length delimited. Does not implicitly {@link subtext_handlers.Ping.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.Ping + * @static + * @param {subtext_handlers.Ping.$Properties} message Ping message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + Ping.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes a Ping message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.Ping + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.Ping & subtext_handlers.Ping.$Shape} Ping + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + Ping.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.Ping(); + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + reader.skipType(tag & 7, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes a Ping message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.Ping + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.Ping & subtext_handlers.Ping.$Shape} Ping + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + Ping.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies a Ping message. + * @function verify + * @memberof subtext_handlers.Ping + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + Ping.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + return null; + }; + + /** + * Creates a Ping message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.Ping + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.Ping} Ping + */ + Ping.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.Ping) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + return new $root.subtext_handlers.Ping(); + }; + + /** + * Creates a plain object from a Ping message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.Ping + * @static + * @param {subtext_handlers.Ping} message Ping + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + Ping.toObject = function toObject() { + return {}; + }; + + /** + * Converts this Ping to JSON. + * @function toJSON + * @memberof subtext_handlers.Ping + * @instance + * @returns {Object.} JSON object + */ + Ping.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for Ping + * @function getTypeUrl + * @memberof subtext_handlers.Ping + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + Ping.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.Ping"; + }; + + return Ping; + })(); + + subtext_handlers.ApplyUpdateV2 = (function() { + + /** + * Properties of an ApplyUpdateV2. + * @typedef {Object} subtext_handlers.ApplyUpdateV2.$Properties + * @property {string|null} [vaultPath] ApplyUpdateV2 vaultPath + * @property {Uint8Array|null} [update] ApplyUpdateV2 update + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of an ApplyUpdateV2. + * @memberof subtext_handlers + * @interface IApplyUpdateV2 + * @augments subtext_handlers.ApplyUpdateV2.$Properties + * @deprecated Use subtext_handlers.ApplyUpdateV2.$Properties instead. + */ + + /** + * Shape of an ApplyUpdateV2. + * @typedef {subtext_handlers.ApplyUpdateV2.$Properties} subtext_handlers.ApplyUpdateV2.$Shape + */ + + /** + * Constructs a new ApplyUpdateV2. + * @memberof subtext_handlers + * @classdesc Represents an ApplyUpdateV2. + * @constructor + * @param {subtext_handlers.ApplyUpdateV2.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function ApplyUpdateV2(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * ApplyUpdateV2 vaultPath. + * @member {string} vaultPath + * @memberof subtext_handlers.ApplyUpdateV2 + * @instance + */ + ApplyUpdateV2.prototype.vaultPath = ""; + + /** + * ApplyUpdateV2 update. + * @member {Uint8Array} update + * @memberof subtext_handlers.ApplyUpdateV2 + * @instance + */ + ApplyUpdateV2.prototype.update = $util.newBuffer([]); + + /** + * Creates a new ApplyUpdateV2 instance using the specified properties. + * @function create + * @memberof subtext_handlers.ApplyUpdateV2 + * @static + * @param {subtext_handlers.ApplyUpdateV2.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.ApplyUpdateV2} ApplyUpdateV2 instance + * @type {{ + * (properties: subtext_handlers.ApplyUpdateV2.$Shape): subtext_handlers.ApplyUpdateV2 & subtext_handlers.ApplyUpdateV2.$Shape; + * (properties?: subtext_handlers.ApplyUpdateV2.$Properties): subtext_handlers.ApplyUpdateV2; + * }} + */ + ApplyUpdateV2.create = function create(properties) { + return new ApplyUpdateV2(properties); + }; + + /** + * Encodes the specified ApplyUpdateV2 message. Does not implicitly {@link subtext_handlers.ApplyUpdateV2.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.ApplyUpdateV2 + * @static + * @param {subtext_handlers.ApplyUpdateV2.$Properties} message ApplyUpdateV2 message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + ApplyUpdateV2.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.vaultPath != null && Object.hasOwnProperty.call(message, "vaultPath")) + writer.uint32(/* id 1, wireType 2 =*/10).string(message.vaultPath); + if (message.update != null && Object.hasOwnProperty.call(message, "update")) + writer.uint32(/* id 2, wireType 2 =*/18).bytes(message.update); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified ApplyUpdateV2 message, length delimited. Does not implicitly {@link subtext_handlers.ApplyUpdateV2.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.ApplyUpdateV2 + * @static + * @param {subtext_handlers.ApplyUpdateV2.$Properties} message ApplyUpdateV2 message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + ApplyUpdateV2.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes an ApplyUpdateV2 message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.ApplyUpdateV2 + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.ApplyUpdateV2 & subtext_handlers.ApplyUpdateV2.$Shape} ApplyUpdateV2 + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + ApplyUpdateV2.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.ApplyUpdateV2(), value; + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + let wireType = tag & 7; + switch (tag >>>= 3) { + case 1: { + if (wireType !== 2) + break; + if ((value = reader.string()).length) + message.vaultPath = value; + else + delete message.vaultPath; + continue; + } + case 2: { + if (wireType !== 2) + break; + if ((value = reader.bytes()).length) + message.update = value; + else + delete message.update; + continue; + } + } + reader.skipType(wireType, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes an ApplyUpdateV2 message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.ApplyUpdateV2 + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.ApplyUpdateV2 & subtext_handlers.ApplyUpdateV2.$Shape} ApplyUpdateV2 + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + ApplyUpdateV2.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies an ApplyUpdateV2 message. + * @function verify + * @memberof subtext_handlers.ApplyUpdateV2 + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + ApplyUpdateV2.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + if (message.vaultPath != null && message.hasOwnProperty("vaultPath")) + if (!$util.isString(message.vaultPath)) + return "vaultPath: string expected"; + if (message.update != null && message.hasOwnProperty("update")) + if (!(message.update && typeof message.update.length === "number" || $util.isString(message.update))) + return "update: buffer expected"; + return null; + }; + + /** + * Creates an ApplyUpdateV2 message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.ApplyUpdateV2 + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.ApplyUpdateV2} ApplyUpdateV2 + */ + ApplyUpdateV2.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.ApplyUpdateV2) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let message = new $root.subtext_handlers.ApplyUpdateV2(); + if (object.vaultPath != null) + if (typeof object.vaultPath !== "string" || object.vaultPath.length) + message.vaultPath = String(object.vaultPath); + if (object.update != null) + if (object.update.length) + if (typeof object.update === "string") + $util.base64.decode(object.update, message.update = $util.newBuffer($util.base64.length(object.update)), 0); + else if (object.update.length >= 0) + message.update = object.update; + return message; + }; + + /** + * Creates a plain object from an ApplyUpdateV2 message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.ApplyUpdateV2 + * @static + * @param {subtext_handlers.ApplyUpdateV2} message ApplyUpdateV2 + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + ApplyUpdateV2.toObject = function toObject(message, options, _depth) { + if (!options) + options = {}; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let object = {}; + if (options.defaults) { + object.vaultPath = ""; + if (options.bytes === String) + object.update = ""; + else { + object.update = []; + if (options.bytes !== Array) + object.update = $util.newBuffer(object.update); + } + } + if (message.vaultPath != null && message.hasOwnProperty("vaultPath")) + object.vaultPath = message.vaultPath; + if (message.update != null && message.hasOwnProperty("update")) + object.update = options.bytes === String ? $util.base64.encode(message.update, 0, message.update.length) : options.bytes === Array ? Array.prototype.slice.call(message.update) : message.update; + return object; + }; + + /** + * Converts this ApplyUpdateV2 to JSON. + * @function toJSON + * @memberof subtext_handlers.ApplyUpdateV2 + * @instance + * @returns {Object.} JSON object + */ + ApplyUpdateV2.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for ApplyUpdateV2 + * @function getTypeUrl + * @memberof subtext_handlers.ApplyUpdateV2 + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + ApplyUpdateV2.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.ApplyUpdateV2"; + }; + + return ApplyUpdateV2; + })(); + + subtext_handlers.GetStateVector = (function() { + + /** + * Properties of a GetStateVector. + * @typedef {Object} subtext_handlers.GetStateVector.$Properties + * @property {string|null} [vaultPath] GetStateVector vaultPath + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of a GetStateVector. + * @memberof subtext_handlers + * @interface IGetStateVector + * @augments subtext_handlers.GetStateVector.$Properties + * @deprecated Use subtext_handlers.GetStateVector.$Properties instead. + */ + + /** + * Shape of a GetStateVector. + * @typedef {subtext_handlers.GetStateVector.$Properties} subtext_handlers.GetStateVector.$Shape + */ + + /** + * Constructs a new GetStateVector. + * @memberof subtext_handlers + * @classdesc Represents a GetStateVector. + * @constructor + * @param {subtext_handlers.GetStateVector.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function GetStateVector(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * GetStateVector vaultPath. + * @member {string} vaultPath + * @memberof subtext_handlers.GetStateVector + * @instance + */ + GetStateVector.prototype.vaultPath = ""; + + /** + * Creates a new GetStateVector instance using the specified properties. + * @function create + * @memberof subtext_handlers.GetStateVector + * @static + * @param {subtext_handlers.GetStateVector.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.GetStateVector} GetStateVector instance + * @type {{ + * (properties: subtext_handlers.GetStateVector.$Shape): subtext_handlers.GetStateVector & subtext_handlers.GetStateVector.$Shape; + * (properties?: subtext_handlers.GetStateVector.$Properties): subtext_handlers.GetStateVector; + * }} + */ + GetStateVector.create = function create(properties) { + return new GetStateVector(properties); + }; + + /** + * Encodes the specified GetStateVector message. Does not implicitly {@link subtext_handlers.GetStateVector.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.GetStateVector + * @static + * @param {subtext_handlers.GetStateVector.$Properties} message GetStateVector message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + GetStateVector.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.vaultPath != null && Object.hasOwnProperty.call(message, "vaultPath")) + writer.uint32(/* id 1, wireType 2 =*/10).string(message.vaultPath); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified GetStateVector message, length delimited. Does not implicitly {@link subtext_handlers.GetStateVector.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.GetStateVector + * @static + * @param {subtext_handlers.GetStateVector.$Properties} message GetStateVector message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + GetStateVector.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes a GetStateVector message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.GetStateVector + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.GetStateVector & subtext_handlers.GetStateVector.$Shape} GetStateVector + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + GetStateVector.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.GetStateVector(), value; + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + let wireType = tag & 7; + switch (tag >>>= 3) { + case 1: { + if (wireType !== 2) + break; + if ((value = reader.string()).length) + message.vaultPath = value; + else + delete message.vaultPath; + continue; + } + } + reader.skipType(wireType, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes a GetStateVector message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.GetStateVector + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.GetStateVector & subtext_handlers.GetStateVector.$Shape} GetStateVector + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + GetStateVector.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies a GetStateVector message. + * @function verify + * @memberof subtext_handlers.GetStateVector + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + GetStateVector.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + if (message.vaultPath != null && message.hasOwnProperty("vaultPath")) + if (!$util.isString(message.vaultPath)) + return "vaultPath: string expected"; + return null; + }; + + /** + * Creates a GetStateVector message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.GetStateVector + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.GetStateVector} GetStateVector + */ + GetStateVector.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.GetStateVector) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let message = new $root.subtext_handlers.GetStateVector(); + if (object.vaultPath != null) + if (typeof object.vaultPath !== "string" || object.vaultPath.length) + message.vaultPath = String(object.vaultPath); + return message; + }; + + /** + * Creates a plain object from a GetStateVector message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.GetStateVector + * @static + * @param {subtext_handlers.GetStateVector} message GetStateVector + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + GetStateVector.toObject = function toObject(message, options, _depth) { + if (!options) + options = {}; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let object = {}; + if (options.defaults) + object.vaultPath = ""; + if (message.vaultPath != null && message.hasOwnProperty("vaultPath")) + object.vaultPath = message.vaultPath; + return object; + }; + + /** + * Converts this GetStateVector to JSON. + * @function toJSON + * @memberof subtext_handlers.GetStateVector + * @instance + * @returns {Object.} JSON object + */ + GetStateVector.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for GetStateVector + * @function getTypeUrl + * @memberof subtext_handlers.GetStateVector + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + GetStateVector.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.GetStateVector"; + }; + + return GetStateVector; + })(); + + subtext_handlers.GetFullState = (function() { + + /** + * Properties of a GetFullState. + * @typedef {Object} subtext_handlers.GetFullState.$Properties + * @property {string|null} [vaultPath] GetFullState vaultPath + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of a GetFullState. + * @memberof subtext_handlers + * @interface IGetFullState + * @augments subtext_handlers.GetFullState.$Properties + * @deprecated Use subtext_handlers.GetFullState.$Properties instead. + */ + + /** + * Shape of a GetFullState. + * @typedef {subtext_handlers.GetFullState.$Properties} subtext_handlers.GetFullState.$Shape + */ + + /** + * Constructs a new GetFullState. + * @memberof subtext_handlers + * @classdesc Represents a GetFullState. + * @constructor + * @param {subtext_handlers.GetFullState.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function GetFullState(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * GetFullState vaultPath. + * @member {string} vaultPath + * @memberof subtext_handlers.GetFullState + * @instance + */ + GetFullState.prototype.vaultPath = ""; + + /** + * Creates a new GetFullState instance using the specified properties. + * @function create + * @memberof subtext_handlers.GetFullState + * @static + * @param {subtext_handlers.GetFullState.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.GetFullState} GetFullState instance + * @type {{ + * (properties: subtext_handlers.GetFullState.$Shape): subtext_handlers.GetFullState & subtext_handlers.GetFullState.$Shape; + * (properties?: subtext_handlers.GetFullState.$Properties): subtext_handlers.GetFullState; + * }} + */ + GetFullState.create = function create(properties) { + return new GetFullState(properties); + }; + + /** + * Encodes the specified GetFullState message. Does not implicitly {@link subtext_handlers.GetFullState.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.GetFullState + * @static + * @param {subtext_handlers.GetFullState.$Properties} message GetFullState message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + GetFullState.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.vaultPath != null && Object.hasOwnProperty.call(message, "vaultPath")) + writer.uint32(/* id 1, wireType 2 =*/10).string(message.vaultPath); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified GetFullState message, length delimited. Does not implicitly {@link subtext_handlers.GetFullState.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.GetFullState + * @static + * @param {subtext_handlers.GetFullState.$Properties} message GetFullState message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + GetFullState.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes a GetFullState message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.GetFullState + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.GetFullState & subtext_handlers.GetFullState.$Shape} GetFullState + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + GetFullState.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.GetFullState(), value; + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + let wireType = tag & 7; + switch (tag >>>= 3) { + case 1: { + if (wireType !== 2) + break; + if ((value = reader.string()).length) + message.vaultPath = value; + else + delete message.vaultPath; + continue; + } + } + reader.skipType(wireType, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes a GetFullState message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.GetFullState + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.GetFullState & subtext_handlers.GetFullState.$Shape} GetFullState + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + GetFullState.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies a GetFullState message. + * @function verify + * @memberof subtext_handlers.GetFullState + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + GetFullState.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + if (message.vaultPath != null && message.hasOwnProperty("vaultPath")) + if (!$util.isString(message.vaultPath)) + return "vaultPath: string expected"; + return null; + }; + + /** + * Creates a GetFullState message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.GetFullState + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.GetFullState} GetFullState + */ + GetFullState.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.GetFullState) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let message = new $root.subtext_handlers.GetFullState(); + if (object.vaultPath != null) + if (typeof object.vaultPath !== "string" || object.vaultPath.length) + message.vaultPath = String(object.vaultPath); + return message; + }; + + /** + * Creates a plain object from a GetFullState message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.GetFullState + * @static + * @param {subtext_handlers.GetFullState} message GetFullState + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + GetFullState.toObject = function toObject(message, options, _depth) { + if (!options) + options = {}; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let object = {}; + if (options.defaults) + object.vaultPath = ""; + if (message.vaultPath != null && message.hasOwnProperty("vaultPath")) + object.vaultPath = message.vaultPath; + return object; + }; + + /** + * Converts this GetFullState to JSON. + * @function toJSON + * @memberof subtext_handlers.GetFullState + * @instance + * @returns {Object.} JSON object + */ + GetFullState.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for GetFullState + * @function getTypeUrl + * @memberof subtext_handlers.GetFullState + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + GetFullState.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.GetFullState"; + }; + + return GetFullState; + })(); + + subtext_handlers.ListFiles = (function() { + + /** + * Properties of a ListFiles. + * @typedef {Object} subtext_handlers.ListFiles.$Properties + * @property {string|null} [prefix] ListFiles prefix + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of a ListFiles. + * @memberof subtext_handlers + * @interface IListFiles + * @augments subtext_handlers.ListFiles.$Properties + * @deprecated Use subtext_handlers.ListFiles.$Properties instead. + */ + + /** + * Shape of a ListFiles. + * @typedef {subtext_handlers.ListFiles.$Properties} subtext_handlers.ListFiles.$Shape + */ + + /** + * Constructs a new ListFiles. + * @memberof subtext_handlers + * @classdesc Represents a ListFiles. + * @constructor + * @param {subtext_handlers.ListFiles.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function ListFiles(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * ListFiles prefix. + * @member {string} prefix + * @memberof subtext_handlers.ListFiles + * @instance + */ + ListFiles.prototype.prefix = ""; + + /** + * Creates a new ListFiles instance using the specified properties. + * @function create + * @memberof subtext_handlers.ListFiles + * @static + * @param {subtext_handlers.ListFiles.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.ListFiles} ListFiles instance + * @type {{ + * (properties: subtext_handlers.ListFiles.$Shape): subtext_handlers.ListFiles & subtext_handlers.ListFiles.$Shape; + * (properties?: subtext_handlers.ListFiles.$Properties): subtext_handlers.ListFiles; + * }} + */ + ListFiles.create = function create(properties) { + return new ListFiles(properties); + }; + + /** + * Encodes the specified ListFiles message. Does not implicitly {@link subtext_handlers.ListFiles.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.ListFiles + * @static + * @param {subtext_handlers.ListFiles.$Properties} message ListFiles message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + ListFiles.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.prefix != null && Object.hasOwnProperty.call(message, "prefix")) + writer.uint32(/* id 1, wireType 2 =*/10).string(message.prefix); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified ListFiles message, length delimited. Does not implicitly {@link subtext_handlers.ListFiles.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.ListFiles + * @static + * @param {subtext_handlers.ListFiles.$Properties} message ListFiles message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + ListFiles.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes a ListFiles message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.ListFiles + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.ListFiles & subtext_handlers.ListFiles.$Shape} ListFiles + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + ListFiles.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.ListFiles(), value; + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + let wireType = tag & 7; + switch (tag >>>= 3) { + case 1: { + if (wireType !== 2) + break; + if ((value = reader.string()).length) + message.prefix = value; + else + delete message.prefix; + continue; + } + } + reader.skipType(wireType, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes a ListFiles message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.ListFiles + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.ListFiles & subtext_handlers.ListFiles.$Shape} ListFiles + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + ListFiles.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies a ListFiles message. + * @function verify + * @memberof subtext_handlers.ListFiles + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + ListFiles.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + if (message.prefix != null && message.hasOwnProperty("prefix")) + if (!$util.isString(message.prefix)) + return "prefix: string expected"; + return null; + }; + + /** + * Creates a ListFiles message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.ListFiles + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.ListFiles} ListFiles + */ + ListFiles.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.ListFiles) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let message = new $root.subtext_handlers.ListFiles(); + if (object.prefix != null) + if (typeof object.prefix !== "string" || object.prefix.length) + message.prefix = String(object.prefix); + return message; + }; + + /** + * Creates a plain object from a ListFiles message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.ListFiles + * @static + * @param {subtext_handlers.ListFiles} message ListFiles + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + ListFiles.toObject = function toObject(message, options, _depth) { + if (!options) + options = {}; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let object = {}; + if (options.defaults) + object.prefix = ""; + if (message.prefix != null && message.hasOwnProperty("prefix")) + object.prefix = message.prefix; + return object; + }; + + /** + * Converts this ListFiles to JSON. + * @function toJSON + * @memberof subtext_handlers.ListFiles + * @instance + * @returns {Object.} JSON object + */ + ListFiles.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for ListFiles + * @function getTypeUrl + * @memberof subtext_handlers.ListFiles + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + ListFiles.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.ListFiles"; + }; + + return ListFiles; + })(); + + subtext_handlers.FileExists = (function() { + + /** + * Properties of a FileExists. + * @typedef {Object} subtext_handlers.FileExists.$Properties + * @property {string|null} [vaultPath] FileExists vaultPath + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of a FileExists. + * @memberof subtext_handlers + * @interface IFileExists + * @augments subtext_handlers.FileExists.$Properties + * @deprecated Use subtext_handlers.FileExists.$Properties instead. + */ + + /** + * Shape of a FileExists. + * @typedef {subtext_handlers.FileExists.$Properties} subtext_handlers.FileExists.$Shape + */ + + /** + * Constructs a new FileExists. + * @memberof subtext_handlers + * @classdesc Represents a FileExists. + * @constructor + * @param {subtext_handlers.FileExists.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function FileExists(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * FileExists vaultPath. + * @member {string} vaultPath + * @memberof subtext_handlers.FileExists + * @instance + */ + FileExists.prototype.vaultPath = ""; + + /** + * Creates a new FileExists instance using the specified properties. + * @function create + * @memberof subtext_handlers.FileExists + * @static + * @param {subtext_handlers.FileExists.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.FileExists} FileExists instance + * @type {{ + * (properties: subtext_handlers.FileExists.$Shape): subtext_handlers.FileExists & subtext_handlers.FileExists.$Shape; + * (properties?: subtext_handlers.FileExists.$Properties): subtext_handlers.FileExists; + * }} + */ + FileExists.create = function create(properties) { + return new FileExists(properties); + }; + + /** + * Encodes the specified FileExists message. Does not implicitly {@link subtext_handlers.FileExists.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.FileExists + * @static + * @param {subtext_handlers.FileExists.$Properties} message FileExists message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + FileExists.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.vaultPath != null && Object.hasOwnProperty.call(message, "vaultPath")) + writer.uint32(/* id 1, wireType 2 =*/10).string(message.vaultPath); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified FileExists message, length delimited. Does not implicitly {@link subtext_handlers.FileExists.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.FileExists + * @static + * @param {subtext_handlers.FileExists.$Properties} message FileExists message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + FileExists.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes a FileExists message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.FileExists + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.FileExists & subtext_handlers.FileExists.$Shape} FileExists + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + FileExists.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.FileExists(), value; + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + let wireType = tag & 7; + switch (tag >>>= 3) { + case 1: { + if (wireType !== 2) + break; + if ((value = reader.string()).length) + message.vaultPath = value; + else + delete message.vaultPath; + continue; + } + } + reader.skipType(wireType, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes a FileExists message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.FileExists + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.FileExists & subtext_handlers.FileExists.$Shape} FileExists + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + FileExists.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies a FileExists message. + * @function verify + * @memberof subtext_handlers.FileExists + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + FileExists.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + if (message.vaultPath != null && message.hasOwnProperty("vaultPath")) + if (!$util.isString(message.vaultPath)) + return "vaultPath: string expected"; + return null; + }; + + /** + * Creates a FileExists message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.FileExists + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.FileExists} FileExists + */ + FileExists.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.FileExists) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let message = new $root.subtext_handlers.FileExists(); + if (object.vaultPath != null) + if (typeof object.vaultPath !== "string" || object.vaultPath.length) + message.vaultPath = String(object.vaultPath); + return message; + }; + + /** + * Creates a plain object from a FileExists message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.FileExists + * @static + * @param {subtext_handlers.FileExists} message FileExists + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + FileExists.toObject = function toObject(message, options, _depth) { + if (!options) + options = {}; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let object = {}; + if (options.defaults) + object.vaultPath = ""; + if (message.vaultPath != null && message.hasOwnProperty("vaultPath")) + object.vaultPath = message.vaultPath; + return object; + }; + + /** + * Converts this FileExists to JSON. + * @function toJSON + * @memberof subtext_handlers.FileExists + * @instance + * @returns {Object.} JSON object + */ + FileExists.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for FileExists + * @function getTypeUrl + * @memberof subtext_handlers.FileExists + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + FileExists.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.FileExists"; + }; + + return FileExists; + })(); + + subtext_handlers.CreateFile = (function() { + + /** + * Properties of a CreateFile. + * @typedef {Object} subtext_handlers.CreateFile.$Properties + * @property {string|null} [vaultPath] CreateFile vaultPath + * @property {Uint8Array|null} [initialState] CreateFile initialState + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of a CreateFile. + * @memberof subtext_handlers + * @interface ICreateFile + * @augments subtext_handlers.CreateFile.$Properties + * @deprecated Use subtext_handlers.CreateFile.$Properties instead. + */ + + /** + * Shape of a CreateFile. + * @typedef {subtext_handlers.CreateFile.$Properties} subtext_handlers.CreateFile.$Shape + */ + + /** + * Constructs a new CreateFile. + * @memberof subtext_handlers + * @classdesc Represents a CreateFile. + * @constructor + * @param {subtext_handlers.CreateFile.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function CreateFile(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * CreateFile vaultPath. + * @member {string} vaultPath + * @memberof subtext_handlers.CreateFile + * @instance + */ + CreateFile.prototype.vaultPath = ""; + + /** + * CreateFile initialState. + * @member {Uint8Array} initialState + * @memberof subtext_handlers.CreateFile + * @instance + */ + CreateFile.prototype.initialState = $util.newBuffer([]); + + /** + * Creates a new CreateFile instance using the specified properties. + * @function create + * @memberof subtext_handlers.CreateFile + * @static + * @param {subtext_handlers.CreateFile.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.CreateFile} CreateFile instance + * @type {{ + * (properties: subtext_handlers.CreateFile.$Shape): subtext_handlers.CreateFile & subtext_handlers.CreateFile.$Shape; + * (properties?: subtext_handlers.CreateFile.$Properties): subtext_handlers.CreateFile; + * }} + */ + CreateFile.create = function create(properties) { + return new CreateFile(properties); + }; + + /** + * Encodes the specified CreateFile message. Does not implicitly {@link subtext_handlers.CreateFile.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.CreateFile + * @static + * @param {subtext_handlers.CreateFile.$Properties} message CreateFile message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + CreateFile.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.vaultPath != null && Object.hasOwnProperty.call(message, "vaultPath")) + writer.uint32(/* id 1, wireType 2 =*/10).string(message.vaultPath); + if (message.initialState != null && Object.hasOwnProperty.call(message, "initialState")) + writer.uint32(/* id 2, wireType 2 =*/18).bytes(message.initialState); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified CreateFile message, length delimited. Does not implicitly {@link subtext_handlers.CreateFile.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.CreateFile + * @static + * @param {subtext_handlers.CreateFile.$Properties} message CreateFile message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + CreateFile.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes a CreateFile message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.CreateFile + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.CreateFile & subtext_handlers.CreateFile.$Shape} CreateFile + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + CreateFile.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.CreateFile(), value; + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + let wireType = tag & 7; + switch (tag >>>= 3) { + case 1: { + if (wireType !== 2) + break; + if ((value = reader.string()).length) + message.vaultPath = value; + else + delete message.vaultPath; + continue; + } + case 2: { + if (wireType !== 2) + break; + if ((value = reader.bytes()).length) + message.initialState = value; + else + delete message.initialState; + continue; + } + } + reader.skipType(wireType, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes a CreateFile message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.CreateFile + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.CreateFile & subtext_handlers.CreateFile.$Shape} CreateFile + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + CreateFile.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies a CreateFile message. + * @function verify + * @memberof subtext_handlers.CreateFile + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + CreateFile.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + if (message.vaultPath != null && message.hasOwnProperty("vaultPath")) + if (!$util.isString(message.vaultPath)) + return "vaultPath: string expected"; + if (message.initialState != null && message.hasOwnProperty("initialState")) + if (!(message.initialState && typeof message.initialState.length === "number" || $util.isString(message.initialState))) + return "initialState: buffer expected"; + return null; + }; + + /** + * Creates a CreateFile message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.CreateFile + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.CreateFile} CreateFile + */ + CreateFile.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.CreateFile) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let message = new $root.subtext_handlers.CreateFile(); + if (object.vaultPath != null) + if (typeof object.vaultPath !== "string" || object.vaultPath.length) + message.vaultPath = String(object.vaultPath); + if (object.initialState != null) + if (object.initialState.length) + if (typeof object.initialState === "string") + $util.base64.decode(object.initialState, message.initialState = $util.newBuffer($util.base64.length(object.initialState)), 0); + else if (object.initialState.length >= 0) + message.initialState = object.initialState; + return message; + }; + + /** + * Creates a plain object from a CreateFile message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.CreateFile + * @static + * @param {subtext_handlers.CreateFile} message CreateFile + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + CreateFile.toObject = function toObject(message, options, _depth) { + if (!options) + options = {}; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let object = {}; + if (options.defaults) { + object.vaultPath = ""; + if (options.bytes === String) + object.initialState = ""; + else { + object.initialState = []; + if (options.bytes !== Array) + object.initialState = $util.newBuffer(object.initialState); + } + } + if (message.vaultPath != null && message.hasOwnProperty("vaultPath")) + object.vaultPath = message.vaultPath; + if (message.initialState != null && message.hasOwnProperty("initialState")) + object.initialState = options.bytes === String ? $util.base64.encode(message.initialState, 0, message.initialState.length) : options.bytes === Array ? Array.prototype.slice.call(message.initialState) : message.initialState; + return object; + }; + + /** + * Converts this CreateFile to JSON. + * @function toJSON + * @memberof subtext_handlers.CreateFile + * @instance + * @returns {Object.} JSON object + */ + CreateFile.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for CreateFile + * @function getTypeUrl + * @memberof subtext_handlers.CreateFile + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + CreateFile.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.CreateFile"; + }; + + return CreateFile; + })(); + + subtext_handlers.RenameFile = (function() { + + /** + * Properties of a RenameFile. + * @typedef {Object} subtext_handlers.RenameFile.$Properties + * @property {string|null} [oldVaultPath] RenameFile oldVaultPath + * @property {string|null} [newVaultPath] RenameFile newVaultPath + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of a RenameFile. + * @memberof subtext_handlers + * @interface IRenameFile + * @augments subtext_handlers.RenameFile.$Properties + * @deprecated Use subtext_handlers.RenameFile.$Properties instead. + */ + + /** + * Shape of a RenameFile. + * @typedef {subtext_handlers.RenameFile.$Properties} subtext_handlers.RenameFile.$Shape + */ + + /** + * Constructs a new RenameFile. + * @memberof subtext_handlers + * @classdesc Represents a RenameFile. + * @constructor + * @param {subtext_handlers.RenameFile.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function RenameFile(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * RenameFile oldVaultPath. + * @member {string} oldVaultPath + * @memberof subtext_handlers.RenameFile + * @instance + */ + RenameFile.prototype.oldVaultPath = ""; + + /** + * RenameFile newVaultPath. + * @member {string} newVaultPath + * @memberof subtext_handlers.RenameFile + * @instance + */ + RenameFile.prototype.newVaultPath = ""; + + /** + * Creates a new RenameFile instance using the specified properties. + * @function create + * @memberof subtext_handlers.RenameFile + * @static + * @param {subtext_handlers.RenameFile.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.RenameFile} RenameFile instance + * @type {{ + * (properties: subtext_handlers.RenameFile.$Shape): subtext_handlers.RenameFile & subtext_handlers.RenameFile.$Shape; + * (properties?: subtext_handlers.RenameFile.$Properties): subtext_handlers.RenameFile; + * }} + */ + RenameFile.create = function create(properties) { + return new RenameFile(properties); + }; + + /** + * Encodes the specified RenameFile message. Does not implicitly {@link subtext_handlers.RenameFile.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.RenameFile + * @static + * @param {subtext_handlers.RenameFile.$Properties} message RenameFile message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + RenameFile.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.oldVaultPath != null && Object.hasOwnProperty.call(message, "oldVaultPath")) + writer.uint32(/* id 1, wireType 2 =*/10).string(message.oldVaultPath); + if (message.newVaultPath != null && Object.hasOwnProperty.call(message, "newVaultPath")) + writer.uint32(/* id 2, wireType 2 =*/18).string(message.newVaultPath); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified RenameFile message, length delimited. Does not implicitly {@link subtext_handlers.RenameFile.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.RenameFile + * @static + * @param {subtext_handlers.RenameFile.$Properties} message RenameFile message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + RenameFile.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes a RenameFile message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.RenameFile + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.RenameFile & subtext_handlers.RenameFile.$Shape} RenameFile + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + RenameFile.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.RenameFile(), value; + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + let wireType = tag & 7; + switch (tag >>>= 3) { + case 1: { + if (wireType !== 2) + break; + if ((value = reader.string()).length) + message.oldVaultPath = value; + else + delete message.oldVaultPath; + continue; + } + case 2: { + if (wireType !== 2) + break; + if ((value = reader.string()).length) + message.newVaultPath = value; + else + delete message.newVaultPath; + continue; + } + } + reader.skipType(wireType, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes a RenameFile message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.RenameFile + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.RenameFile & subtext_handlers.RenameFile.$Shape} RenameFile + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + RenameFile.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies a RenameFile message. + * @function verify + * @memberof subtext_handlers.RenameFile + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + RenameFile.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + if (message.oldVaultPath != null && message.hasOwnProperty("oldVaultPath")) + if (!$util.isString(message.oldVaultPath)) + return "oldVaultPath: string expected"; + if (message.newVaultPath != null && message.hasOwnProperty("newVaultPath")) + if (!$util.isString(message.newVaultPath)) + return "newVaultPath: string expected"; + return null; + }; + + /** + * Creates a RenameFile message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.RenameFile + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.RenameFile} RenameFile + */ + RenameFile.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.RenameFile) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let message = new $root.subtext_handlers.RenameFile(); + if (object.oldVaultPath != null) + if (typeof object.oldVaultPath !== "string" || object.oldVaultPath.length) + message.oldVaultPath = String(object.oldVaultPath); + if (object.newVaultPath != null) + if (typeof object.newVaultPath !== "string" || object.newVaultPath.length) + message.newVaultPath = String(object.newVaultPath); + return message; + }; + + /** + * Creates a plain object from a RenameFile message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.RenameFile + * @static + * @param {subtext_handlers.RenameFile} message RenameFile + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + RenameFile.toObject = function toObject(message, options, _depth) { + if (!options) + options = {}; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let object = {}; + if (options.defaults) { + object.oldVaultPath = ""; + object.newVaultPath = ""; + } + if (message.oldVaultPath != null && message.hasOwnProperty("oldVaultPath")) + object.oldVaultPath = message.oldVaultPath; + if (message.newVaultPath != null && message.hasOwnProperty("newVaultPath")) + object.newVaultPath = message.newVaultPath; + return object; + }; + + /** + * Converts this RenameFile to JSON. + * @function toJSON + * @memberof subtext_handlers.RenameFile + * @instance + * @returns {Object.} JSON object + */ + RenameFile.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for RenameFile + * @function getTypeUrl + * @memberof subtext_handlers.RenameFile + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + RenameFile.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.RenameFile"; + }; + + return RenameFile; + })(); + + subtext_handlers.Response = (function() { + + /** + * Properties of a Response. + * @typedef {Object} subtext_handlers.Response.$Properties + * @property {number|Long|null} [requestId] Response requestId + * @property {subtext_handlers.Pong.$Properties|null} [pong] Response pong + * @property {subtext_handlers.Ack.$Properties|null} [ack] Response ack + * @property {subtext_handlers.Error.$Properties|null} [error] Response error + * @property {subtext_handlers.BytesPayload.$Properties|null} [bytesPayload] Response bytesPayload + * @property {subtext_handlers.FileList.$Properties|null} [fileList] Response fileList + * @property {subtext_handlers.FileExistsResult.$Properties|null} [fileExistsResult] Response fileExistsResult + * @property {"pong"|"ack"|"error"|"bytesPayload"|"fileList"|"fileExistsResult"} [content] Response content + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of a Response. + * @memberof subtext_handlers + * @interface IResponse + * @augments subtext_handlers.Response.$Properties + * @deprecated Use subtext_handlers.Response.$Properties instead. + */ + + /** + * Narrowed shape of a Response. + * @typedef {{ + * requestId?: number|Long|null; + * pong?: subtext_handlers.Pong.$Shape|null; + * ack?: subtext_handlers.Ack.$Shape|null; + * error?: subtext_handlers.Error.$Shape|null; + * bytesPayload?: subtext_handlers.BytesPayload.$Shape|null; + * fileList?: subtext_handlers.FileList.$Shape|null; + * fileExistsResult?: subtext_handlers.FileExistsResult.$Shape|null; + * $unknowns?: Array.; + * } & ( + * ({ content?: undefined; pong?: null; ack?: null; error?: null; bytesPayload?: null; fileList?: null; fileExistsResult?: null }|{ content?: "pong"; pong: subtext_handlers.Pong.$Shape; ack?: null; error?: null; bytesPayload?: null; fileList?: null; fileExistsResult?: null }|{ content?: "ack"; pong?: null; ack: subtext_handlers.Ack.$Shape; error?: null; bytesPayload?: null; fileList?: null; fileExistsResult?: null }|{ content?: "error"; pong?: null; ack?: null; error: subtext_handlers.Error.$Shape; bytesPayload?: null; fileList?: null; fileExistsResult?: null }|{ content?: "bytesPayload"; pong?: null; ack?: null; error?: null; bytesPayload: subtext_handlers.BytesPayload.$Shape; fileList?: null; fileExistsResult?: null }|{ content?: "fileList"; pong?: null; ack?: null; error?: null; bytesPayload?: null; fileList: subtext_handlers.FileList.$Shape; fileExistsResult?: null }|{ content?: "fileExistsResult"; pong?: null; ack?: null; error?: null; bytesPayload?: null; fileList?: null; fileExistsResult: subtext_handlers.FileExistsResult.$Shape }) + * )} subtext_handlers.Response.$Shape + */ + + /** + * Constructs a new Response. + * @memberof subtext_handlers + * @classdesc Represents a Response. + * @constructor + * @param {subtext_handlers.Response.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function Response(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * Response requestId. + * @member {number|Long} requestId + * @memberof subtext_handlers.Response + * @instance + */ + Response.prototype.requestId = $util.Long ? $util.Long.fromBits(0,0,true) : 0; + + /** + * Response pong. + * @member {subtext_handlers.Pong.$Properties|null|undefined} pong + * @memberof subtext_handlers.Response + * @instance + */ + Response.prototype.pong = null; + + /** + * Response ack. + * @member {subtext_handlers.Ack.$Properties|null|undefined} ack + * @memberof subtext_handlers.Response + * @instance + */ + Response.prototype.ack = null; + + /** + * Response error. + * @member {subtext_handlers.Error.$Properties|null|undefined} error + * @memberof subtext_handlers.Response + * @instance + */ + Response.prototype.error = null; + + /** + * Response bytesPayload. + * @member {subtext_handlers.BytesPayload.$Properties|null|undefined} bytesPayload + * @memberof subtext_handlers.Response + * @instance + */ + Response.prototype.bytesPayload = null; + + /** + * Response fileList. + * @member {subtext_handlers.FileList.$Properties|null|undefined} fileList + * @memberof subtext_handlers.Response + * @instance + */ + Response.prototype.fileList = null; + + /** + * Response fileExistsResult. + * @member {subtext_handlers.FileExistsResult.$Properties|null|undefined} fileExistsResult + * @memberof subtext_handlers.Response + * @instance + */ + Response.prototype.fileExistsResult = null; + + // OneOf field names bound to virtual getters and setters + let $oneOfFields; + + /** + * Response content. + * @member {"pong"|"ack"|"error"|"bytesPayload"|"fileList"|"fileExistsResult"|undefined} content + * @memberof subtext_handlers.Response + * @instance + */ + Object.defineProperty(Response.prototype, "content", { + get: $util.oneOfGetter($oneOfFields = ["pong", "ack", "error", "bytesPayload", "fileList", "fileExistsResult"]), + set: $util.oneOfSetter($oneOfFields) + }); + + /** + * Creates a new Response instance using the specified properties. + * @function create + * @memberof subtext_handlers.Response + * @static + * @param {subtext_handlers.Response.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.Response} Response instance + * @type {{ + * (properties: subtext_handlers.Response.$Shape): subtext_handlers.Response & subtext_handlers.Response.$Shape; + * (properties?: subtext_handlers.Response.$Properties): subtext_handlers.Response; + * }} + */ + Response.create = function create(properties) { + return new Response(properties); + }; + + /** + * Encodes the specified Response message. Does not implicitly {@link subtext_handlers.Response.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.Response + * @static + * @param {subtext_handlers.Response.$Properties} message Response message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + Response.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.requestId != null && Object.hasOwnProperty.call(message, "requestId")) + writer.uint32(/* id 1, wireType 0 =*/8).uint64(message.requestId); + if (message.pong != null && Object.hasOwnProperty.call(message, "pong")) + $root.subtext_handlers.Pong.encode(message.pong, writer.uint32(/* id 2, wireType 2 =*/18).fork(), _depth + 1).ldelim(); + if (message.ack != null && Object.hasOwnProperty.call(message, "ack")) + $root.subtext_handlers.Ack.encode(message.ack, writer.uint32(/* id 3, wireType 2 =*/26).fork(), _depth + 1).ldelim(); + if (message.error != null && Object.hasOwnProperty.call(message, "error")) + $root.subtext_handlers.Error.encode(message.error, writer.uint32(/* id 4, wireType 2 =*/34).fork(), _depth + 1).ldelim(); + if (message.bytesPayload != null && Object.hasOwnProperty.call(message, "bytesPayload")) + $root.subtext_handlers.BytesPayload.encode(message.bytesPayload, writer.uint32(/* id 5, wireType 2 =*/42).fork(), _depth + 1).ldelim(); + if (message.fileList != null && Object.hasOwnProperty.call(message, "fileList")) + $root.subtext_handlers.FileList.encode(message.fileList, writer.uint32(/* id 6, wireType 2 =*/50).fork(), _depth + 1).ldelim(); + if (message.fileExistsResult != null && Object.hasOwnProperty.call(message, "fileExistsResult")) + $root.subtext_handlers.FileExistsResult.encode(message.fileExistsResult, writer.uint32(/* id 7, wireType 2 =*/58).fork(), _depth + 1).ldelim(); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified Response message, length delimited. Does not implicitly {@link subtext_handlers.Response.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.Response + * @static + * @param {subtext_handlers.Response.$Properties} message Response message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + Response.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes a Response message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.Response + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.Response & subtext_handlers.Response.$Shape} Response + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + Response.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.Response(), value; + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + let wireType = tag & 7; + switch (tag >>>= 3) { + case 1: { + if (wireType !== 0) + break; + if (typeof (value = reader.uint64()) === "object" ? value.low || value.high : value !== 0) + message.requestId = value; + else + delete message.requestId; + continue; + } + case 2: { + if (wireType !== 2) + break; + message.pong = $root.subtext_handlers.Pong.decode(reader, reader.uint32(), undefined, _depth + 1, message.pong); + message.content = "pong"; + continue; + } + case 3: { + if (wireType !== 2) + break; + message.ack = $root.subtext_handlers.Ack.decode(reader, reader.uint32(), undefined, _depth + 1, message.ack); + message.content = "ack"; + continue; + } + case 4: { + if (wireType !== 2) + break; + message.error = $root.subtext_handlers.Error.decode(reader, reader.uint32(), undefined, _depth + 1, message.error); + message.content = "error"; + continue; + } + case 5: { + if (wireType !== 2) + break; + message.bytesPayload = $root.subtext_handlers.BytesPayload.decode(reader, reader.uint32(), undefined, _depth + 1, message.bytesPayload); + message.content = "bytesPayload"; + continue; + } + case 6: { + if (wireType !== 2) + break; + message.fileList = $root.subtext_handlers.FileList.decode(reader, reader.uint32(), undefined, _depth + 1, message.fileList); + message.content = "fileList"; + continue; + } + case 7: { + if (wireType !== 2) + break; + message.fileExistsResult = $root.subtext_handlers.FileExistsResult.decode(reader, reader.uint32(), undefined, _depth + 1, message.fileExistsResult); + message.content = "fileExistsResult"; + continue; + } + } + reader.skipType(wireType, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes a Response message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.Response + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.Response & subtext_handlers.Response.$Shape} Response + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + Response.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies a Response message. + * @function verify + * @memberof subtext_handlers.Response + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + Response.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + let properties = {}; + if (message.requestId != null && message.hasOwnProperty("requestId")) + if (!$util.isInteger(message.requestId) && !(message.requestId && $util.isInteger(message.requestId.low) && $util.isInteger(message.requestId.high))) + return "requestId: integer|Long expected"; + if (message.pong != null && message.hasOwnProperty("pong")) { + properties.content = 1; + { + let error = $root.subtext_handlers.Pong.verify(message.pong, _depth + 1); + if (error) + return "pong." + error; + } + } + if (message.ack != null && message.hasOwnProperty("ack")) { + if (properties.content === 1) + return "content: multiple values"; + properties.content = 1; + { + let error = $root.subtext_handlers.Ack.verify(message.ack, _depth + 1); + if (error) + return "ack." + error; + } + } + if (message.error != null && message.hasOwnProperty("error")) { + if (properties.content === 1) + return "content: multiple values"; + properties.content = 1; + { + let error = $root.subtext_handlers.Error.verify(message.error, _depth + 1); + if (error) + return "error." + error; + } + } + if (message.bytesPayload != null && message.hasOwnProperty("bytesPayload")) { + if (properties.content === 1) + return "content: multiple values"; + properties.content = 1; + { + let error = $root.subtext_handlers.BytesPayload.verify(message.bytesPayload, _depth + 1); + if (error) + return "bytesPayload." + error; + } + } + if (message.fileList != null && message.hasOwnProperty("fileList")) { + if (properties.content === 1) + return "content: multiple values"; + properties.content = 1; + { + let error = $root.subtext_handlers.FileList.verify(message.fileList, _depth + 1); + if (error) + return "fileList." + error; + } + } + if (message.fileExistsResult != null && message.hasOwnProperty("fileExistsResult")) { + if (properties.content === 1) + return "content: multiple values"; + properties.content = 1; + { + let error = $root.subtext_handlers.FileExistsResult.verify(message.fileExistsResult, _depth + 1); + if (error) + return "fileExistsResult." + error; + } + } + return null; + }; + + /** + * Creates a Response message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.Response + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.Response} Response + */ + Response.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.Response) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let message = new $root.subtext_handlers.Response(); + if (object.requestId != null) + if (typeof object.requestId === "object" ? object.requestId.low || object.requestId.high : Number(object.requestId) !== 0) + if ($util.Long) + message.requestId = $util.Long.fromValue(object.requestId, true); + else if (typeof object.requestId === "string") + message.requestId = parseInt(object.requestId, 10); + else if (typeof object.requestId === "number") + message.requestId = object.requestId; + else if (typeof object.requestId === "object") + message.requestId = new $util.LongBits(object.requestId.low >>> 0, object.requestId.high >>> 0).toNumber(true); + if (object.pong != null) { + if (typeof object.pong !== "object") + throw TypeError(".subtext_handlers.Response.pong: object expected"); + message.pong = $root.subtext_handlers.Pong.fromObject(object.pong, _depth + 1); + } + if (object.ack != null) { + if (typeof object.ack !== "object") + throw TypeError(".subtext_handlers.Response.ack: object expected"); + message.ack = $root.subtext_handlers.Ack.fromObject(object.ack, _depth + 1); + } + if (object.error != null) { + if (typeof object.error !== "object") + throw TypeError(".subtext_handlers.Response.error: object expected"); + message.error = $root.subtext_handlers.Error.fromObject(object.error, _depth + 1); + } + if (object.bytesPayload != null) { + if (typeof object.bytesPayload !== "object") + throw TypeError(".subtext_handlers.Response.bytesPayload: object expected"); + message.bytesPayload = $root.subtext_handlers.BytesPayload.fromObject(object.bytesPayload, _depth + 1); + } + if (object.fileList != null) { + if (typeof object.fileList !== "object") + throw TypeError(".subtext_handlers.Response.fileList: object expected"); + message.fileList = $root.subtext_handlers.FileList.fromObject(object.fileList, _depth + 1); + } + if (object.fileExistsResult != null) { + if (typeof object.fileExistsResult !== "object") + throw TypeError(".subtext_handlers.Response.fileExistsResult: object expected"); + message.fileExistsResult = $root.subtext_handlers.FileExistsResult.fromObject(object.fileExistsResult, _depth + 1); + } + return message; + }; + + /** + * Creates a plain object from a Response message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.Response + * @static + * @param {subtext_handlers.Response} message Response + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + Response.toObject = function toObject(message, options, _depth) { + if (!options) + options = {}; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let object = {}; + if (options.defaults) + if ($util.Long) { + let long = new $util.Long(0, 0, true); + object.requestId = options.longs === String ? long.toString() : options.longs === Number ? long.toNumber() : typeof BigInt !== "undefined" && options.longs === BigInt ? long.toBigInt() : long; + } else + object.requestId = options.longs === String ? "0" : typeof BigInt !== "undefined" && options.longs === BigInt ? BigInt("0") : 0; + if (message.requestId != null && message.hasOwnProperty("requestId")) + if (typeof BigInt !== "undefined" && options.longs === BigInt) + object.requestId = typeof message.requestId === "number" ? BigInt(message.requestId) : $util.Long.fromBits(message.requestId.low >>> 0, message.requestId.high >>> 0, true).toBigInt(); + else if (typeof message.requestId === "number") + object.requestId = options.longs === String ? String(message.requestId) : message.requestId; + else + object.requestId = options.longs === String ? $util.Long.prototype.toString.call(message.requestId) : options.longs === Number ? new $util.LongBits(message.requestId.low >>> 0, message.requestId.high >>> 0).toNumber(true) : message.requestId; + if (message.pong != null && message.hasOwnProperty("pong")) { + object.pong = $root.subtext_handlers.Pong.toObject(message.pong, options, _depth + 1); + if (options.oneofs) + object.content = "pong"; + } + if (message.ack != null && message.hasOwnProperty("ack")) { + object.ack = $root.subtext_handlers.Ack.toObject(message.ack, options, _depth + 1); + if (options.oneofs) + object.content = "ack"; + } + if (message.error != null && message.hasOwnProperty("error")) { + object.error = $root.subtext_handlers.Error.toObject(message.error, options, _depth + 1); + if (options.oneofs) + object.content = "error"; + } + if (message.bytesPayload != null && message.hasOwnProperty("bytesPayload")) { + object.bytesPayload = $root.subtext_handlers.BytesPayload.toObject(message.bytesPayload, options, _depth + 1); + if (options.oneofs) + object.content = "bytesPayload"; + } + if (message.fileList != null && message.hasOwnProperty("fileList")) { + object.fileList = $root.subtext_handlers.FileList.toObject(message.fileList, options, _depth + 1); + if (options.oneofs) + object.content = "fileList"; + } + if (message.fileExistsResult != null && message.hasOwnProperty("fileExistsResult")) { + object.fileExistsResult = $root.subtext_handlers.FileExistsResult.toObject(message.fileExistsResult, options, _depth + 1); + if (options.oneofs) + object.content = "fileExistsResult"; + } + return object; + }; + + /** + * Converts this Response to JSON. + * @function toJSON + * @memberof subtext_handlers.Response + * @instance + * @returns {Object.} JSON object + */ + Response.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for Response + * @function getTypeUrl + * @memberof subtext_handlers.Response + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + Response.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.Response"; + }; + + return Response; + })(); + + subtext_handlers.Pong = (function() { + + /** + * Properties of a Pong. + * @typedef {Object} subtext_handlers.Pong.$Properties + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of a Pong. + * @memberof subtext_handlers + * @interface IPong + * @augments subtext_handlers.Pong.$Properties + * @deprecated Use subtext_handlers.Pong.$Properties instead. + */ + + /** + * Shape of a Pong. + * @typedef {subtext_handlers.Pong.$Properties} subtext_handlers.Pong.$Shape + */ + + /** + * Constructs a new Pong. + * @memberof subtext_handlers + * @classdesc Represents a Pong. + * @constructor + * @param {subtext_handlers.Pong.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function Pong(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * Creates a new Pong instance using the specified properties. + * @function create + * @memberof subtext_handlers.Pong + * @static + * @param {subtext_handlers.Pong.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.Pong} Pong instance + * @type {{ + * (properties: subtext_handlers.Pong.$Shape): subtext_handlers.Pong & subtext_handlers.Pong.$Shape; + * (properties?: subtext_handlers.Pong.$Properties): subtext_handlers.Pong; + * }} + */ + Pong.create = function create(properties) { + return new Pong(properties); + }; + + /** + * Encodes the specified Pong message. Does not implicitly {@link subtext_handlers.Pong.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.Pong + * @static + * @param {subtext_handlers.Pong.$Properties} message Pong message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + Pong.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified Pong message, length delimited. Does not implicitly {@link subtext_handlers.Pong.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.Pong + * @static + * @param {subtext_handlers.Pong.$Properties} message Pong message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + Pong.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes a Pong message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.Pong + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.Pong & subtext_handlers.Pong.$Shape} Pong + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + Pong.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.Pong(); + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + reader.skipType(tag & 7, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes a Pong message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.Pong + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.Pong & subtext_handlers.Pong.$Shape} Pong + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + Pong.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies a Pong message. + * @function verify + * @memberof subtext_handlers.Pong + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + Pong.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + return null; + }; + + /** + * Creates a Pong message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.Pong + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.Pong} Pong + */ + Pong.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.Pong) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + return new $root.subtext_handlers.Pong(); + }; + + /** + * Creates a plain object from a Pong message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.Pong + * @static + * @param {subtext_handlers.Pong} message Pong + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + Pong.toObject = function toObject() { + return {}; + }; + + /** + * Converts this Pong to JSON. + * @function toJSON + * @memberof subtext_handlers.Pong + * @instance + * @returns {Object.} JSON object + */ + Pong.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for Pong + * @function getTypeUrl + * @memberof subtext_handlers.Pong + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + Pong.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.Pong"; + }; + + return Pong; + })(); + + subtext_handlers.Ack = (function() { + + /** + * Properties of an Ack. + * @typedef {Object} subtext_handlers.Ack.$Properties + * @property {string|null} [message] Ack message + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of an Ack. + * @memberof subtext_handlers + * @interface IAck + * @augments subtext_handlers.Ack.$Properties + * @deprecated Use subtext_handlers.Ack.$Properties instead. + */ + + /** + * Shape of an Ack. + * @typedef {subtext_handlers.Ack.$Properties} subtext_handlers.Ack.$Shape + */ + + /** + * Constructs a new Ack. + * @memberof subtext_handlers + * @classdesc Represents an Ack. + * @constructor + * @param {subtext_handlers.Ack.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function Ack(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * Ack message. + * @member {string} message + * @memberof subtext_handlers.Ack + * @instance + */ + Ack.prototype.message = ""; + + /** + * Creates a new Ack instance using the specified properties. + * @function create + * @memberof subtext_handlers.Ack + * @static + * @param {subtext_handlers.Ack.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.Ack} Ack instance + * @type {{ + * (properties: subtext_handlers.Ack.$Shape): subtext_handlers.Ack & subtext_handlers.Ack.$Shape; + * (properties?: subtext_handlers.Ack.$Properties): subtext_handlers.Ack; + * }} + */ + Ack.create = function create(properties) { + return new Ack(properties); + }; + + /** + * Encodes the specified Ack message. Does not implicitly {@link subtext_handlers.Ack.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.Ack + * @static + * @param {subtext_handlers.Ack.$Properties} message Ack message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + Ack.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.message != null && Object.hasOwnProperty.call(message, "message")) + writer.uint32(/* id 1, wireType 2 =*/10).string(message.message); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified Ack message, length delimited. Does not implicitly {@link subtext_handlers.Ack.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.Ack + * @static + * @param {subtext_handlers.Ack.$Properties} message Ack message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + Ack.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes an Ack message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.Ack + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.Ack & subtext_handlers.Ack.$Shape} Ack + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + Ack.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.Ack(), value; + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + let wireType = tag & 7; + switch (tag >>>= 3) { + case 1: { + if (wireType !== 2) + break; + if ((value = reader.string()).length) + message.message = value; + else + delete message.message; + continue; + } + } + reader.skipType(wireType, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes an Ack message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.Ack + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.Ack & subtext_handlers.Ack.$Shape} Ack + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + Ack.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies an Ack message. + * @function verify + * @memberof subtext_handlers.Ack + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + Ack.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + if (message.message != null && message.hasOwnProperty("message")) + if (!$util.isString(message.message)) + return "message: string expected"; + return null; + }; + + /** + * Creates an Ack message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.Ack + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.Ack} Ack + */ + Ack.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.Ack) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let message = new $root.subtext_handlers.Ack(); + if (object.message != null) + if (typeof object.message !== "string" || object.message.length) + message.message = String(object.message); + return message; + }; + + /** + * Creates a plain object from an Ack message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.Ack + * @static + * @param {subtext_handlers.Ack} message Ack + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + Ack.toObject = function toObject(message, options, _depth) { + if (!options) + options = {}; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let object = {}; + if (options.defaults) + object.message = ""; + if (message.message != null && message.hasOwnProperty("message")) + object.message = message.message; + return object; + }; + + /** + * Converts this Ack to JSON. + * @function toJSON + * @memberof subtext_handlers.Ack + * @instance + * @returns {Object.} JSON object + */ + Ack.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for Ack + * @function getTypeUrl + * @memberof subtext_handlers.Ack + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + Ack.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.Ack"; + }; + + return Ack; + })(); + + subtext_handlers.Error = (function() { + + /** + * Properties of an Error. + * @typedef {Object} subtext_handlers.Error.$Properties + * @property {string|null} [message] Error message + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of an Error. + * @memberof subtext_handlers + * @interface IError + * @augments subtext_handlers.Error.$Properties + * @deprecated Use subtext_handlers.Error.$Properties instead. + */ + + /** + * Shape of an Error. + * @typedef {subtext_handlers.Error.$Properties} subtext_handlers.Error.$Shape + */ + + /** + * Constructs a new Error. + * @memberof subtext_handlers + * @classdesc Represents an Error. + * @constructor + * @param {subtext_handlers.Error.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function Error(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * Error message. + * @member {string} message + * @memberof subtext_handlers.Error + * @instance + */ + Error.prototype.message = ""; + + /** + * Creates a new Error instance using the specified properties. + * @function create + * @memberof subtext_handlers.Error + * @static + * @param {subtext_handlers.Error.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.Error} Error instance + * @type {{ + * (properties: subtext_handlers.Error.$Shape): subtext_handlers.Error & subtext_handlers.Error.$Shape; + * (properties?: subtext_handlers.Error.$Properties): subtext_handlers.Error; + * }} + */ + Error.create = function create(properties) { + return new Error(properties); + }; + + /** + * Encodes the specified Error message. Does not implicitly {@link subtext_handlers.Error.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.Error + * @static + * @param {subtext_handlers.Error.$Properties} message Error message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + Error.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.message != null && Object.hasOwnProperty.call(message, "message")) + writer.uint32(/* id 1, wireType 2 =*/10).string(message.message); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified Error message, length delimited. Does not implicitly {@link subtext_handlers.Error.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.Error + * @static + * @param {subtext_handlers.Error.$Properties} message Error message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + Error.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes an Error message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.Error + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.Error & subtext_handlers.Error.$Shape} Error + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + Error.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.Error(), value; + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + let wireType = tag & 7; + switch (tag >>>= 3) { + case 1: { + if (wireType !== 2) + break; + if ((value = reader.string()).length) + message.message = value; + else + delete message.message; + continue; + } + } + reader.skipType(wireType, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes an Error message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.Error + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.Error & subtext_handlers.Error.$Shape} Error + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + Error.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies an Error message. + * @function verify + * @memberof subtext_handlers.Error + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + Error.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + if (message.message != null && message.hasOwnProperty("message")) + if (!$util.isString(message.message)) + return "message: string expected"; + return null; + }; + + /** + * Creates an Error message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.Error + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.Error} Error + */ + Error.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.Error) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let message = new $root.subtext_handlers.Error(); + if (object.message != null) + if (typeof object.message !== "string" || object.message.length) + message.message = String(object.message); + return message; + }; + + /** + * Creates a plain object from an Error message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.Error + * @static + * @param {subtext_handlers.Error} message Error + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + Error.toObject = function toObject(message, options, _depth) { + if (!options) + options = {}; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let object = {}; + if (options.defaults) + object.message = ""; + if (message.message != null && message.hasOwnProperty("message")) + object.message = message.message; + return object; + }; + + /** + * Converts this Error to JSON. + * @function toJSON + * @memberof subtext_handlers.Error + * @instance + * @returns {Object.} JSON object + */ + Error.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for Error + * @function getTypeUrl + * @memberof subtext_handlers.Error + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + Error.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.Error"; + }; + + return Error; + })(); + + subtext_handlers.BytesPayload = (function() { + + /** + * Properties of a BytesPayload. + * @typedef {Object} subtext_handlers.BytesPayload.$Properties + * @property {Uint8Array|null} [data] BytesPayload data + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of a BytesPayload. + * @memberof subtext_handlers + * @interface IBytesPayload + * @augments subtext_handlers.BytesPayload.$Properties + * @deprecated Use subtext_handlers.BytesPayload.$Properties instead. + */ + + /** + * Shape of a BytesPayload. + * @typedef {subtext_handlers.BytesPayload.$Properties} subtext_handlers.BytesPayload.$Shape + */ + + /** + * Constructs a new BytesPayload. + * @memberof subtext_handlers + * @classdesc Represents a BytesPayload. + * @constructor + * @param {subtext_handlers.BytesPayload.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function BytesPayload(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * BytesPayload data. + * @member {Uint8Array} data + * @memberof subtext_handlers.BytesPayload + * @instance + */ + BytesPayload.prototype.data = $util.newBuffer([]); + + /** + * Creates a new BytesPayload instance using the specified properties. + * @function create + * @memberof subtext_handlers.BytesPayload + * @static + * @param {subtext_handlers.BytesPayload.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.BytesPayload} BytesPayload instance + * @type {{ + * (properties: subtext_handlers.BytesPayload.$Shape): subtext_handlers.BytesPayload & subtext_handlers.BytesPayload.$Shape; + * (properties?: subtext_handlers.BytesPayload.$Properties): subtext_handlers.BytesPayload; + * }} + */ + BytesPayload.create = function create(properties) { + return new BytesPayload(properties); + }; + + /** + * Encodes the specified BytesPayload message. Does not implicitly {@link subtext_handlers.BytesPayload.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.BytesPayload + * @static + * @param {subtext_handlers.BytesPayload.$Properties} message BytesPayload message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + BytesPayload.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.data != null && Object.hasOwnProperty.call(message, "data")) + writer.uint32(/* id 1, wireType 2 =*/10).bytes(message.data); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified BytesPayload message, length delimited. Does not implicitly {@link subtext_handlers.BytesPayload.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.BytesPayload + * @static + * @param {subtext_handlers.BytesPayload.$Properties} message BytesPayload message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + BytesPayload.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes a BytesPayload message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.BytesPayload + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.BytesPayload & subtext_handlers.BytesPayload.$Shape} BytesPayload + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + BytesPayload.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.BytesPayload(), value; + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + let wireType = tag & 7; + switch (tag >>>= 3) { + case 1: { + if (wireType !== 2) + break; + if ((value = reader.bytes()).length) + message.data = value; + else + delete message.data; + continue; + } + } + reader.skipType(wireType, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes a BytesPayload message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.BytesPayload + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.BytesPayload & subtext_handlers.BytesPayload.$Shape} BytesPayload + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + BytesPayload.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies a BytesPayload message. + * @function verify + * @memberof subtext_handlers.BytesPayload + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + BytesPayload.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + if (message.data != null && message.hasOwnProperty("data")) + if (!(message.data && typeof message.data.length === "number" || $util.isString(message.data))) + return "data: buffer expected"; + return null; + }; + + /** + * Creates a BytesPayload message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.BytesPayload + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.BytesPayload} BytesPayload + */ + BytesPayload.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.BytesPayload) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let message = new $root.subtext_handlers.BytesPayload(); + if (object.data != null) + if (object.data.length) + if (typeof object.data === "string") + $util.base64.decode(object.data, message.data = $util.newBuffer($util.base64.length(object.data)), 0); + else if (object.data.length >= 0) + message.data = object.data; + return message; + }; + + /** + * Creates a plain object from a BytesPayload message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.BytesPayload + * @static + * @param {subtext_handlers.BytesPayload} message BytesPayload + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + BytesPayload.toObject = function toObject(message, options, _depth) { + if (!options) + options = {}; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let object = {}; + if (options.defaults) + if (options.bytes === String) + object.data = ""; + else { + object.data = []; + if (options.bytes !== Array) + object.data = $util.newBuffer(object.data); + } + if (message.data != null && message.hasOwnProperty("data")) + object.data = options.bytes === String ? $util.base64.encode(message.data, 0, message.data.length) : options.bytes === Array ? Array.prototype.slice.call(message.data) : message.data; + return object; + }; + + /** + * Converts this BytesPayload to JSON. + * @function toJSON + * @memberof subtext_handlers.BytesPayload + * @instance + * @returns {Object.} JSON object + */ + BytesPayload.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for BytesPayload + * @function getTypeUrl + * @memberof subtext_handlers.BytesPayload + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + BytesPayload.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.BytesPayload"; + }; + + return BytesPayload; + })(); + + subtext_handlers.FileList = (function() { + + /** + * Properties of a FileList. + * @typedef {Object} subtext_handlers.FileList.$Properties + * @property {Array.|null} [paths] FileList paths + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of a FileList. + * @memberof subtext_handlers + * @interface IFileList + * @augments subtext_handlers.FileList.$Properties + * @deprecated Use subtext_handlers.FileList.$Properties instead. + */ + + /** + * Shape of a FileList. + * @typedef {subtext_handlers.FileList.$Properties} subtext_handlers.FileList.$Shape + */ + + /** + * Constructs a new FileList. + * @memberof subtext_handlers + * @classdesc Represents a FileList. + * @constructor + * @param {subtext_handlers.FileList.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function FileList(properties) { + this.paths = []; + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * FileList paths. + * @member {Array.} paths + * @memberof subtext_handlers.FileList + * @instance + */ + FileList.prototype.paths = $util.emptyArray; + + /** + * Creates a new FileList instance using the specified properties. + * @function create + * @memberof subtext_handlers.FileList + * @static + * @param {subtext_handlers.FileList.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.FileList} FileList instance + * @type {{ + * (properties: subtext_handlers.FileList.$Shape): subtext_handlers.FileList & subtext_handlers.FileList.$Shape; + * (properties?: subtext_handlers.FileList.$Properties): subtext_handlers.FileList; + * }} + */ + FileList.create = function create(properties) { + return new FileList(properties); + }; + + /** + * Encodes the specified FileList message. Does not implicitly {@link subtext_handlers.FileList.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.FileList + * @static + * @param {subtext_handlers.FileList.$Properties} message FileList message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + FileList.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.paths != null && message.paths.length) + for (let i = 0; i < message.paths.length; ++i) + writer.uint32(/* id 1, wireType 2 =*/10).string(message.paths[i]); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified FileList message, length delimited. Does not implicitly {@link subtext_handlers.FileList.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.FileList + * @static + * @param {subtext_handlers.FileList.$Properties} message FileList message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + FileList.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes a FileList message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.FileList + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.FileList & subtext_handlers.FileList.$Shape} FileList + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + FileList.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.FileList(); + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + let wireType = tag & 7; + switch (tag >>>= 3) { + case 1: { + if (wireType !== 2) + break; + if (!(message.paths && message.paths.length)) + message.paths = []; + message.paths.push(reader.string()); + continue; + } + } + reader.skipType(wireType, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes a FileList message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.FileList + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.FileList & subtext_handlers.FileList.$Shape} FileList + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + FileList.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies a FileList message. + * @function verify + * @memberof subtext_handlers.FileList + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + FileList.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + if (message.paths != null && message.hasOwnProperty("paths")) { + if (!Array.isArray(message.paths)) + return "paths: array expected"; + for (let i = 0; i < message.paths.length; ++i) + if (!$util.isString(message.paths[i])) + return "paths: string[] expected"; + } + return null; + }; + + /** + * Creates a FileList message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.FileList + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.FileList} FileList + */ + FileList.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.FileList) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let message = new $root.subtext_handlers.FileList(); + if (object.paths) { + if (!Array.isArray(object.paths)) + throw TypeError(".subtext_handlers.FileList.paths: array expected"); + message.paths = Array(object.paths.length); + for (let i = 0; i < object.paths.length; ++i) + message.paths[i] = String(object.paths[i]); + } + return message; + }; + + /** + * Creates a plain object from a FileList message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.FileList + * @static + * @param {subtext_handlers.FileList} message FileList + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + FileList.toObject = function toObject(message, options, _depth) { + if (!options) + options = {}; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let object = {}; + if (options.arrays || options.defaults) + object.paths = []; + if (message.paths && message.paths.length) { + object.paths = Array(message.paths.length); + for (let j = 0; j < message.paths.length; ++j) + object.paths[j] = message.paths[j]; + } + return object; + }; + + /** + * Converts this FileList to JSON. + * @function toJSON + * @memberof subtext_handlers.FileList + * @instance + * @returns {Object.} JSON object + */ + FileList.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for FileList + * @function getTypeUrl + * @memberof subtext_handlers.FileList + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + FileList.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.FileList"; + }; + + return FileList; + })(); + + subtext_handlers.FileExistsResult = (function() { + + /** + * Properties of a FileExistsResult. + * @typedef {Object} subtext_handlers.FileExistsResult.$Properties + * @property {boolean|null} [exists] FileExistsResult exists + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + + /** + * Properties of a FileExistsResult. + * @memberof subtext_handlers + * @interface IFileExistsResult + * @augments subtext_handlers.FileExistsResult.$Properties + * @deprecated Use subtext_handlers.FileExistsResult.$Properties instead. + */ + + /** + * Shape of a FileExistsResult. + * @typedef {subtext_handlers.FileExistsResult.$Properties} subtext_handlers.FileExistsResult.$Shape + */ + + /** + * Constructs a new FileExistsResult. + * @memberof subtext_handlers + * @classdesc Represents a FileExistsResult. + * @constructor + * @param {subtext_handlers.FileExistsResult.$Properties=} [properties] Properties to set + * @property {Array.} [$unknowns] Unknown fields preserved while decoding + */ + function FileExistsResult(properties) { + if (properties) + for (let keys = Object.keys(properties), i = 0; i < keys.length; ++i) + if (properties[keys[i]] != null && keys[i] !== "__proto__") + this[keys[i]] = properties[keys[i]]; + } + + /** + * FileExistsResult exists. + * @member {boolean} exists + * @memberof subtext_handlers.FileExistsResult + * @instance + */ + FileExistsResult.prototype.exists = false; + + /** + * Creates a new FileExistsResult instance using the specified properties. + * @function create + * @memberof subtext_handlers.FileExistsResult + * @static + * @param {subtext_handlers.FileExistsResult.$Properties=} [properties] Properties to set + * @returns {subtext_handlers.FileExistsResult} FileExistsResult instance + * @type {{ + * (properties: subtext_handlers.FileExistsResult.$Shape): subtext_handlers.FileExistsResult & subtext_handlers.FileExistsResult.$Shape; + * (properties?: subtext_handlers.FileExistsResult.$Properties): subtext_handlers.FileExistsResult; + * }} + */ + FileExistsResult.create = function create(properties) { + return new FileExistsResult(properties); + }; + + /** + * Encodes the specified FileExistsResult message. Does not implicitly {@link subtext_handlers.FileExistsResult.verify|verify} messages. + * @function encode + * @memberof subtext_handlers.FileExistsResult + * @static + * @param {subtext_handlers.FileExistsResult.$Properties} message FileExistsResult message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + FileExistsResult.encode = function encode(message, writer, _depth) { + if (!writer) + writer = $Writer.create(); + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + if (message.exists != null && Object.hasOwnProperty.call(message, "exists")) + writer.uint32(/* id 1, wireType 0 =*/8).bool(message.exists); + if (message.$unknowns != null && Object.hasOwnProperty.call(message, "$unknowns")) + for (let i = 0; i < message.$unknowns.length; ++i) + writer.raw(message.$unknowns[i]); + return writer; + }; + + /** + * Encodes the specified FileExistsResult message, length delimited. Does not implicitly {@link subtext_handlers.FileExistsResult.verify|verify} messages. + * @function encodeDelimited + * @memberof subtext_handlers.FileExistsResult + * @static + * @param {subtext_handlers.FileExistsResult.$Properties} message FileExistsResult message or plain object to encode + * @param {$protobuf.Writer} [writer] Writer to encode to + * @returns {$protobuf.Writer} Writer + */ + FileExistsResult.encodeDelimited = function encodeDelimited(message, writer) { + return this.encode(message, writer && writer.len ? writer.fork() : writer).ldelim(); + }; + + /** + * Decodes a FileExistsResult message from the specified reader or buffer. + * @function decode + * @memberof subtext_handlers.FileExistsResult + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @param {number} [length] Message length if known beforehand + * @returns {subtext_handlers.FileExistsResult & subtext_handlers.FileExistsResult.$Shape} FileExistsResult + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + FileExistsResult.decode = function decode(reader, length, _end, _depth, _target) { + if (!(reader instanceof $Reader)) + reader = $Reader.create(reader); + if (_depth === undefined) + _depth = 0; + if (_depth > $Reader.recursionLimit) + throw Error("max depth exceeded"); + let end = length === undefined ? reader.len : reader.pos + length, message = _target || new $root.subtext_handlers.FileExistsResult(), value; + while (reader.pos < end) { + let start = reader.pos; + let tag = reader.tag(); + if (tag === _end) { + _end = undefined; + break; + } + let wireType = tag & 7; + switch (tag >>>= 3) { + case 1: { + if (wireType !== 0) + break; + if (value = reader.bool()) + message.exists = value; + else + delete message.exists; + continue; + } + } + reader.skipType(wireType, _depth, tag); + $util.makeProp(message, "$unknowns", false); + (message.$unknowns || (message.$unknowns = [])).push(reader.raw(start, reader.pos)); + } + if (_end !== undefined) + throw Error("missing end group"); + return message; + }; + + /** + * Decodes a FileExistsResult message from the specified reader or buffer, length delimited. + * @function decodeDelimited + * @memberof subtext_handlers.FileExistsResult + * @static + * @param {$protobuf.Reader|Uint8Array} reader Reader or buffer to decode from + * @returns {subtext_handlers.FileExistsResult & subtext_handlers.FileExistsResult.$Shape} FileExistsResult + * @throws {Error} If the payload is not a reader or valid buffer + * @throws {$protobuf.util.ProtocolError} If required fields are missing + */ + FileExistsResult.decodeDelimited = function decodeDelimited(reader) { + if (!(reader instanceof $Reader)) + reader = new $Reader(reader); + return this.decode(reader, reader.uint32()); + }; + + /** + * Verifies a FileExistsResult message. + * @function verify + * @memberof subtext_handlers.FileExistsResult + * @static + * @param {Object.} message Plain object to verify + * @returns {string|null} `null` if valid, otherwise the reason why it is not + */ + FileExistsResult.verify = function verify(message, _depth) { + if (typeof message !== "object" || message === null) + return "object expected"; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + return "max depth exceeded"; + if (message.exists != null && message.hasOwnProperty("exists")) + if (typeof message.exists !== "boolean") + return "exists: boolean expected"; + return null; + }; + + /** + * Creates a FileExistsResult message from a plain object. Also converts values to their respective internal types. + * @function fromObject + * @memberof subtext_handlers.FileExistsResult + * @static + * @param {Object.} object Plain object + * @returns {subtext_handlers.FileExistsResult} FileExistsResult + */ + FileExistsResult.fromObject = function fromObject(object, _depth) { + if (object instanceof $root.subtext_handlers.FileExistsResult) + return object; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let message = new $root.subtext_handlers.FileExistsResult(); + if (object.exists != null) + if (object.exists) + message.exists = Boolean(object.exists); + return message; + }; + + /** + * Creates a plain object from a FileExistsResult message. Also converts values to other types if specified. + * @function toObject + * @memberof subtext_handlers.FileExistsResult + * @static + * @param {subtext_handlers.FileExistsResult} message FileExistsResult + * @param {$protobuf.IConversionOptions} [options] Conversion options + * @returns {Object.} Plain object + */ + FileExistsResult.toObject = function toObject(message, options, _depth) { + if (!options) + options = {}; + if (_depth === undefined) + _depth = 0; + if (_depth > $util.recursionLimit) + throw Error("max depth exceeded"); + let object = {}; + if (options.defaults) + object.exists = false; + if (message.exists != null && message.hasOwnProperty("exists")) + object.exists = message.exists; + return object; + }; + + /** + * Converts this FileExistsResult to JSON. + * @function toJSON + * @memberof subtext_handlers.FileExistsResult + * @instance + * @returns {Object.} JSON object + */ + FileExistsResult.prototype.toJSON = function toJSON() { + return this.constructor.toObject(this, $protobuf.util.toJSONOptions); + }; + + /** + * Gets the type url for FileExistsResult + * @function getTypeUrl + * @memberof subtext_handlers.FileExistsResult + * @static + * @param {string} [prefix] Custom type url prefix, defaults to `"type.googleapis.com"` + * @returns {string} The type url + */ + FileExistsResult.getTypeUrl = function getTypeUrl(prefix) { + if (prefix === undefined) + prefix = "type.googleapis.com"; + return prefix + "/subtext_handlers.FileExistsResult"; + }; + + return FileExistsResult; + })(); + + return subtext_handlers; +})(); + +export { + $root as default +}; diff --git a/src/subtext/tcpClient.ts b/src/subtext/tcpClient.ts new file mode 100644 index 0000000..12ed265 --- /dev/null +++ b/src/subtext/tcpClient.ts @@ -0,0 +1,296 @@ +import * as net from 'net'; +import { subtext_handlers } from './proto'; + +const DEFAULT_ADDR = '127.0.0.1:8081'; +const TCP_TIMEOUT_MS = 5000; + +function getDaemonAddr(): string { + return process.env.SUBTEXT_DAEMON_ADDR ?? DEFAULT_ADDR; +} + +/** Encode a number as a LEB128 / protobuf varint. */ +function encodeVarint(value: number): Buffer { + const bytes: number[] = []; + while (value >= 0x80) { + bytes.push((value & 0x7f) | 0x80); + value >>>= 7; + } + bytes.push(value); + return Buffer.from(bytes); +} + +/** Try to decode a LEB128 / protobuf varint from the front of a buffer. */ +function decodeVarint(buf: Buffer): { value: number; bytesRead: number } | null { + let value = 0; + let shift = 0; + let bytesRead = 0; + while (bytesRead < buf.length) { + const byte = buf[bytesRead]; + value |= (byte & 0x7f) << shift; + bytesRead++; + if ((byte & 0x80) === 0) { + return { value, bytesRead }; + } + shift += 7; + if (shift >= 32) throw new Error('varint too long'); + } + return null; // incomplete +} + +/** + * Length-delimited protobuf client for the Subtext application-handler TCP port. + * + * Uses **protobuf varint (LEB128)** framing to match [`prost::Message::encode_length_delimited`] + * on the Rust side. + * + * Maintains a persistent socket and auto-reconnects with exponential backoff + * (max 3 retries). + */ +export class SubtextTCPClient { + private socket: net.Socket | null = null; + private addr: string; + private reconnectAttempts = 0; + private readonly maxReconnectAttempts = 3; + private readonly baseReconnectDelayMs = 500; + private connected = false; + private pending = new Map< + number, + { resolve: (resp: subtext_handlers.Response) => void; reject: (err: Error) => void } + >(); + private nextId = 1; + private readBuf = Buffer.alloc(0); + + constructor(addr?: string) { + this.addr = addr ?? getDaemonAddr(); + } + + get isConnected(): boolean { + return this.connected; + } + + async connect(): Promise { + if (this.connected && this.socket && !this.socket.destroyed) { + return; + } + console.log('[subtext] connecting to', this.addr); + return new Promise((resolve, reject) => { + const [host, portStr] = this.addr.split(':'); + const port = parseInt(portStr ?? '8081', 10); + + const sock = new net.Socket(); + sock.once('connect', () => { + console.log('[subtext] connected'); + this.socket = sock; + this.connected = true; + this.reconnectAttempts = 0; + this.setupSocketHandlers(); + resolve(); + }); + sock.once('error', (err) => { + console.warn('[subtext] connection error:', err.message); + reject(err); + }); + sock.connect(port, host ?? '127.0.0.1'); + }); + } + + disconnect(): void { + this.socket?.destroy(); + this.socket = null; + this.connected = false; + } + + private setupSocketHandlers(): void { + if (!this.socket) return; + this.socket.on('data', (chunk: Buffer) => { + console.log('[subtext] received', chunk.length, 'bytes'); + this.readBuf = Buffer.concat([this.readBuf, chunk]); + this.tryDecodeResponse(); + }); + this.socket.on('close', () => { + console.warn('[subtext] socket closed'); + this.connected = false; + this.socket = null; + this.attemptReconnect(); + }); + this.socket.on('error', (err) => { + console.warn('[subtext] socket error:', err.message); + }); + } + + private tryDecodeResponse(): void { + console.log('[subtext] trying decode, buffer length:', this.readBuf.length); + while (true) { + const result = decodeVarint(this.readBuf); + if (!result) { + console.log('[subtext] incomplete varint, waiting for more data'); + break; + } + const { value: len, bytesRead } = result; + console.log('[subtext] decoded varint: len=', len, 'bytesRead=', bytesRead); + if (this.readBuf.length < bytesRead + len) { + console.log('[subtext] incomplete frame, need', bytesRead + len, 'have', this.readBuf.length); + break; + } + const frame = this.readBuf.subarray(bytesRead, bytesRead + len); + this.readBuf = this.readBuf.subarray(bytesRead + len); + console.log('[subtext] decoded frame,', frame.length, 'bytes'); + try { + const resp = subtext_handlers.Response.decode(frame); + console.log('[subtext] decoded response id=', resp.requestId, 'content=', resp.content); + if (resp.requestId != null) { + const pending = this.pending.get(Number(resp.requestId)); + if (pending) { + console.log('[subtext] resolving pending request', resp.requestId); + this.pending.delete(Number(resp.requestId)); + pending.resolve(resp); + } else { + console.warn('[subtext] no pending request for id', resp.requestId); + } + } + } catch (e) { + console.warn('[subtext] decode error:', e); + } + } + } + + private attemptReconnect(): void { + if (this.reconnectAttempts >= this.maxReconnectAttempts) { + console.warn('[subtext] max reconnect attempts reached'); + return; + } + this.reconnectAttempts += 1; + const delay = this.baseReconnectDelayMs * 2 ** (this.reconnectAttempts - 1); + console.log('[subtext] reconnecting in', delay, 'ms (attempt', this.reconnectAttempts, ')'); + setTimeout(() => { + this.connect().catch(() => { + // retry loop continues on next close + }); + }, delay); + } + + private async send(req: subtext_handlers.Request): Promise { + await this.connect(); + if (!this.socket) { + throw new Error('subtext socket not connected'); + } + return new Promise((resolve, reject) => { + const id = this.nextId++; + req.id = id; + console.log('[subtext] sending request', id, 'content:', Object.keys(req).filter(k => k !== 'id' && (req as any)[k])); + this.pending.set(id, { resolve, reject }); + + // TCP-level timeout: if no response arrives in time, reject and clean up + const timer = setTimeout(() => { + if (this.pending.has(id)) { + console.warn('[subtext] request', id, 'timed out after', TCP_TIMEOUT_MS, 'ms'); + this.pending.delete(id); + reject(new Error(`subtext TCP timeout after ${TCP_TIMEOUT_MS}ms`)); + } + }, TCP_TIMEOUT_MS); + + const encoded = subtext_handlers.Request.encode(req).finish(); + const lenBuf = encodeVarint(encoded.length); + const frame = Buffer.concat([lenBuf, Buffer.from(encoded)]); + console.log('[subtext] writing frame:', frame.length, 'bytes (varint:', lenBuf.length, 'bytes, payload:', encoded.length, 'bytes)'); + this.socket!.write(frame, (err) => { + if (err) { + console.warn('[subtext] write error:', err.message); + clearTimeout(timer); + this.pending.delete(id); + reject(err); + } + }); + }); + } + + async ping(): Promise { + try { + const resp = await this.send( + subtext_handlers.Request.create({ ping: subtext_handlers.Ping.create() }), + ); + return resp.pong != null; + } catch { + return false; + } + } + + async getFullState(vaultPath: string): Promise { + const resp = await this.send( + subtext_handlers.Request.create({ + getFullState: subtext_handlers.GetFullState.create({ vaultPath }), + }), + ); + if (resp.error) { + throw new Error(resp.error.message ?? 'subtext error'); + } + if (resp.bytesPayload?.data) { + const data = resp.bytesPayload.data; + if (Buffer.isBuffer(data)) { + return new Uint8Array(data.buffer, data.byteOffset, data.byteLength); + } + if (typeof data === 'string') { + return new TextEncoder().encode(data); + } + return data as Uint8Array; + } + return null; + } + + async applyUpdate(vaultPath: string, update: Uint8Array): Promise { + const resp = await this.send( + subtext_handlers.Request.create({ + applyUpdateV2: subtext_handlers.ApplyUpdateV2.create({ vaultPath, update }), + }), + ); + if (resp.error) { + throw new Error(resp.error.message ?? 'subtext error'); + } + } + + async listFiles(prefix?: string): Promise { + const resp = await this.send( + subtext_handlers.Request.create({ + listFiles: subtext_handlers.ListFiles.create({ prefix: prefix ?? '' }), + }), + ); + if (resp.error) { + throw new Error(resp.error.message ?? 'subtext error'); + } + return resp.fileList?.paths ?? []; + } + + async fileExists(vaultPath: string): Promise { + const resp = await this.send( + subtext_handlers.Request.create({ + fileExists: subtext_handlers.FileExists.create({ vaultPath }), + }), + ); + if (resp.error) { + throw new Error(resp.error.message ?? 'subtext error'); + } + return resp.fileExistsResult?.exists ?? false; + } + + async createFile(vaultPath: string, initialState: Uint8Array): Promise { + const resp = await this.send( + subtext_handlers.Request.create({ + createFile: subtext_handlers.CreateFile.create({ vaultPath, initialState }), + }), + ); + if (resp.error) { + throw new Error(resp.error.message ?? 'subtext error'); + } + } + + async renameFile(oldVaultPath: string, newVaultPath: string): Promise { + const resp = await this.send( + subtext_handlers.Request.create({ + renameFile: subtext_handlers.RenameFile.create({ oldVaultPath, newVaultPath }), + }), + ); + if (resp.error) { + throw new Error(resp.error.message ?? 'subtext error'); + } + } +} diff --git a/src/subtext/testClient.ts b/src/subtext/testClient.ts new file mode 100644 index 0000000..9044867 --- /dev/null +++ b/src/subtext/testClient.ts @@ -0,0 +1,56 @@ +/** + * Standalone test for the Subtext TCP client. + * + * Run this directly with Node.js while the subtext daemon is running: + * + * npx tsx src/subtext/testClient.ts + * + * Or compile first: + * + * npx tsc src/subtext/testClient.ts --outDir /tmp/subtext-test --module commonjs + * node /tmp/subtext-test/testClient.js + */ + +import { SubtextTCPClient } from './tcpClient'; + +async function main() { + const client = new SubtextTCPClient(); + + console.log('--- ping ---'); + const pong = await client.ping(); + console.log('ping result:', pong); + + console.log('\n--- listFiles ---'); + const files = await client.listFiles(); + console.log('files:', files); + + console.log('\n--- createFile ---'); + const testPath = 'test.md'; + const initialState = new Uint8Array([0, 0, 0, 0, 1]); // minimal empty doc envelope + try { + await client.createFile(testPath, initialState); + console.log('created', testPath); + } catch (e) { + console.error('create failed:', e); + } + + console.log('\n--- fileExists ---'); + const exists = await client.fileExists(testPath); + console.log(testPath, 'exists:', exists); + + console.log('\n--- getFullState ---'); + const state = await client.getFullState(testPath); + console.log(testPath, 'state length:', state?.length ?? null); + + console.log('\n--- listFiles again ---'); + const files2 = await client.listFiles(); + console.log('files:', files2); + + client.disconnect(); + console.log('\nDone.'); +} + +main().catch((e) => { + console.error('Fatal:', e); + process.exit(1); +}); diff --git a/src/vite-env.d.ts b/src/vite-env.d.ts index 3cbb786..e2080e2 100644 --- a/src/vite-env.d.ts +++ b/src/vite-env.d.ts @@ -6,6 +6,15 @@ declare global { platform: NodeJS.Platform; onOpenSettings: (callback: () => void) => () => void; startHabitatLogin: (url: string, redirectUri: string) => Promise; + subtext: { + getFullState: (vaultPath: string) => Promise; + applyUpdate: (vaultPath: string, update: Uint8Array) => Promise; + listFiles: () => Promise; + fileExists: (vaultPath: string) => Promise; + createFile: (vaultPath: string, initialState: Uint8Array) => Promise; + renameFile: (oldVaultPath: string, newVaultPath: string) => Promise; + status: () => Promise<{ connected: boolean }>; + }; }; } } -- 2.51.2