{"id":13726253,"url":"https://github.com/glennsl/bs-json","last_synced_at":"2025-10-04T21:30:31.834Z","repository":{"id":20409767,"uuid":"87158693","full_name":"glennsl/bs-json","owner":"glennsl","description":"Compositional JSON encode/decode library for BuckleScript","archived":true,"fork":false,"pushed_at":"2023-12-06T22:46:34.000Z","size":1684,"stargazers_count":273,"open_issues_count":2,"forks_count":48,"subscribers_count":6,"default_branch":"master","last_synced_at":"2024-10-29T09:08:51.118Z","etag":null,"topics":["bucklescript","js","json","ocaml"],"latest_commit_sha":null,"homepage":"","language":"OCaml","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"lgpl-3.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/glennsl.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null}},"created_at":"2017-04-04T07:21:51.000Z","updated_at":"2024-10-05T20:54:53.000Z","dependencies_parsed_at":"2023-01-13T20:57:39.650Z","dependency_job_id":"aaba8b31-1810-49f2-9e7b-f9cb0a262fe5","html_url":"https://github.com/glennsl/bs-json","commit_stats":{"total_commits":215,"total_committers":25,"mean_commits":8.6,"dds":"0.31162790697674414","last_synced_commit":"47ad1febb7c0d52dac2964e1dd4cdff63508b4b4"},"previous_names":[],"tags_count":23,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/glennsl%2Fbs-json","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/glennsl%2Fbs-json/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/glennsl%2Fbs-json/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/glennsl%2Fbs-json/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/glennsl","download_url":"https://codeload.github.com/glennsl/bs-json/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":234902750,"owners_count":18904524,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["bucklescript","js","json","ocaml"],"created_at":"2024-08-03T01:02:56.992Z","updated_at":"2025-10-04T21:30:26.408Z","avatar_url":"https://github.com/glennsl.png","language":"OCaml","funding_links":[],"categories":["OCaml"],"sub_categories":[],"readme":"# bs-json\n\nCompositional JSON encode/decode library for BuckleScript.\n\n**NOTE: This project has been deprecated. For rescript users, consider the spiritual successor library [rescript-json-combinators](https://github.com/glennsl/rescript-json-combinators). For melange users, consider [melange-json](https://github.com/melange-community/melange-json)**\n\n[![npm](https://img.shields.io/npm/v/@glennsl/bs-json.svg)](https://npmjs.org/@glennsl/bs-json)\n[![Travis](https://img.shields.io/travis/glennsl/bs-json/master.svg)](https://travis-ci.org/glennsl/bs-json)\n[![Coveralls](https://img.shields.io/coveralls/glennsl/bs-json/master.svg)](https://coveralls.io/github/glennsl/bs-json?branch=master)\n[![Issues](https://img.shields.io/github/issues/glennsl/bs-json.svg)](https://github.com/glennsl/bs-json/issues)\n[![Last Commit](https://img.shields.io/github/last-commit/glennsl/bs-json.svg)](https://github.com/glennsl/bs-json/commits/master)\n\nThe Decode module in particular provides a basic set of decoder functions to be composed into more complex decoders. A\ndecoder is a function that takes a `Js.Json.t` and either returns a value of the desired type if successful or raises a\n`DecodeError` exception if not. Other functions accept a decoder and produce another decoder. Like `array`, which when\ngiven a decoder for type `t` will return a decoder that tries to produce a value of type `t array`. So to decode an\n`int array` you combine `Json.Decode.int` with `Json.Decode.array` into `Json.Decode.(array int)`. An array of arrays of\nints? `Json.Decode.(array (array int))`. Dict containing arrays of ints? `Json.Decode.(dict (array int))`.\n\n## Example\n\n```reason\ntype line = {\n  start: point,\n  end_: point,\n  thickness: option(int)\n}\nand point = {\n  x: int,\n  y: int\n};\n\nmodule Decode = {\n  let point = json =\u003e\n    Json.Decode.{\n      x: json |\u003e field(\"x\", int),\n      y: json |\u003e field(\"y\", int)\n    };\n\n  let line = json =\u003e\n    Json.Decode.{\n      start:     json |\u003e field(\"start\", point),\n      end_:      json |\u003e field(\"end\", point),\n      thickness: json |\u003e optional(field(\"thickness\", int))\n    };\n};\n\nlet data = {| {\n  \"start\": { \"x\": 1, \"y\": -4 },\n  \"end\":   { \"x\": 5, \"y\": 8 }\n} |};\n\nlet line = data |\u003e Json.parseOrRaise\n                |\u003e Decode.line;\n```\n\nNOTE: `Json.Decode.{ ... }` creates an ordinary record, but also opens the `Json.Decode` module locally, within the\nscope delimited by the curly braces, so we don't have to qualify the functions we use from it, like `field`, `int` and\n`optional` here. You can also use `Json.Decode.( ... )` to open the module locally within the parentheses, if you're not\ncreating a record.\n\nSee [examples](https://github.com/glennsl/bs-json/blob/master/examples/) for more.\n\n## Installation\n\n```sh\nnpm install --save @glennsl/bs-json\n```\n\nThen add `@glennsl/bs-json` to `bs-dependencies` in your `bsconfig.json`:\n```js\n{\n  ...\n  \"bs-dependencies\": [\"@glennsl/bs-json\"]\n}\n```\n\n## Documentation\n\n### API\n\nFor the moment, please see the interface files:\n\n* [Json](https://github.com/glennsl/bs-json/blob/master/src/Json.mli)\n* [Json.Encode](https://github.com/glennsl/bs-json/blob/master/src/Json_encode.mli)\n* [Json.Decode](https://github.com/glennsl/bs-json/blob/master/src/Json_decode.mli)\n\n### Writing custom decoders and encoders\n\nIf you look at the type signature of `Json.Decode.array`, for example, you'll see it takes an `'a decoder` and returns an\n`'a array decoder`. `'a decoder` is just an alias for `Js.Json.t -\u003e 'a`, so if we expand the type signature of `array`\nwe'll get `(Js.Json.t -\u003e 'a) -\u003e Js.Json.t -\u003e 'a array`. We can now see that it is a function that takes a decoder and\nreturns a function, itself a decoder. Applying the `int` decoder to `array` will give us an `int array decoder`, a\nfunction `Js.Json.t -\u003e int array`.\n\nIf you've written a function that takes just `Js.Json.t` and returns user-defined types of your own, you've already been\nwriting composable decoders! Let's look at `Decode.point` from the example above:\n\n```reason\nlet point = json =\u003e {\n  open! Json.Decode;\n  {\n    x: json |\u003e field(\"x\", int),\n    y: json |\u003e field(\"y\", int)\n  };\n};\n```\n\nThis is a function `Js.Json.t -\u003e point`, or a `point decoder`. So if we'd like to decode an array of points, we can just\npass it to `Json.Decode.array` to get a `point array decoder` in return.\n\n#### Builders\n\nTo write a decoder _builder_ like `Json.Decode.array` we need to take another decoder as an argument, and thanks to\ncurrying we just need to apply it where we'd otherwise use a fixed decoder. Say we want to be able to decode both\n`int point`s and `float point`s. First we'd have to parameterize the type:\n\n```reason\ntype point('a) = {\n  x: 'a,\n  y: 'a\n}\n```\n\nThen we can change our `point` function from above to take and use a decoder argument:\n\n```reason\nlet point = (decodeNumber, json) =\u003e {\n  open! Json.Decode;\n  {\n    x: json |\u003e field(\"x\", decodeNumber),\n    y: json |\u003e field(\"y\", decodeNumber)\n  };\n};\n```\n\nAnd if we wish we can now create aliases for each variant:\n\n```reason\nlet intPoint = point(Json.Decode.int);\nlet floatPoint = point(Json.Decode.float);\n```\n\n#### Encoders\n\nEncoders work exactly the same way, just in reverse. `'a encoder` is just an alias for `'a -\u003e Js.Json.t`, and this also\ntransfers to composition: `'a encoder -\u003e 'a array encoder` expands to `('a -\u003e Js.Json.t) -\u003e 'a array -\u003e Js.Json.t`.\n\n## License\n\nThis work is dual-licensed under LGPL 3.0 and MPL 2.0.\nYou can choose between one of them if you use this work.\n\nPlease see LICENSE.LGPL-3.0 and LICENSE.MPL-2.0 for the full text of each license.\n\n`SPDX-License-Identifier: LGPL-3.0 OR MPL-2.0`\n\n## Changes\n\n### 5.0.4\n* Rewrote `Encode.list` to be stack-safe and much faster.\n\n### 5.0.2\n* Added `Json.Decode.id`\n\n### 5.0.1\n* Dual licensed as LGPL-3.0 and MPL-2.0. MPL is mostly equivalent to LGPL but relaxes its restriction on linking, which works better with the JavaScript packaging and distribution model.\n\n### 5.0.0\n* Removed deprecated `arrayOf` encoder\n* Renamed `dict` encoder to `jsonDict`\n* Added new `dict` encoder that takes an additional encoder argument used to encode the contained values, and so it's consistent with the respective `dict` decoder.\n\n### 4.0.0\n* Bumped `bs-platform` peer dependency to 5.0.4 to stop the compiler's complaining.\n\n### 3.0.0\n* Replace usage of `Js.Date.toJSON` with `Js.Date.toJSONUsafe`, which is exactly the same, just to avoid deprecation warnings for end users (Thanks Bob!)\n* Requires `bs-platform` \u003e= 4.0.2\n\n### 2.0.0\n* Removed `Json.Decode.boolean`, `Json.Encode.boolean`, `Json.Encode.booleanArray`\n* Requires `bs-platform` \u003e= 3.0.0\n\n### 1.3.1\n* Reverted commits that broke backwards compatibility despite only affecting the implementation\n\n### 1.3.0\n* Deprecated `Json.Decode.boolean`, `Json.Encode.boolean`, `Json.Encode.booleanArray`\n* Added `Json.Encode.boolArray`\n\n### 1.2.0\n* Added `Json.Encode.char` and `Json.Decode.char`\n\n### 1.1.0\n* Added \"stack traces\" to higher-order decoders, making it easier to find the location of an error.\n\n### 1.0.1\n* Moved repository from `reasonml-community/bs-json` to `glennsl/bs-json`\n* Renamed NPM package from `bs-json` to `@glennsl/bs-json`\n\n### 1.0.0\n* Replaced `Json.Encoder.array` with `Json.Encode.arrayOf` renamed to `array`. Deprecated `arrayOf` alias.\n* Added `Json.parse`, `Json.parseOrRaise`, `Json.stringify`\n* Added `date` encoder and decoder\n* Added `tuple2`/`tuple3`/`tuple4` encoders and decoders\n* Fixed bug where js integers \u003e 32-bit were rejected as integers by Json.Decode.int (#15)\n\n### 0.2.4\n* Added `Json.Encode.bool`\n* Added `Json.Encode.pair`\n* Added `Json.Encode.withDefault`\n* Added `Json.Encode.nullable`\n* Added `Json.Encode.arrayOf`\n* Added `Json.Encode.jsonArray` as replacement for `Json.Encode.array`\n* Deprecated `Json.Encode.array`\n\n### 0.2.3\n* Fixed embarrassing bug where an API was used that isn't available on IE (honestly more embarrassed on behalf of IE though)\n\n### 0.2.2\n* Added `Json.Decode.pair`\n\n### 0.2.1\n* Added `Json.Encode.list`\n\n### 0.2.0\n* Breaking: Renamed `Json.Encode.object_` to `Json.Encode.dict`\n* Added `Json.Encode.object_` taking a list of properties instead of a Json.Dict.t as before\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fglennsl%2Fbs-json","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fglennsl%2Fbs-json","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fglennsl%2Fbs-json/lists"}