mirror of
https://github.com/dbgate/dbgate
synced 2024-11-07 20:26:23 +00:00
client metadata caching
This commit is contained in:
parent
cd645afd00
commit
e9c03345c3
@ -39,14 +39,14 @@ module.exports = {
|
||||
} else {
|
||||
res = await this.datastore.insert(connection);
|
||||
}
|
||||
socket.emit('connection-list-changed');
|
||||
socket.emitChanged('connection-list-changed');
|
||||
return res;
|
||||
},
|
||||
|
||||
delete_meta: 'post',
|
||||
async delete(connection) {
|
||||
const res = await this.datastore.remove(_.pick(connection, '_id'));
|
||||
socket.emit('connection-list-changed');
|
||||
socket.emitChanged('connection-list-changed');
|
||||
return res;
|
||||
},
|
||||
|
||||
|
@ -13,7 +13,7 @@ module.exports = {
|
||||
const existing = this.opened.find((x) => x.conid == conid && x.database == database);
|
||||
if (!existing) return;
|
||||
existing.structure = structure;
|
||||
socket.emit(`database-structure-changed-${conid}-${database}`);
|
||||
socket.emitChanged(`database-structure-changed-${conid}-${database}`);
|
||||
},
|
||||
handle_error(conid, database, props) {
|
||||
const { error } = props;
|
||||
|
@ -9,7 +9,7 @@ module.exports = {
|
||||
const existing = this.opened.find(x => x.conid == conid);
|
||||
if (!existing) return;
|
||||
existing.databases = databases;
|
||||
socket.emit(`database-list-changed-${conid}`);
|
||||
socket.emitChanged(`database-list-changed-${conid}`);
|
||||
},
|
||||
handle_error(conid, { error }) {
|
||||
console.log(`Error in server connection ${conid}: ${error}`);
|
||||
|
@ -11,4 +11,9 @@ module.exports = {
|
||||
console.log('EMIT:', message, data);
|
||||
socket.emit(message, data);
|
||||
},
|
||||
emitChanged(key) {
|
||||
console.log('EMIT_CHANGED:', key);
|
||||
socket.emit(key);
|
||||
socket.emit('clean-cache', key);
|
||||
}
|
||||
};
|
||||
|
@ -1,6 +1,7 @@
|
||||
import io from 'socket.io-client';
|
||||
import React from 'react';
|
||||
import resolveApi from './resolveApi';
|
||||
import { cacheClean } from './cache';
|
||||
|
||||
const SocketContext = React.createContext(null);
|
||||
|
||||
@ -10,6 +11,7 @@ export function SocketProvider({ children }) {
|
||||
// const newSocket = io('http://localhost:3000', { transports: ['websocket'] });
|
||||
const newSocket = io(resolveApi());
|
||||
setSocket(newSocket);
|
||||
newSocket.on('clean-cache', (reloadTrigger) => cacheClean(reloadTrigger));
|
||||
}, []);
|
||||
return <SocketContext.Provider value={socket}>{children}</SocketContext.Provider>;
|
||||
}
|
||||
|
33
packages/web/src/utility/cache.js
Normal file
33
packages/web/src/utility/cache.js
Normal file
@ -0,0 +1,33 @@
|
||||
let cachedByKey = {};
|
||||
let cachedPromisesByKey = {};
|
||||
const cachedKeysByReloadTrigger = {};
|
||||
|
||||
export function cacheGet(key) {
|
||||
return cachedByKey[key];
|
||||
}
|
||||
|
||||
export function cacheSet(key, value, reloadTrigger) {
|
||||
cachedByKey[key] = value;
|
||||
if (!(reloadTrigger in cachedKeysByReloadTrigger)) {
|
||||
cachedKeysByReloadTrigger[reloadTrigger] = [];
|
||||
}
|
||||
cachedKeysByReloadTrigger[reloadTrigger].push(key);
|
||||
}
|
||||
|
||||
export function cacheClean(reloadTrigger) {
|
||||
const keys = cachedKeysByReloadTrigger[reloadTrigger];
|
||||
if (keys) {
|
||||
for (const key of keys) {
|
||||
delete cachedByKey[key];
|
||||
delete cachedPromisesByKey[key];
|
||||
}
|
||||
}
|
||||
delete cachedKeysByReloadTrigger[reloadTrigger];
|
||||
}
|
||||
|
||||
export function getCachedPromise(key, func) {
|
||||
if (key in cachedPromisesByKey) return cachedPromisesByKey[key];
|
||||
const promise = func();
|
||||
cachedPromisesByKey[key] = promise;
|
||||
return promise;
|
||||
}
|
@ -1,5 +1,7 @@
|
||||
import useFetch from './useFetch';
|
||||
import axios from './axios';
|
||||
import { cacheGet, cacheSet, getCachedPromise } from './cache';
|
||||
import stableStringify from 'json-stable-stringify';
|
||||
|
||||
const tableInfoLoader = ({ conid, database, schemaName, pureName }) => ({
|
||||
url: 'metadata/table-info',
|
||||
@ -9,21 +11,34 @@ const tableInfoLoader = ({ conid, database, schemaName, pureName }) => ({
|
||||
|
||||
async function getCore(loader, args) {
|
||||
const { url, params, reloadTrigger } = loader(args);
|
||||
const resp = await axios.request({
|
||||
method: 'get',
|
||||
url,
|
||||
params,
|
||||
});
|
||||
return resp.data;
|
||||
const key = stableStringify({ url, ...params });
|
||||
|
||||
async function doLoad() {
|
||||
const resp = await axios.request({
|
||||
method: 'get',
|
||||
url,
|
||||
params,
|
||||
});
|
||||
return resp.data;
|
||||
}
|
||||
|
||||
const fromCache = cacheGet(key);
|
||||
if (fromCache) return fromCache;
|
||||
const res = getCachedPromise(key, doLoad);
|
||||
|
||||
cacheSet(key, res, reloadTrigger);
|
||||
return res;
|
||||
}
|
||||
|
||||
function useCore(loader, args) {
|
||||
const { url, params, reloadTrigger } = loader(args);
|
||||
const cacheKey = stableStringify({ url, ...params });
|
||||
|
||||
const res = useFetch({
|
||||
url,
|
||||
params,
|
||||
reloadTrigger,
|
||||
cacheKey,
|
||||
});
|
||||
|
||||
return res;
|
||||
|
@ -3,6 +3,7 @@ import _ from 'lodash';
|
||||
import axios from './axios';
|
||||
import useSocket from './SocketProvider';
|
||||
import stableStringify from 'json-stable-stringify';
|
||||
import { getCachedPromise, cacheGet, cacheSet } from './cache';
|
||||
|
||||
export default function useFetch({
|
||||
url,
|
||||
@ -10,6 +11,7 @@ export default function useFetch({
|
||||
params = undefined,
|
||||
defaultValue = undefined,
|
||||
reloadTrigger = undefined,
|
||||
cacheKey = undefined,
|
||||
...config
|
||||
}) {
|
||||
const [value, setValue] = React.useState([defaultValue, []]);
|
||||
@ -23,14 +25,27 @@ export default function useFetch({
|
||||
const indicators = [url, stableStringify(data), stableStringify(params), loadCounter];
|
||||
|
||||
async function loadValue(loadedIndicators) {
|
||||
const resp = await axios.request({
|
||||
method: 'get',
|
||||
params,
|
||||
url,
|
||||
data,
|
||||
...config,
|
||||
});
|
||||
setValue([resp.data, loadedIndicators]);
|
||||
async function doLoad() {
|
||||
const resp = await axios.request({
|
||||
method: 'get',
|
||||
params,
|
||||
url,
|
||||
data,
|
||||
...config,
|
||||
});
|
||||
return resp.data;
|
||||
}
|
||||
|
||||
if (cacheKey) {
|
||||
const fromCache = cacheGet(cacheKey);
|
||||
if (fromCache) return fromCache;
|
||||
const res = await getCachedPromise(cacheKey, doLoad);
|
||||
setValue([res, loadedIndicators]);
|
||||
cacheSet(cacheKey, res, reloadTrigger);
|
||||
} else {
|
||||
const res = await doLoad();
|
||||
setValue([res, loadedIndicators]);
|
||||
}
|
||||
}
|
||||
|
||||
// React.useEffect(() => {
|
||||
|
Loading…
Reference in New Issue
Block a user