json-entity
The goal of this package is to provide an easy, reusable, and secure way to control and format data for output (e.g. from a REST API). Using an Entity, you can specify the fields you'd like to be included in the output representation of your data, as well as additional options for tweaking the structure. In this manner, this package takes a whitelist-only approach, forcing clear definitions of properties that will be exposed. This package is heavily inspired by Grape::Entity.
Example
const User = // Use `true` to always expose a field id: true firstName: true lastName: true // Use a function to return a custom value (return `undefined` to hide in JSON) { return ` `; } // Use an object to specify additional options location: // Expose field using an alternate name as: 'hometown' // Expose field only if function returns "truthy" optionsoutput === 'full' // See additional options below }; User; /* { id: 1, firstName: "Josh", lastName: "Swan", fullName: "Josh Swan", hometown: "San Francisco, CA" } */
Methods
Entity.isEntity
Static helper method to determine whether a supplied object is an Entity.
Entity; // trueEntity; // false
extend
Create a new Entity using the current Entity as a base. The new Entity inherits all exposed properties from the base in addition to any new properties specified on the object passed to extend
.
const User = id: true firstName: true; const UserFull = User; User;// { id: 1, firstName: "Josh" } UserFull;// { id: 1, firstName: "Josh", lastName: "Swan", location: "San Francisco, CA" }
represent
Use the exposed properties defined on the Entity to create a new object from the supplied data. Only whitelisted/exposed properties will be included in the resulting object, and any options specified will be used to modify the output.
const User = id: true firstName: true; const user = id: 1 firstName: 'Josh' lastName: 'Swan' ; const representation = User;// { id: 1, firstName: "Josh" } console; // false // Supply an options object that will be passed to `filter` and `if` functions. You can also set// `safe` to `false` in your options object to enable strict mode and throw an error on any missing// property, regardless of `require` option (see below).const representation = User;const throws = User;
Options
The following options can be specified using the { [property]: {options} } syntax shown in the example above. Multiple options can be specified and will work together, though some combinations may be logically incompatible.
String
as Expose a property using an alternate name.
const Example = fullName: as: 'name' ; Example;// { name: "Josh Swan" }
Any
default Provide a default value in case the property is not defined.
const Example = admin: default: false ; Example;// { admin: false }
Function
filter Filter an array value based on a function. The function is invoked with three arguments: item
(the current item of the array), data
(the full data object supplied to represent
), and options
(the options object supplied to represent
). Note: An error will be thrown if filter
is applied to a non-array value.
const Example = roles: role !== 'admin' ; Example;// { roles: ['user'] }
Function
if Conditionally expose a field based on function return value ("truthy" = expose). The function is invoked with the same arguments as represent
(i.e. data, [options={}]
).
const Example = country: objcountry !== 'US' ; Example;// { country: "CA" } Example;// { }
Boolean
merge Merge properties into parent directly (or concatenate if array). NOTE: When merging arrays from multiple properties using as
, the merge
option must be specified on all properties that will be merged or those without will overwrite any existing values during the merge process (see example below).
const Example = id: true address: merge: true ; Example;// { id: 1, city: "San Francisco", region: "CA", country: "US" } const Example2 = id: true roles: merge: true scopes: as: 'roles' merge: true // Merge into `roles` - must also specify `merge` on `roles`; Example2;// { id: 1, roles: ['admin', 'user'] }
Boolean
require Throw an error if this property is absent from data supplied to represent
.
const Example = id: require: true ; Example;// Error: data missing required property id!
Entity
using Apply an Entity to the value of the property (for nesting Entities).
const User = id: true firstName: true; const Example = user: using: User ; Example;// { user: { id: 1, firstName: "Josh" } }
Any
value Always use the specified value for this property, regardless of property value in supplied data.
const Example = id: true type: value: 'User' ; Example;// { id: 1, type: "User" }