jaune-web
Version:
172 lines (125 loc) • 4.76 kB
text/coffeescript
###*
* @file Source code for Json Responder
* @author Alvaro Juste
###
'use strict'
# 3rd
lodash = require 'lodash'
{bind} = lodash
{isObject} = lodash
{isNumber} = lodash
{extend} = lodash
{has} = lodash
{defaultsDeep} = lodash
{chunk} = lodash
# Configuration section for pages
PagesConfigSection = 'jaune.pages'
# Generic error for 404
GenericPage404 = 'notFound'
# Generic error for 500
GenericPage500 = 'error'
getDefaultLocalization = (page, settings, localeManager)->
{localization} = settings
return unless page.defaults and settings?.localization?.defaults?
for key in page.defaults
continue unless (setting = localization.defaults[key])?
if isObject settings
{key, value} = setting
{key, value: localeManager.getStringResource value, yes}
else
key: setting, value: localeManager.getStringResource setting, yes
resolveLocalization = (page, settings, data) ->
localeManager = @jaune.engine().Locale.Manager
localizations = export: {}
{localization} = settings
pageLocalization = page.localization
return localizations unless localization?
# client localization
format = settings.localization.format ? 'array'
{keys, title} = pageLocalization if pageLocalization?
# add default values
clientLoc = getDefaultLocalization page, settings, localeManager
# add page's specific localization
if title?
localizations.title = localeManager.getStringResource(
pageLocalization.title)
if keys?
for key of pageLocalization.keys
clientLoc.push {key, value: localeManager.getStringResource(
page.localization.keys[key], yes)}
switch format
when 'object'
result = {}
result[key] = value for {key, value} in clientLoc
localizations[localization.property] =
localizations.export[localization.property] = result
else
localizations[localization.property] =
localizations.export[localization.property] = localizations
localizations
splitIntoChunks = (chunkSize, data = export: {}) ->
raw = JSON.stringify data.export ? ''
chunked = chunks raw, chunkSize
exported : {
chunkAvailable : chunked.length > 0,
chunkCount : chunked.length,
chunks : chunked
}
resolvePageData = (page, settings, data) ->
{splitDataIntoChunks} = settings
if @_jaune_web_responder_global?
data = extend data ? {}, @_jaune_web_responder_global
# localization
defaultsDeep data, resolveLocalization.call(this, page, settings)
# split into chunks for browser support
if isNumber(splitDataIntoChunks) and splitDataIntoChunks > 0
extend data, splitIntoChunks.call(this, splitDataIntoChunks, data)
data
###*
* @function Respond with page response
* @param {*} [result.data] Data to be sent to client
* @param {Number} [result.securityCheck] Security check for request
* @param {Boolean} [opts.sendNotFoundOnNoData] Sends 404 on no data
###
send = (name, opts) ->
settings = @jaune.engine().Environment.getEnvProperty PagesConfigSection
page = settings?.definitions[name]
throw new Error "Page not defined: #{name}" unless page?
yield render this, page, opts?.result
###*
* @function Respond with not found
###
sendNotFound = (opts) ->
yield render(this,
getGenericPageSettings(this, GenericPage404), opts?.result)
###*
* @function Respond with error
###
sendError = (err, message) ->
yield render(this,
getGenericPageSettings(this, GenericPage500), {message, err})
getGenericPageSettings = (ctx, name) ->
settings = ctx.jaune.engine().Environment.getEnvProperty PagesConfigSection
settings?.definitions?.generic?[name]
###*
* @function Adds data that will be used in page responder to render the page
* @param {Object} ctx Context object
* @param {Object} data Data that extends global
###
extendGlobalData = (data) ->
return unless data?
@_jaune_web_responder_global = extend @_jaune_web_responder_global ? {}, data
render = (ctx, page, data) ->
httpResponder = ctx.jaune.responder.http
return httpResponder.notFound.call ctx unless page
settings = ctx.jaune.engine().Environment.getEnvProperty PagesConfigSection
data = data ? ctx.jaune.data() ? ''
if ctx.render.constructor.name is 'GeneratorFunction'
yield ctx.render page.view, resolvePageData.call(ctx, page, settings, data)
else
ctx.render page.view, resolvePageData.call(ctx, page, settings, data)
module.exports = (context) ->
send: bind send, context
sendNotFound: bind sendNotFound, context
sendError: bind sendError, context
extendGlobalData: bind extendGlobalData, context