mirror of
https://github.com/Llewellynvdm/nativefier.git
synced 2024-12-22 10:08:55 +00:00
Integrate prettier
This commit is contained in:
parent
949dcfadd8
commit
95fc46d38d
@ -13,7 +13,7 @@ insert_final_newline = true
|
|||||||
[*.{js,py}]
|
[*.{js,py}]
|
||||||
charset = utf-8
|
charset = utf-8
|
||||||
indent_style = space
|
indent_style = space
|
||||||
indent_size = 4
|
indent_size = 2
|
||||||
|
|
||||||
# 2 space indentation
|
# 2 space indentation
|
||||||
[*.{html,css,less,scss,yml,json}]
|
[*.{html,css,less,scss,yml,json}]
|
||||||
|
@ -1,11 +1,15 @@
|
|||||||
extends: airbnb-base
|
extends:
|
||||||
|
- airbnb-base
|
||||||
|
- prettier
|
||||||
env:
|
env:
|
||||||
# TODO: find out how to turn this on only for src/**/*.test.js files
|
# TODO: find out how to turn this on only for src/**/*.test.js files
|
||||||
jest: true
|
jest: true
|
||||||
plugins:
|
plugins:
|
||||||
- import
|
- import
|
||||||
|
- prettier
|
||||||
rules:
|
rules:
|
||||||
# TODO: Remove this when we have shifted away from the async package
|
# TODO: Remove this when we have shifted away from the async package
|
||||||
no-shadow: 'warn'
|
no-shadow: 'warn'
|
||||||
# Gulpfiles and tests use dev dependencies
|
# Gulpfiles and tests use dev dependencies
|
||||||
import/no-extraneous-dependencies: ['error', { devDependencies: ['gulpfile.babel.js', 'gulp/**/**.js', 'test/**/**.js']}]
|
import/no-extraneous-dependencies: ['error', { devDependencies: ['gulpfile.babel.js', 'gulp/**/**.js', 'test/**/**.js']}]
|
||||||
|
prettier/prettier: "error"
|
||||||
|
3
.prettierrc.yaml
Normal file
3
.prettierrc.yaml
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
arrowParens: always
|
||||||
|
singleQuote: true
|
||||||
|
trailingComma: all
|
@ -8,7 +8,9 @@ function createLoginWindow(loginCallback) {
|
|||||||
frame: false,
|
frame: false,
|
||||||
resizable: false,
|
resizable: false,
|
||||||
});
|
});
|
||||||
loginWindow.loadURL(`file://${path.join(__dirname, '/static/login/login.html')}`);
|
loginWindow.loadURL(
|
||||||
|
`file://${path.join(__dirname, '/static/login/login.html')}`,
|
||||||
|
);
|
||||||
|
|
||||||
ipcMain.once('login-message', (event, usernameAndPassword) => {
|
ipcMain.once('login-message', (event, usernameAndPassword) => {
|
||||||
loginCallback(usernameAndPassword[0], usernameAndPassword[1]);
|
loginCallback(usernameAndPassword[0], usernameAndPassword[1]);
|
||||||
|
@ -7,7 +7,12 @@ import createMenu from './../menu/menu';
|
|||||||
import initContextMenu from './../contextMenu/contextMenu';
|
import initContextMenu from './../contextMenu/contextMenu';
|
||||||
|
|
||||||
const {
|
const {
|
||||||
isOSX, linkIsInternal, getCssToInject, shouldInjectCss, getAppIcon, nativeTabsSupported,
|
isOSX,
|
||||||
|
linkIsInternal,
|
||||||
|
getCssToInject,
|
||||||
|
shouldInjectCss,
|
||||||
|
getAppIcon,
|
||||||
|
nativeTabsSupported,
|
||||||
} = helpers;
|
} = helpers;
|
||||||
|
|
||||||
const ZOOM_INTERVAL = 0.1;
|
const ZOOM_INTERVAL = 0.1;
|
||||||
@ -37,7 +42,10 @@ function maybeInjectCss(browserWindow) {
|
|||||||
|
|
||||||
browserWindow.webContents.on('did-finish-load', () => {
|
browserWindow.webContents.on('did-finish-load', () => {
|
||||||
// remove the injection of css the moment the page is loaded
|
// remove the injection of css the moment the page is loaded
|
||||||
browserWindow.webContents.removeListener('did-get-response-details', injectCss);
|
browserWindow.webContents.removeListener(
|
||||||
|
'did-get-response-details',
|
||||||
|
injectCss,
|
||||||
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
// on every page navigation inject the css
|
// on every page navigation inject the css
|
||||||
@ -48,7 +56,6 @@ function maybeInjectCss(browserWindow) {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* @param {{}} inpOptions AppArgs from nativefier.json
|
* @param {{}} inpOptions AppArgs from nativefier.json
|
||||||
@ -78,7 +85,9 @@ function createMainWindow(inpOptions, onAppQuit, setDockBadge) {
|
|||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
const mainWindow = new BrowserWindow(Object.assign({
|
const mainWindow = new BrowserWindow(
|
||||||
|
Object.assign(
|
||||||
|
{
|
||||||
frame: !options.hideWindowFrame,
|
frame: !options.hideWindowFrame,
|
||||||
width: mainWindowState.width,
|
width: mainWindowState.width,
|
||||||
height: mainWindowState.height,
|
height: mainWindowState.height,
|
||||||
@ -95,7 +104,10 @@ function createMainWindow(inpOptions, onAppQuit, setDockBadge) {
|
|||||||
fullscreen: options.fullScreen || undefined,
|
fullscreen: options.fullScreen || undefined,
|
||||||
// Whether the window should always stay on top of other windows. Default is false.
|
// Whether the window should always stay on top of other windows. Default is false.
|
||||||
alwaysOnTop: options.alwaysOnTop,
|
alwaysOnTop: options.alwaysOnTop,
|
||||||
}, DEFAULT_WINDOW_OPTIONS));
|
},
|
||||||
|
DEFAULT_WINDOW_OPTIONS,
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
mainWindowState.manage(mainWindow);
|
mainWindowState.manage(mainWindow);
|
||||||
|
|
||||||
@ -103,12 +115,17 @@ function createMainWindow(inpOptions, onAppQuit, setDockBadge) {
|
|||||||
if (options.maximize) {
|
if (options.maximize) {
|
||||||
mainWindow.maximize();
|
mainWindow.maximize();
|
||||||
options.maximize = undefined;
|
options.maximize = undefined;
|
||||||
fs.writeFileSync(path.join(__dirname, '..', 'nativefier.json'), JSON.stringify(options));
|
fs.writeFileSync(
|
||||||
|
path.join(__dirname, '..', 'nativefier.json'),
|
||||||
|
JSON.stringify(options),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
const withFocusedWindow = (block) => {
|
const withFocusedWindow = (block) => {
|
||||||
const focusedWindow = BrowserWindow.getFocusedWindow();
|
const focusedWindow = BrowserWindow.getFocusedWindow();
|
||||||
if (focusedWindow) { block(focusedWindow); }
|
if (focusedWindow) {
|
||||||
|
block(focusedWindow);
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
const adjustWindowZoom = (window, adjustment) => {
|
const adjustWindowZoom = (window, adjustment) => {
|
||||||
@ -118,11 +135,15 @@ function createMainWindow(inpOptions, onAppQuit, setDockBadge) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const onZoomIn = () => {
|
const onZoomIn = () => {
|
||||||
withFocusedWindow(focusedWindow => adjustWindowZoom(focusedWindow, ZOOM_INTERVAL));
|
withFocusedWindow((focusedWindow) =>
|
||||||
|
adjustWindowZoom(focusedWindow, ZOOM_INTERVAL),
|
||||||
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
const onZoomOut = () => {
|
const onZoomOut = () => {
|
||||||
withFocusedWindow(focusedWindow => adjustWindowZoom(focusedWindow, -ZOOM_INTERVAL));
|
withFocusedWindow((focusedWindow) =>
|
||||||
|
adjustWindowZoom(focusedWindow, -ZOOM_INTERVAL),
|
||||||
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
const onZoomReset = () => {
|
const onZoomReset = () => {
|
||||||
@ -132,13 +153,17 @@ function createMainWindow(inpOptions, onAppQuit, setDockBadge) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const clearAppData = () => {
|
const clearAppData = () => {
|
||||||
dialog.showMessageBox(mainWindow, {
|
dialog.showMessageBox(
|
||||||
|
mainWindow,
|
||||||
|
{
|
||||||
type: 'warning',
|
type: 'warning',
|
||||||
buttons: ['Yes', 'Cancel'],
|
buttons: ['Yes', 'Cancel'],
|
||||||
defaultId: 1,
|
defaultId: 1,
|
||||||
title: 'Clear cache confirmation',
|
title: 'Clear cache confirmation',
|
||||||
message: 'This will clear all data (cookies, local storage etc) from this app. Are you sure you wish to proceed?',
|
message:
|
||||||
}, (response) => {
|
'This will clear all data (cookies, local storage etc) from this app. Are you sure you wish to proceed?',
|
||||||
|
},
|
||||||
|
(response) => {
|
||||||
if (response !== 0) {
|
if (response !== 0) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@ -148,7 +173,8 @@ function createMainWindow(inpOptions, onAppQuit, setDockBadge) {
|
|||||||
mainWindow.loadURL(options.targetUrl);
|
mainWindow.loadURL(options.targetUrl);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
},
|
||||||
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
const onGoBack = () => {
|
const onGoBack = () => {
|
||||||
@ -236,7 +262,10 @@ function createMainWindow(inpOptions, onAppQuit, setDockBadge) {
|
|||||||
|
|
||||||
createMenu(menuOptions);
|
createMenu(menuOptions);
|
||||||
if (!options.disableContextMenu) {
|
if (!options.disableContextMenu) {
|
||||||
initContextMenu(createNewWindow, nativeTabsSupported() ? createNewTab : undefined);
|
initContextMenu(
|
||||||
|
createNewWindow,
|
||||||
|
nativeTabsSupported() ? createNewTab : undefined,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (options.userAgent) {
|
if (options.userAgent) {
|
||||||
@ -280,7 +309,10 @@ function createMainWindow(inpOptions, onAppQuit, setDockBadge) {
|
|||||||
mainWindow.moveTabToNewWindow();
|
mainWindow.moveTabToNewWindow();
|
||||||
}
|
}
|
||||||
mainWindow.setFullScreen(false);
|
mainWindow.setFullScreen(false);
|
||||||
mainWindow.once('leave-full-screen', maybeHideWindow.bind(this, mainWindow, event, options.fastQuit));
|
mainWindow.once(
|
||||||
|
'leave-full-screen',
|
||||||
|
maybeHideWindow.bind(this, mainWindow, event, options.fastQuit),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
maybeHideWindow(mainWindow, event, options.fastQuit, options.tray);
|
maybeHideWindow(mainWindow, event, options.fastQuit, options.tray);
|
||||||
});
|
});
|
||||||
|
@ -29,9 +29,10 @@ function createMenu({
|
|||||||
if (Menu.getApplicationMenu()) {
|
if (Menu.getApplicationMenu()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const zoomResetLabel = (zoomBuildTimeValue === 1.0) ?
|
const zoomResetLabel =
|
||||||
'Reset Zoom' :
|
zoomBuildTimeValue === 1.0
|
||||||
`Reset Zoom (to ${zoomBuildTimeValue * 100}%, set at build time)`;
|
? 'Reset Zoom'
|
||||||
|
: `Reset Zoom (to ${zoomBuildTimeValue * 100}%, set at build time)`;
|
||||||
|
|
||||||
const template = [
|
const template = [
|
||||||
{
|
{
|
||||||
|
@ -1,8 +1,6 @@
|
|||||||
import helpers from './../../helpers/helpers';
|
import helpers from './../../helpers/helpers';
|
||||||
|
|
||||||
const {
|
const { app, Tray, Menu, ipcMain, nativeImage } = require('electron');
|
||||||
app, Tray, Menu, ipcMain, nativeImage,
|
|
||||||
} = require('electron');
|
|
||||||
|
|
||||||
const { getAppIcon } = helpers;
|
const { getAppIcon } = helpers;
|
||||||
|
|
||||||
|
@ -47,7 +47,7 @@ function findSync(pattern, basePath, findDir) {
|
|||||||
matches.push(childPath);
|
matches.push(childPath);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}(basePath));
|
})(basePath);
|
||||||
return matches;
|
return matches;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -56,11 +56,18 @@ function linuxMatch() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function windowsMatch() {
|
function windowsMatch() {
|
||||||
return findSync(/pepflashplayer\.dll/, 'C:\\Program Files (x86)\\Google\\Chrome')[0];
|
return findSync(
|
||||||
|
/pepflashplayer\.dll/,
|
||||||
|
'C:\\Program Files (x86)\\Google\\Chrome',
|
||||||
|
)[0];
|
||||||
}
|
}
|
||||||
|
|
||||||
function darwinMatch() {
|
function darwinMatch() {
|
||||||
return findSync(/PepperFlashPlayer.plugin/, '/Applications/Google Chrome.app/', true)[0];
|
return findSync(
|
||||||
|
/PepperFlashPlayer.plugin/,
|
||||||
|
'/Applications/Google Chrome.app/',
|
||||||
|
true,
|
||||||
|
)[0];
|
||||||
}
|
}
|
||||||
|
|
||||||
function inferFlash() {
|
function inferFlash() {
|
||||||
|
@ -55,11 +55,17 @@ if (appArgs.diskCacheSize) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (appArgs.basicAuthUsername) {
|
if (appArgs.basicAuthUsername) {
|
||||||
app.commandLine.appendSwitch('basic-auth-username', appArgs.basicAuthUsername);
|
app.commandLine.appendSwitch(
|
||||||
|
'basic-auth-username',
|
||||||
|
appArgs.basicAuthUsername,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (appArgs.basicAuthPassword) {
|
if (appArgs.basicAuthPassword) {
|
||||||
app.commandLine.appendSwitch('basic-auth-password', appArgs.basicAuthPassword);
|
app.commandLine.appendSwitch(
|
||||||
|
'basic-auth-password',
|
||||||
|
appArgs.basicAuthPassword,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
// do nothing for setDockBadge if not OSX
|
// do nothing for setDockBadge if not OSX
|
||||||
@ -126,7 +132,10 @@ app.on('login', (event, webContents, request, authInfo, callback) => {
|
|||||||
// for http authentication
|
// for http authentication
|
||||||
event.preventDefault();
|
event.preventDefault();
|
||||||
|
|
||||||
if (appArgs.basicAuthUsername !== null && appArgs.basicAuthPassword !== null) {
|
if (
|
||||||
|
appArgs.basicAuthUsername !== null &&
|
||||||
|
appArgs.basicAuthPassword !== null
|
||||||
|
) {
|
||||||
callback(appArgs.basicAuthUsername, appArgs.basicAuthPassword);
|
callback(appArgs.basicAuthUsername, appArgs.basicAuthPassword);
|
||||||
} else {
|
} else {
|
||||||
createLoginWindow(callback);
|
createLoginWindow(callback);
|
||||||
@ -137,9 +146,12 @@ if (appArgs.singleInstance) {
|
|||||||
const shouldQuit = app.makeSingleInstance(() => {
|
const shouldQuit = app.makeSingleInstance(() => {
|
||||||
// Someone tried to run a second instance, we should focus our window.
|
// Someone tried to run a second instance, we should focus our window.
|
||||||
if (mainWindow) {
|
if (mainWindow) {
|
||||||
if (!mainWindow.isVisible()) { // tray
|
if (!mainWindow.isVisible()) {
|
||||||
|
// tray
|
||||||
mainWindow.show();
|
mainWindow.show();
|
||||||
} if (mainWindow.isMinimized()) { // minimized
|
}
|
||||||
|
if (mainWindow.isMinimized()) {
|
||||||
|
// minimized
|
||||||
mainWindow.restore();
|
mainWindow.restore();
|
||||||
}
|
}
|
||||||
mainWindow.focus();
|
mainWindow.focus();
|
||||||
|
@ -4,6 +4,9 @@ import PATHS from './../helpers/src-paths';
|
|||||||
|
|
||||||
const webpackConfig = require('./../../webpack.config.js');
|
const webpackConfig = require('./../../webpack.config.js');
|
||||||
|
|
||||||
gulp.task('build-app', ['build-static'], () => gulp.src(PATHS.APP_MAIN_JS)
|
gulp.task('build-app', ['build-static'], () =>
|
||||||
|
gulp
|
||||||
|
.src(PATHS.APP_MAIN_JS)
|
||||||
.pipe(webpack(webpackConfig))
|
.pipe(webpack(webpackConfig))
|
||||||
.pipe(gulp.dest(PATHS.APP_DEST)));
|
.pipe(gulp.dest(PATHS.APP_DEST)),
|
||||||
|
);
|
||||||
|
@ -4,4 +4,6 @@ import helpers from './../helpers/gulp-helpers';
|
|||||||
|
|
||||||
const { buildES6 } = helpers;
|
const { buildES6 } = helpers;
|
||||||
|
|
||||||
gulp.task('build-cli', done => buildES6(PATHS.CLI_SRC_JS, PATHS.CLI_DEST, done));
|
gulp.task('build-cli', (done) =>
|
||||||
|
buildES6(PATHS.CLI_SRC_JS, PATHS.CLI_DEST, done),
|
||||||
|
);
|
||||||
|
@ -4,9 +4,14 @@ import helpers from './../helpers/gulp-helpers';
|
|||||||
|
|
||||||
const { buildES6 } = helpers;
|
const { buildES6 } = helpers;
|
||||||
|
|
||||||
gulp.task('build-static-not-js', () => gulp.src([PATHS.APP_STATIC_ALL, '!**/*.js'])
|
gulp.task('build-static-not-js', () =>
|
||||||
.pipe(gulp.dest(PATHS.APP_STATIC_DEST)));
|
gulp
|
||||||
|
.src([PATHS.APP_STATIC_ALL, '!**/*.js'])
|
||||||
|
.pipe(gulp.dest(PATHS.APP_STATIC_DEST)),
|
||||||
|
);
|
||||||
|
|
||||||
gulp.task('build-static-js', done => buildES6(PATHS.APP_STATIC_JS, PATHS.APP_STATIC_DEST, done));
|
gulp.task('build-static-js', (done) =>
|
||||||
|
buildES6(PATHS.APP_STATIC_JS, PATHS.APP_STATIC_DEST, done),
|
||||||
|
);
|
||||||
|
|
||||||
gulp.task('build-static', ['build-static-js', 'build-static-not-js']);
|
gulp.task('build-static', ['build-static-js', 'build-static-not-js']);
|
||||||
|
@ -14,7 +14,8 @@ function shellExec(cmd, silent, callback) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function buildES6(src, dest, callback) {
|
function buildES6(src, dest, callback) {
|
||||||
return gulp.src(src)
|
return gulp
|
||||||
|
.src(src)
|
||||||
.pipe(sourcemaps.init())
|
.pipe(sourcemaps.init())
|
||||||
.pipe(babel())
|
.pipe(babel())
|
||||||
.on('error', callback)
|
.on('error', callback)
|
||||||
|
@ -8,4 +8,4 @@ gulp.task('publish', (done) => {
|
|||||||
shellExec('npm publish', false, done);
|
shellExec('npm publish', false, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
gulp.task('release', callback => runSequence('build', 'publish', callback));
|
gulp.task('release', (callback) => runSequence('build', 'publish', callback));
|
||||||
|
@ -23,7 +23,8 @@
|
|||||||
"watch": "while true ; do gulp watch ; done",
|
"watch": "while true ; do gulp watch ; done",
|
||||||
"package-placeholder": "npm run build && node lib/cli.js http://www.bennish.net/web-notifications.html ~/Desktop --overwrite --name notification-test --icon ./test-resources/iconSampleGrey.png --inject ./test-resources/test-injection.js --inject ./test-resources/test-injection.css && open ~/Desktop/notification-test-darwin-x64/notification-test.app",
|
"package-placeholder": "npm run build && node lib/cli.js http://www.bennish.net/web-notifications.html ~/Desktop --overwrite --name notification-test --icon ./test-resources/iconSampleGrey.png --inject ./test-resources/test-injection.js --inject ./test-resources/test-injection.css && open ~/Desktop/notification-test-darwin-x64/notification-test.app",
|
||||||
"start-placeholder": "npm run build && electron app",
|
"start-placeholder": "npm run build && electron app",
|
||||||
"changelog": "./scripts/changelog"
|
"changelog": "./scripts/changelog",
|
||||||
|
"format": "prettier --write '{gulp,src}/**/*.js' 'app/src/**/*.js'"
|
||||||
},
|
},
|
||||||
"bin": {
|
"bin": {
|
||||||
"nativefier": "lib/cli.js"
|
"nativefier": "lib/cli.js"
|
||||||
@ -68,11 +69,14 @@
|
|||||||
"del": "^3.0.0",
|
"del": "^3.0.0",
|
||||||
"eslint": "^4.17.0",
|
"eslint": "^4.17.0",
|
||||||
"eslint-config-airbnb-base": "^12.1.0",
|
"eslint-config-airbnb-base": "^12.1.0",
|
||||||
|
"eslint-config-prettier": "^2.9.0",
|
||||||
"eslint-plugin-import": "^2.8.0",
|
"eslint-plugin-import": "^2.8.0",
|
||||||
|
"eslint-plugin-prettier": "^2.6.0",
|
||||||
"gulp": "^3.9.1",
|
"gulp": "^3.9.1",
|
||||||
"gulp-babel": "^7.0.1",
|
"gulp-babel": "^7.0.1",
|
||||||
"gulp-sourcemaps": "^2.6.4",
|
"gulp-sourcemaps": "^2.6.4",
|
||||||
"jest": "^22.1.4",
|
"jest": "^22.1.4",
|
||||||
|
"prettier": "^1.12.1",
|
||||||
"regenerator-runtime": "^0.11.1",
|
"regenerator-runtime": "^0.11.1",
|
||||||
"require-dir": "^1.0.0",
|
"require-dir": "^1.0.0",
|
||||||
"run-sequence": "^2.2.1",
|
"run-sequence": "^2.2.1",
|
||||||
|
@ -64,7 +64,9 @@ function maybeCopyScripts(srcs, dest) {
|
|||||||
resolve();
|
resolve();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
const promises = srcs.map(src => new Promise((resolve, reject) => {
|
const promises = srcs.map(
|
||||||
|
(src) =>
|
||||||
|
new Promise((resolve, reject) => {
|
||||||
if (!fs.existsSync(src)) {
|
if (!fs.existsSync(src)) {
|
||||||
reject(new Error('Error copying injection files: file not found'));
|
reject(new Error('Error copying injection files: file not found'));
|
||||||
return;
|
return;
|
||||||
@ -87,7 +89,8 @@ function maybeCopyScripts(srcs, dest) {
|
|||||||
}
|
}
|
||||||
resolve();
|
resolve();
|
||||||
});
|
});
|
||||||
}));
|
}),
|
||||||
|
);
|
||||||
|
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
Promise.all(promises)
|
Promise.all(promises)
|
||||||
@ -133,7 +136,10 @@ function buildApp(src, dest, options, callback) {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
fs.writeFileSync(path.join(dest, '/nativefier.json'), JSON.stringify(appArgs));
|
fs.writeFileSync(
|
||||||
|
path.join(dest, '/nativefier.json'),
|
||||||
|
JSON.stringify(appArgs),
|
||||||
|
);
|
||||||
|
|
||||||
maybeCopyScripts(options.inject, dest)
|
maybeCopyScripts(options.inject, dest)
|
||||||
.catch((err) => {
|
.catch((err) => {
|
||||||
@ -146,5 +152,4 @@ function buildApp(src, dest, options, callback) {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
export default buildApp;
|
export default buildApp;
|
||||||
|
@ -28,7 +28,10 @@ function getAppPath(appPathArray) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (appPathArray.length > 1) {
|
if (appPathArray.length > 1) {
|
||||||
log.warn('Warning: This should not be happening, packaged app path contains more than one element:', appPathArray);
|
log.warn(
|
||||||
|
'Warning: This should not be happening, packaged app path contains more than one element:',
|
||||||
|
appPathArray,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
return appPathArray[0];
|
return appPathArray[0];
|
||||||
@ -43,7 +46,9 @@ function maybeNoIconOption(options) {
|
|||||||
const packageOptions = JSON.parse(JSON.stringify(options));
|
const packageOptions = JSON.parse(JSON.stringify(options));
|
||||||
if (options.platform === 'win32' && !isWindows()) {
|
if (options.platform === 'win32' && !isWindows()) {
|
||||||
if (!hasBinary.sync('wine')) {
|
if (!hasBinary.sync('wine')) {
|
||||||
log.warn('Wine is required to set the icon for a Windows app when packaging on non-windows platforms');
|
log.warn(
|
||||||
|
'Wine is required to set the icon for a Windows app when packaging on non-windows platforms',
|
||||||
|
);
|
||||||
packageOptions.icon = null;
|
packageOptions.icon = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -86,7 +91,9 @@ function removeInvalidOptions(options, param) {
|
|||||||
const packageOptions = JSON.parse(JSON.stringify(options));
|
const packageOptions = JSON.parse(JSON.stringify(options));
|
||||||
if (options.platform === 'win32' && !isWindows()) {
|
if (options.platform === 'win32' && !isWindows()) {
|
||||||
if (!hasBinary.sync('wine')) {
|
if (!hasBinary.sync('wine')) {
|
||||||
log.warn(`Wine is required to use "${param}" option for a Windows app when packaging on non-windows platforms`);
|
log.warn(
|
||||||
|
`Wine is required to use "${param}" option for a Windows app when packaging on non-windows platforms`,
|
||||||
|
);
|
||||||
packageOptions[param] = null;
|
packageOptions[param] = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -161,13 +168,15 @@ function buildMain(inpOptions, callback) {
|
|||||||
|
|
||||||
const progress = new DishonestProgress(5);
|
const progress = new DishonestProgress(5);
|
||||||
|
|
||||||
async.waterfall([
|
async.waterfall(
|
||||||
|
[
|
||||||
(cb) => {
|
(cb) => {
|
||||||
progress.tick('inferring');
|
progress.tick('inferring');
|
||||||
optionsFactory(options)
|
optionsFactory(options)
|
||||||
.then((result) => {
|
.then((result) => {
|
||||||
cb(null, result);
|
cb(null, result);
|
||||||
}).catch((error) => {
|
})
|
||||||
|
.catch((error) => {
|
||||||
cb(error);
|
cb(error);
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
@ -179,7 +188,9 @@ function buildMain(inpOptions, callback) {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
// Change the reference file for the Electron app to be the temporary path
|
// Change the reference file for the Electron app to be the temporary path
|
||||||
const newOptions = Object.assign({}, opts, { dir: tmpPath });
|
const newOptions = Object.assign({}, opts, {
|
||||||
|
dir: tmpPath,
|
||||||
|
});
|
||||||
cb(null, newOptions);
|
cb(null, newOptions);
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
@ -225,10 +236,12 @@ function buildMain(inpOptions, callback) {
|
|||||||
cb(error, appPath);
|
cb(error, appPath);
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
], (error, appPath) => {
|
],
|
||||||
|
(error, appPath) => {
|
||||||
packagerConsole.playback();
|
packagerConsole.playback();
|
||||||
callback(error, appPath);
|
callback(error, appPath);
|
||||||
});
|
},
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
export default buildMain;
|
export default buildMain;
|
||||||
|
@ -84,7 +84,9 @@ function iconBuild(inpOptions, callback) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!isOSX()) {
|
if (!isOSX()) {
|
||||||
log.warn('Skipping icon conversion to .icns, conversion is only supported on OSX');
|
log.warn(
|
||||||
|
'Skipping icon conversion to .icns, conversion is only supported on OSX',
|
||||||
|
);
|
||||||
returnCallback();
|
returnCallback();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
171
src/cli.js
171
src/cli.js
@ -28,12 +28,13 @@ function getProcessEnvs(val) {
|
|||||||
function checkInternet() {
|
function checkInternet() {
|
||||||
dns.lookup('npmjs.com', (err) => {
|
dns.lookup('npmjs.com', (err) => {
|
||||||
if (err && err.code === 'ENOTFOUND') {
|
if (err && err.code === 'ENOTFOUND') {
|
||||||
log.warn('\nNo Internet Connection\nTo offline build, download electron from https://github.com/electron/electron/releases\nand place in ~/AppData/Local/electron/Cache/ on Windows,\n~/.cache/electron on Linux or ~/Library/Caches/electron/ on Mac\nUse --electron-version to specify the version you downloaded.');
|
log.warn(
|
||||||
|
'\nNo Internet Connection\nTo offline build, download electron from https://github.com/electron/electron/releases\nand place in ~/AppData/Local/electron/Cache/ on Windows,\n~/.cache/electron on Linux or ~/Library/Caches/electron/ on Mac\nUse --electron-version to specify the version you downloaded.',
|
||||||
|
);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if (require.main === module) {
|
if (require.main === module) {
|
||||||
program
|
program
|
||||||
.version(packageJson.version)
|
.version(packageJson.version)
|
||||||
@ -43,51 +44,153 @@ if (require.main === module) {
|
|||||||
program.out = appDir;
|
program.out = appDir;
|
||||||
})
|
})
|
||||||
.option('-n, --name <value>', 'app name')
|
.option('-n, --name <value>', 'app name')
|
||||||
.option('-p, --platform <value>', '\'osx\', \'mas\', \'linux\' or \'windows\'')
|
.option('-p, --platform <value>', "'osx', 'mas', 'linux' or 'windows'")
|
||||||
.option('-a, --arch <value>', '\'ia32\' or \'x64\' or \'armv7l\'')
|
.option('-a, --arch <value>', "'ia32' or 'x64' or 'armv7l'")
|
||||||
.option('--app-version <value>', 'The release version of the application. Maps to the `ProductVersion` metadata property on Windows, and `CFBundleShortVersionString` on OS X.')
|
.option(
|
||||||
.option('--build-version <value>', 'The build version of the application. Maps to the `FileVersion` metadata property on Windows, and `CFBundleVersion` on OS X.')
|
'--app-version <value>',
|
||||||
.option('--app-copyright <value>', 'The human-readable copyright line for the app. Maps to the `LegalCopyright` metadata property on Windows, and `NSHumanReadableCopyright` on OS X')
|
'The release version of the application. Maps to the `ProductVersion` metadata property on Windows, and `CFBundleShortVersionString` on OS X.',
|
||||||
.option('--win32metadata <json-string>', 'a JSON string of key/value pairs of application metadata (ProductName, InternalName, FileDescription) to embed into the executable (Windows only).', parseJson)
|
)
|
||||||
.option('-e, --electron-version <value>', 'electron version to package, without the \'v\', see https://github.com/atom/electron/releases')
|
.option(
|
||||||
.option('--no-overwrite', 'do not override output directory if it already exists, defaults to false')
|
'--build-version <value>',
|
||||||
.option('-c, --conceal', 'packages the source code within your app into an archive, defaults to false, see http://electron.atom.io/docs/v0.36.0/tutorial/application-packaging/')
|
'The build version of the application. Maps to the `FileVersion` metadata property on Windows, and `CFBundleVersion` on OS X.',
|
||||||
.option('--counter', 'if the target app should use a persistent counter badge in the dock (macOS only), defaults to false')
|
)
|
||||||
.option('--bounce', 'if the the dock icon should bounce when counter increases (macOS only), defaults to false')
|
.option(
|
||||||
.option('-i, --icon <value>', 'the icon file to use as the icon for the app (should be a .png)')
|
'--app-copyright <value>',
|
||||||
.option('--width <value>', 'set window default width, defaults to 1280px', parseInt)
|
'The human-readable copyright line for the app. Maps to the `LegalCopyright` metadata property on Windows, and `NSHumanReadableCopyright` on OS X',
|
||||||
.option('--height <value>', 'set window default height, defaults to 800px', parseInt)
|
)
|
||||||
.option('--min-width <value>', 'set window minimum width, defaults to 0px', parseInt)
|
.option(
|
||||||
.option('--min-height <value>', 'set window minimum height, defaults to 0px', parseInt)
|
'--win32metadata <json-string>',
|
||||||
.option('--max-width <value>', 'set window maximum width, default is no limit', parseInt)
|
'a JSON string of key/value pairs of application metadata (ProductName, InternalName, FileDescription) to embed into the executable (Windows only).',
|
||||||
.option('--max-height <value>', 'set window maximum height, default is no limit', parseInt)
|
parseJson,
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'-e, --electron-version <value>',
|
||||||
|
"electron version to package, without the 'v', see https://github.com/atom/electron/releases",
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--no-overwrite',
|
||||||
|
'do not override output directory if it already exists, defaults to false',
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'-c, --conceal',
|
||||||
|
'packages the source code within your app into an archive, defaults to false, see http://electron.atom.io/docs/v0.36.0/tutorial/application-packaging/',
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--counter',
|
||||||
|
'if the target app should use a persistent counter badge in the dock (macOS only), defaults to false',
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--bounce',
|
||||||
|
'if the the dock icon should bounce when counter increases (macOS only), defaults to false',
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'-i, --icon <value>',
|
||||||
|
'the icon file to use as the icon for the app (should be a .png)',
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--width <value>',
|
||||||
|
'set window default width, defaults to 1280px',
|
||||||
|
parseInt,
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--height <value>',
|
||||||
|
'set window default height, defaults to 800px',
|
||||||
|
parseInt,
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--min-width <value>',
|
||||||
|
'set window minimum width, defaults to 0px',
|
||||||
|
parseInt,
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--min-height <value>',
|
||||||
|
'set window minimum height, defaults to 0px',
|
||||||
|
parseInt,
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--max-width <value>',
|
||||||
|
'set window maximum width, default is no limit',
|
||||||
|
parseInt,
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--max-height <value>',
|
||||||
|
'set window maximum height, default is no limit',
|
||||||
|
parseInt,
|
||||||
|
)
|
||||||
.option('--x <value>', 'set window x location', parseInt)
|
.option('--x <value>', 'set window x location', parseInt)
|
||||||
.option('--y <value>', 'set window y location', parseInt)
|
.option('--y <value>', 'set window y location', parseInt)
|
||||||
.option('-m, --show-menu-bar', 'set menu bar visible, defaults to false')
|
.option('-m, --show-menu-bar', 'set menu bar visible, defaults to false')
|
||||||
.option('-f, --fast-quit', 'quit app after window close (macOS only), defaults to false')
|
.option(
|
||||||
|
'-f, --fast-quit',
|
||||||
|
'quit app after window close (macOS only), defaults to false',
|
||||||
|
)
|
||||||
.option('-u, --user-agent <value>', 'set the user agent string for the app')
|
.option('-u, --user-agent <value>', 'set the user agent string for the app')
|
||||||
.option('--honest', 'prevent the nativefied app from changing the user agent string to masquerade as a regular chrome browser')
|
.option(
|
||||||
|
'--honest',
|
||||||
|
'prevent the nativefied app from changing the user agent string to masquerade as a regular chrome browser',
|
||||||
|
)
|
||||||
.option('--ignore-certificate', 'ignore certificate related errors')
|
.option('--ignore-certificate', 'ignore certificate related errors')
|
||||||
.option('--disable-gpu', 'disable hardware acceleration')
|
.option('--disable-gpu', 'disable hardware acceleration')
|
||||||
.option('--ignore-gpu-blacklist', 'allow WebGl apps to work on non supported graphics cards')
|
.option(
|
||||||
|
'--ignore-gpu-blacklist',
|
||||||
|
'allow WebGl apps to work on non supported graphics cards',
|
||||||
|
)
|
||||||
.option('--enable-es3-apis', 'force activation of WebGl 2.0')
|
.option('--enable-es3-apis', 'force activation of WebGl 2.0')
|
||||||
.option('--insecure', 'enable loading of insecure content, defaults to false')
|
.option(
|
||||||
|
'--insecure',
|
||||||
|
'enable loading of insecure content, defaults to false',
|
||||||
|
)
|
||||||
.option('--flash', 'if flash should be enabled')
|
.option('--flash', 'if flash should be enabled')
|
||||||
.option('--flash-path <value>', 'path to Chrome flash plugin, find it in `Chrome://plugins`')
|
.option(
|
||||||
.option('--disk-cache-size <value>', 'forces the maximum disk space (in bytes) to be used by the disk cache')
|
'--flash-path <value>',
|
||||||
.option('--inject <value>', 'path to a CSS/JS file to be injected', collect, [])
|
'path to Chrome flash plugin, find it in `Chrome://plugins`',
|
||||||
.option('--full-screen', 'if the app should always be started in full screen')
|
)
|
||||||
|
.option(
|
||||||
|
'--disk-cache-size <value>',
|
||||||
|
'forces the maximum disk space (in bytes) to be used by the disk cache',
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--inject <value>',
|
||||||
|
'path to a CSS/JS file to be injected',
|
||||||
|
collect,
|
||||||
|
[],
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--full-screen',
|
||||||
|
'if the app should always be started in full screen',
|
||||||
|
)
|
||||||
.option('--maximize', 'if the app should always be started maximized')
|
.option('--maximize', 'if the app should always be started maximized')
|
||||||
.option('--hide-window-frame', 'disable window frame and controls')
|
.option('--hide-window-frame', 'disable window frame and controls')
|
||||||
.option('--verbose', 'if verbose logs should be displayed')
|
.option('--verbose', 'if verbose logs should be displayed')
|
||||||
.option('--disable-context-menu', 'disable the context menu')
|
.option('--disable-context-menu', 'disable the context menu')
|
||||||
.option('--disable-dev-tools', 'disable developer tools')
|
.option('--disable-dev-tools', 'disable developer tools')
|
||||||
.option('--zoom <value>', 'default zoom factor to use when the app is opened, defaults to 1.0', parseFloat)
|
.option(
|
||||||
.option('--internal-urls <value>', 'regular expression of URLs to consider "internal"; all other URLs will be opened in an external browser. (default: URLs on same second-level domain as app)')
|
'--zoom <value>',
|
||||||
.option('--crash-reporter <value>', 'remote server URL to send crash reports')
|
'default zoom factor to use when the app is opened, defaults to 1.0',
|
||||||
.option('--single-instance', 'allow only a single instance of the application')
|
parseFloat,
|
||||||
.option('--processEnvs <json-string>', 'a JSON string of key/value pairs to be set as environment variables before any browser windows are opened.', getProcessEnvs)
|
)
|
||||||
.option('--file-download-options <json-string>', 'a JSON string of key/value pairs to be set as file download options. See https://github.com/sindresorhus/electron-dl for available options.', parseJson)
|
.option(
|
||||||
|
'--internal-urls <value>',
|
||||||
|
'regular expression of URLs to consider "internal"; all other URLs will be opened in an external browser. (default: URLs on same second-level domain as app)',
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--crash-reporter <value>',
|
||||||
|
'remote server URL to send crash reports',
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--single-instance',
|
||||||
|
'allow only a single instance of the application',
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--processEnvs <json-string>',
|
||||||
|
'a JSON string of key/value pairs to be set as environment variables before any browser windows are opened.',
|
||||||
|
getProcessEnvs,
|
||||||
|
)
|
||||||
|
.option(
|
||||||
|
'--file-download-options <json-string>',
|
||||||
|
'a JSON string of key/value pairs to be set as file download options. See https://github.com/sindresorhus/electron-dl for available options.',
|
||||||
|
parseJson,
|
||||||
|
)
|
||||||
.option('--tray', 'allow app to stay in system tray')
|
.option('--tray', 'allow app to stay in system tray')
|
||||||
.option('--basic-auth-username <value>', 'basic http(s) auth username')
|
.option('--basic-auth-username <value>', 'basic http(s) auth username')
|
||||||
.option('--basic-auth-password <value>', 'basic http(s) auth password')
|
.option('--basic-auth-password <value>', 'basic http(s) auth password')
|
||||||
|
@ -26,13 +26,19 @@ function convertToIcns(pngSrc, icnsDest, callback) {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
shell.exec(`${PNG_TO_ICNS_BIN_PATH} ${pngSrc} ${icnsDest}`, { silent: true }, (exitCode, stdOut, stdError) => {
|
shell.exec(
|
||||||
|
`${PNG_TO_ICNS_BIN_PATH} ${pngSrc} ${icnsDest}`,
|
||||||
|
{ silent: true },
|
||||||
|
(exitCode, stdOut, stdError) => {
|
||||||
if (stdOut.includes('icon.iconset:error') || exitCode) {
|
if (stdOut.includes('icon.iconset:error') || exitCode) {
|
||||||
if (exitCode) {
|
if (exitCode) {
|
||||||
callback({
|
callback(
|
||||||
|
{
|
||||||
stdOut,
|
stdOut,
|
||||||
stdError,
|
stdError,
|
||||||
}, pngSrc);
|
},
|
||||||
|
pngSrc,
|
||||||
|
);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -41,7 +47,8 @@ function convertToIcns(pngSrc, icnsDest, callback) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
callback(null, icnsDest);
|
callback(null, icnsDest);
|
||||||
});
|
},
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -12,7 +12,8 @@ function isWindows() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function downloadFile(fileUrl) {
|
function downloadFile(fileUrl) {
|
||||||
return axios.get(fileUrl, {
|
return axios
|
||||||
|
.get(fileUrl, {
|
||||||
responseType: 'arraybuffer',
|
responseType: 'arraybuffer',
|
||||||
})
|
})
|
||||||
.then((response) => {
|
.then((response) => {
|
||||||
@ -55,7 +56,9 @@ function allowedIconFormats(platform) {
|
|||||||
formats.push('.ico');
|
formats.push('.ico');
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
throw new Error(`function allowedIconFormats error: Unknown platform ${platform}`);
|
throw new Error(
|
||||||
|
`function allowedIconFormats error: Unknown platform ${platform}`,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
return formats;
|
return formats;
|
||||||
}
|
}
|
||||||
@ -89,7 +92,9 @@ function allowedIconFormats(platform) {
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
throw new Error(`function allowedIconFormats error: Unknown platform ${platform}`);
|
throw new Error(
|
||||||
|
`function allowedIconFormats error: Unknown platform ${platform}`,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
return formats;
|
return formats;
|
||||||
}
|
}
|
||||||
|
@ -27,7 +27,10 @@ function iconShellHelper(shellScriptPath, icoSrc, dest) {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
shell.exec(`${shellScriptPath} ${icoSrc} ${dest}`, { silent: true }, (exitCode, stdOut, stdError) => {
|
shell.exec(
|
||||||
|
`${shellScriptPath} ${icoSrc} ${dest}`,
|
||||||
|
{ silent: true },
|
||||||
|
(exitCode, stdOut, stdError) => {
|
||||||
if (exitCode) {
|
if (exitCode) {
|
||||||
// eslint-disable-next-line prefer-promise-reject-errors
|
// eslint-disable-next-line prefer-promise-reject-errors
|
||||||
reject({
|
reject({
|
||||||
@ -38,7 +41,8 @@ function iconShellHelper(shellScriptPath, icoSrc, dest) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
resolve(dest);
|
resolve(dest);
|
||||||
});
|
},
|
||||||
|
);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -54,22 +58,40 @@ function getTmpDirPath() {
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
function singleIco(icoSrc) {
|
function singleIco(icoSrc) {
|
||||||
return iconShellHelper(SCRIPT_PATHS.singleIco, icoSrc, `${getTmpDirPath()}/icon.ico`);
|
return iconShellHelper(
|
||||||
|
SCRIPT_PATHS.singleIco,
|
||||||
|
icoSrc,
|
||||||
|
`${getTmpDirPath()}/icon.ico`,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
function convertToPng(icoSrc) {
|
function convertToPng(icoSrc) {
|
||||||
return iconShellHelper(SCRIPT_PATHS.convertToPng, icoSrc, `${getTmpDirPath()}/icon.png`);
|
return iconShellHelper(
|
||||||
|
SCRIPT_PATHS.convertToPng,
|
||||||
|
icoSrc,
|
||||||
|
`${getTmpDirPath()}/icon.png`,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
function convertToIco(icoSrc) {
|
function convertToIco(icoSrc) {
|
||||||
return iconShellHelper(SCRIPT_PATHS.convertToIco, icoSrc, `${getTmpDirPath()}/icon.ico`);
|
return iconShellHelper(
|
||||||
|
SCRIPT_PATHS.convertToIco,
|
||||||
|
icoSrc,
|
||||||
|
`${getTmpDirPath()}/icon.ico`,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
function convertToIcns(icoSrc) {
|
function convertToIcns(icoSrc) {
|
||||||
if (!isOSX()) {
|
if (!isOSX()) {
|
||||||
return new Promise((resolve, reject) => reject(new Error('OSX is required to convert to a .icns icon')));
|
return new Promise((resolve, reject) =>
|
||||||
|
reject(new Error('OSX is required to convert to a .icns icon')),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
return iconShellHelper(SCRIPT_PATHS.convertToIcns, icoSrc, `${getTmpDirPath()}/icon.icns`);
|
return iconShellHelper(
|
||||||
|
SCRIPT_PATHS.convertToIcns,
|
||||||
|
icoSrc,
|
||||||
|
`${getTmpDirPath()}/icon.icns`,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
|
@ -25,14 +25,13 @@ function getMaxMatchScore(iconWithScores) {
|
|||||||
*/
|
*/
|
||||||
function getMatchingIcons(iconsWithScores, maxScore) {
|
function getMatchingIcons(iconsWithScores, maxScore) {
|
||||||
return iconsWithScores
|
return iconsWithScores
|
||||||
.filter(item => item.score === maxScore)
|
.filter((item) => item.score === maxScore)
|
||||||
.map(item => Object.assign({}, item, { ext: path.extname(item.url) }));
|
.map((item) => Object.assign({}, item, { ext: path.extname(item.url) }));
|
||||||
}
|
}
|
||||||
|
|
||||||
function mapIconWithMatchScore(fileIndex, targetUrl) {
|
function mapIconWithMatchScore(fileIndex, targetUrl) {
|
||||||
const normalisedTargetUrl = targetUrl.toLowerCase();
|
const normalisedTargetUrl = targetUrl.toLowerCase();
|
||||||
return fileIndex
|
return fileIndex.map((item) => {
|
||||||
.map((item) => {
|
|
||||||
const itemWords = item.name.split(GITCLOUD_SPACE_DELIMITER);
|
const itemWords = item.name.split(GITCLOUD_SPACE_DELIMITER);
|
||||||
const score = itemWords.reduce((currentScore, word) => {
|
const score = itemWords.reduce((currentScore, word) => {
|
||||||
if (normalisedTargetUrl.includes(word)) {
|
if (normalisedTargetUrl.includes(word)) {
|
||||||
@ -48,8 +47,8 @@ function mapIconWithMatchScore(fileIndex, targetUrl) {
|
|||||||
function inferIconFromStore(targetUrl, platform) {
|
function inferIconFromStore(targetUrl, platform) {
|
||||||
const allowedFormats = new Set(allowedIconFormats(platform));
|
const allowedFormats = new Set(allowedIconFormats(platform));
|
||||||
|
|
||||||
return gitCloud('https://jiahaog.github.io/nativefier-icons/')
|
return gitCloud('https://jiahaog.github.io/nativefier-icons/').then(
|
||||||
.then((fileIndex) => {
|
(fileIndex) => {
|
||||||
const iconWithScores = mapIconWithMatchScore(fileIndex, targetUrl);
|
const iconWithScores = mapIconWithMatchScore(fileIndex, targetUrl);
|
||||||
const maxScore = getMaxMatchScore(iconWithScores);
|
const maxScore = getMaxMatchScore(iconWithScores);
|
||||||
|
|
||||||
@ -58,7 +57,9 @@ function inferIconFromStore(targetUrl, platform) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
const iconsMatchingScore = getMatchingIcons(iconWithScores, maxScore);
|
const iconsMatchingScore = getMatchingIcons(iconWithScores, maxScore);
|
||||||
const iconsMatchingExt = iconsMatchingScore.filter(icon => allowedFormats.has(icon.ext));
|
const iconsMatchingExt = iconsMatchingScore.filter((icon) =>
|
||||||
|
allowedFormats.has(icon.ext),
|
||||||
|
);
|
||||||
const matchingIcon = iconsMatchingExt[0];
|
const matchingIcon = iconsMatchingExt[0];
|
||||||
const iconUrl = matchingIcon && matchingIcon.url;
|
const iconUrl = matchingIcon && matchingIcon.url;
|
||||||
|
|
||||||
@ -66,7 +67,8 @@ function inferIconFromStore(targetUrl, platform) {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
return downloadFile(iconUrl);
|
return downloadFile(iconUrl);
|
||||||
});
|
},
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
function writeFilePromise(outPath, data) {
|
function writeFilePromise(outPath, data) {
|
||||||
@ -88,8 +90,7 @@ function inferFromPage(targetUrl, platform, outDir) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// todo might want to pass list of preferences instead
|
// todo might want to pass list of preferences instead
|
||||||
return pageIcon(targetUrl, { ext: preferredExt })
|
return pageIcon(targetUrl, { ext: preferredExt }).then((icon) => {
|
||||||
.then((icon) => {
|
|
||||||
if (!icon) {
|
if (!icon) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
@ -106,8 +107,7 @@ function inferFromPage(targetUrl, platform, outDir) {
|
|||||||
* @param {string} outDir
|
* @param {string} outDir
|
||||||
*/
|
*/
|
||||||
function inferIconFromUrlToPath(targetUrl, platform, outDir) {
|
function inferIconFromUrlToPath(targetUrl, platform, outDir) {
|
||||||
return inferIconFromStore(targetUrl, platform)
|
return inferIconFromStore(targetUrl, platform).then((icon) => {
|
||||||
.then((icon) => {
|
|
||||||
if (!icon) {
|
if (!icon) {
|
||||||
return inferFromPage(targetUrl, platform, outDir);
|
return inferFromPage(targetUrl, platform, outDir);
|
||||||
}
|
}
|
||||||
|
@ -2,7 +2,12 @@ import os from 'os';
|
|||||||
|
|
||||||
function inferPlatform() {
|
function inferPlatform() {
|
||||||
const platform = os.platform();
|
const platform = os.platform();
|
||||||
if ((platform === 'darwin' || platform === 'mas') || platform === 'win32' || platform === 'linux') {
|
if (
|
||||||
|
platform === 'darwin' ||
|
||||||
|
platform === 'mas' ||
|
||||||
|
platform === 'win32' ||
|
||||||
|
platform === 'linux'
|
||||||
|
) {
|
||||||
return platform;
|
return platform;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,7 +1,8 @@
|
|||||||
import axios from 'axios';
|
import axios from 'axios';
|
||||||
import cheerio from 'cheerio';
|
import cheerio from 'cheerio';
|
||||||
|
|
||||||
const USER_AGENT = 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_10_1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/41.0.2227.1 Safari/537.36';
|
const USER_AGENT =
|
||||||
|
'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_10_1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/41.0.2227.1 Safari/537.36';
|
||||||
|
|
||||||
function inferTitle(url) {
|
function inferTitle(url) {
|
||||||
const options = {
|
const options = {
|
||||||
@ -15,7 +16,10 @@ function inferTitle(url) {
|
|||||||
|
|
||||||
return axios(options).then(({ data }) => {
|
return axios(options).then(({ data }) => {
|
||||||
const $ = cheerio.load(data);
|
const $ = cheerio.load(data);
|
||||||
return $('title').first().text().replace(/\//g, '');
|
return $('title')
|
||||||
|
.first()
|
||||||
|
.text()
|
||||||
|
.replace(/\//g, '');
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -5,21 +5,25 @@ import log from 'loglevel';
|
|||||||
const ELECTRON_VERSIONS_URL = 'https://atom.io/download/atom-shell/index.json';
|
const ELECTRON_VERSIONS_URL = 'https://atom.io/download/atom-shell/index.json';
|
||||||
const DEFAULT_CHROME_VERSION = '58.0.3029.110';
|
const DEFAULT_CHROME_VERSION = '58.0.3029.110';
|
||||||
|
|
||||||
function getChromeVersionForElectronVersion(electronVersion, url = ELECTRON_VERSIONS_URL) {
|
function getChromeVersionForElectronVersion(
|
||||||
return axios.get(url, { timeout: 5000 })
|
electronVersion,
|
||||||
.then((response) => {
|
url = ELECTRON_VERSIONS_URL,
|
||||||
|
) {
|
||||||
|
return axios.get(url, { timeout: 5000 }).then((response) => {
|
||||||
if (response.status !== 200) {
|
if (response.status !== 200) {
|
||||||
throw new Error(`Bad request: Status code ${response.status}`);
|
throw new Error(`Bad request: Status code ${response.status}`);
|
||||||
}
|
}
|
||||||
|
|
||||||
const { data } = response;
|
const { data } = response;
|
||||||
const electronVersionToChromeVersion = _.zipObject(
|
const electronVersionToChromeVersion = _.zipObject(
|
||||||
data.map(d => d.version),
|
data.map((d) => d.version),
|
||||||
data.map(d => d.chrome),
|
data.map((d) => d.chrome),
|
||||||
);
|
);
|
||||||
|
|
||||||
if (!(electronVersion in electronVersionToChromeVersion)) {
|
if (!(electronVersion in electronVersionToChromeVersion)) {
|
||||||
throw new Error(`Electron version '${electronVersion}' not found in retrieved version list!`);
|
throw new Error(
|
||||||
|
`Electron version '${electronVersion}' not found in retrieved version list!`,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
return electronVersionToChromeVersion[electronVersion];
|
return electronVersionToChromeVersion[electronVersion];
|
||||||
@ -40,16 +44,24 @@ export function getUserAgentString(chromeVersion, platform) {
|
|||||||
userAgent = `Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/${chromeVersion} Safari/537.36`;
|
userAgent = `Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/${chromeVersion} Safari/537.36`;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
throw new Error('Error invalid platform specified to getUserAgentString()');
|
throw new Error(
|
||||||
|
'Error invalid platform specified to getUserAgentString()',
|
||||||
|
);
|
||||||
}
|
}
|
||||||
return userAgent;
|
return userAgent;
|
||||||
}
|
}
|
||||||
|
|
||||||
function inferUserAgent(electronVersion, platform, url = ELECTRON_VERSIONS_URL) {
|
function inferUserAgent(
|
||||||
|
electronVersion,
|
||||||
|
platform,
|
||||||
|
url = ELECTRON_VERSIONS_URL,
|
||||||
|
) {
|
||||||
return getChromeVersionForElectronVersion(electronVersion, url)
|
return getChromeVersionForElectronVersion(electronVersion, url)
|
||||||
.then(chromeVersion => getUserAgentString(chromeVersion, platform))
|
.then((chromeVersion) => getUserAgentString(chromeVersion, platform))
|
||||||
.catch(() => {
|
.catch(() => {
|
||||||
log.warn(`Unable to infer chrome version for user agent, using ${DEFAULT_CHROME_VERSION}`);
|
log.warn(
|
||||||
|
`Unable to infer chrome version for user agent, using ${DEFAULT_CHROME_VERSION}`,
|
||||||
|
);
|
||||||
return getUserAgentString(DEFAULT_CHROME_VERSION, platform);
|
return getUserAgentString(DEFAULT_CHROME_VERSION, platform);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -20,7 +20,9 @@ function testPlatform(platform) {
|
|||||||
|
|
||||||
describe('Infer User Agent', () => {
|
describe('Infer User Agent', () => {
|
||||||
test('Can infer userAgent for all platforms', (done) => {
|
test('Can infer userAgent for all platforms', (done) => {
|
||||||
const testPromises = _.keys(TEST_RESULT).map(platform => testPlatform(platform));
|
const testPromises = _.keys(TEST_RESULT).map((platform) =>
|
||||||
|
testPlatform(platform),
|
||||||
|
);
|
||||||
Promise.all(testPromises)
|
Promise.all(testPromises)
|
||||||
.then(() => {
|
.then(() => {
|
||||||
done();
|
done();
|
||||||
@ -36,7 +38,9 @@ describe('Infer User Agent', () => {
|
|||||||
const TIMEOUT_URL = 'http://www.google.com:81/';
|
const TIMEOUT_URL = 'http://www.google.com:81/';
|
||||||
inferUserAgent('1.6.7', 'darwin', TIMEOUT_URL)
|
inferUserAgent('1.6.7', 'darwin', TIMEOUT_URL)
|
||||||
.then((userAgent) => {
|
.then((userAgent) => {
|
||||||
expect(userAgent).toBe('Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_5) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.110 Safari/537.36');
|
expect(userAgent).toBe(
|
||||||
|
'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_5) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.110 Safari/537.36',
|
||||||
|
);
|
||||||
done();
|
done();
|
||||||
})
|
})
|
||||||
.catch(done);
|
.catch(done);
|
||||||
|
@ -1,7 +1,10 @@
|
|||||||
import fields from './fields';
|
import fields from './fields';
|
||||||
|
|
||||||
function resultArrayToObject(fieldResults) {
|
function resultArrayToObject(fieldResults) {
|
||||||
return fieldResults.reduce((accumulator, value) => Object.assign({}, accumulator, value), {});
|
return fieldResults.reduce(
|
||||||
|
(accumulator, value) => Object.assign({}, accumulator, value),
|
||||||
|
{},
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
function inferredOptions(oldOptions, fieldResults) {
|
function inferredOptions(oldOptions, fieldResults) {
|
||||||
@ -11,8 +14,9 @@ function inferredOptions(oldOptions, fieldResults) {
|
|||||||
|
|
||||||
// Takes the options object and infers new values
|
// Takes the options object and infers new values
|
||||||
// which may need async work
|
// which may need async work
|
||||||
export default function (options) {
|
export default function(options) {
|
||||||
const tasks = fields(options);
|
const tasks = fields(options);
|
||||||
return Promise.all(tasks)
|
return Promise.all(tasks).then((fieldResults) =>
|
||||||
.then(fieldResults => inferredOptions(options, fieldResults));
|
inferredOptions(options, fieldResults),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
@ -3,9 +3,11 @@ import fields from './fields';
|
|||||||
|
|
||||||
jest.mock('./fields');
|
jest.mock('./fields');
|
||||||
|
|
||||||
fields.mockImplementation(() => [Promise.resolve({
|
fields.mockImplementation(() => [
|
||||||
|
Promise.resolve({
|
||||||
someField: 'newValue',
|
someField: 'newValue',
|
||||||
})]);
|
}),
|
||||||
|
]);
|
||||||
|
|
||||||
test('it should merge the result of the promise', () => {
|
test('it should merge the result of the promise', () => {
|
||||||
const param = { another: 'field', someField: 'oldValue' };
|
const param = { another: 'field', someField: 'oldValue' };
|
||||||
@ -15,4 +17,3 @@ test('it should merge the result of the promise', () => {
|
|||||||
expect(result).toEqual(expected);
|
expect(result).toEqual(expected);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -1,14 +1,13 @@
|
|||||||
import log from 'loglevel';
|
import log from 'loglevel';
|
||||||
import { inferIcon } from './../../infer';
|
import { inferIcon } from './../../infer';
|
||||||
|
|
||||||
export default function ({ icon, targetUrl, platform }) {
|
export default function({ icon, targetUrl, platform }) {
|
||||||
// Icon is the path to the icon
|
// Icon is the path to the icon
|
||||||
if (icon) {
|
if (icon) {
|
||||||
return Promise.resolve(icon);
|
return Promise.resolve(icon);
|
||||||
}
|
}
|
||||||
|
|
||||||
return inferIcon(targetUrl, platform)
|
return inferIcon(targetUrl, platform).catch((error) => {
|
||||||
.catch((error) => {
|
|
||||||
log.warn('Cannot automatically retrieve the app icon:', error);
|
log.warn('Cannot automatically retrieve the app icon:', error);
|
||||||
return null;
|
return null;
|
||||||
});
|
});
|
||||||
|
@ -29,12 +29,17 @@ describe('when the icon parameter is not passed', () => {
|
|||||||
|
|
||||||
describe('when inferIcon resolves with an error', () => {
|
describe('when inferIcon resolves with an error', () => {
|
||||||
test('it should handle the error', () => {
|
test('it should handle the error', () => {
|
||||||
inferIcon.mockImplementationOnce(() => Promise.reject(new Error('some error')));
|
inferIcon.mockImplementationOnce(() =>
|
||||||
|
Promise.reject(new Error('some error')),
|
||||||
|
);
|
||||||
const params = { targetUrl: 'some url', platform: 'mac' };
|
const params = { targetUrl: 'some url', platform: 'mac' };
|
||||||
|
|
||||||
return icon(params).then((result) => {
|
return icon(params).then((result) => {
|
||||||
expect(result).toBe(null);
|
expect(result).toBe(null);
|
||||||
expect(inferIcon).toHaveBeenCalledWith(params.targetUrl, params.platform);
|
expect(inferIcon).toHaveBeenCalledWith(
|
||||||
|
params.targetUrl,
|
||||||
|
params.platform,
|
||||||
|
);
|
||||||
expect(log.warn).toHaveBeenCalledTimes(1);
|
expect(log.warn).toHaveBeenCalledTimes(1);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -2,28 +2,31 @@ import icon from './icon';
|
|||||||
import userAgent from './userAgent';
|
import userAgent from './userAgent';
|
||||||
import name from './name';
|
import name from './name';
|
||||||
|
|
||||||
const fields = [{
|
const fields = [
|
||||||
|
{
|
||||||
field: 'userAgent',
|
field: 'userAgent',
|
||||||
task: userAgent,
|
task: userAgent,
|
||||||
}, {
|
},
|
||||||
|
{
|
||||||
field: 'icon',
|
field: 'icon',
|
||||||
task: icon,
|
task: icon,
|
||||||
}, {
|
},
|
||||||
|
{
|
||||||
field: 'name',
|
field: 'name',
|
||||||
task: name,
|
task: name,
|
||||||
}];
|
},
|
||||||
|
];
|
||||||
|
|
||||||
// Modifies the result of each promise from a scalar
|
// Modifies the result of each promise from a scalar
|
||||||
// value to a object containing its fieldname
|
// value to a object containing its fieldname
|
||||||
function wrap(fieldName, promise, args) {
|
function wrap(fieldName, promise, args) {
|
||||||
return promise(args)
|
return promise(args).then((result) => ({
|
||||||
.then(result => ({
|
|
||||||
[fieldName]: result,
|
[fieldName]: result,
|
||||||
}));
|
}));
|
||||||
}
|
}
|
||||||
|
|
||||||
// Returns a list of promises which will all resolve
|
// Returns a list of promises which will all resolve
|
||||||
// with the following result: {[fieldName]: fieldvalue}
|
// with the following result: {[fieldName]: fieldvalue}
|
||||||
export default function (options) {
|
export default function(options) {
|
||||||
return fields.map(({ field, task }) => wrap(field, task, options));
|
return fields.map(({ field, task }) => wrap(field, task, options));
|
||||||
}
|
}
|
||||||
|
@ -19,4 +19,3 @@ test('it should return a list of promises', () => {
|
|||||||
expect(value).toBeInstanceOf(Promise);
|
expect(value).toBeInstanceOf(Promise);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -10,14 +10,17 @@ function tryToInferName({ name, targetUrl }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
return inferTitle(targetUrl)
|
return inferTitle(targetUrl)
|
||||||
.then(pageTitle => (pageTitle || DEFAULT_APP_NAME))
|
.then((pageTitle) => pageTitle || DEFAULT_APP_NAME)
|
||||||
.catch((error) => {
|
.catch((error) => {
|
||||||
log.warn(`Unable to automatically determine app name, falling back to '${DEFAULT_APP_NAME}'. Reason: ${error}`);
|
log.warn(
|
||||||
|
`Unable to automatically determine app name, falling back to '${DEFAULT_APP_NAME}'. Reason: ${error}`,
|
||||||
|
);
|
||||||
return DEFAULT_APP_NAME;
|
return DEFAULT_APP_NAME;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
export default function ({ platform, name, targetUrl }) {
|
export default function({ platform, name, targetUrl }) {
|
||||||
return tryToInferName({ name, targetUrl })
|
return tryToInferName({ name, targetUrl }).then((result) =>
|
||||||
.then(result => sanitizeFilename(platform, result));
|
sanitizeFilename(platform, result),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
@ -14,12 +14,14 @@ const mockedResult = 'mock name';
|
|||||||
|
|
||||||
describe('well formed name parameters', () => {
|
describe('well formed name parameters', () => {
|
||||||
const params = { name: 'appname', platform: 'something' };
|
const params = { name: 'appname', platform: 'something' };
|
||||||
test('it should not call inferTitle', () => name(params).then((result) => {
|
test('it should not call inferTitle', () =>
|
||||||
|
name(params).then((result) => {
|
||||||
expect(inferTitle).toHaveBeenCalledTimes(0);
|
expect(inferTitle).toHaveBeenCalledTimes(0);
|
||||||
expect(result).toBe(params.name);
|
expect(result).toBe(params.name);
|
||||||
}));
|
}));
|
||||||
|
|
||||||
test('it should call sanitize filename', () => name(params).then((result) => {
|
test('it should call sanitize filename', () =>
|
||||||
|
name(params).then((result) => {
|
||||||
expect(sanitizeFilename).toHaveBeenCalledWith(params.platform, result);
|
expect(sanitizeFilename).toHaveBeenCalledWith(params.platform, result);
|
||||||
}));
|
}));
|
||||||
});
|
});
|
||||||
@ -31,7 +33,8 @@ describe('bad name parameters', () => {
|
|||||||
|
|
||||||
const params = { targetUrl: 'some url' };
|
const params = { targetUrl: 'some url' };
|
||||||
describe('when the name is undefined', () => {
|
describe('when the name is undefined', () => {
|
||||||
test('it should call inferTitle', () => name(params).then(() => {
|
test('it should call inferTitle', () =>
|
||||||
|
name(params).then(() => {
|
||||||
expect(inferTitle).toHaveBeenCalledWith(params.targetUrl);
|
expect(inferTitle).toHaveBeenCalledWith(params.targetUrl);
|
||||||
}));
|
}));
|
||||||
});
|
});
|
||||||
@ -46,7 +49,8 @@ describe('bad name parameters', () => {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
test('it should call sanitize filename', () => name(params).then((result) => {
|
test('it should call sanitize filename', () =>
|
||||||
|
name(params).then((result) => {
|
||||||
expect(sanitizeFilename).toHaveBeenCalledWith(params.platform, result);
|
expect(sanitizeFilename).toHaveBeenCalledWith(params.platform, result);
|
||||||
}));
|
}));
|
||||||
});
|
});
|
||||||
@ -75,7 +79,9 @@ describe('handling inferTitle results', () => {
|
|||||||
|
|
||||||
describe('when inferTitle resolves with an error', () => {
|
describe('when inferTitle resolves with an error', () => {
|
||||||
test('it should return the default app name', () => {
|
test('it should return the default app name', () => {
|
||||||
inferTitle.mockImplementationOnce(() => Promise.reject(new Error('some error')));
|
inferTitle.mockImplementationOnce(() =>
|
||||||
|
Promise.reject(new Error('some error')),
|
||||||
|
);
|
||||||
|
|
||||||
return name(params).then((result) => {
|
return name(params).then((result) => {
|
||||||
expect(result).toBe(DEFAULT_APP_NAME);
|
expect(result).toBe(DEFAULT_APP_NAME);
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
import { inferUserAgent } from './../../infer';
|
import { inferUserAgent } from './../../infer';
|
||||||
|
|
||||||
export default function ({ userAgent, electronVersion, platform }) {
|
export default function({ userAgent, electronVersion, platform }) {
|
||||||
if (userAgent) {
|
if (userAgent) {
|
||||||
return Promise.resolve(userAgent);
|
return Promise.resolve(userAgent);
|
||||||
}
|
}
|
||||||
|
@ -13,6 +13,8 @@ test('when a userAgent parameter is passed', () => {
|
|||||||
test('no userAgent parameter is passed', () => {
|
test('no userAgent parameter is passed', () => {
|
||||||
const params = { electronVersion: '123', platform: 'mac' };
|
const params = { electronVersion: '123', platform: 'mac' };
|
||||||
userAgent(params);
|
userAgent(params);
|
||||||
expect(inferUserAgent).toHaveBeenCalledWith(params.electronVersion, params.platform);
|
expect(inferUserAgent).toHaveBeenCalledWith(
|
||||||
|
params.electronVersion,
|
||||||
|
params.platform,
|
||||||
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -1,7 +1,9 @@
|
|||||||
import normalizeUrl from './normalizeUrl';
|
import normalizeUrl from './normalizeUrl';
|
||||||
|
|
||||||
test("a proper URL shouldn't be mangled", () => {
|
test("a proper URL shouldn't be mangled", () => {
|
||||||
expect(normalizeUrl('http://www.google.com')).toEqual('http://www.google.com');
|
expect(normalizeUrl('http://www.google.com')).toEqual(
|
||||||
|
'http://www.google.com',
|
||||||
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
test('missing protocol should default to http', () => {
|
test('missing protocol should default to http', () => {
|
||||||
@ -9,5 +11,7 @@ test('missing protocol should default to http', () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
test("a proper URL shouldn't be mangled", () => {
|
test("a proper URL shouldn't be mangled", () => {
|
||||||
expect(() => { normalizeUrl('http://ssddfoo bar'); }).toThrow('Your Url: "http://ssddfoo bar" is invalid!');
|
expect(() => {
|
||||||
|
normalizeUrl('http://ssddfoo bar');
|
||||||
|
}).toThrow('Your Url: "http://ssddfoo bar" is invalid!');
|
||||||
});
|
});
|
||||||
|
@ -13,7 +13,7 @@ const { inferPlatform, inferArch } = inferOs;
|
|||||||
* @param {Object} inpOptions
|
* @param {Object} inpOptions
|
||||||
* @returns {Promise}
|
* @returns {Promise}
|
||||||
*/
|
*/
|
||||||
export default function (inpOptions) {
|
export default function(inpOptions) {
|
||||||
const options = {
|
const options = {
|
||||||
dir: PLACEHOLDER_APP_DIR,
|
dir: PLACEHOLDER_APP_DIR,
|
||||||
name: inpOptions.name,
|
name: inpOptions.name,
|
||||||
@ -93,7 +93,10 @@ export default function (inpOptions) {
|
|||||||
options.platform = 'win32';
|
options.platform = 'win32';
|
||||||
}
|
}
|
||||||
|
|
||||||
if (options.platform.toLowerCase() === 'osx' || options.platform.toLowerCase() === 'mac') {
|
if (
|
||||||
|
options.platform.toLowerCase() === 'osx' ||
|
||||||
|
options.platform.toLowerCase() === 'mac'
|
||||||
|
) {
|
||||||
options.platform = 'darwin';
|
options.platform = 'darwin';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2,7 +2,7 @@ import _ from 'lodash';
|
|||||||
import sanitizeFilenameLib from 'sanitize-filename';
|
import sanitizeFilenameLib from 'sanitize-filename';
|
||||||
import { DEFAULT_APP_NAME } from './../constants';
|
import { DEFAULT_APP_NAME } from './../constants';
|
||||||
|
|
||||||
export default function (platform, str) {
|
export default function(platform, str) {
|
||||||
let result = sanitizeFilenameLib(str);
|
let result = sanitizeFilenameLib(str);
|
||||||
|
|
||||||
// remove all non ascii or use default app name
|
// remove all non ascii or use default app name
|
||||||
|
@ -3,7 +3,7 @@ import sanitizeFilename from './sanitizeFilename';
|
|||||||
import { DEFAULT_APP_NAME } from './../constants';
|
import { DEFAULT_APP_NAME } from './../constants';
|
||||||
|
|
||||||
jest.mock('sanitize-filename');
|
jest.mock('sanitize-filename');
|
||||||
sanitizeFilenameLib.mockImplementation(str => str);
|
sanitizeFilenameLib.mockImplementation((str) => str);
|
||||||
|
|
||||||
test('it should call the sanitize-filename npm module', () => {
|
test('it should call the sanitize-filename npm module', () => {
|
||||||
const param = 'abc';
|
const param = 'abc';
|
||||||
|
Loading…
Reference in New Issue
Block a user