proxy settings global and collection level

This commit is contained in:
Mirko Golze 2023-10-15 20:26:36 +02:00
parent f2bdf2eaf6
commit 6dd6879e8f
7 changed files with 254 additions and 254 deletions

View File

@ -19,7 +19,7 @@ const ProxySettings = ({ proxyConfig, onUpdate }) => {
port: Yup.number() port: Yup.number()
.when('enabled', { .when('enabled', {
is: 'enabled', is: 'enabled',
then: (port) => port.typeError('Specify port between 1 and 65535'), then: (port) => port.required('Specify port between 1 and 65535').typeError('Specify port between 1 and 65535'),
otherwise: (port) => port.nullable().transform((_, val) => (val ? Number(val) : null)) otherwise: (port) => port.nullable().transform((_, val) => (val ? Number(val) : null))
}) })
.min(1) .min(1)
@ -208,7 +208,7 @@ const ProxySettings = ({ proxyConfig, onUpdate }) => {
value={formik.values.hostname || ''} value={formik.values.hostname || ''}
/> />
{formik.touched.hostname && formik.errors.hostname ? ( {formik.touched.hostname && formik.errors.hostname ? (
<div className="text-red-500">{formik.errors.hostname}</div> <div className="ml-3 text-red-500">{formik.errors.hostname}</div>
) : null} ) : null}
</div> </div>
<div className="mb-3 flex items-center"> <div className="mb-3 flex items-center">
@ -227,7 +227,9 @@ const ProxySettings = ({ proxyConfig, onUpdate }) => {
onChange={formik.handleChange} onChange={formik.handleChange}
value={formik.values.port} value={formik.values.port}
/> />
{formik.touched.port && formik.errors.port ? <div className="text-red-500">{formik.errors.port}</div> : null} {formik.touched.port && formik.errors.port ? (
<div className="ml-3 text-red-500">{formik.errors.port}</div>
) : null}
</div> </div>
<div className="mb-3 flex items-center"> <div className="mb-3 flex items-center">
<label className="settings-label" htmlFor="auth.enabled"> <label className="settings-label" htmlFor="auth.enabled">
@ -258,7 +260,7 @@ const ProxySettings = ({ proxyConfig, onUpdate }) => {
onChange={formik.handleChange} onChange={formik.handleChange}
/> />
{formik.touched.auth?.username && formik.errors.auth?.username ? ( {formik.touched.auth?.username && formik.errors.auth?.username ? (
<div className="text-red-500">{formik.errors.auth.username}</div> <div className="ml-3 text-red-500">{formik.errors.auth.username}</div>
) : null} ) : null}
</div> </div>
<div className="mb-3 flex items-center"> <div className="mb-3 flex items-center">
@ -278,7 +280,7 @@ const ProxySettings = ({ proxyConfig, onUpdate }) => {
onChange={formik.handleChange} onChange={formik.handleChange}
/> />
{formik.touched.auth?.password && formik.errors.auth?.password ? ( {formik.touched.auth?.password && formik.errors.auth?.password ? (
<div className="text-red-500">{formik.errors.auth.password}</div> <div className="ml-3 text-red-500">{formik.errors.auth.password}</div>
) : null} ) : null}
</div> </div>
</div> </div>
@ -299,7 +301,7 @@ const ProxySettings = ({ proxyConfig, onUpdate }) => {
value={formik.values.noProxy || ''} value={formik.values.noProxy || ''}
/> />
{formik.touched.noProxy && formik.errors.noProxy ? ( {formik.touched.noProxy && formik.errors.noProxy ? (
<div className="text-red-500">{formik.errors.noProxy}</div> <div className="ml-3 text-red-500">{formik.errors.noProxy}</div>
) : null} ) : null}
</div> </div>
<div className="mt-6"> <div className="mt-6">

View File

@ -2,12 +2,55 @@ import React, { useEffect } from 'react';
import { useFormik } from 'formik'; import { useFormik } from 'formik';
import * as Yup from 'yup'; import * as Yup from 'yup';
import toast from 'react-hot-toast'; import toast from 'react-hot-toast';
import { savePreferences } from 'providers/ReduxStore/slices/app';
import StyledWrapper from './StyledWrapper'; import StyledWrapper from './StyledWrapper';
import { usePreferences } from 'providers/Preferences'; import { useDispatch, useSelector } from 'react-redux';
const ProxySettings = () => { const ProxySettings = ({ close }) => {
const { preferences, setPreferences } = usePreferences(); const preferences = useSelector((state) => state.app.preferences);
const dispatch = useDispatch();
const proxySchema = Yup.object({
enabled: Yup.boolean(),
protocol: Yup.string().required().oneOf(['http', 'https', 'socks4', 'socks5']),
hostname: Yup.string()
.when('enabled', {
is: true,
then: (hostname) => hostname.required('Specify the hostname for your proxy.'),
otherwise: (hostname) => hostname.nullable()
})
.max(1024),
port: Yup.number()
.when('enabled', {
is: true,
then: (port) => port.required('Specify port between 1 and 65535').typeError('Specify port between 1 and 65535'),
otherwise: (port) => port.nullable().transform((_, val) => (val ? Number(val) : null))
})
.min(1)
.max(65535),
auth: Yup.object()
.when('enabled', {
is: true,
then: Yup.object({
enabled: Yup.boolean(),
username: Yup.string()
.when(['enabled'], {
is: true,
then: (username) => username.required('Specify username for proxy authentication.')
})
.max(1024),
password: Yup.string()
.when('enabled', {
is: true,
then: (password) => password.required('Specify password for proxy authentication.')
})
.max(1024)
})
})
.optional(),
noProxy: Yup.string().optional().max(1024)
});
const formik = useFormik({ const formik = useFormik({
initialValues: { initialValues: {
@ -22,35 +65,28 @@ const ProxySettings = () => {
}, },
noProxy: preferences.proxy.noProxy || '' noProxy: preferences.proxy.noProxy || ''
}, },
validationSchema: Yup.object({ validationSchema: proxySchema,
enabled: Yup.boolean(),
protocol: Yup.string().oneOf(['http', 'https', 'socks4', 'socks5']),
hostname: Yup.string().max(1024),
port: Yup.number().min(0).max(65535),
auth: Yup.object({
enabled: Yup.boolean(),
username: Yup.string().max(1024),
password: Yup.string().max(1024)
}),
noProxy: Yup.string().max(1024)
}),
onSubmit: (values) => { onSubmit: (values) => {
onUpdate(values); onUpdate(values);
} }
}); });
const onUpdate = (values) => { const onUpdate = (values) => {
const updatedPreferences = { proxySchema
.validate(values, { abortEarly: true })
.then((validatedProxy) => {
dispatch(
savePreferences({
...preferences, ...preferences,
proxy: values proxy: validatedProxy
};
setPreferences(updatedPreferences)
.then(() => {
toast.success('Proxy settings updated successfully.');
}) })
.catch((err) => { ).then(() => {
console.error(err); close();
});
})
.catch((error) => {
let errMsg = error.message || 'Preferences validation error';
toast.error(errMsg);
}); });
}; };
@ -147,7 +183,7 @@ const ProxySettings = () => {
value={formik.values.hostname || ''} value={formik.values.hostname || ''}
/> />
{formik.touched.hostname && formik.errors.hostname ? ( {formik.touched.hostname && formik.errors.hostname ? (
<div className="text-red-500">{formik.errors.hostname}</div> <div className="ml-3 text-red-500">{formik.errors.hostname}</div>
) : null} ) : null}
</div> </div>
<div className="ml-4 mb-3 flex items-center"> <div className="ml-4 mb-3 flex items-center">
@ -166,7 +202,9 @@ const ProxySettings = () => {
onChange={formik.handleChange} onChange={formik.handleChange}
value={formik.values.port} value={formik.values.port}
/> />
{formik.touched.port && formik.errors.port ? <div className="text-red-500">{formik.errors.port}</div> : null} {formik.touched.port && formik.errors.port ? (
<div className="ml-3 text-red-500">{formik.errors.port}</div>
) : null}
</div> </div>
<div className="ml-4 mb-3 flex items-center"> <div className="ml-4 mb-3 flex items-center">
<label className="settings-label" htmlFor="auth.enabled"> <label className="settings-label" htmlFor="auth.enabled">
@ -197,7 +235,7 @@ const ProxySettings = () => {
onChange={formik.handleChange} onChange={formik.handleChange}
/> />
{formik.touched.auth?.username && formik.errors.auth?.username ? ( {formik.touched.auth?.username && formik.errors.auth?.username ? (
<div className="text-red-500">{formik.errors.auth.username}</div> <div className="ml-3 text-red-500">{formik.errors.auth.username}</div>
) : null} ) : null}
</div> </div>
<div className="ml-4 mb-3 flex items-center"> <div className="ml-4 mb-3 flex items-center">
@ -217,7 +255,7 @@ const ProxySettings = () => {
onChange={formik.handleChange} onChange={formik.handleChange}
/> />
{formik.touched.auth?.password && formik.errors.auth?.password ? ( {formik.touched.auth?.password && formik.errors.auth?.password ? (
<div className="text-red-500">{formik.errors.auth.password}</div> <div className="ml-3 text-red-500">{formik.errors.auth.password}</div>
) : null} ) : null}
</div> </div>
</div> </div>
@ -238,7 +276,7 @@ const ProxySettings = () => {
value={formik.values.noProxy || ''} value={formik.values.noProxy || ''}
/> />
{formik.touched.noProxy && formik.errors.noProxy ? ( {formik.touched.noProxy && formik.errors.noProxy ? (
<div className="text-red-500">{formik.errors.noProxy}</div> <div className="ml-3 text-red-500">{formik.errors.noProxy}</div>
) : null} ) : null}
</div> </div>
<div className="mt-6"> <div className="mt-6">

View File

@ -87,8 +87,7 @@ const runSingleRequest = async function (
const httpsAgentRequestFields = {}; const httpsAgentRequestFields = {};
if (insecure) { if (insecure) {
httpsAgentRequestFields['rejectUnauthorized'] = false; httpsAgentRequestFields['rejectUnauthorized'] = false;
} } else {
const caCertArray = [options['cacert'], process.env.SSL_CERT_FILE, process.env.NODE_EXTRA_CA_CERTS]; const caCertArray = [options['cacert'], process.env.SSL_CERT_FILE, process.env.NODE_EXTRA_CA_CERTS];
const caCert = caCertArray.find((el) => el); const caCert = caCertArray.find((el) => el);
if (caCert && caCert.length > 1) { if (caCert && caCert.length > 1) {
@ -98,11 +97,12 @@ const runSingleRequest = async function (
console.log('Error reading CA cert file:' + caCert, err); console.log('Error reading CA cert file:' + caCert, err);
} }
} }
}
// set proxy if enabled // set proxy if enabled
const proxyEnabled = get(brunoConfig, 'proxy.enabled', false); const proxyEnabled = get(brunoConfig, 'proxy.enabled', false);
const proxyByPass = shouldUseProxy(request.url, get(brunoConfig, 'proxy.noProxy', '')); const shouldProxy = shouldUseProxy(request.url, get(brunoConfig, 'proxy.noProxy', ''));
if (proxyEnabled && !proxyByPass) { if (proxyEnabled && shouldProxy) {
let proxyUri; let proxyUri;
const interpolationOptions = { const interpolationOptions = {
envVars: envVariables, envVars: envVariables,

View File

@ -1,72 +0,0 @@
const { ipcMain } = require('electron');
const chokidar = require('chokidar');
const stores = require('../store');
const registerApplicationIpc = (mainWindow, preferences) => {
const change = async (pathname, store) => {
if (store === stores.PREFERENCES) {
mainWindow.webContents.send('main:preferences-read', preferences.getAll());
}
};
class StoreWatcher {
constructor() {
this.watchers = {};
}
addWatcher(watchPath, store) {
console.log(`watcher add: ${watchPath} for store ${store}`);
if (this.watchers[watchPath]) {
this.watchers[watchPath].close();
}
const self = this;
setTimeout(() => {
const watcher = chokidar.watch(watchPath, {
ignoreInitial: false,
usePolling: false,
persistent: true,
ignorePermissionErrors: true,
awaitWriteFinish: {
stabilityThreshold: 80,
pollInterval: 10
},
depth: 20
});
watcher.on('change', (pathname) => change(pathname, store));
self.watchers[watchPath] = watcher;
}, 100);
}
hasWatcher(watchPath) {
return this.watchers[watchPath];
}
removeWatcher(watchPath) {
if (this.watchers[watchPath]) {
this.watchers[watchPath].close();
this.watchers[watchPath] = null;
}
}
}
const storeWatcher = new StoreWatcher();
storeWatcher.addWatcher(preferences.getPath(), stores.PREFERENCES);
ipcMain.handle('renderer:ready-application', async () => {
mainWindow.webContents.send('main:preferences-read', preferences.getAll());
});
ipcMain.handle('renderer:set-preferences', async (event, newPreferences) => {
preferences.setPreferences(newPreferences);
});
ipcMain.handle('renderer:migrate-preferences', async (event, sslVerification) => {
preferences.migrateSslVerification(sslVerification);
});
};
module.exports = registerApplicationIpc;

View File

@ -16,7 +16,7 @@ const { uuid } = require('../../utils/common');
const interpolateVars = require('./interpolate-vars'); const interpolateVars = require('./interpolate-vars');
const { interpolateString } = require('./interpolate-string'); const { interpolateString } = require('./interpolate-string');
const { sortFolder, getAllRequestsInFolderRecursively } = require('./helper'); const { sortFolder, getAllRequestsInFolderRecursively } = require('./helper');
const preferences = require('../../store/preferences'); const { preferences } = require('../../store/preferences');
const { getProcessEnvVars } = require('../../store/process-env'); const { getProcessEnvVars } = require('../../store/process-env');
const { getBrunoConfig } = require('../../store/bruno-config'); const { getBrunoConfig } = require('../../store/bruno-config');
const { HttpsProxyAgent } = require('https-proxy-agent'); const { HttpsProxyAgent } = require('https-proxy-agent');
@ -84,12 +84,11 @@ const getSize = (data) => {
return 0; return 0;
}; };
function getHttpsAgentRequestFields() { const configureRequest = async (collectionUid, request, envVars, collectionVariables, processEnvVars) => {
const httpsAgentRequestFields = {}; const httpsAgentRequestFields = {};
if (!preferences.isTlsVerification()) { if (!preferences.isTlsVerification()) {
httpsAgentRequestFields['rejectUnauthorized'] = false; httpsAgentRequestFields['rejectUnauthorized'] = false;
} } else {
const cacCrtArray = [preferences.getCaCert(), process.env.SSL_CERT_FILE, process.env.NODE_EXTRA_CA_CERTS]; const cacCrtArray = [preferences.getCaCert(), process.env.SSL_CERT_FILE, process.env.NODE_EXTRA_CA_CERTS];
let caCertFile = cacCrtArray.find((el) => el); let caCertFile = cacCrtArray.find((el) => el);
if (caCertFile && caCertFile.length > 1) { if (caCertFile && caCertFile.length > 1) {
@ -99,8 +98,67 @@ function getHttpsAgentRequestFields() {
console.log('Error reading CA cert file:' + caCertFile, err); console.log('Error reading CA cert file:' + caCertFile, err);
} }
} }
return httpsAgentRequestFields; }
}
// proxy configuration
const brunoConfig = getBrunoConfig(collectionUid);
let proxyConfig = get(brunoConfig, 'proxy', {});
let proxyEnabled = get(proxyConfig, 'enabled', 'disabled');
if (proxyEnabled === 'global') {
proxyConfig = preferences.getProxyConfig();
proxyEnabled = get(proxyConfig, 'enabled', false);
}
const shouldProxy = shouldUseProxy(request.url, get(proxyConfig, 'noProxy', ''));
if ((proxyEnabled === true || proxyEnabled === 'enabled') && shouldProxy) {
let proxyUri;
const interpolationOptions = {
envVars,
collectionVariables,
processEnvVars
};
const proxyProtocol = interpolateString(get(proxyConfig, 'protocol'), interpolationOptions);
const proxyHostname = interpolateString(get(proxyConfig, 'hostname'), interpolationOptions);
const proxyPort = interpolateString(get(proxyConfig, 'port'), interpolationOptions);
const proxyAuthEnabled = get(proxyConfig, 'auth.enabled', false);
const socksEnabled = proxyProtocol.includes('socks');
if (proxyAuthEnabled) {
const proxyAuthUsername = interpolateString(get(proxyConfig, 'auth.username'), interpolationOptions);
const proxyAuthPassword = interpolateString(get(proxyConfig, 'auth.password'), interpolationOptions);
proxyUri = `${proxyProtocol}://${proxyAuthUsername}:${proxyAuthPassword}@${proxyHostname}:${proxyPort}`;
} else {
proxyUri = `${proxyProtocol}://${proxyHostname}:${proxyPort}`;
}
if (socksEnabled) {
const socksProxyAgent = new SocksProxyAgent(proxyUri);
request.httpsAgent = socksProxyAgent;
request.httpAgent = socksProxyAgent;
} else {
request.httpsAgent = new HttpsProxyAgent(
proxyUri,
Object.keys(httpsAgentRequestFields).length > 0 ? { ...httpsAgentRequestFields } : undefined
);
request.httpAgent = new HttpProxyAgent(proxyUri);
}
} else if (Object.keys(httpsAgentRequestFields).length > 0) {
request.httpsAgent = new https.Agent({
...httpsAgentRequestFields
});
}
const axiosInstance = makeAxiosInstance();
if (request.awsv4config) {
request.awsv4config = await resolveCredentials(request);
addAwsV4Interceptor(axiosInstance, request);
delete request.awsv4config;
}
return axiosInstance;
};
const registerNetworkIpc = (mainWindow) => { const registerNetworkIpc = (mainWindow) => {
// handler for sending http request // handler for sending http request
@ -224,64 +282,13 @@ const registerNetworkIpc = (mainWindow) => {
cancelTokenUid cancelTokenUid
}); });
const httpsAgentRequestFields = getHttpsAgentRequestFields(); const axiosInstance = await configureRequest(
collectionUid,
// proxy configuration request,
const brunoConfig = getBrunoConfig(collectionUid);
let proxyConfig = get(brunoConfig, 'proxy', {});
let proxyEnabled = get(proxyConfig, 'enabled', 'disabled');
if (proxyEnabled === 'global') {
proxyConfig = preferences.getProxyConfig();
proxyEnabled = get(proxyConfig, 'enabled', false);
}
const proxyByPass = shouldUseProxy(request.url, get(proxyConfig, 'noProxy', ''));
if ((proxyEnabled === true || proxyEnabled === 'enabled') && !proxyByPass) {
let proxyUri;
const interpolationOptions = {
envVars, envVars,
collectionVariables, collectionVariables,
processEnvVars processEnvVars
};
const proxyProtocol = interpolateString(get(proxyConfig, 'protocol'), interpolationOptions);
const proxyHostname = interpolateString(get(proxyConfig, 'hostname'), interpolationOptions);
const proxyPort = interpolateString(get(proxyConfig, 'port'), interpolationOptions);
const proxyAuthEnabled = get(proxyConfig, 'auth.enabled', false);
const socksEnabled = proxyProtocol.includes('socks');
if (proxyAuthEnabled) {
const proxyAuthUsername = interpolateString(get(proxyConfig, 'auth.username'), interpolationOptions);
const proxyAuthPassword = interpolateString(get(proxyConfig, 'auth.password'), interpolationOptions);
proxyUri = `${proxyProtocol}://${proxyAuthUsername}:${proxyAuthPassword}@${proxyHostname}:${proxyPort}`;
} else {
proxyUri = `${proxyProtocol}://${proxyHostname}:${proxyPort}`;
}
if (socksEnabled) {
const socksProxyAgent = new SocksProxyAgent(proxyUri);
request.httpsAgent = socksProxyAgent;
request.httpAgent = socksProxyAgent;
} else {
request.httpsAgent = new HttpsProxyAgent(
proxyUri,
Object.keys(httpsAgentRequestFields).length > 0 ? { ...httpsAgentRequestFields } : undefined
); );
request.httpAgent = new HttpProxyAgent(proxyUri);
}
} else if (Object.keys(httpsAgentRequestFields).length > 0) {
request.httpsAgent = new https.Agent({
...httpsAgentRequestFields
});
}
const axiosInstance = makeAxiosInstance();
if (request.awsv4config) {
request.awsv4config = await resolveCredentials(request);
addAwsV4Interceptor(axiosInstance, request);
delete request.awsv4config;
}
/** @type {import('axios').AxiosResponse} */ /** @type {import('axios').AxiosResponse} */
const response = await axiosInstance(request); const response = await axiosInstance(request);
@ -684,60 +691,17 @@ const registerNetworkIpc = (mainWindow) => {
...eventData ...eventData
}); });
const httpsAgentRequestFields = getHttpsAgentRequestFields(); const axiosInstance = await configureRequest(
collectionUid,
// proxy configuration request,
const brunoConfig = getBrunoConfig(collectionUid);
let proxyConfig = get(brunoConfig, 'proxy', {});
let proxyEnabled = get(proxyConfig, 'enabled', 'disabled');
if (proxyEnabled === 'global') {
proxyConfig = preferences.getProxyConfig();
proxyEnabled = get(proxyConfig, 'enabled', false);
}
const proxyByPass = shouldUseProxy(request.url, get(proxyConfig, 'noProxy', ''));
if ((proxyEnabled === true || proxyEnabled === 'enabled') && !proxyByPass) {
let proxyUri;
const interpolationOptions = {
envVars, envVars,
collectionVariables, collectionVariables,
processEnvVars processEnvVars
};
const proxyProtocol = interpolateString(get(proxyConfig, 'protocol'), interpolationOptions);
const proxyHostname = interpolateString(get(proxyConfig, 'hostname'), interpolationOptions);
const proxyPort = interpolateString(get(proxyConfig, 'port'), interpolationOptions);
const proxyAuthEnabled = get(proxyConfig, 'auth.enabled', false);
const socksEnabled = proxyProtocol.includes('socks');
if (proxyAuthEnabled) {
const proxyAuthUsername = interpolateString(get(proxyConfig, 'auth.username'), interpolationOptions);
const proxyAuthPassword = interpolateString(get(proxyConfig, 'auth.password'), interpolationOptions);
proxyUri = `${proxyProtocol}://${proxyAuthUsername}:${proxyAuthPassword}@${proxyHostname}:${proxyPort}`;
} else {
proxyUri = `${proxyProtocol}://${proxyHostname}:${proxyPort}`;
}
if (socksEnabled) {
const socksProxyAgent = new SocksProxyAgent(proxyUri);
request.httpsAgent = socksProxyAgent;
request.httpAgent = socksProxyAgent;
} else {
request.httpsAgent = new HttpsProxyAgent(
proxyUri,
Object.keys(httpsAgentRequestFields).length > 0 ? { ...httpsAgentRequestFields } : undefined
); );
request.httpAgent = new HttpProxyAgent(proxyUri);
}
} else if (Object.keys(httpsAgentRequestFields).length > 0) {
request.httpsAgent = new https.Agent({
...httpsAgentRequestFields
});
}
// send request
timeStart = Date.now(); timeStart = Date.now();
const response = await axios(request); /** @type {import('axios').AxiosResponse} */
const response = await axiosInstance(request);
timeEnd = Date.now(); timeEnd = Date.now();
// run post-response vars // run post-response vars

View File

@ -1,9 +1,64 @@
const { ipcMain } = require('electron'); const { ipcMain } = require('electron');
const { getPreferences, savePreferences } = require('../store/preferences'); const { getPreferences, savePreferences, getPath } = require('../store/preferences');
const { isDirectory } = require('../utils/filesystem'); const { isDirectory } = require('../utils/filesystem');
const { openCollection } = require('../app/collections'); const { openCollection } = require('../app/collections');
const stores = require('../store');
const chokidar = require('chokidar');
const registerPreferencesIpc = (mainWindow, watcher, lastOpenedCollections) => { const registerPreferencesIpc = (mainWindow, watcher, lastOpenedCollections) => {
const change = async (pathname, store) => {
if (store === stores.PREFERENCES) {
mainWindow.webContents.send('main:load-preferences', getPreferences());
}
};
class StoreWatcher {
constructor() {
this.watchers = {};
}
addWatcher(watchPath, store) {
console.log(`watcher add: ${watchPath} for store ${store}`);
if (this.watchers[watchPath]) {
this.watchers[watchPath].close();
}
const self = this;
setTimeout(() => {
const watcher = chokidar.watch(watchPath, {
ignoreInitial: false,
usePolling: false,
persistent: true,
ignorePermissionErrors: true,
awaitWriteFinish: {
stabilityThreshold: 80,
pollInterval: 10
},
depth: 20
});
watcher.on('change', (pathname) => change(pathname, store));
self.watchers[watchPath] = watcher;
}, 100);
}
hasWatcher(watchPath) {
return this.watchers[watchPath];
}
removeWatcher(watchPath) {
if (this.watchers[watchPath]) {
this.watchers[watchPath].close();
this.watchers[watchPath] = null;
}
}
}
const storeWatcher = new StoreWatcher();
storeWatcher.addWatcher(getPath(), stores.PREFERENCES);
ipcMain.handle('renderer:ready', async (event) => { ipcMain.handle('renderer:ready', async (event) => {
// load preferences // load preferences
const preferences = getPreferences(); const preferences = getPreferences();
@ -15,7 +70,7 @@ const registerPreferencesIpc = (mainWindow, watcher, lastOpenedCollections) => {
if (lastOpened && lastOpened.length) { if (lastOpened && lastOpened.length) {
for (let collectionPath of lastOpened) { for (let collectionPath of lastOpened) {
if (isDirectory(collectionPath)) { if (isDirectory(collectionPath)) {
openCollection(mainWindow, watcher, collectionPath, { await openCollection(mainWindow, watcher, collectionPath, {
dontSendDisplayErrors: true dontSendDisplayErrors: true
}); });
} }

View File

@ -47,6 +47,18 @@ const preferencesSchema = Yup.object().shape({
}), }),
font: Yup.object().shape({ font: Yup.object().shape({
codeFont: Yup.string().nullable() codeFont: Yup.string().nullable()
}),
proxy: Yup.object({
enabled: Yup.boolean(),
protocol: Yup.string().oneOf(['http', 'https', 'socks4', 'socks5']),
hostname: Yup.string().max(1024),
port: Yup.number().min(1).max(65535),
auth: Yup.object({
enabled: Yup.boolean(),
username: Yup.string().max(1024),
password: Yup.string().max(1024)
}).optional(),
noProxy: Yup.string().optional().max(1024)
}) })
}); });
@ -58,9 +70,13 @@ class PreferencesStore {
}); });
} }
getPath() {
return this.store.path;
}
getPreferences() { getPreferences() {
return { return {
defaultPreferences, ...defaultPreferences,
...this.store.get('preferences') ...this.store.get('preferences')
}; };
} }
@ -90,17 +106,13 @@ const savePreferences = async (newPreferences) => {
}); });
}; };
const preferences = { const getPath = () => {
getAll() {
return getPreferences();
},
getPath() {
return preferencesStore.getPath(); return preferencesStore.getPath();
}, };
const preferences = {
isTlsVerification: () => { isTlsVerification: () => {
return get(getPreferences(), 'request.tlsVerification', true); return get(getPreferences(), 'request.sslVerification', true);
}, },
getCaCert: () => { getCaCert: () => {
@ -115,5 +127,6 @@ const preferences = {
module.exports = { module.exports = {
getPreferences, getPreferences,
savePreferences, savePreferences,
getPath,
preferences preferences
}; };