{"id":13507117,"url":"https://github.com/devinus/poison","last_synced_at":"2025-05-13T19:10:59.011Z","repository":{"id":15762921,"uuid":"18501766","full_name":"devinus/poison","owner":"devinus","description":"An incredibly fast, pure Elixir JSON library","archived":false,"fork":false,"pushed_at":"2024-08-12T12:23:55.000Z","size":2376,"stargazers_count":2034,"open_issues_count":39,"forks_count":217,"subscribers_count":33,"default_branch":"master","last_synced_at":"2025-05-10T11:37:56.394Z","etag":null,"topics":["elixir","elixir-libraries","json","json-library","json-parser"],"latest_commit_sha":null,"homepage":"","language":"Elixir","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":"sole/Animated_GIF","license":"0bsd","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/devinus.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","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,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2014-04-06T23:29:31.000Z","updated_at":"2025-04-29T06:31:15.000Z","dependencies_parsed_at":"2024-05-01T17:06:45.689Z","dependency_job_id":"d08a5abb-03ed-4eaf-99f1-41d9011c6ab2","html_url":"https://github.com/devinus/poison","commit_stats":{"total_commits":219,"total_committers":40,"mean_commits":5.475,"dds":0.4246575342465754,"last_synced_commit":"ffb05bab421b6c29d7e2f0663a0b821bd5fa163a"},"previous_names":[],"tags_count":24,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/devinus%2Fpoison","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/devinus%2Fpoison/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/devinus%2Fpoison/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/devinus%2Fpoison/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/devinus","download_url":"https://codeload.github.com/devinus/poison/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":253411468,"owners_count":21904141,"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":["elixir","elixir-libraries","json","json-library","json-parser"],"created_at":"2024-08-01T02:00:24.324Z","updated_at":"2025-05-13T19:10:58.994Z","avatar_url":"https://github.com/devinus.png","language":"Elixir","funding_links":[],"categories":["Top 20 packages","JSON","Elixir","Uncategorized"],"sub_categories":["Uncategorized"],"readme":"# Poison\n\n[![Build Status](https://img.shields.io/github/actions/workflow/status/devinus/poison/ci.yml)](https://github.com/devinus/poison/actions/workflows/ci.yml)\n[![Coverage Status](https://img.shields.io/coverallsCoverage/github/devinus/poison)](https://coveralls.io/github/devinus/poison?branch=master))\n[![Hex.pm Version](https://img.shields.io/hexpm/v/poison)](https://hex.pm/packages/poison)\n[![Hex.pm Download Total](https://img.shields.io/hexpm/dt/poison)](https://hex.pm/packages/poison)\n[![Hex.pm Dependents](https://img.shields.io/librariesio/dependents/hex/poison)](https://hex.pm/packages/poison)\n\nPoison is a new JSON library for Elixir focusing on wicked-fast **speed**\nwithout sacrificing **simplicity**, **completeness**, or **correctness**.\n\nPoison takes several approaches to be the fastest JSON library for Elixir.\n\nPoison uses extensive [sub binary matching][1], a **hand-rolled parser** using\nseveral techniques that are [known to benefit BeamAsm][2] for JIT compilation,\n[IO list][3] encoding and **single-pass** decoding.\n\nPoison benchmarks sometimes puts Poison's performance close to `jiffy` and\nusually faster than other Erlang/Elixir libraries.\n\nPoison fully conforms to [RFC 8259][4], [ECMA 404][5], and fully passes the\n[JSONTestSuite][6].\n\n## Installation\n\nFirst, add Poison to your `mix.exs` dependencies:\n\n```elixir\ndef deps do\n  [{:poison, \"~\u003e 6.0\"}]\nend\n```\n\nThen, update your dependencies:\n\n```sh\nmix deps.get\n```\n\n## Usage\n\n```elixir\nPoison.encode!(%{\"age\" =\u003e 27, \"name\" =\u003e \"Devin Torres\"})\n#=\u003e \"{\\\"name\\\":\\\"Devin Torres\\\",\\\"age\\\":27}\"\n\nPoison.decode!(~s({\"name\": \"Devin Torres\", \"age\": 27}))\n#=\u003e %{\"age\" =\u003e 27, \"name\" =\u003e \"Devin Torres\"}\n\ndefmodule Person do\n  @derive [Poison.Encoder]\n  defstruct [:name, :age]\nend\n\nPoison.encode!(%Person{name: \"Devin Torres\", age: 27})\n#=\u003e \"{\\\"name\\\":\\\"Devin Torres\\\",\\\"age\\\":27}\"\n\nPoison.decode!(~s({\"name\": \"Devin Torres\", \"age\": 27}), as: %Person{})\n#=\u003e %Person{name: \"Devin Torres\", age: 27}\n\nPoison.decode!(~s({\"people\": [{\"name\": \"Devin Torres\", \"age\": 27}]}),\n  as: %{\"people\" =\u003e [%Person{}]})\n#=\u003e %{\"people\" =\u003e [%Person{age: 27, name: \"Devin Torres\"}]}\n```\n\nEvery component of Poison (encoder, decoder, and parser) are all usable on\ntheir own without buying into other functionality. For example, if you were\ninterested purely in the speed of parsing JSON without a decoding step, you\ncould simply call `Poison.Parser.parse`.\n\n## Parser\n\n```iex\niex\u003e Poison.Parser.parse!(~s({\"name\": \"Devin Torres\", \"age\": 27}), %{})\n%{\"name\" =\u003e \"Devin Torres\", \"age\" =\u003e 27}\niex\u003e Poison.Parser.parse!(~s({\"name\": \"Devin Torres\", \"age\": 27}), %{keys: :atoms!})\n%{name: \"Devin Torres\", age: 27}\n```\n\nNote that `keys: :atoms!` reuses existing atoms, i.e. if `:name` was not\nallocated before the call, you will encounter an `argument error` message.\n\nYou can use the `keys: :atoms` variant to make sure all atoms are created as\nneeded. However, unless you absolutely know what you're doing, do **not** do\nit. Atoms are not garbage-collected, see\n[Erlang Efficiency Guide](http://www.erlang.org/doc/efficiency_guide/commoncaveats.html)\nfor more info:\n\n\u003e Atoms are not garbage-collected. Once an atom is created, it will never be\n\u003e removed. The emulator will terminate if the limit for the number of atoms\n\u003e (1048576 by default) is reached.\n\n## Encoder\n\n```iex\niex\u003e Poison.Encoder.encode([1, 2, 3], %{}) |\u003e IO.iodata_to_binary\n\"[1,2,3]\"\n```\n\nAnything implementing the Encoder protocol is expected to return an\n[IO list][7] to be embedded within any other Encoder's implementation and\npassable to any IO subsystem without conversion.\n\n```elixir\ndefimpl Poison.Encoder, for: Person do\n  def encode(%{name: name, age: age}, options) do\n    Poison.Encoder.BitString.encode(\"#{name} (#{age})\", options)\n  end\nend\n```\n\nFor maximum performance, make sure you `@derive [Poison.Encoder]` for any\nstruct you plan on encoding.\n\n### Encoding only some attributes\n\nWhen deriving structs for encoding, it is possible to select or exclude\nspecific attributes. This is achieved by deriving `Poison.Encoder` with the\n`:only` or `:except` options set:\n\n```elixir\ndefmodule PersonOnlyName do\n  @derive {Poison.Encoder, only: [:name]}\n  defstruct [:name, :age]\nend\n\ndefmodule PersonWithoutName do\n  @derive {Poison.Encoder, except: [:name]}\n  defstruct [:name, :age]\nend\n```\n\nIn case both `:only` and `:except` keys are defined, the `:except` option is\nignored.\n\n### Key Validation\n\nAccording to [RFC 8259][4] keys in a JSON object should be unique. This is\nenforced and resolved in different ways in other libraries. In the Ruby JSON\nlibrary for example, the output generated from encoding a hash with a duplicate\nkey (say one is a string, the other an atom) will include both keys. When\nparsing JSON of this type, Chromium will override all previous values with the\nfinal one.\n\nPoison will generate JSON with duplicate keys if you attempt to encode a map\nwith atom and string keys whose encoded names would clash. If you'd like to\nensure that your generated JSON doesn't have this issue, you can pass the\n`strict_keys: true` option when encoding. This will force the encoding to fail.\n\n_Note:_ Validating keys can cause a small performance hit.\n\n```iex\niex\u003e Poison.encode!(%{:foo =\u003e \"foo1\", \"foo\" =\u003e \"foo2\"}, strict_keys: true)\n** (Poison.EncodeError) duplicate key found: :foo\n```\n\n## Benchmarking\n\n```sh\nMIX_ENV=bench mix run bench/run.exs\n```\n\n### Current Benchmarks\n\nAs of 2024-06-06:\n\n- Amazon EC2 c6i.2xlarge instance running Ubuntu Server 22.04:\n  \u003chttps://gist.github.com/devinus/afb351ae45194a6b93b6db9bf2d4c163\u003e\n\n## License\n\nPoison is released under the [public-domain-equivalent][8] [0BSD][9] license.\n\n[1]: https://erlang.org/euc/07/papers/1700Gustafsson.pdf\n[2]: https://erlang.org/documentation/doc-12.0-rc1/erts-12.0/doc/html/BeamAsm.html\n[3]: https://jlouisramblings.blogspot.com/2013/07/problematic-traits-in-erlang.html\n[4]: https://datatracker.ietf.org/doc/html/rfc8259\n[5]: https://ecma-international.org/wp-content/uploads/ECMA-404_2nd_edition_december_2017.pdf\n[6]: https://github.com/nst/JSONTestSuite\n[7]: https://prog21.dadgum.com/70.html\n[8]: https://en.wikipedia.org/wiki/Public-domain-equivalent_license\n[9]: https://opensource.org/licenses/0BSD\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdevinus%2Fpoison","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fdevinus%2Fpoison","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdevinus%2Fpoison/lists"}