Created
March 7, 2016 08:23
-
-
Save dimik/bb656be267f91c1e9c63 to your computer and use it in GitHub Desktop.
Traverson context cache decorators and example
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import client from './client' | |
import {Base as TraversonBase} from 'ydw-ui-common/traverson' | |
TraversonBase.client = client | |
class CoachApi extends TraversonBase { | |
getPlanEvents(params) { | |
return this.getResource([ | |
'planEvents', | |
'search', | |
{type: 'link-rel', value: 'by-parameters', params: params} | |
]).then(data => { | |
return data._embedded.planEvents | |
}).catch(() => { | |
return [] | |
}) | |
} | |
createMotion(data) { | |
return this.createResource( | |
['motions'], | |
data | |
) | |
} | |
patchPlanEvent(eventId, data) { | |
return this.patchResource([ | |
'planEvents', | |
'search', | |
{type: 'link-rel', value: 'by-event-id', params: {eventId: eventId}}, | |
'self' | |
], data).catch(() => { | |
return {} | |
}) | |
} | |
deletePlanEvent(eventId) { | |
return this.deleteResource([ | |
'planEvents', | |
'search', | |
{type: 'link-rel', value: 'by-event-id', params: {eventId: eventId}}, | |
'self' | |
]).catch(() => { | |
return {} | |
}) | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import traverson from 'traverson' | |
import JsonHalAdapter from 'traverson-hal' | |
traverson.registerMediaType(JsonHalAdapter.mediaType, JsonHalAdapter) | |
const API_CONFIG = { | |
url: 'http://localhost:8080/api/v1/', | |
auth: { | |
user: 'member', | |
pass: 'member' | |
} | |
} | |
const client = traverson | |
.from(API_CONFIG.url) | |
.jsonHal() | |
.withRequestOptions({ | |
auth: API_CONFIG.auth, | |
headers: { | |
'Content-Type': 'application/hal+json', | |
'Accept': 'application/hal+json', | |
} | |
}) | |
export default client |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
function noop() {} | |
function promisify(target, name, descriptor) { | |
let fn = descriptor.value | |
descriptor.value = function(...args) { | |
let callback = args[fn.length - 1] || noop | |
return new Promise(function(resolve, reject) { | |
fn.apply(target, args.slice(0, fn.length - 1).concat(function(err, val, ...other) { | |
callback(err, val, ...other) | |
if (err) { | |
reject(err) | |
} | |
else { | |
resolve(val) | |
} | |
})) | |
}) | |
} | |
return descriptor | |
} | |
export default promisify |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import {promisify} from '../core-decorators' | |
import ContextCache from './TraversonContextCache' | |
class TraversonBase { | |
@ContextCache.store | |
@ContextCache.retrieve | |
@promisify | |
getResource(links, context=TraversonBase.client, callback) { | |
let [{ | |
params, | |
...link, | |
}] = links | |
if (typeof context.continue === 'function') { | |
context = context.continue() | |
} | |
context = context | |
.newRequest() | |
.follow(link.value ? [link] : links) | |
if (params) { | |
context = context.withTemplateParameters(params) | |
} | |
context.getResource(callback) | |
} | |
@promisify | |
createResource(links, resource, callback) { | |
if (links.length === 1) { | |
return this._createResource(links, resource, TraversonBase.client, callback) | |
} | |
let getLinks = links.slice(0, -1) | |
this.getResource(getLinks) | |
.then(_ => { | |
this._createResource( | |
links.slice(-1), | |
resource, | |
ContextCache.get(getLinks).continue(), | |
callback | |
) | |
}) | |
} | |
_createResource(links, resource, context, callback) { | |
context | |
.newRequest() | |
.follow(links) | |
.convertResponseToObject() | |
.post(resource, callback) | |
} | |
@promisify | |
patchResource(links, body, callback) { | |
if (links.length === 1) { | |
return this._patchResource(links, body, TraversonBase.client, callback) | |
} | |
let getLinks = links.slice(0, -1) | |
this.getResource(getLinks) | |
.then(_ => { | |
this._patchResource( | |
links.slice(-1), | |
body, | |
ContextCache.get(getLinks).continue(), | |
callback | |
) | |
}) | |
} | |
_patchResource(links, body, context, callback) { | |
context | |
.newRequest() | |
.follow(links) | |
.convertResponseToObject() | |
.patch(body, callback) | |
} | |
@promisify | |
deleteResource(links, callback) { | |
if (links.length === 1) { | |
return this._deleteResource(links, TraversonBase.client, callback) | |
} | |
let getLinks = links.slice(0, -1) | |
this.getResource(getLinks) | |
.then(_ => { | |
this._deleteResource( | |
links.slice(-1), | |
ContextCache.get(getLinks).continue(), | |
callback | |
) | |
}) | |
} | |
_deleteResource(links, context, callback) { | |
context | |
.newRequest() | |
.follow(links) | |
.delete(callback) | |
} | |
} | |
export default TraversonBase |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
let cache = {} | |
function putKey(key, val) { | |
return cache[JSON.stringify(key)] = val | |
} | |
function get(key) { | |
return cache[JSON.stringify(key)] | |
} | |
function dropKey(key) { | |
delete cache[JSON.stringify(key)] | |
} | |
function hasKey(key) { | |
return JSON.stringify(key) in cache | |
} | |
function drop() { | |
cache = {} | |
} | |
function retrieve(target, name, descriptor) { | |
let fn = descriptor.value | |
descriptor.value = function(links, _, callback) { | |
return fn.call(target, links.slice(-1), get(links.slice(0, -1)), callback) | |
} | |
return descriptor | |
} | |
function store(target, name, descriptor) { | |
let fn = descriptor.value | |
descriptor.value = function(links, _) { | |
if (hasKey(links)) { | |
dropKey(links) | |
} | |
let promises = [] | |
for (let i = 0, len = links.length; i < len; i++) { | |
let key = links.slice(0, i + 1) | |
if (!hasKey(key)) { | |
promises.push( | |
fn.bind(target, key, _, function(err, resource, context) { | |
putKey(key, context) | |
}) | |
) | |
} | |
} | |
return promises.reduce(function(soFar, fn) { | |
return soFar.then(fn) | |
}, Promise.resolve()) | |
} | |
return descriptor | |
} | |
export default { | |
store: store, | |
retrieve: retrieve, | |
get: get, | |
hasKey: hasKey, | |
dropKey: dropKey, | |
drop: drop, | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment