graphql-hooks
Advanced tools
Comparing version 3.6.0 to 3.6.1
@@ -6,2 +6,10 @@ # Change Log | ||
## [3.6.1](https://github.com/nearform/graphql-hooks/compare/graphql-hooks@3.6.0...graphql-hooks@3.6.1) (2019-08-05) | ||
**Note:** Version bump only for package graphql-hooks | ||
# [3.6.0](https://github.com/nearform/graphql-hooks/compare/graphql-hooks@3.5.1...graphql-hooks@3.6.0) (2019-06-21) | ||
@@ -8,0 +16,0 @@ |
@@ -24,16 +24,31 @@ (function (global, factory) { | ||
function _objectSpread(target) { | ||
function ownKeys(object, enumerableOnly) { | ||
var keys = Object.keys(object); | ||
if (Object.getOwnPropertySymbols) { | ||
var symbols = Object.getOwnPropertySymbols(object); | ||
if (enumerableOnly) symbols = symbols.filter(function (sym) { | ||
return Object.getOwnPropertyDescriptor(object, sym).enumerable; | ||
}); | ||
keys.push.apply(keys, symbols); | ||
} | ||
return keys; | ||
} | ||
function _objectSpread2(target) { | ||
for (var i = 1; i < arguments.length; i++) { | ||
var source = arguments[i] != null ? arguments[i] : {}; | ||
var ownKeys = Object.keys(source); | ||
if (typeof Object.getOwnPropertySymbols === 'function') { | ||
ownKeys = ownKeys.concat(Object.getOwnPropertySymbols(source).filter(function (sym) { | ||
return Object.getOwnPropertyDescriptor(source, sym).enumerable; | ||
})); | ||
if (i % 2) { | ||
ownKeys(source, true).forEach(function (key) { | ||
_defineProperty(target, key, source[key]); | ||
}); | ||
} else if (Object.getOwnPropertyDescriptors) { | ||
Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); | ||
} else { | ||
ownKeys(source).forEach(function (key) { | ||
Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); | ||
}); | ||
} | ||
ownKeys.forEach(function (key) { | ||
_defineProperty(target, key, source[key]); | ||
}); | ||
} | ||
@@ -224,3 +239,3 @@ | ||
var fetchOptions = _objectSpread({}, this.fetchOptions, options.fetchOptionsOverrides); | ||
var fetchOptions = _objectSpread2({}, this.fetchOptions, {}, options.fetchOptionsOverrides); | ||
@@ -231,2 +246,16 @@ return { | ||
}; | ||
}; | ||
_proto.getCache = function getCache(cacheKey) { | ||
var cacheHit = this.cache ? this.cache.get(cacheKey) : null; | ||
if (cacheHit) { | ||
return cacheHit; | ||
} | ||
}; | ||
_proto.saveCache = function saveCache(cacheKey, value) { | ||
if (this.cache) { | ||
this.cache.set(cacheKey, value); | ||
} | ||
} // Kudos to Jayden Seric (@jaydenseric) for this piece of code. | ||
@@ -241,6 +270,6 @@ // See original source: https://github.com/jaydenseric/graphql-react/blob/82d576b5fe6664c4a01cd928d79f33ddc3f7bbfd/src/universal/graphqlFetchOptions.mjs. | ||
var fetchOptions = _objectSpread({ | ||
var fetchOptions = _objectSpread2({ | ||
method: 'POST', | ||
headers: _objectSpread({}, this.headers) | ||
}, this.fetchOptions, fetchOptionsOverrides); | ||
headers: _objectSpread2({}, this.headers) | ||
}, this.fetchOptions, {}, fetchOptionsOverrides); | ||
@@ -326,2 +355,21 @@ var _extractFiles = extractFiles(operation), | ||
function dequal(foo, bar) { | ||
var ctor, len; | ||
if (foo === bar) return true; | ||
if (foo && bar && (ctor=foo.constructor) === bar.constructor) { | ||
if (ctor === Date) return foo.getTime() === bar.getTime(); | ||
if (ctor === RegExp) return foo.toString() === bar.toString(); | ||
if (ctor === Array && (len=foo.length) === bar.length) { | ||
while (len-- && dequal(foo[len], bar[len])); | ||
return len === -1; | ||
} | ||
if (ctor === Object) { | ||
if (Object.keys(foo).length !== Object.keys(bar).length) return false; | ||
for (len in foo) if (!(len in bar) || !dequal(foo[len], bar[len])) return false; | ||
return true; | ||
} | ||
} | ||
return foo !== foo && bar !== bar; | ||
} | ||
var actionTypes = { | ||
@@ -344,3 +392,3 @@ RESET_STATE: 'RESET_STATE', | ||
return _objectSpread({}, state, { | ||
return _objectSpread2({}, state, { | ||
loading: true | ||
@@ -356,3 +404,3 @@ }); | ||
return _objectSpread({}, action.result, { | ||
return _objectSpread2({}, action.result, { | ||
cacheHit: true, | ||
@@ -363,3 +411,4 @@ loading: false | ||
case actionTypes.REQUEST_RESULT: | ||
return _objectSpread({}, action.result, { | ||
return _objectSpread2({}, action.result, { | ||
data: state.data && action.result.data && action.updateData ? action.updateData(state.data, action.result.data) : action.result.data, | ||
cacheHit: false, | ||
@@ -373,2 +422,12 @@ loading: false | ||
} | ||
function useDeepCompareCallback(callback, deps) { | ||
var ref = React.useRef(); | ||
if (!dequal(deps, ref.current)) { | ||
ref.current = deps; | ||
} | ||
return React.useCallback(callback, ref.current); | ||
} | ||
/* | ||
@@ -405,3 +464,3 @@ options include: | ||
var initialState = _objectSpread({}, initialCacheHit, { | ||
var initialState = _objectSpread2({}, initialCacheHit, { | ||
cacheHit: !!initialCacheHit, | ||
@@ -436,8 +495,8 @@ loading: isDeferred ? false : !initialCacheHit | ||
function fetchData(newOpts) { | ||
var fetchData = useDeepCompareCallback(function (newOpts) { | ||
if (!isMounted.current) return Promise.resolve(); | ||
var revisedOpts = _objectSpread({}, initialOpts, newOpts); | ||
var revisedOpts = _objectSpread2({}, initialOpts, {}, newOpts); | ||
var revisedOperation = _objectSpread({}, operation, { | ||
var revisedOperation = _objectSpread2({}, operation, { | ||
variables: revisedOpts.variables, | ||
@@ -452,3 +511,3 @@ operationName: revisedOpts.operationName | ||
activeCacheKey.current = revisedCacheKey; | ||
var cacheHit = revisedOpts.skipCache || !client.cache ? null : client.cache.get(revisedCacheKey); | ||
var cacheHit = revisedOpts.skipCache ? null : client.getCache(revisedCacheKey); | ||
@@ -467,12 +526,11 @@ if (cacheHit) { | ||
return client.request(revisedOperation, revisedOpts).then(function (result) { | ||
if (state.data && result.data && revisedOpts.updateData) { | ||
if (typeof revisedOpts.updateData !== 'function') { | ||
throw new Error('options.updateData must be a function'); | ||
} | ||
result.data = revisedOpts.updateData(state.data, result.data); | ||
if (revisedOpts.updateData && typeof revisedOpts.updateData !== 'function') { | ||
throw new Error('options.updateData must be a function'); | ||
} | ||
if (revisedOpts.useCache && client.cache) { | ||
client.cache.set(revisedCacheKey, result); | ||
var actionResult = _objectSpread2({}, result); | ||
if (revisedOpts.useCache) { | ||
actionResult.useCache = true; | ||
actionResult.cacheKey = revisedCacheKey; | ||
} | ||
@@ -483,3 +541,4 @@ | ||
type: actionTypes.REQUEST_RESULT, | ||
result: result | ||
updateData: revisedOpts.updateData, | ||
result: actionResult | ||
}); | ||
@@ -490,4 +549,10 @@ } | ||
}); | ||
} | ||
}, [client, initialOpts, operation]); // We perform caching after reducer update | ||
// To include the outcome of updateData | ||
React.useEffect(function () { | ||
if (state.useCache) { | ||
client.saveCache(state.cacheKey, state); | ||
} | ||
}, [client, state]); | ||
return [fetchData, state]; | ||
@@ -505,3 +570,3 @@ } | ||
var allOpts = _objectSpread({}, defaultOpts, opts); | ||
var allOpts = _objectSpread2({}, defaultOpts, {}, opts); | ||
@@ -520,3 +585,3 @@ var client = React.useContext(ClientContext); | ||
// result may already be in the cache from previous SSR iterations | ||
if (!state.data && !state.error) { | ||
if (!state.loading && !state.data && !state.error) { | ||
var p = queryReq(); | ||
@@ -534,4 +599,4 @@ client.ssrPromises.push(p); | ||
return _objectSpread({}, state, { | ||
refetch: function refetch(options) { | ||
return _objectSpread2({}, state, { | ||
refetch: React.useCallback(function (options) { | ||
if (options === void 0) { | ||
@@ -541,3 +606,3 @@ options = {}; | ||
return queryReq(_objectSpread({ | ||
return queryReq(_objectSpread2({ | ||
skipCache: true, | ||
@@ -551,3 +616,3 @@ // don't call the updateData that has been passed into useQuery here | ||
}, options)); | ||
} | ||
}, [queryReq]) | ||
}); | ||
@@ -557,3 +622,3 @@ } | ||
var useManualQuery = function useManualQuery(query, options) { | ||
return useClientRequest(query, _objectSpread({ | ||
return useClientRequest(query, _objectSpread2({ | ||
useCache: true, | ||
@@ -565,3 +630,3 @@ isManual: true | ||
var useMutation = function useMutation(query, options) { | ||
return useClientRequest(query, _objectSpread({ | ||
return useClientRequest(query, _objectSpread2({ | ||
isMutation: true | ||
@@ -568,0 +633,0 @@ }, options)); |
@@ -1,1 +0,1 @@ | ||
!function(e,r){"object"==typeof exports&&"undefined"!=typeof module?r(exports,require("react")):"function"==typeof define&&define.amd?define(["exports","react"],r):r((e=e||self).GraphQLHooks={},e.React)}(this,function(e,r){"use strict";function t(e,r,t){return r in e?Object.defineProperty(e,r,{value:t,enumerable:!0,configurable:!0,writable:!0}):e[r]=t,e}function o(e){for(var r=1;arguments.length>r;r++){var o=null!=arguments[r]?arguments[r]:{},n=Object.keys(o);"function"==typeof Object.getOwnPropertySymbols&&(n=n.concat(Object.getOwnPropertySymbols(o).filter(function(e){return Object.getOwnPropertyDescriptor(o,e).enumerable}))),n.forEach(function(r){t(e,r,o[r])})}return e}var n=(r=r&&r.hasOwnProperty("default")?r.default:r).createContext();n.displayName="ClientContext";var a=function(e){var r=e.name,t=e.type;this.uri=e.uri,this.name=r,this.type=t};var i=function(){function e(e){if(void 0===e&&(e={}),!e.url)throw Error("GraphQLClient: config.url is required");if(e.fetch&&"function"!=typeof e.fetch)throw Error("GraphQLClient: config.fetch must be a function");if(!e.fetch&&!fetch)throw Error("GraphQLClient: fetch must be polyfilled or passed in new GraphQLClient({ fetch })");if(e.ssrMode&&!e.cache)throw Error("GraphQLClient: config.cache is required when in ssrMode");this.cache=e.cache,this.headers=e.headers||{},this.ssrMode=e.ssrMode,this.ssrPromises=[],this.url=e.url,this.fetch=e.fetch||fetch.bind(),this.fetchOptions=e.fetchOptions||{},this.logErrors=void 0===e.logErrors||e.logErrors,this.onError=e.onError}var r=e.prototype;return r.setHeader=function(e,r){return this.headers[e]=r,this},r.setHeaders=function(e){return this.headers=e,this},r.removeHeader=function(e){return delete this.headers[e],this},r.logErrorResult=function(e){var r=e.result,t=e.operation;if(this.onError)return this.onError({result:r,operation:t});console.error("GraphQL Hooks Error"),console.groupCollapsed("---\x3e Full Error Details"),console.groupCollapsed("Operation:"),console.log(t),console.groupEnd(),r.fetchError&&(console.groupCollapsed("FETCH ERROR:"),console.log(r.fetchError),console.groupEnd()),r.httpError&&(console.groupCollapsed("HTTP ERROR:"),console.log(r.httpError),console.groupEnd()),r.graphQLErrors&&r.graphQLErrors.length>0&&(console.groupCollapsed("GRAPHQL ERROR:"),r.graphQLErrors.forEach(function(e){return console.log(e)}),console.groupEnd()),console.groupEnd()},r.generateResult=function(e){var r=e.fetchError,t=e.httpError,o=e.graphQLErrors;return{error:!!(o&&o.length>0||r||t),fetchError:r,httpError:t,graphQLErrors:o,data:e.data}},r.getCacheKey=function(e,r){return void 0===r&&(r={}),{operation:e,fetchOptions:o({},this.fetchOptions,r.fetchOptionsOverrides)}},r.getFetchOptions=function(e,r){void 0===r&&(r={});var t=o({method:"POST",headers:o({},this.headers)},this.fetchOptions,r),n=function e(r,t){var o;void 0===t&&(t="");var n=new Map;function i(e,r){var t=n.get(r);t?t.push.apply(t,e):n.set(r,e)}if("undefined"!=typeof File&&r instanceof File||"undefined"!=typeof Blob&&r instanceof Blob||r instanceof a)o=null,i([t],r);else{var s=t?t+".":"";if("undefined"!=typeof FileList&&r instanceof FileList)o=Array.prototype.map.call(r,function(e,r){return i([""+s+r],e),null});else if(Array.isArray(r))o=r.map(function(r,t){var o=e(r,""+s+t);return o.files.forEach(i),o.clone});else if(r&&r.constructor===Object)for(var u in o={},r){var c=e(r[u],""+s+u);c.files.forEach(i),o[u]=c.clone}else o=r}return{clone:o,files:n}}(e),i=n.files,s=JSON.stringify(n.clone);if(i.size){var u=new FormData;u.append("operations",s);var c={},f=0;i.forEach(function(e){c[++f]=e}),u.append("map",JSON.stringify(c)),f=0,i.forEach(function(e,r){u.append(""+ ++f,r,r.name)}),t.body=u}else t.headers["Content-Type"]="application/json",t.body=s;return t},r.request=function(e,r){var t=this;return void 0===r&&(r={}),this.fetch(this.url,this.getFetchOptions(e,r.fetchOptionsOverrides)).then(function(e){return e.ok?e.json().then(function(e){return t.generateResult({graphQLErrors:e.errors,data:e.data})}):e.text().then(function(r){return t.generateResult({httpError:{status:e.status,statusText:e.statusText,body:r}})})}).catch(function(e){return t.generateResult({fetchError:e})}).then(function(r){return r.error&&t.logErrors&&t.logErrorResult({result:r,operation:e}),r})},e}(),s={RESET_STATE:"RESET_STATE",LOADING:"LOADING",CACHE_HIT:"CACHE_HIT",REQUEST_RESULT:"REQUEST_RESULT"};function u(e,r){switch(r.type){case s.RESET_STATE:return r.initialState;case s.LOADING:return e.loading?e:o({},e,{loading:!0});case s.CACHE_HIT:return e.cacheHit?e:o({},r.result,{cacheHit:!0,loading:!1});case s.REQUEST_RESULT:return o({},r.result,{cacheHit:!1,loading:!1});default:return e}}function c(e,t){if(void 0===t&&(t={}),"string"!=typeof e)throw Error("Your query must be a string. If you are using the `gql` template literal from graphql-tag, remove it from your query.");var a=r.useContext(n),i=r.useRef(!0),c=r.useRef(null),f={query:e,variables:t.variables,operationName:t.operationName},l=a.getCacheKey(f,t),h=t.isMutation||t.isManual,p=t.skipCache||!a.cache?null:a.cache.get(l),d=o({},p,{cacheHit:!!p,loading:!h&&!p}),E=r.useReducer(u,d),g=E[0],y=E[1],v=JSON.stringify(l);return r.useEffect(function(){t.updateData||y({type:s.RESET_STATE,initialState:d})},[v]),r.useEffect(function(){return i.current=!0,function(){i.current=!1}},[]),[function(e){if(!i.current)return Promise.resolve();var r=o({},t,e),n=o({},f,{variables:r.variables,operationName:r.operationName}),u=a.getCacheKey(n,r);c.current=u;var l=r.skipCache||!a.cache?null:a.cache.get(u);return l?(y({type:s.CACHE_HIT,result:l}),Promise.resolve(l)):(y({type:s.LOADING}),a.request(n,r).then(function(e){if(g.data&&e.data&&r.updateData){if("function"!=typeof r.updateData)throw Error("options.updateData must be a function");e.data=r.updateData(g.data,e.data)}return r.useCache&&a.cache&&a.cache.set(u,e),i.current&&u===c.current&&y({type:s.REQUEST_RESULT,result:e}),e}))},g]}var f={useCache:!0};e.ClientContext=n,e.GraphQLClient=i,e.useClientRequest=c,e.useManualQuery=function(e,r){return c(e,o({useCache:!0,isManual:!0},r))},e.useMutation=function(e,r){return c(e,o({isMutation:!0},r))},e.useQuery=function(e,t){void 0===t&&(t={});var a=o({},f,t),i=r.useContext(n),s=r.useState(!1),u=s[0],l=s[1],h=c(e,a),p=h[0],d=h[1];if(i.ssrMode&&!1!==t.ssr&&!u){if(!d.data&&!d.error){var E=p();i.ssrPromises.push(E)}l(!0)}var g=JSON.stringify(a);return r.useEffect(function(){p()},[e,g]),o({},d,{refetch:function(e){return void 0===e&&(e={}),p(o({skipCache:!0,updateData:function(e,r){return r}},e))}})},Object.defineProperty(e,"__esModule",{value:!0})}); | ||
!function(e,r){"object"==typeof exports&&"undefined"!=typeof module?r(exports,require("react")):"function"==typeof define&&define.amd?define(["exports","react"],r):r((e=e||self).GraphQLHooks={},e.React)}(this,function(e,r){"use strict";function t(e,r,t){return r in e?Object.defineProperty(e,r,{value:t,enumerable:!0,configurable:!0,writable:!0}):e[r]=t,e}function n(e,r){var t=Object.keys(e);if(Object.getOwnPropertySymbols){var n=Object.getOwnPropertySymbols(e);r&&(n=n.filter(function(r){return Object.getOwnPropertyDescriptor(e,r).enumerable})),t.push.apply(t,n)}return t}function o(e){for(var r=1;arguments.length>r;r++){var o=null!=arguments[r]?arguments[r]:{};r%2?n(o,!0).forEach(function(r){t(e,r,o[r])}):Object.getOwnPropertyDescriptors?Object.defineProperties(e,Object.getOwnPropertyDescriptors(o)):n(o).forEach(function(r){Object.defineProperty(e,r,Object.getOwnPropertyDescriptor(o,r))})}return e}var a=(r=r&&r.hasOwnProperty("default")?r.default:r).createContext();a.displayName="ClientContext";var i=function(e){var r=e.name,t=e.type;this.uri=e.uri,this.name=r,this.type=t};var s=function(){function e(e){if(void 0===e&&(e={}),!e.url)throw Error("GraphQLClient: config.url is required");if(e.fetch&&"function"!=typeof e.fetch)throw Error("GraphQLClient: config.fetch must be a function");if(!e.fetch&&!fetch)throw Error("GraphQLClient: fetch must be polyfilled or passed in new GraphQLClient({ fetch })");if(e.ssrMode&&!e.cache)throw Error("GraphQLClient: config.cache is required when in ssrMode");this.cache=e.cache,this.headers=e.headers||{},this.ssrMode=e.ssrMode,this.ssrPromises=[],this.url=e.url,this.fetch=e.fetch||fetch.bind(),this.fetchOptions=e.fetchOptions||{},this.logErrors=void 0===e.logErrors||e.logErrors,this.onError=e.onError}var r=e.prototype;return r.setHeader=function(e,r){return this.headers[e]=r,this},r.setHeaders=function(e){return this.headers=e,this},r.removeHeader=function(e){return delete this.headers[e],this},r.logErrorResult=function(e){var r=e.result,t=e.operation;if(this.onError)return this.onError({result:r,operation:t});console.error("GraphQL Hooks Error"),console.groupCollapsed("---\x3e Full Error Details"),console.groupCollapsed("Operation:"),console.log(t),console.groupEnd(),r.fetchError&&(console.groupCollapsed("FETCH ERROR:"),console.log(r.fetchError),console.groupEnd()),r.httpError&&(console.groupCollapsed("HTTP ERROR:"),console.log(r.httpError),console.groupEnd()),r.graphQLErrors&&r.graphQLErrors.length>0&&(console.groupCollapsed("GRAPHQL ERROR:"),r.graphQLErrors.forEach(function(e){return console.log(e)}),console.groupEnd()),console.groupEnd()},r.generateResult=function(e){var r=e.fetchError,t=e.httpError,n=e.graphQLErrors;return{error:!!(n&&n.length>0||r||t),fetchError:r,httpError:t,graphQLErrors:n,data:e.data}},r.getCacheKey=function(e,r){return void 0===r&&(r={}),{operation:e,fetchOptions:o({},this.fetchOptions,{},r.fetchOptionsOverrides)}},r.getCache=function(e){var r=this.cache?this.cache.get(e):null;if(r)return r},r.saveCache=function(e,r){this.cache&&this.cache.set(e,r)},r.getFetchOptions=function(e,r){void 0===r&&(r={});var t=o({method:"POST",headers:o({},this.headers)},this.fetchOptions,{},r),n=function e(r,t){var n;void 0===t&&(t="");var o=new Map;function a(e,r){var t=o.get(r);t?t.push.apply(t,e):o.set(r,e)}if("undefined"!=typeof File&&r instanceof File||"undefined"!=typeof Blob&&r instanceof Blob||r instanceof i)n=null,a([t],r);else{var s=t?t+".":"";if("undefined"!=typeof FileList&&r instanceof FileList)n=Array.prototype.map.call(r,function(e,r){return a([""+s+r],e),null});else if(Array.isArray(r))n=r.map(function(r,t){var n=e(r,""+s+t);return n.files.forEach(a),n.clone});else if(r&&r.constructor===Object)for(var u in n={},r){var c=e(r[u],""+s+u);c.files.forEach(a),n[u]=c.clone}else n=r}return{clone:n,files:o}}(e),a=n.files,s=JSON.stringify(n.clone);if(a.size){var u=new FormData;u.append("operations",s);var c={},f=0;a.forEach(function(e){c[++f]=e}),u.append("map",JSON.stringify(c)),f=0,a.forEach(function(e,r){u.append(""+ ++f,r,r.name)}),t.body=u}else t.headers["Content-Type"]="application/json",t.body=s;return t},r.request=function(e,r){var t=this;return void 0===r&&(r={}),this.fetch(this.url,this.getFetchOptions(e,r.fetchOptionsOverrides)).then(function(e){return e.ok?e.json().then(function(e){return t.generateResult({graphQLErrors:e.errors,data:e.data})}):e.text().then(function(r){return t.generateResult({httpError:{status:e.status,statusText:e.statusText,body:r}})})}).catch(function(e){return t.generateResult({fetchError:e})}).then(function(r){return r.error&&t.logErrors&&t.logErrorResult({result:r,operation:e}),r})},e}();var u={RESET_STATE:"RESET_STATE",LOADING:"LOADING",CACHE_HIT:"CACHE_HIT",REQUEST_RESULT:"REQUEST_RESULT"};function c(e,r){switch(r.type){case u.RESET_STATE:return r.initialState;case u.LOADING:return e.loading?e:o({},e,{loading:!0});case u.CACHE_HIT:return e.cacheHit?e:o({},r.result,{cacheHit:!0,loading:!1});case u.REQUEST_RESULT:return o({},r.result,{data:e.data&&r.result.data&&r.updateData?r.updateData(e.data,r.result.data):r.result.data,cacheHit:!1,loading:!1});default:return e}}function f(e,t){var n=r.useRef();return function e(r,t){var n,o;if(r===t)return!0;if(r&&t&&(n=r.constructor)===t.constructor){if(n===Date)return r.getTime()===t.getTime();if(n===RegExp)return""+r==""+t;if(n===Array&&(o=r.length)===t.length){for(;o--&&e(r[o],t[o]););return-1===o}if(n===Object){if(Object.keys(r).length!==Object.keys(t).length)return!1;for(o in r)if(!(o in t&&e(r[o],t[o])))return!1;return!0}}return r!=r&&t!=t}(t,n.current)||(n.current=t),r.useCallback(e,n.current)}function l(e,t){if(void 0===t&&(t={}),"string"!=typeof e)throw Error("Your query must be a string. If you are using the `gql` template literal from graphql-tag, remove it from your query.");var n=r.useContext(a),i=r.useRef(!0),s=r.useRef(null),l={query:e,variables:t.variables,operationName:t.operationName},h=n.getCacheKey(l,t),p=t.isMutation||t.isManual,d=t.skipCache||!n.cache?null:n.cache.get(h),E=o({},d,{cacheHit:!!d,loading:!p&&!d}),g=r.useReducer(c,E),y=g[0],v=g[1],C=JSON.stringify(h);r.useEffect(function(){t.updateData||v({type:u.RESET_STATE,initialState:E})},[C]),r.useEffect(function(){return i.current=!0,function(){i.current=!1}},[]);var O=f(function(e){if(!i.current)return Promise.resolve();var r=o({},t,{},e),a=o({},l,{variables:r.variables,operationName:r.operationName}),c=n.getCacheKey(a,r);s.current=c;var f=r.skipCache?null:n.getCache(c);return f?(v({type:u.CACHE_HIT,result:f}),Promise.resolve(f)):(v({type:u.LOADING}),n.request(a,r).then(function(e){if(r.updateData&&"function"!=typeof r.updateData)throw Error("options.updateData must be a function");var t=o({},e);return r.useCache&&(t.useCache=!0,t.cacheKey=c),i.current&&c===s.current&&v({type:u.REQUEST_RESULT,updateData:r.updateData,result:t}),e}))},[n,t,l]);return r.useEffect(function(){y.useCache&&n.saveCache(y.cacheKey,y)},[n,y]),[O,y]}var h={useCache:!0};e.ClientContext=a,e.GraphQLClient=s,e.useClientRequest=l,e.useManualQuery=function(e,r){return l(e,o({useCache:!0,isManual:!0},r))},e.useMutation=function(e,r){return l(e,o({isMutation:!0},r))},e.useQuery=function(e,t){void 0===t&&(t={});var n=o({},h,{},t),i=r.useContext(a),s=r.useState(!1),u=s[0],c=s[1],f=l(e,n),p=f[0],d=f[1];if(i.ssrMode&&!1!==t.ssr&&!u){if(!d.loading&&!d.data&&!d.error){var E=p();i.ssrPromises.push(E)}c(!0)}var g=JSON.stringify(n);return r.useEffect(function(){p()},[e,g]),o({},d,{refetch:r.useCallback(function(e){return void 0===e&&(e={}),p(o({skipCache:!0,updateData:function(e,r){return r}},e))},[p])})},Object.defineProperty(e,"__esModule",{value:!0})}); |
import React from 'react'; | ||
import { extractFiles } from 'extract-files'; | ||
import deepEqual from 'dequal'; | ||
@@ -19,16 +20,31 @@ function _defineProperty(obj, key, value) { | ||
function _objectSpread(target) { | ||
function ownKeys(object, enumerableOnly) { | ||
var keys = Object.keys(object); | ||
if (Object.getOwnPropertySymbols) { | ||
var symbols = Object.getOwnPropertySymbols(object); | ||
if (enumerableOnly) symbols = symbols.filter(function (sym) { | ||
return Object.getOwnPropertyDescriptor(object, sym).enumerable; | ||
}); | ||
keys.push.apply(keys, symbols); | ||
} | ||
return keys; | ||
} | ||
function _objectSpread2(target) { | ||
for (var i = 1; i < arguments.length; i++) { | ||
var source = arguments[i] != null ? arguments[i] : {}; | ||
var ownKeys = Object.keys(source); | ||
if (typeof Object.getOwnPropertySymbols === 'function') { | ||
ownKeys = ownKeys.concat(Object.getOwnPropertySymbols(source).filter(function (sym) { | ||
return Object.getOwnPropertyDescriptor(source, sym).enumerable; | ||
})); | ||
if (i % 2) { | ||
ownKeys(source, true).forEach(function (key) { | ||
_defineProperty(target, key, source[key]); | ||
}); | ||
} else if (Object.getOwnPropertyDescriptors) { | ||
Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); | ||
} else { | ||
ownKeys(source).forEach(function (key) { | ||
Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); | ||
}); | ||
} | ||
ownKeys.forEach(function (key) { | ||
_defineProperty(target, key, source[key]); | ||
}); | ||
} | ||
@@ -159,3 +175,3 @@ | ||
var fetchOptions = _objectSpread({}, this.fetchOptions, options.fetchOptionsOverrides); | ||
var fetchOptions = _objectSpread2({}, this.fetchOptions, {}, options.fetchOptionsOverrides); | ||
@@ -166,2 +182,16 @@ return { | ||
}; | ||
}; | ||
_proto.getCache = function getCache(cacheKey) { | ||
var cacheHit = this.cache ? this.cache.get(cacheKey) : null; | ||
if (cacheHit) { | ||
return cacheHit; | ||
} | ||
}; | ||
_proto.saveCache = function saveCache(cacheKey, value) { | ||
if (this.cache) { | ||
this.cache.set(cacheKey, value); | ||
} | ||
} // Kudos to Jayden Seric (@jaydenseric) for this piece of code. | ||
@@ -176,6 +206,6 @@ // See original source: https://github.com/jaydenseric/graphql-react/blob/82d576b5fe6664c4a01cd928d79f33ddc3f7bbfd/src/universal/graphqlFetchOptions.mjs. | ||
var fetchOptions = _objectSpread({ | ||
var fetchOptions = _objectSpread2({ | ||
method: 'POST', | ||
headers: _objectSpread({}, this.headers) | ||
}, this.fetchOptions, fetchOptionsOverrides); | ||
headers: _objectSpread2({}, this.headers) | ||
}, this.fetchOptions, {}, fetchOptionsOverrides); | ||
@@ -278,3 +308,3 @@ var _extractFiles = extractFiles(operation), | ||
return _objectSpread({}, state, { | ||
return _objectSpread2({}, state, { | ||
loading: true | ||
@@ -290,3 +320,3 @@ }); | ||
return _objectSpread({}, action.result, { | ||
return _objectSpread2({}, action.result, { | ||
cacheHit: true, | ||
@@ -297,3 +327,4 @@ loading: false | ||
case actionTypes.REQUEST_RESULT: | ||
return _objectSpread({}, action.result, { | ||
return _objectSpread2({}, action.result, { | ||
data: state.data && action.result.data && action.updateData ? action.updateData(state.data, action.result.data) : action.result.data, | ||
cacheHit: false, | ||
@@ -307,2 +338,12 @@ loading: false | ||
} | ||
function useDeepCompareCallback(callback, deps) { | ||
var ref = React.useRef(); | ||
if (!deepEqual(deps, ref.current)) { | ||
ref.current = deps; | ||
} | ||
return React.useCallback(callback, ref.current); | ||
} | ||
/* | ||
@@ -339,3 +380,3 @@ options include: | ||
var initialState = _objectSpread({}, initialCacheHit, { | ||
var initialState = _objectSpread2({}, initialCacheHit, { | ||
cacheHit: !!initialCacheHit, | ||
@@ -370,8 +411,8 @@ loading: isDeferred ? false : !initialCacheHit | ||
function fetchData(newOpts) { | ||
var fetchData = useDeepCompareCallback(function (newOpts) { | ||
if (!isMounted.current) return Promise.resolve(); | ||
var revisedOpts = _objectSpread({}, initialOpts, newOpts); | ||
var revisedOpts = _objectSpread2({}, initialOpts, {}, newOpts); | ||
var revisedOperation = _objectSpread({}, operation, { | ||
var revisedOperation = _objectSpread2({}, operation, { | ||
variables: revisedOpts.variables, | ||
@@ -386,3 +427,3 @@ operationName: revisedOpts.operationName | ||
activeCacheKey.current = revisedCacheKey; | ||
var cacheHit = revisedOpts.skipCache || !client.cache ? null : client.cache.get(revisedCacheKey); | ||
var cacheHit = revisedOpts.skipCache ? null : client.getCache(revisedCacheKey); | ||
@@ -401,12 +442,11 @@ if (cacheHit) { | ||
return client.request(revisedOperation, revisedOpts).then(function (result) { | ||
if (state.data && result.data && revisedOpts.updateData) { | ||
if (typeof revisedOpts.updateData !== 'function') { | ||
throw new Error('options.updateData must be a function'); | ||
} | ||
result.data = revisedOpts.updateData(state.data, result.data); | ||
if (revisedOpts.updateData && typeof revisedOpts.updateData !== 'function') { | ||
throw new Error('options.updateData must be a function'); | ||
} | ||
if (revisedOpts.useCache && client.cache) { | ||
client.cache.set(revisedCacheKey, result); | ||
var actionResult = _objectSpread2({}, result); | ||
if (revisedOpts.useCache) { | ||
actionResult.useCache = true; | ||
actionResult.cacheKey = revisedCacheKey; | ||
} | ||
@@ -417,3 +457,4 @@ | ||
type: actionTypes.REQUEST_RESULT, | ||
result: result | ||
updateData: revisedOpts.updateData, | ||
result: actionResult | ||
}); | ||
@@ -424,4 +465,10 @@ } | ||
}); | ||
} | ||
}, [client, initialOpts, operation]); // We perform caching after reducer update | ||
// To include the outcome of updateData | ||
React.useEffect(function () { | ||
if (state.useCache) { | ||
client.saveCache(state.cacheKey, state); | ||
} | ||
}, [client, state]); | ||
return [fetchData, state]; | ||
@@ -439,3 +486,3 @@ } | ||
var allOpts = _objectSpread({}, defaultOpts, opts); | ||
var allOpts = _objectSpread2({}, defaultOpts, {}, opts); | ||
@@ -454,3 +501,3 @@ var client = React.useContext(ClientContext); | ||
// result may already be in the cache from previous SSR iterations | ||
if (!state.data && !state.error) { | ||
if (!state.loading && !state.data && !state.error) { | ||
var p = queryReq(); | ||
@@ -468,4 +515,4 @@ client.ssrPromises.push(p); | ||
return _objectSpread({}, state, { | ||
refetch: function refetch(options) { | ||
return _objectSpread2({}, state, { | ||
refetch: React.useCallback(function (options) { | ||
if (options === void 0) { | ||
@@ -475,3 +522,3 @@ options = {}; | ||
return queryReq(_objectSpread({ | ||
return queryReq(_objectSpread2({ | ||
skipCache: true, | ||
@@ -485,3 +532,3 @@ // don't call the updateData that has been passed into useQuery here | ||
}, options)); | ||
} | ||
}, [queryReq]) | ||
}); | ||
@@ -491,3 +538,3 @@ } | ||
var useManualQuery = function useManualQuery(query, options) { | ||
return useClientRequest(query, _objectSpread({ | ||
return useClientRequest(query, _objectSpread2({ | ||
useCache: true, | ||
@@ -499,3 +546,3 @@ isManual: true | ||
var useMutation = function useMutation(query, options) { | ||
return useClientRequest(query, _objectSpread({ | ||
return useClientRequest(query, _objectSpread2({ | ||
isMutation: true | ||
@@ -502,0 +549,0 @@ }, options)); |
@@ -9,2 +9,3 @@ 'use strict'; | ||
var extractFiles = require('extract-files'); | ||
var deepEqual = _interopDefault(require('dequal')); | ||
@@ -26,16 +27,31 @@ function _defineProperty(obj, key, value) { | ||
function _objectSpread(target) { | ||
function ownKeys(object, enumerableOnly) { | ||
var keys = Object.keys(object); | ||
if (Object.getOwnPropertySymbols) { | ||
var symbols = Object.getOwnPropertySymbols(object); | ||
if (enumerableOnly) symbols = symbols.filter(function (sym) { | ||
return Object.getOwnPropertyDescriptor(object, sym).enumerable; | ||
}); | ||
keys.push.apply(keys, symbols); | ||
} | ||
return keys; | ||
} | ||
function _objectSpread2(target) { | ||
for (var i = 1; i < arguments.length; i++) { | ||
var source = arguments[i] != null ? arguments[i] : {}; | ||
var ownKeys = Object.keys(source); | ||
if (typeof Object.getOwnPropertySymbols === 'function') { | ||
ownKeys = ownKeys.concat(Object.getOwnPropertySymbols(source).filter(function (sym) { | ||
return Object.getOwnPropertyDescriptor(source, sym).enumerable; | ||
})); | ||
if (i % 2) { | ||
ownKeys(source, true).forEach(function (key) { | ||
_defineProperty(target, key, source[key]); | ||
}); | ||
} else if (Object.getOwnPropertyDescriptors) { | ||
Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); | ||
} else { | ||
ownKeys(source).forEach(function (key) { | ||
Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); | ||
}); | ||
} | ||
ownKeys.forEach(function (key) { | ||
_defineProperty(target, key, source[key]); | ||
}); | ||
} | ||
@@ -166,3 +182,3 @@ | ||
var fetchOptions = _objectSpread({}, this.fetchOptions, options.fetchOptionsOverrides); | ||
var fetchOptions = _objectSpread2({}, this.fetchOptions, {}, options.fetchOptionsOverrides); | ||
@@ -173,2 +189,16 @@ return { | ||
}; | ||
}; | ||
_proto.getCache = function getCache(cacheKey) { | ||
var cacheHit = this.cache ? this.cache.get(cacheKey) : null; | ||
if (cacheHit) { | ||
return cacheHit; | ||
} | ||
}; | ||
_proto.saveCache = function saveCache(cacheKey, value) { | ||
if (this.cache) { | ||
this.cache.set(cacheKey, value); | ||
} | ||
} // Kudos to Jayden Seric (@jaydenseric) for this piece of code. | ||
@@ -183,6 +213,6 @@ // See original source: https://github.com/jaydenseric/graphql-react/blob/82d576b5fe6664c4a01cd928d79f33ddc3f7bbfd/src/universal/graphqlFetchOptions.mjs. | ||
var fetchOptions = _objectSpread({ | ||
var fetchOptions = _objectSpread2({ | ||
method: 'POST', | ||
headers: _objectSpread({}, this.headers) | ||
}, this.fetchOptions, fetchOptionsOverrides); | ||
headers: _objectSpread2({}, this.headers) | ||
}, this.fetchOptions, {}, fetchOptionsOverrides); | ||
@@ -285,3 +315,3 @@ var _extractFiles = extractFiles.extractFiles(operation), | ||
return _objectSpread({}, state, { | ||
return _objectSpread2({}, state, { | ||
loading: true | ||
@@ -297,3 +327,3 @@ }); | ||
return _objectSpread({}, action.result, { | ||
return _objectSpread2({}, action.result, { | ||
cacheHit: true, | ||
@@ -304,3 +334,4 @@ loading: false | ||
case actionTypes.REQUEST_RESULT: | ||
return _objectSpread({}, action.result, { | ||
return _objectSpread2({}, action.result, { | ||
data: state.data && action.result.data && action.updateData ? action.updateData(state.data, action.result.data) : action.result.data, | ||
cacheHit: false, | ||
@@ -314,2 +345,12 @@ loading: false | ||
} | ||
function useDeepCompareCallback(callback, deps) { | ||
var ref = React.useRef(); | ||
if (!deepEqual(deps, ref.current)) { | ||
ref.current = deps; | ||
} | ||
return React.useCallback(callback, ref.current); | ||
} | ||
/* | ||
@@ -346,3 +387,3 @@ options include: | ||
var initialState = _objectSpread({}, initialCacheHit, { | ||
var initialState = _objectSpread2({}, initialCacheHit, { | ||
cacheHit: !!initialCacheHit, | ||
@@ -377,8 +418,8 @@ loading: isDeferred ? false : !initialCacheHit | ||
function fetchData(newOpts) { | ||
var fetchData = useDeepCompareCallback(function (newOpts) { | ||
if (!isMounted.current) return Promise.resolve(); | ||
var revisedOpts = _objectSpread({}, initialOpts, newOpts); | ||
var revisedOpts = _objectSpread2({}, initialOpts, {}, newOpts); | ||
var revisedOperation = _objectSpread({}, operation, { | ||
var revisedOperation = _objectSpread2({}, operation, { | ||
variables: revisedOpts.variables, | ||
@@ -393,3 +434,3 @@ operationName: revisedOpts.operationName | ||
activeCacheKey.current = revisedCacheKey; | ||
var cacheHit = revisedOpts.skipCache || !client.cache ? null : client.cache.get(revisedCacheKey); | ||
var cacheHit = revisedOpts.skipCache ? null : client.getCache(revisedCacheKey); | ||
@@ -408,12 +449,11 @@ if (cacheHit) { | ||
return client.request(revisedOperation, revisedOpts).then(function (result) { | ||
if (state.data && result.data && revisedOpts.updateData) { | ||
if (typeof revisedOpts.updateData !== 'function') { | ||
throw new Error('options.updateData must be a function'); | ||
} | ||
result.data = revisedOpts.updateData(state.data, result.data); | ||
if (revisedOpts.updateData && typeof revisedOpts.updateData !== 'function') { | ||
throw new Error('options.updateData must be a function'); | ||
} | ||
if (revisedOpts.useCache && client.cache) { | ||
client.cache.set(revisedCacheKey, result); | ||
var actionResult = _objectSpread2({}, result); | ||
if (revisedOpts.useCache) { | ||
actionResult.useCache = true; | ||
actionResult.cacheKey = revisedCacheKey; | ||
} | ||
@@ -424,3 +464,4 @@ | ||
type: actionTypes.REQUEST_RESULT, | ||
result: result | ||
updateData: revisedOpts.updateData, | ||
result: actionResult | ||
}); | ||
@@ -431,4 +472,10 @@ } | ||
}); | ||
} | ||
}, [client, initialOpts, operation]); // We perform caching after reducer update | ||
// To include the outcome of updateData | ||
React.useEffect(function () { | ||
if (state.useCache) { | ||
client.saveCache(state.cacheKey, state); | ||
} | ||
}, [client, state]); | ||
return [fetchData, state]; | ||
@@ -446,3 +493,3 @@ } | ||
var allOpts = _objectSpread({}, defaultOpts, opts); | ||
var allOpts = _objectSpread2({}, defaultOpts, {}, opts); | ||
@@ -461,3 +508,3 @@ var client = React.useContext(ClientContext); | ||
// result may already be in the cache from previous SSR iterations | ||
if (!state.data && !state.error) { | ||
if (!state.loading && !state.data && !state.error) { | ||
var p = queryReq(); | ||
@@ -475,4 +522,4 @@ client.ssrPromises.push(p); | ||
return _objectSpread({}, state, { | ||
refetch: function refetch(options) { | ||
return _objectSpread2({}, state, { | ||
refetch: React.useCallback(function (options) { | ||
if (options === void 0) { | ||
@@ -482,3 +529,3 @@ options = {}; | ||
return queryReq(_objectSpread({ | ||
return queryReq(_objectSpread2({ | ||
skipCache: true, | ||
@@ -492,3 +539,3 @@ // don't call the updateData that has been passed into useQuery here | ||
}, options)); | ||
} | ||
}, [queryReq]) | ||
}); | ||
@@ -498,3 +545,3 @@ } | ||
var useManualQuery = function useManualQuery(query, options) { | ||
return useClientRequest(query, _objectSpread({ | ||
return useClientRequest(query, _objectSpread2({ | ||
useCache: true, | ||
@@ -506,3 +553,3 @@ isManual: true | ||
var useMutation = function useMutation(query, options) { | ||
return useClientRequest(query, _objectSpread({ | ||
return useClientRequest(query, _objectSpread2({ | ||
isMutation: true | ||
@@ -509,0 +556,0 @@ }, options)); |
{ | ||
"name": "graphql-hooks", | ||
"version": "3.6.0", | ||
"version": "3.6.1", | ||
"description": "Graphql Hooks", | ||
@@ -10,3 +10,3 @@ "main": "lib/graphql-hooks.js", | ||
"scripts": { | ||
"build": "../../node_modules/.bin/rollup -c", | ||
"build": "rollup -c", | ||
"prepublishOnly": "npm run build && cp ../../README.md . && cp ../../LICENSE ." | ||
@@ -37,2 +37,3 @@ }, | ||
"dependencies": { | ||
"dequal": "^1.0.0", | ||
"extract-files": "^5.0.1" | ||
@@ -42,2 +43,3 @@ }, | ||
"@testing-library/react": "^8.0.1", | ||
"@testing-library/react-hooks": "^1.1.0", | ||
"formdata-node": "^1.6.0", | ||
@@ -47,3 +49,2 @@ "jest-fetch-mock": "^2.1.2", | ||
"react-dom": "^16.8.6", | ||
"react-hooks-testing-library": "^0.5.1", | ||
"react-test-renderer": "^16.8.6" | ||
@@ -58,3 +59,4 @@ }, | ||
}, | ||
"homepage": "https://github.com/nearform/graphql-hooks#readme" | ||
"homepage": "https://github.com/nearform/graphql-hooks#readme", | ||
"gitHead": "e8f7b4aa56cba0ae16c61b16a9bb71c3d44cd332" | ||
} |
@@ -8,3 +8,3 @@ # graphql-hooks | ||
[](https://www.npmjs.com/package/graphql-hooks) | ||
[](#contributors) | ||
[](#contributors) | ||
[](https://lernajs.io/) | ||
@@ -728,3 +728,22 @@ | ||
<!-- prettier-ignore --> | ||
<table><tr><td align="center"><a href="https://twitter.com/bmullan91"><img src="https://avatars1.githubusercontent.com/u/1939483?v=4" width="100px;" alt="Brian Mullan"/><br /><sub><b>Brian Mullan</b></sub></a><br /><a href="#question-bmullan91" title="Answering Questions">💬</a> <a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Abmullan91" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=bmullan91" title="Code">💻</a> <a href="#content-bmullan91" title="Content">🖋</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=bmullan91" title="Documentation">📖</a> <a href="#example-bmullan91" title="Examples">💡</a> <a href="#ideas-bmullan91" title="Ideas, Planning, & Feedback">🤔</a> <a href="#maintenance-bmullan91" title="Maintenance">🚧</a> <a href="#review-bmullan91" title="Reviewed Pull Requests">👀</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=bmullan91" title="Tests">⚠️</a></td><td align="center"><a href="https://jackdc.com"><img src="https://avatars0.githubusercontent.com/u/1485654?v=4" width="100px;" alt="Jack Clark"/><br /><sub><b>Jack Clark</b></sub></a><br /><a href="#question-jackdclark" title="Answering Questions">💬</a> <a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Ajackdclark" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=jackdclark" title="Code">💻</a> <a href="#content-jackdclark" title="Content">🖋</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=jackdclark" title="Documentation">📖</a> <a href="#example-jackdclark" title="Examples">💡</a> <a href="#ideas-jackdclark" title="Ideas, Planning, & Feedback">🤔</a> <a href="#maintenance-jackdclark" title="Maintenance">🚧</a> <a href="#review-jackdclark" title="Reviewed Pull Requests">👀</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=jackdclark" title="Tests">⚠️</a></td><td align="center"><a href="http://twitter.com/joezo"><img src="https://avatars1.githubusercontent.com/u/2870255?v=4" width="100px;" alt="Joe Warren"/><br /><sub><b>Joe Warren</b></sub></a><br /><a href="#question-Joezo" title="Answering Questions">💬</a> <a href="https://github.com/nearform/graphql-hooks/issues?q=author%3AJoezo" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=Joezo" title="Code">💻</a> <a href="#content-Joezo" title="Content">🖋</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=Joezo" title="Documentation">📖</a> <a href="#example-Joezo" title="Examples">💡</a> <a href="#ideas-Joezo" title="Ideas, Planning, & Feedback">🤔</a> <a href="#maintenance-Joezo" title="Maintenance">🚧</a> <a href="#review-Joezo" title="Reviewed Pull Requests">👀</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=Joezo" title="Tests">⚠️</a></td><td align="center"><a href="http://simoneb.github.io"><img src="https://avatars1.githubusercontent.com/u/20181?v=4" width="100px;" alt="Simone Busoli"/><br /><sub><b>Simone Busoli</b></sub></a><br /><a href="#question-simoneb" title="Answering Questions">💬</a> <a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Asimoneb" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=simoneb" title="Documentation">📖</a></td><td align="center"><a href="https://jheytompkins.com"><img src="https://avatars1.githubusercontent.com/u/842246?v=4" width="100px;" alt="jhey tompkins"/><br /><sub><b>jhey tompkins</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/commits?author=jh3y" title="Tests">⚠️</a> <a href="#question-jh3y" title="Answering Questions">💬</a> <a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Ajh3y" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=jh3y" title="Code">💻</a> <a href="#content-jh3y" title="Content">🖋</a> <a href="#review-jh3y" title="Reviewed Pull Requests">👀</a></td><td align="center"><a href="https://haroen.me"><img src="https://avatars3.githubusercontent.com/u/6270048?v=4" width="100px;" alt="Haroen Viaene"/><br /><sub><b>Haroen Viaene</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/issues?q=author%3AHaroenv" title="Bug reports">🐛</a></td><td align="center"><a href="https://github.com/aribouius"><img src="https://avatars2.githubusercontent.com/u/10748727?v=4" width="100px;" alt="Ari Bouius"/><br /><sub><b>Ari Bouius</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/commits?author=aribouius" title="Documentation">📖</a> <a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Aaribouius" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=aribouius" title="Code">💻</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=aribouius" title="Tests">⚠️</a></td></tr><tr><td align="center"><a href="https://github.com/kkogovsek"><img src="https://avatars1.githubusercontent.com/u/8089644?v=4" width="100px;" alt="Klemen Kogovšek"/><br /><sub><b>Klemen Kogovšek</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Akkogovsek" title="Bug reports">🐛</a> <a href="#ideas-kkogovsek" title="Ideas, Planning, & Feedback">🤔</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=kkogovsek" title="Code">💻</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=kkogovsek" title="Tests">⚠️</a></td><td align="center"><a href="https://github.com/wescoder"><img src="https://avatars0.githubusercontent.com/u/22945955?v=4" width="100px;" alt="Wésley Queiroz"/><br /><sub><b>Wésley Queiroz</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Awescoder" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=wescoder" title="Code">💻</a></td><td align="center"><a href="https://www.good-idea.studio"><img src="https://avatars3.githubusercontent.com/u/11514928?v=4" width="100px;" alt="Joseph Thomas"/><br /><sub><b>Joseph Thomas</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Agood-idea" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=good-idea" title="Code">💻</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=good-idea" title="Tests">⚠️</a></td><td align="center"><a href="http://edvinasbartkus.lt"><img src="https://avatars0.githubusercontent.com/u/202988?v=4" width="100px;" alt="Edvinas Bartkus"/><br /><sub><b>Edvinas Bartkus</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/commits?author=edvinasbartkus" title="Code">💻</a></td><td align="center"><a href="https://github.com/olistic"><img src="https://avatars1.githubusercontent.com/u/5600126?v=4" width="100px;" alt="Matías Olivera"/><br /><sub><b>Matías Olivera</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Aolistic" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=olistic" title="Code">💻</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=olistic" title="Tests">⚠️</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=olistic" title="Documentation">📖</a></td><td align="center"><a href="https://github.com/tcudok-jg"><img src="https://avatars3.githubusercontent.com/u/50208575?v=4" width="100px;" alt="tcudok-jg"/><br /><sub><b>tcudok-jg</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/commits?author=tcudok-jg" title="Code">💻</a></td></tr></table> | ||
<table> | ||
<tr> | ||
<td align="center"><a href="https://twitter.com/bmullan91"><img src="https://avatars1.githubusercontent.com/u/1939483?v=4" width="100px;" alt="Brian Mullan"/><br /><sub><b>Brian Mullan</b></sub></a><br /><a href="#question-bmullan91" title="Answering Questions">💬</a> <a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Abmullan91" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=bmullan91" title="Code">💻</a> <a href="#content-bmullan91" title="Content">🖋</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=bmullan91" title="Documentation">📖</a> <a href="#example-bmullan91" title="Examples">💡</a> <a href="#ideas-bmullan91" title="Ideas, Planning, & Feedback">🤔</a> <a href="#maintenance-bmullan91" title="Maintenance">🚧</a> <a href="#review-bmullan91" title="Reviewed Pull Requests">👀</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=bmullan91" title="Tests">⚠️</a></td> | ||
<td align="center"><a href="https://jackdc.com"><img src="https://avatars0.githubusercontent.com/u/1485654?v=4" width="100px;" alt="Jack Clark"/><br /><sub><b>Jack Clark</b></sub></a><br /><a href="#question-jackdclark" title="Answering Questions">💬</a> <a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Ajackdclark" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=jackdclark" title="Code">💻</a> <a href="#content-jackdclark" title="Content">🖋</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=jackdclark" title="Documentation">📖</a> <a href="#example-jackdclark" title="Examples">💡</a> <a href="#ideas-jackdclark" title="Ideas, Planning, & Feedback">🤔</a> <a href="#maintenance-jackdclark" title="Maintenance">🚧</a> <a href="#review-jackdclark" title="Reviewed Pull Requests">👀</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=jackdclark" title="Tests">⚠️</a></td> | ||
<td align="center"><a href="http://twitter.com/joezo"><img src="https://avatars1.githubusercontent.com/u/2870255?v=4" width="100px;" alt="Joe Warren"/><br /><sub><b>Joe Warren</b></sub></a><br /><a href="#question-Joezo" title="Answering Questions">💬</a> <a href="https://github.com/nearform/graphql-hooks/issues?q=author%3AJoezo" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=Joezo" title="Code">💻</a> <a href="#content-Joezo" title="Content">🖋</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=Joezo" title="Documentation">📖</a> <a href="#example-Joezo" title="Examples">💡</a> <a href="#ideas-Joezo" title="Ideas, Planning, & Feedback">🤔</a> <a href="#maintenance-Joezo" title="Maintenance">🚧</a> <a href="#review-Joezo" title="Reviewed Pull Requests">👀</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=Joezo" title="Tests">⚠️</a></td> | ||
<td align="center"><a href="http://simoneb.github.io"><img src="https://avatars1.githubusercontent.com/u/20181?v=4" width="100px;" alt="Simone Busoli"/><br /><sub><b>Simone Busoli</b></sub></a><br /><a href="#question-simoneb" title="Answering Questions">💬</a> <a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Asimoneb" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=simoneb" title="Documentation">📖</a></td> | ||
<td align="center"><a href="https://jheytompkins.com"><img src="https://avatars1.githubusercontent.com/u/842246?v=4" width="100px;" alt="jhey tompkins"/><br /><sub><b>jhey tompkins</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/commits?author=jh3y" title="Tests">⚠️</a> <a href="#question-jh3y" title="Answering Questions">💬</a> <a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Ajh3y" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=jh3y" title="Code">💻</a> <a href="#content-jh3y" title="Content">🖋</a> <a href="#review-jh3y" title="Reviewed Pull Requests">👀</a></td> | ||
<td align="center"><a href="https://haroen.me"><img src="https://avatars3.githubusercontent.com/u/6270048?v=4" width="100px;" alt="Haroen Viaene"/><br /><sub><b>Haroen Viaene</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/issues?q=author%3AHaroenv" title="Bug reports">🐛</a></td> | ||
<td align="center"><a href="https://github.com/aribouius"><img src="https://avatars2.githubusercontent.com/u/10748727?v=4" width="100px;" alt="Ari Bouius"/><br /><sub><b>Ari Bouius</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/commits?author=aribouius" title="Documentation">📖</a> <a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Aaribouius" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=aribouius" title="Code">💻</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=aribouius" title="Tests">⚠️</a></td> | ||
</tr> | ||
<tr> | ||
<td align="center"><a href="https://github.com/kkogovsek"><img src="https://avatars1.githubusercontent.com/u/8089644?v=4" width="100px;" alt="Klemen Kogovšek"/><br /><sub><b>Klemen Kogovšek</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Akkogovsek" title="Bug reports">🐛</a> <a href="#ideas-kkogovsek" title="Ideas, Planning, & Feedback">🤔</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=kkogovsek" title="Code">💻</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=kkogovsek" title="Tests">⚠️</a></td> | ||
<td align="center"><a href="https://github.com/wescoder"><img src="https://avatars0.githubusercontent.com/u/22945955?v=4" width="100px;" alt="Wésley Queiroz"/><br /><sub><b>Wésley Queiroz</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Awescoder" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=wescoder" title="Code">💻</a></td> | ||
<td align="center"><a href="https://www.good-idea.studio"><img src="https://avatars3.githubusercontent.com/u/11514928?v=4" width="100px;" alt="Joseph Thomas"/><br /><sub><b>Joseph Thomas</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Agood-idea" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=good-idea" title="Code">💻</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=good-idea" title="Tests">⚠️</a></td> | ||
<td align="center"><a href="http://edvinasbartkus.lt"><img src="https://avatars0.githubusercontent.com/u/202988?v=4" width="100px;" alt="Edvinas Bartkus"/><br /><sub><b>Edvinas Bartkus</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/commits?author=edvinasbartkus" title="Code">💻</a> <a href="#question-edvinasbartkus" title="Answering Questions">💬</a> <a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Aedvinasbartkus" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=edvinasbartkus" title="Documentation">📖</a> <a href="#example-edvinasbartkus" title="Examples">💡</a> <a href="#ideas-edvinasbartkus" title="Ideas, Planning, & Feedback">🤔</a> <a href="#maintenance-edvinasbartkus" title="Maintenance">🚧</a> <a href="#review-edvinasbartkus" title="Reviewed Pull Requests">👀</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=edvinasbartkus" title="Tests">⚠️</a></td> | ||
<td align="center"><a href="https://github.com/olistic"><img src="https://avatars1.githubusercontent.com/u/5600126?v=4" width="100px;" alt="Matías Olivera"/><br /><sub><b>Matías Olivera</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/issues?q=author%3Aolistic" title="Bug reports">🐛</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=olistic" title="Code">💻</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=olistic" title="Tests">⚠️</a> <a href="https://github.com/nearform/graphql-hooks/commits?author=olistic" title="Documentation">📖</a></td> | ||
<td align="center"><a href="https://github.com/tcudok-jg"><img src="https://avatars3.githubusercontent.com/u/50208575?v=4" width="100px;" alt="tcudok-jg"/><br /><sub><b>tcudok-jg</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/commits?author=tcudok-jg" title="Code">💻</a></td> | ||
<td align="center"><a href="https://github.com/heymartinadams"><img src="https://avatars2.githubusercontent.com/u/11673745?v=4" width="100px;" alt="Martin Adams"/><br /><sub><b>Martin Adams</b></sub></a><br /><a href="https://github.com/nearform/graphql-hooks/commits?author=heymartinadams" title="Documentation">📖</a></td> | ||
</tr> | ||
</table> | ||
@@ -731,0 +750,0 @@ <!-- ALL-CONTRIBUTORS-LIST:END --> |
@@ -109,2 +109,16 @@ import { extractFiles } from 'extract-files' | ||
getCache(cacheKey) { | ||
const cacheHit = this.cache ? this.cache.get(cacheKey) : null | ||
if (cacheHit) { | ||
return cacheHit | ||
} | ||
} | ||
saveCache(cacheKey, value) { | ||
if (this.cache) { | ||
this.cache.set(cacheKey, value) | ||
} | ||
} | ||
// Kudos to Jayden Seric (@jaydenseric) for this piece of code. | ||
@@ -111,0 +125,0 @@ // See original source: https://github.com/jaydenseric/graphql-react/blob/82d576b5fe6664c4a01cd928d79f33ddc3f7bbfd/src/universal/graphqlFetchOptions.mjs. |
import React from 'react' | ||
import deepEqual from 'dequal' | ||
import ClientContext from './ClientContext' | ||
@@ -37,2 +38,6 @@ | ||
...action.result, | ||
data: | ||
state.data && action.result.data && action.updateData | ||
? action.updateData(state.data, action.result.data) | ||
: action.result.data, | ||
cacheHit: false, | ||
@@ -46,2 +51,12 @@ loading: false | ||
function useDeepCompareCallback(callback, deps) { | ||
const ref = React.useRef() | ||
if (!deepEqual(deps, ref.current)) { | ||
ref.current = deps | ||
} | ||
return React.useCallback(callback, ref.current) | ||
} | ||
/* | ||
@@ -101,60 +116,73 @@ options include: | ||
// arguments to fetchData override the useClientRequest arguments | ||
function fetchData(newOpts) { | ||
if (!isMounted.current) return Promise.resolve() | ||
const revisedOpts = { | ||
...initialOpts, | ||
...newOpts | ||
} | ||
const fetchData = useDeepCompareCallback( | ||
newOpts => { | ||
if (!isMounted.current) return Promise.resolve() | ||
const revisedOpts = { | ||
...initialOpts, | ||
...newOpts | ||
} | ||
const revisedOperation = { | ||
...operation, | ||
variables: revisedOpts.variables, | ||
operationName: revisedOpts.operationName | ||
} | ||
const revisedOperation = { | ||
...operation, | ||
variables: revisedOpts.variables, | ||
operationName: revisedOpts.operationName | ||
} | ||
const revisedCacheKey = client.getCacheKey(revisedOperation, revisedOpts) | ||
const revisedCacheKey = client.getCacheKey(revisedOperation, revisedOpts) | ||
// NOTE: There is a possibility of a race condition whereby | ||
// the second query could finish before the first one, dispatching an old result | ||
// see https://github.com/nearform/graphql-hooks/issues/150 | ||
activeCacheKey.current = revisedCacheKey | ||
// NOTE: There is a possibility of a race condition whereby | ||
// the second query could finish before the first one, dispatching an old result | ||
// see https://github.com/nearform/graphql-hooks/issues/150 | ||
activeCacheKey.current = revisedCacheKey | ||
const cacheHit = | ||
revisedOpts.skipCache || !client.cache | ||
const cacheHit = revisedOpts.skipCache | ||
? null | ||
: client.cache.get(revisedCacheKey) | ||
: client.getCache(revisedCacheKey) | ||
if (cacheHit) { | ||
dispatch({ | ||
type: actionTypes.CACHE_HIT, | ||
result: cacheHit | ||
}) | ||
if (cacheHit) { | ||
dispatch({ | ||
type: actionTypes.CACHE_HIT, | ||
result: cacheHit | ||
}) | ||
return Promise.resolve(cacheHit) | ||
} | ||
return Promise.resolve(cacheHit) | ||
} | ||
dispatch({ type: actionTypes.LOADING }) | ||
return client.request(revisedOperation, revisedOpts).then(result => { | ||
if (state.data && result.data && revisedOpts.updateData) { | ||
if (typeof revisedOpts.updateData !== 'function') { | ||
dispatch({ type: actionTypes.LOADING }) | ||
return client.request(revisedOperation, revisedOpts).then(result => { | ||
if ( | ||
revisedOpts.updateData && | ||
typeof revisedOpts.updateData !== 'function' | ||
) { | ||
throw new Error('options.updateData must be a function') | ||
} | ||
result.data = revisedOpts.updateData(state.data, result.data) | ||
} | ||
if (revisedOpts.useCache && client.cache) { | ||
client.cache.set(revisedCacheKey, result) | ||
} | ||
const actionResult = { ...result } | ||
if (revisedOpts.useCache) { | ||
actionResult.useCache = true | ||
actionResult.cacheKey = revisedCacheKey | ||
} | ||
if (isMounted.current && revisedCacheKey === activeCacheKey.current) { | ||
dispatch({ | ||
type: actionTypes.REQUEST_RESULT, | ||
result | ||
}) | ||
} | ||
if (isMounted.current && revisedCacheKey === activeCacheKey.current) { | ||
dispatch({ | ||
type: actionTypes.REQUEST_RESULT, | ||
updateData: revisedOpts.updateData, | ||
result: actionResult | ||
}) | ||
} | ||
return result | ||
}) | ||
} | ||
return result | ||
}) | ||
}, | ||
[client, initialOpts, operation] | ||
) | ||
// We perform caching after reducer update | ||
// To include the outcome of updateData | ||
React.useEffect(() => { | ||
if (state.useCache) { | ||
client.saveCache(state.cacheKey, state) | ||
} | ||
}, [client, state]) | ||
return [fetchData, state] | ||
@@ -161,0 +189,0 @@ } |
@@ -18,3 +18,3 @@ import React from 'react' | ||
// result may already be in the cache from previous SSR iterations | ||
if (!state.data && !state.error) { | ||
if (!state.loading && !state.data && !state.error) { | ||
const p = queryReq() | ||
@@ -32,11 +32,14 @@ client.ssrPromises.push(p) | ||
...state, | ||
refetch: (options = {}) => | ||
queryReq({ | ||
skipCache: true, | ||
// don't call the updateData that has been passed into useQuery here | ||
// reset to the default behaviour of returning the raw query result | ||
// this can be overridden in refetch options | ||
updateData: (_, data) => data, | ||
...options | ||
}) | ||
refetch: React.useCallback( | ||
(options = {}) => | ||
queryReq({ | ||
skipCache: true, | ||
// don't call the updateData that has been passed into useQuery here | ||
// reset to the default behaviour of returning the raw query result | ||
// this can be overridden in refetch options | ||
updateData: (_, data) => data, | ||
...options | ||
}), | ||
[queryReq] | ||
) | ||
} | ||
@@ -43,0 +46,0 @@ } |
Sorry, the diff of this file is not supported yet
115966
2008
755
3
+ Addeddequal@^1.0.0
+ Addeddequal@1.0.1(transitive)