{"id":21405992,"url":"https://github.com/jes/formpacker","last_synced_at":"2026-07-02T20:03:51.740Z","repository":{"id":237195939,"uuid":"794011051","full_name":"jes/formpacker","owner":"jes","description":null,"archived":false,"fork":false,"pushed_at":"2024-05-01T18:56:05.000Z","size":18,"stargazers_count":1,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"master","last_synced_at":"2025-10-28T10:36:43.333Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/jes.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2024-04-30T09:36:39.000Z","updated_at":"2025-03-04T04:24:18.000Z","dependencies_parsed_at":"2024-04-30T14:15:56.144Z","dependency_job_id":"3879cec1-a83f-421a-868b-0b816e46c1a1","html_url":"https://github.com/jes/formpacker","commit_stats":null,"previous_names":["jes/formpack","jes/formpacker"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/jes/formpacker","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jes%2Fformpacker","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jes%2Fformpacker/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jes%2Fformpacker/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jes%2Fformpacker/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/jes","download_url":"https://codeload.github.com/jes/formpacker/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jes%2Fformpacker/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":35060917,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-07-02T02:00:06.368Z","response_time":173,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-11-22T16:30:00.223Z","updated_at":"2026-07-02T20:03:51.716Z","avatar_url":"https://github.com/jes.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Formpacker\n\nFormpacker creates compact copy-pastable representations of form values.\n\nYou would show a Formpacker representation in a convenient copyable place near your form, and also have a box\nwhere people can paste in a Formpacker representation to populate the form.\n\nThe output takes up substantially less space than base64 of JSON, at the cost of slightly more work in your\ncode to define the field spec.\n\nAs an example, let's take an object like:\n\n    {\n        height: 180.52,\n        name: \"Homer Simpson\",\n        admin: false,\n        department: \"tech\",\n    };\n\nbase64 of JSON is:\n\n    eyJoZWlnaHQiOjE4MC41MiwibmFtZSI6IkhvbWVyIFNpbXBzb24iLCJhZG1pbiI6ZmFsc2UsImRlcGFydG1lbnQiOiJ0ZWNoIn0=\n\nFormpacker reduces this to:\n\n    vaICkJVC8LqhWSs7JK8Hyjv4Jj\n\nSee below for example code.\n\n## Design goals\n\nThe intended purpose is for users to store \u0026 share form contents through any text-based channel (e.g.\nin plain text files, spreadsheet cells, email, IM, etc.\n\nDesign goals include:\n\n * no special characters, because they are sometimes annoying to select by double-clicking, for example if they are detected as a word boundary\n * output should be reasonably as short as possible\n * detect corrupted inputs and incorrect inputs, instead of creating weird output\n * preserve leading/trailing zero's in numeric values\n\n## Install\n\n### npm\n\nInstall with `npm i formpacker`, and load it like so:\n\n    const Formpacker = require('formpacker'); \n    \n    ...\n\n### Script tag\n\nLoad Formpacker with a script tag:\n\n    \u003chtml\u003e\u003cbody\u003e\n    \u003cscript src=\"formpacker.js\"\u003e\u003c/script\u003e\n    \u003cscript\u003e\n        ...\n    \u003c/script\u003e\n    \u003c/body\u003e\u003c/html\u003e\n\n## Usage\n\nLoad Formpacker with either npm or a script tag, as above,\nand then:\n\n    let f = new Formpacker();\n\n    // Construct your form representation with these functions.\n    // The order you add them is important as it goes directly\n    // into the order of the underlying data in the output.\n    // The same fields added in a different order will create an\n    // incompatible format.\n    f.numField(\"height\");\n    f.stringField(\"name\", 32); // 32 is maximum length of string\n    f.boolField(\"admin\");\n    f.multiField(\"department\", [\"tech\", \"sales\", \"support\"]);\n\n    // Create an object containing your form field values, with names\n    // matching the ones above.\n    let employee = {\n        height: 180.52,\n        name: \"Homer Simpson\",\n        admin: false,\n        department: \"tech\",\n    };\n\n    // Encode an object into a compact string representation.\n    let str = f.pack(employee);\n    console.log(str); // vaICkJVC8LqhWSs7JK8Hyjv4Jj\n\n    // Decode a string into an object.\n    let newEmployee = f.unpack(str);\n    console.log(newEmployee); // { height: 180.52, name: \"Homer Simpson\", admin: false, department: \"tech\" }\n\n## How it works\n\nFormpacker efficiently encodes all of your fields into one large number, and then the string output is\na base62 encoding of the number. (Broadly like base64, but with no special characters).\n\nAlso encoded in the large number is a checksum of the field spec, so that it can detect if you try to decode data\nwith an incorrect field spec, and a checksum of the field contents, so that it can detect corrupted input.\n\nThe field types are encoded as follows, which may or may not make sense. Maybe better to read the code.\n\n### Boolean: \"bool\"\n\nA base-2 value of either 0 or 1 is added into the bigint.\n\n### Multiple choice: \"multi\"\n\nA base-N value i is added into the bigint, where N is the number of choices,\nand i is the index of the chosen choice.\n\n### Numbers: \"num\"\n\nFirst a sign bit is encoded in the same manner as a boolean (true for negative),\nand then the integer part of the number is encoded, one decimal digit at a time, but as if it were a base-11 value.\nThen a base-11 digit \"10\" is encoded to signify the end of the integer part, and then the fractional part\nis encoded in the same way (base-10 representation, but in base-11 digits, followed by a base-11 \"10\").\n\n### Strings: \"string\"\n\nThe string is encoded with utf-8.\n\nFirst the length of the string is encoded as a base-N value where N is 1 more than the specified\nmaximum length of the string. And then each character of the utf-8 string is encoded as a base-256\nvalue.\n\n## Drawbacks\n\nIf you change the field spec, then all previous encoded values will no longer work. A suggested solution\nis to keep all versions of your Formpacker encoding available, and if decoding with the most recent one fails\nby throwing an error, then fall back to the next most recent, etc., until you either successfully decode an object\nor run out of possible field specs.\n\nPossible ways to change the field spec include:\n\n * adding/removing a field\n * changing the order in which you declare the fields\n * changing the name of a field\n * changing the maximum length of a string\n * changing the order of options in a multiple-choice\n * adding/removing a multiple-choice option\n\n## Bugs\n\nNumeric values do not support scientific notation. If you have a numeric value like \"1.2e8\", it will be\nrejected because \"e\" can not be encoded.\n\n## Potential improvements\n\nShould the \"string\" and \"num\" field types use Huffman coding instead of the weird variable-base stuff?\n\nShould the length of a string be encoded as a \"num\" instead of a fixed-size value?\n\n## Contact\n\nFormpacker is created by James Stanley. You can email me on james@incoherency.co.uk or read my blog at https://incoherency.co.uk/\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjes%2Fformpacker","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjes%2Fformpacker","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjes%2Fformpacker/lists"}