{"id":13492909,"url":"https://github.com/gpbl/denormalizr","last_synced_at":"2025-03-28T11:31:03.870Z","repository":{"id":66139236,"uuid":"54338867","full_name":"gpbl/denormalizr","owner":"gpbl","description":"Denormalize data normalized with normalizr","archived":true,"fork":false,"pushed_at":"2017-06-12T14:41:51.000Z","size":213,"stargazers_count":228,"open_issues_count":6,"forks_count":24,"subscribers_count":5,"default_branch":"master","last_synced_at":"2024-10-31T07:34:04.537Z","etag":null,"topics":["data-structure","flux","normalizr","redux"],"latest_commit_sha":null,"homepage":"https://www.npmjs.com/package/denormalizr","language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/gpbl.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}},"created_at":"2016-03-20T20:31:07.000Z","updated_at":"2024-06-13T01:15:08.000Z","dependencies_parsed_at":null,"dependency_job_id":"21362361-2474-4f95-becc-591d3cc124c3","html_url":"https://github.com/gpbl/denormalizr","commit_stats":null,"previous_names":[],"tags_count":12,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gpbl%2Fdenormalizr","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gpbl%2Fdenormalizr/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gpbl%2Fdenormalizr/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gpbl%2Fdenormalizr/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/gpbl","download_url":"https://codeload.github.com/gpbl/denormalizr/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":246020827,"owners_count":20710827,"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":["data-structure","flux","normalizr","redux"],"created_at":"2024-07-31T19:01:10.363Z","updated_at":"2025-03-28T11:31:03.569Z","avatar_url":"https://github.com/gpbl.png","language":"JavaScript","funding_links":[],"categories":["JavaScript"],"sub_categories":[],"readme":"## Deprecated\n\n⚠️ This package [is deprecated](https://github.com/gpbl/denormalizr/issues/39). Please use normalizr's built-in [`denormalize()`](https://github.com/paularmstrong/normalizr/blob/master/docs/api.md#denormalizeinput-schema-entities), thanks!\n\n--- \n\n\u003cp align=\"center\"\u003e\n    \u003cimg style=\"margin: 0 auto\" src=\"https://cloud.githubusercontent.com/assets/120693/19218826/36eb41c2-8e04-11e6-98a5-2fdad6ca45fe.png\" width=\"359\"\u003e\n\u003c/p\u003e\n\n**denormalizr** takes data and entities normalized by [normalizr](https://github.com/gaearon/normalizr), and returns its complete tree – including nested entities.\n\nThis module is useful when consuming normalized data, e.g. in redux [selectors](http://redux.js.org/docs/recipes/ComputingDerivedData.html). While normalizr is great on making data consistent between the app, reassembling entities can be a tedious work. Denormalizr can help!\n\n\n[![npm version](https://img.shields.io/npm/v/denormalizr.svg?style=flat-square)](https://www.npmjs.com/package/denormalizr)\n[![npm downloads](https://img.shields.io/npm/dm/denormalizr.svg?style=flat-square)](https://www.npmjs.com/package/denormalizr)\n[![build status](https://img.shields.io/travis/gpbl/denormalizr/master.svg?style=flat-square)](https://travis-ci.org/gpbl/denormalizr) \n[![Code Climate](https://img.shields.io/codeclimate/github/gpbl/denormalizr.svg?style=flat-square)](https://codeclimate.com/github/gpbl/denormalizr) \n[![Coveralls](https://img.shields.io/coveralls/gpbl/denormalizr.svg?style=flat-square)](https://coveralls.io/github/gpbl/denormalizr)\n\n```\nnpm install denormalizr --save\n```\n\n```js\nimport { denormalize } from \"denormalizr\";\nconst denormalized = denormalize(entity, entities, entitySchema);\n```\n\n### Documentation \n\n* [API](#api)\n* [Examples](#examples)\n  * [Denormalize a single object](#denormalize-a-single-object)\n  * [Denormalize a list of objects](#denormalize-a-list-of-objects)\n  * [Denormalize by passing the id](#denormalize-by-passing-the-id)\n  * [Denormalize by passing a list of ids](#denormalize-by-passing-a-list-of-ids)\n  * [Recursive schemas](#recursive-schemas)\n* [Usage with Immutable](#usage-with-immutable)\n* [Changelog](CHANGELOG.md)\n\n## API\n\n```\ndenormalize (entity, entities, schema) -\u003e Object|Array|Immutable.Map|Immutable.List\n```\n\n### Params \n\n**entity** `{Object|Array|Number|String|Immutable.Map|Immutable.List}` \n\n\u003e The entity to denormalize, its id, or an array of entities or ids.\n\n**entities** `{Object|Immutable.Map}` \n\n\u003e An object to entities used to denormalize entity and its referred entities.\n\n**entitySchema** `{schema.Entity}`\n\n\u003e The normalizr schema used to define `entity`.\n\n### Returns\n\nThe denormalized object (or Immutable.Map), or an array of denormalized objects (or an Immutable.List).\n\n## Examples\n\nFor the following examples, consider to have a JSON response from a REST API consisting in a list of articles,\nwhere each article has a `author` field.\n\n```json\n{\n  \"articles\": [{\n    \"id\": 1,\n    \"title\": \"10 mindblowing reasons to prefer composition over inheritance\",\n    \"author\": {\n      \"id\": 1,\n      \"name\": \"Dan\"\n    },\n  }, {\n    \"id\": 2,\n    \"title\": \"You won't believe what this high order component is doing\",\n    \"author\": {\n      \"id\": 1,\n      \"name\": \"Dan\"\n    }\n  }]\n}\n```\n\nTo normalize this response with normalizr, we can define two Schemas: `articleSchema` and `authorSchema`.\n\n```js\nimport { normalize, schema } from 'normalizr';\n\nconst articleSchema = new schema.Entity('articles');\nconst authorSchema = new schema.Entity('authors');\nconst articleList = new schema.Array(articleSchema);\n\narticleSchema.define({\n  author: authorSchema,\n});\n\nconst normalized = normalize(response, {\n  articles: articleList,\n})\n```\n\nThis way we have the usual normalized object with entities:\n\n```js\n// content of normalized\n{ entities: \n   { articles: \n      { '1': \n         { id: 1,\n           title: '10 mindblowing reasons to prefer composition over inheritance',\n           author: 1 },\n        '2': \n         { id: 2,\n           title: 'You won\\'t believe what this high order component is doing',\n           author: 1 } },\n     authors: \n      { '1': \n         { id: 1, \n          name: 'Dan' } } },\n  result: { articles: [ 1, 2 ] } }\n```\n\nLet say we want to display the articles with ids `1` and `2`, and for each article its author. \n\nIn order to get the whole author object for each article, we need to loop over the author entities: \n\n```js\nconst articleIds = [1, 2];\nconst articles = articleIds.map(id =\u003e {\n  const article = normalized.entities.articles[id];\n  article.author = normalized.entities.authors[article.author];\n})\n```\n\nWe are basically reverting to the original JSON response. We are, indeed, *denormalizing*. \n\nWithout the need to know the entity's shapes, we can use denormalizr to simplify this process. Thus:\n\n```js\nimport { denormalize } from 'denormalizr';\n\nconst articles = denormalize([1,2], normalized.entities, articleList);\n```\n\n`articles` contains now the selected articles with the authors in them:\n\n```js\n// console.log(articles)\n[ { id: 1,\n    title: '10 mindblowing reasons to prefer composition over inheritance',\n    author: { id: 1, name: 'Dan' } },\n  { id: 2,\n    title: 'You won\\'t believe what this high order component is doing',\n    author: { id: 1, name: 'Dan' } } ]\n```\n\n`denormalize()` accepts as first parameter the **entity** we want to denormalize, which can be a \nsingle object, an array of object, a single id or an array of ids.\nThe second parameter is the whole **entities** object, which is consumed when the **entity schema** (third\nparameter) has references to one or more entities.\n\n### Denormalize a single object\n\n```js\nconst article = normalized.entities.articles['1'];\nconst denormalized = denormalize(article, normalized.entities, articleSchema);\n```\n```js\n// console.log(denormalized)\n{\n  id: 1,\n  title: 'Some Article',\n  author: {\n    id: 1,\n    name: 'Dan'\n  },\n}\n```\n### Denormalize a list of objects\n\n```js\nconst article1 = normalized.entities.articles['1'];\nconst article2 = normalized.entities.articles['2'];\n\nconst denormalized = denormalize([article1, article2], normalized.entities, articleListSchema);\n```\n\n```js\n// console.log(denormalized)\n[{\n  id: 1,\n  title: '10 mindblowing reasons to prefer composition over inheritance',\n  author: {\n    id: 1,\n    name: 'Dan'\n  },\n},{\n  id: 2,\n  title: 'You won\\'t believe what this high order component is doing',\n  author: {\n    id: 1,\n    name: 'Dan'\n  },\n}]\n```\n\n### Denormalize by passing the id\n\n```js\nconst denormalized = denormalize(1, normalized.entities, articleSchema);\n```\n\n```js\n// console.log(denormalized);\n{\n  id: 1,\n  title: '10 mindblowing reasons to prefer composition over inheritance',\n  author: {\n    id: 1,\n    name: 'Dan'\n  },\n}\n```\n\n### Denormalize by passing a list of ids\n\n```js\nconst denormalized = denormalize([1, 2], normalized.entities, articleListSchema);\n```\n\n```js\n// console.log(denormalized)\n[{\n  id: 1,\n  title: '10 mindblowing reasons to prefer composition over inheritance',\n  author: {\n    id: 1,\n    name: 'Dan'\n  },\n},{\n  id: 2,\n  title: 'You won\\'t believe what this high order component is doing',\n  author: {\n    id: 1,\n    name: 'Dan'\n  },\n}]\n```\n\n### Recursive schemas\n\nDenormalizr can handle circular references caused by recursive schemas (see [#2](https://github.com/gpbl/denormalizr/pull/2)). \n\nFor example, take these schemas, where articles have an author property containing a list of articles: \n\n```js\nconst articleSchema = new schema.Entity('articles');\nconst authorSchema = new schema.Entity('author');\nconst articleList = new schema.Array(articleSchema);\n\narticleSchema.define({\n  author: authorSchema,\n});\n\nauthorSchema.define({\n  articles: articleList,\n});\n\nconst JSONResponse = {\n  \"articles\": [{\n    \"id\": 2,\n    \"title\": \"You won\\'t believe what this high order component is doing\",\n    \"author\": {\n      \"id\": 1,\n      \"name\": 'Dan',\n      \"articles\": [2],\n    },\n  }],\n};\n\nconst normalized = normalize(JSONResponse, {\n  articles: articleList,\n});\n\nconst article = data.entities.articles['2'];\nconst denormalized = denormalize(article, data.entities, articleSchema);\n\nconsole.log(denormalized.author.articles[0] === denormalized)); // true\n\n```\n\n## Usage with Immutable\n\nDenormalizr works well with [immutable-js](https://facebook.github.io/immutable-js/), however recursive schemas are [not supported](https://github.com/facebook/immutable-js/issues/259):\n\n```js\n// This nested article contains only a reference to the author's id:\ndenormalized.author.articles[0].author === 1\n```\n\nRelated work:\n\n* [denormalizr-immutable](https://github.com/dehbmarques/denormalizr-immutable).\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgpbl%2Fdenormalizr","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fgpbl%2Fdenormalizr","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgpbl%2Fdenormalizr/lists"}