lib/schema/index.js
function schema ({
  id,
  plural,
  service,
  attributes: attrDefs,
  relationships: relDefs,
  access,
  internal = false
}) {
  const attributes = {
    ...expandFields(attrDefs || {}),
    id: { type: 'string' },
    type: { type: 'string' },
    createdAt: { type: 'date' },
    updatedAt: { type: 'date' }
  }
  const relationships = expandFields(relDefs || {})

  const defaultAttrs = prepareDefaultAttrs(attributes, attrDefs)
  const defaultRels = prepareDefaultRels(relationships, relDefs)

  const castFn = cast({ id, attributes, relationships, defaultAttrs, defaultRels })

  return {
    id,
    plural: plural || `${id}s`,
    service,
    internal,
    attributes,
    relationships,
    access,

    /**
     * Will cast the given data according to the type. Attributes will be
     * coerced to the right format, relationships will be expanded to
     * relationship objects, and object properties will be moved from
     * `attributes` or be set with defaults.
     * @param {Object} data - The data to cast
     * @param {boolean} onlyMappedValues - Will use defaults if true
     * @returns {Object} Returned data in the format expected from the schema
     */
    cast (data, { onlyMappedValues = false } = {}) {
      return mapAny((data) => castFn(data, { onlyMappedValues }), data)
    },

    /**
     * Will create a query object for a relationship, given the relationship id
     * and a data item to get field values from.
     *
     * If the relationship is set up with a query definition object, each prop
     * of this object references field ids in the given data item. The returned
     * query object will have these ids replaced with actual field values.
     *
     * @param {string} relId - The id of a relationship
     * @param {Object} data - A data item to get field values from.
     * @returns {Object} Query object
     */
    castQueryParams (relId, data) {
      return castQueryParams(relId, data, { relationships })
    }
  }
}
function schema ({
  id,
  plural,
  service,
  attributes: attrDefs,
  relationships: relDefs,
  access,
  internal = false
}) {
  const attributes = {
    ...expandFields(attrDefs || {}),
    id: { type: 'string' },
    type: { type: 'string' },
    createdAt: { type: 'date' },
    updatedAt: { type: 'date' }
  }
  const relationships = expandFields(relDefs || {})

  const defaultAttrs = prepareDefaultAttrs(attributes, attrDefs)
  const defaultRels = prepareDefaultRels(relationships, relDefs)

  const castFn = cast({ id, attributes, relationships, defaultAttrs, defaultRels })

  return {
    id,
    plural: plural || `${id}s`,
    service,
    internal,
    attributes,
    relationships,
    access,

    /**
     * Will cast the given data according to the type. Attributes will be
     * coerced to the right format, relationships will be expanded to
     * relationship objects, and object properties will be moved from
     * `attributes` or be set with defaults.
     * @param {Object} data - The data to cast
     * @param {boolean} onlyMappedValues - Will use defaults if true
     * @returns {Object} Returned data in the format expected from the schema
     */
    cast (data, { onlyMappedValues = false } = {}) {
      return mapAny((data) => castFn(data, { onlyMappedValues }), data)
    },

    /**
     * Will create a query object for a relationship, given the relationship id
     * and a data item to get field values from.
     *
     * If the relationship is set up with a query definition object, each prop
     * of this object references field ids in the given data item. The returned
     * query object will have these ids replaced with actual field values.
     *
     * @param {string} relId - The id of a relationship
     * @param {Object} data - A data item to get field values from.
     * @returns {Object} Query object
     */
    castQueryParams (relId, data) {
      return castQueryParams(relId, data, { relationships })
    }
  }
}
Create a schema with the given id and service.
@param {Object} def - Object with id, plural, service, attributes, and relationships
@returns {Object} The created schema