1
0
mirror of https://github.com/BoostIo/Boostnote synced 2025-12-13 17:56:25 +00:00

Merge branch 'master' of https://github.com/BoostIO/Boostnote into spell_check

# Conflicts:
#	browser/components/CodeEditor.js
#	locales/fr.json
#	package.json
This commit is contained in:
ehhc
2018-07-03 09:05:39 +02:00
34 changed files with 326 additions and 236 deletions

View File

@@ -20,6 +20,6 @@ If your issue is regarding boostnote mobile, move to https://github.com/BoostIO/
- OS Version and name : - OS Version and name :
<!-- <!--
Love Boostnote? Please consider supporting us via OpenCollective: Love Boostnote? Please consider supporting us on IssueHunt:
👉 https://opencollective.com/boostnoteio 👉 https://issuehunt.io/repos/53266139
--> -->

View File

@@ -12,12 +12,12 @@ import consts from 'browser/lib/consts'
import styles from '../components/CodeEditor.styl' import styles from '../components/CodeEditor.styl'
import fs from 'fs' import fs from 'fs'
const { ipcRenderer, remote } = require('electron') const { ipcRenderer, remote } = require('electron')
import normalizeEditorFontFamily from 'browser/lib/normalizeEditorFontFamily'
const spellcheck = require('browser/lib/spellcheck') const spellcheck = require('browser/lib/spellcheck')
const buildEditorContextMenu = require('browser/lib/contextMenuBuilder') const buildEditorContextMenu = require('browser/lib/contextMenuBuilder')
CodeMirror.modeURL = '../node_modules/codemirror/mode/%N/%N.js' CodeMirror.modeURL = '../node_modules/codemirror/mode/%N/%N.js'
const defaultEditorFontFamily = ['Monaco', 'Menlo', 'Ubuntu Mono', 'Consolas', 'source-code-pro', 'monospace']
const buildCMRulers = (rulers, enableRulers) => const buildCMRulers = (rulers, enableRulers) =>
enableRulers ? rulers.map(ruler => ({column: ruler})) : [] enableRulers ? rulers.map(ruler => ({column: ruler})) : []
@@ -92,7 +92,7 @@ export default class CodeEditor extends React.Component {
} }
componentDidMount () { componentDidMount () {
const {rulers, enableRulers} = this.props const { rulers, enableRulers } = this.props
const expandSnippet = this.expandSnippet.bind(this) const expandSnippet = this.expandSnippet.bind(this)
const defaultSnippet = [ const defaultSnippet = [
@@ -172,6 +172,7 @@ export default class CodeEditor extends React.Component {
} }
} }
}) })
this.setMode(this.props.mode) this.setMode(this.props.mode)
this.editor.on('focus', this.focusHandler) this.editor.on('focus', this.focusHandler)
@@ -217,7 +218,7 @@ export default class CodeEditor extends React.Component {
wordBeforeCursor.range.from, wordBeforeCursor.range.from,
wordBeforeCursor.range.to wordBeforeCursor.range.to
) )
cm.setCursor({line: cursor.line + cursorLineNumber, ch: cursorLinePosition}) cm.setCursor({ line: cursor.line + cursorLineNumber, ch: cursorLinePosition })
} }
} }
} else { } else {
@@ -512,10 +513,7 @@ export default class CodeEditor extends React.Component {
render () { render () {
const {className, fontSize} = this.props const {className, fontSize} = this.props
let fontFamily = this.props.fontFamily const fontFamily = normalizeEditorFontFamily(this.props.fontFamily)
fontFamily = _.isString(fontFamily) && fontFamily.length > 0
? [fontFamily].concat(defaultEditorFontFamily)
: defaultEditorFontFamily
const width = this.props.width const width = this.props.width
return ( return (
<div <div
@@ -526,7 +524,7 @@ export default class CodeEditor extends React.Component {
ref='root' ref='root'
tabIndex='-1' tabIndex='-1'
style={{ style={{
fontFamily: fontFamily.join(', '), fontFamily,
fontSize: fontSize, fontSize: fontSize,
width: width width: width
}} }}

View File

@@ -21,10 +21,12 @@ const attachmentManagement = require('../main/lib/dataApi/attachmentManagement')
const { app } = remote const { app } = remote
const path = require('path') const path = require('path')
const fileUrl = require('file-url')
const dialog = remote.dialog const dialog = remote.dialog
const markdownStyle = require('!!css!stylus?sourceMap!./markdown.styl')[0][1] const markdownStyle = require('!!css!stylus?sourceMap!./markdown.styl')[0][1]
const appPath = 'file://' + (process.env.NODE_ENV === 'production' const appPath = fileUrl(process.env.NODE_ENV === 'production'
? app.getAppPath() ? app.getAppPath()
: path.resolve()) : path.resolve())
const CSS_FILES = [ const CSS_FILES = [

View File

@@ -315,6 +315,8 @@ $admonition-icon
position absolute position absolute
left 1.2rem left 1.2rem
font-family: "Material Icons" font-family: "Material Icons"
font-weight: normal;
font-style: normal;
font-size: 24px font-size: 24px
display: inline-block; display: inline-block;
line-height: 1; line-height: 1;
@@ -346,27 +348,27 @@ $admonition-title
margin-bottom 0 margin-bottom 0
admonition_types = { admonition_types = {
note: {border-color: #448aff, title-color: rgba(68,138,255,.1), icon: "note"}, note: {color: #0288D1, icon: "note"},
hint: {border-color: #00bfa5, title-color: rgba(0,191,165,.1), icon: "info"}, hint: {color: #009688, icon: "info_outline"},
danger: {border-color: #ff1744, title-color: rgba(255,23,68,.1), icon: "block"}, danger: {color: #c2185b, icon: "block"},
caution: {border-color: #ff9100, title-color: rgba(255,145,0,.1), icon: "warning"}, caution: {color: #ffa726, icon: "warning"},
error: {border-color: #ff1744, title-color: rgba(255,23,68,.1), icon: "error"}, error: {color: #d32f2f, icon: "error_outline"},
attention: {border-color: #64dd17, title-color: rgba(100,221,23,.1), icon: "priority_high"} attention: {color: #455a64, icon: "priority_high"}
} }
for name, val in admonition_types for name, val in admonition_types
.admonition.{name} .admonition.{name}
@extend $admonition @extend $admonition
border-left-color: val[border-color] border-left-color: val[color]
.admonition.{name}>.admonition-title .admonition.{name}>.admonition-title
@extend $admonition-title @extend $admonition-title
border-bottom-color: .1rem solid val[title-color] border-bottom-color: .1rem solid rgba(val[color], 0.2)
background-color: val[title-color] background-color: rgba(val[color], 0.2)
.admonition.{name}>.admonition-title:before .admonition.{name}>.admonition-title:before
@extend $admonition-icon @extend $admonition-icon
color: val[border-color] color: val[color]
content: val[icon] content: val[icon]
themeDarkBackground = darken(#21252B, 10%) themeDarkBackground = darken(#21252B, 10%)

View File

@@ -36,7 +36,15 @@ const consts = {
'Violet Eggplant' 'Violet Eggplant'
], ],
THEMES: ['default'].concat(themes), THEMES: ['default'].concat(themes),
SNIPPET_FILE: snippetFile SNIPPET_FILE: snippetFile,
DEFAULT_EDITOR_FONT_FAMILY: [
'Monaco',
'Menlo',
'Ubuntu Mono',
'Consolas',
'source-code-pro',
'monospace'
]
} }
module.exports = consts module.exports = consts

View File

@@ -0,0 +1,9 @@
import consts from 'browser/lib/consts'
import isString from 'lodash/isString'
export default function normalizeEditorFontFamily (fontFamily) {
const defaultEditorFontFamily = consts.DEFAULT_EDITOR_FONT_FAMILY
return isString(fontFamily) && fontFamily.length > 0
? [fontFamily].concat(defaultEditorFontFamily).join(', ')
: defaultEditorFontFamily.join(', ')
}

View File

@@ -277,6 +277,7 @@ class MarkdownNoteDetail extends React.Component {
handleSwitchMode (type) { handleSwitchMode (type) {
this.setState({ editorType: type }, () => { this.setState({ editorType: type }, () => {
this.focus()
const newConfig = Object.assign({}, this.props.config) const newConfig = Object.assign({}, this.props.config)
newConfig.editor.type = type newConfig.editor.type = type
ConfigManager.set(newConfig) ConfigManager.set(newConfig)

View File

@@ -32,7 +32,7 @@ import { confirmDeleteNote } from 'browser/lib/confirmDeleteNote'
const electron = require('electron') const electron = require('electron')
const { remote } = electron const { remote } = electron
const { Menu, MenuItem, dialog } = remote const { dialog } = remote
class SnippetNoteDetail extends React.Component { class SnippetNoteDetail extends React.Component {
constructor (props) { constructor (props) {
@@ -451,14 +451,14 @@ class SnippetNoteDetail extends React.Component {
} }
handleModeButtonClick (e, index) { handleModeButtonClick (e, index) {
const menu = new Menu() const templetes = []
CodeMirror.modeInfo.sort(function (a, b) { return a.name.localeCompare(b.name) }).forEach((mode) => { CodeMirror.modeInfo.sort(function (a, b) { return a.name.localeCompare(b.name) }).forEach((mode) => {
menu.append(new MenuItem({ templetes.push({
label: mode.name, label: mode.name,
click: (e) => this.handleModeOptionClick(index, mode.name)(e) click: (e) => this.handleModeOptionClick(index, mode.name)(e)
})) })
}) })
menu.popup(remote.getCurrentWindow()) context.popup(templetes)
} }
handleIndentTypeButtonClick (e) { handleIndentTypeButtonClick (e) {

View File

@@ -21,9 +21,10 @@ import AwsMobileAnalyticsConfig from 'browser/main/lib/AwsMobileAnalyticsConfig'
import Markdown from '../../lib/markdown' import Markdown from '../../lib/markdown'
import i18n from 'browser/lib/i18n' import i18n from 'browser/lib/i18n'
import { confirmDeleteNote } from 'browser/lib/confirmDeleteNote' import { confirmDeleteNote } from 'browser/lib/confirmDeleteNote'
import context from 'browser/lib/context'
const { remote } = require('electron') const { remote } = require('electron')
const { Menu, MenuItem, dialog } = remote const { dialog } = remote
const WP_POST_PATH = '/wp/v2/posts' const WP_POST_PATH = '/wp/v2/posts'
function sortByCreatedAt (a, b) { function sortByCreatedAt (a, b) {
@@ -491,55 +492,51 @@ class NoteList extends React.Component {
const updateLabel = i18n.__('Update Blog') const updateLabel = i18n.__('Update Blog')
const openBlogLabel = i18n.__('Open Blog') const openBlogLabel = i18n.__('Open Blog')
const menu = new Menu() const templates = []
if (location.pathname.match(/\/trash/)) { if (location.pathname.match(/\/trash/)) {
menu.append(new MenuItem({ templates.push({
label: restoreNote, label: restoreNote,
click: this.restoreNote click: this.restoreNote
})) }, {
menu.append(new MenuItem({
label: deleteLabel, label: deleteLabel,
click: this.deleteNote click: this.deleteNote
})) })
} else { } else {
if (!location.pathname.match(/\/starred/)) { if (!location.pathname.match(/\/starred/)) {
menu.append(new MenuItem({ templates.push({
label: pinLabel, label: pinLabel,
click: this.pinToTop click: this.pinToTop
})) })
} }
menu.append(new MenuItem({ templates.push({
label: deleteLabel, label: deleteLabel,
click: this.deleteNote click: this.deleteNote
})) }, {
menu.append(new MenuItem({
label: cloneNote, label: cloneNote,
click: this.cloneNote.bind(this) click: this.cloneNote.bind(this)
})) }, {
menu.append(new MenuItem({
label: copyNoteLink, label: copyNoteLink,
click: this.copyNoteLink(note) click: this.copyNoteLink(note)
})) })
if (note.type === 'MARKDOWN_NOTE') { if (note.type === 'MARKDOWN_NOTE') {
if (note.blog && note.blog.blogLink && note.blog.blogId) { if (note.blog && note.blog.blogLink && note.blog.blogId) {
menu.append(new MenuItem({ templates.push({
label: updateLabel, label: updateLabel,
click: this.publishMarkdown.bind(this) click: this.publishMarkdown.bind(this)
})) }, {
menu.append(new MenuItem({
label: openBlogLabel, label: openBlogLabel,
click: () => this.openBlog.bind(this)(note) click: () => this.openBlog.bind(this)(note)
})) })
} else { } else {
menu.append(new MenuItem({ templates.push({
label: publishLabel, label: publishLabel,
click: this.publishMarkdown.bind(this) click: this.publishMarkdown.bind(this)
})) })
} }
} }
} }
menu.popup() context.popup(templates)
} }
updateSelectedNotes (updateFunc, cleanSelection = true) { updateSelectedNotes (updateFunc, cleanSelection = true) {

View File

@@ -11,9 +11,10 @@ import StorageItemChild from 'browser/components/StorageItem'
import _ from 'lodash' import _ from 'lodash'
import { SortableElement } from 'react-sortable-hoc' import { SortableElement } from 'react-sortable-hoc'
import i18n from 'browser/lib/i18n' import i18n from 'browser/lib/i18n'
import context from 'browser/lib/context'
const { remote } = require('electron') const { remote } = require('electron')
const { Menu, dialog } = remote const { dialog } = remote
const escapeStringRegexp = require('escape-string-regexp') const escapeStringRegexp = require('escape-string-regexp')
const path = require('path') const path = require('path')
@@ -21,13 +22,15 @@ class StorageItem extends React.Component {
constructor (props) { constructor (props) {
super(props) super(props)
const { storage } = this.props
this.state = { this.state = {
isOpen: true isOpen: !!storage.isOpen
} }
} }
handleHeaderContextMenu (e) { handleHeaderContextMenu (e) {
const menu = Menu.buildFromTemplate([ context.popup([
{ {
label: i18n.__('Add Folder'), label: i18n.__('Add Folder'),
click: (e) => this.handleAddFolderButtonClick(e) click: (e) => this.handleAddFolderButtonClick(e)
@@ -40,8 +43,6 @@ class StorageItem extends React.Component {
click: (e) => this.handleUnlinkStorageClick(e) click: (e) => this.handleUnlinkStorageClick(e)
} }
]) ])
menu.popup()
} }
handleUnlinkStorageClick (e) { handleUnlinkStorageClick (e) {
@@ -68,8 +69,18 @@ class StorageItem extends React.Component {
} }
handleToggleButtonClick (e) { handleToggleButtonClick (e) {
const { storage, dispatch } = this.props
const isOpen = !this.state.isOpen
dataApi.toggleStorage(storage.key, isOpen)
.then((storage) => {
dispatch({
type: 'EXPAND_STORAGE',
storage,
isOpen
})
})
this.setState({ this.setState({
isOpen: !this.state.isOpen isOpen: isOpen
}) })
} }
@@ -94,7 +105,7 @@ class StorageItem extends React.Component {
} }
handleFolderButtonContextMenu (e, folder) { handleFolderButtonContextMenu (e, folder) {
const menu = Menu.buildFromTemplate([ context.popup([
{ {
label: i18n.__('Rename Folder'), label: i18n.__('Rename Folder'),
click: (e) => this.handleRenameFolderClick(e, folder) click: (e) => this.handleRenameFolderClick(e, folder)
@@ -123,8 +134,6 @@ class StorageItem extends React.Component {
click: (e) => this.handleFolderDeleteClick(e, folder) click: (e) => this.handleFolderDeleteClick(e, folder)
} }
]) ])
menu.popup()
} }
handleRenameFolderClick (e, folder) { handleRenameFolderClick (e, folder) {

View File

@@ -1,8 +1,6 @@
import PropTypes from 'prop-types' import PropTypes from 'prop-types'
import React from 'react' import React from 'react'
import CSSModules from 'browser/lib/CSSModules' import CSSModules from 'browser/lib/CSSModules'
const { remote } = require('electron')
const { Menu } = remote
import dataApi from 'browser/main/lib/dataApi' import dataApi from 'browser/main/lib/dataApi'
import styles from './SideNav.styl' import styles from './SideNav.styl'
import { openModal } from 'browser/main/lib/modal' import { openModal } from 'browser/main/lib/modal'
@@ -19,6 +17,7 @@ import ListButton from './ListButton'
import TagButton from './TagButton' import TagButton from './TagButton'
import {SortableContainer} from 'react-sortable-hoc' import {SortableContainer} from 'react-sortable-hoc'
import i18n from 'browser/lib/i18n' import i18n from 'browser/lib/i18n'
import context from 'browser/lib/context'
class SideNav extends React.Component { class SideNav extends React.Component {
// TODO: should not use electron stuff v0.7 // TODO: should not use electron stuff v0.7
@@ -254,10 +253,9 @@ class SideNav extends React.Component {
handleFilterButtonContextMenu (event) { handleFilterButtonContextMenu (event) {
const { data } = this.props const { data } = this.props
const trashedNotes = data.trashedSet.toJS().map((uniqueKey) => data.noteMap.get(uniqueKey)) const trashedNotes = data.trashedSet.toJS().map((uniqueKey) => data.noteMap.get(uniqueKey))
const menu = Menu.buildFromTemplate([ context.popup([
{ label: i18n.__('Empty Trash'), click: () => this.emptyTrash(trashedNotes) } { label: i18n.__('Empty Trash'), click: () => this.emptyTrash(trashedNotes) }
]) ])
menu.popup()
} }
render () { render () {

View File

@@ -4,10 +4,11 @@ import CSSModules from 'browser/lib/CSSModules'
import styles from './StatusBar.styl' import styles from './StatusBar.styl'
import ZoomManager from 'browser/main/lib/ZoomManager' import ZoomManager from 'browser/main/lib/ZoomManager'
import i18n from 'browser/lib/i18n' import i18n from 'browser/lib/i18n'
import context from 'browser/lib/context'
const electron = require('electron') const electron = require('electron')
const { remote, ipcRenderer } = electron const { remote, ipcRenderer } = electron
const { Menu, MenuItem, dialog } = remote const { dialog } = remote
const zoomOptions = [0.8, 0.9, 1, 1.1, 1.2, 1.3, 1.4, 1.5, 1.6, 1.7, 1.8, 1.9, 2.0] const zoomOptions = [0.8, 0.9, 1, 1.1, 1.2, 1.3, 1.4, 1.5, 1.6, 1.7, 1.8, 1.9, 2.0]
@@ -26,16 +27,16 @@ class StatusBar extends React.Component {
} }
handleZoomButtonClick (e) { handleZoomButtonClick (e) {
const menu = new Menu() const templates = []
zoomOptions.forEach((zoom) => { zoomOptions.forEach((zoom) => {
menu.append(new MenuItem({ templates.push({
label: Math.floor(zoom * 100) + '%', label: Math.floor(zoom * 100) + '%',
click: () => this.handleZoomMenuItemClick(zoom) click: () => this.handleZoomMenuItemClick(zoom)
})) })
}) })
menu.popup(remote.getCurrentWindow()) context.popup(templates)
} }
handleZoomMenuItemClick (zoomFactor) { handleZoomMenuItemClick (zoomFactor) {

View File

@@ -21,8 +21,8 @@ export const DEFAULT_CONFIG = {
listStyle: 'DEFAULT', // 'DEFAULT', 'SMALL' listStyle: 'DEFAULT', // 'DEFAULT', 'SMALL'
amaEnabled: true, amaEnabled: true,
hotkey: { hotkey: {
toggleMain: OSX ? 'Cmd + Alt + L' : 'Super + Alt + E', toggleMain: OSX ? 'Command + Alt + L' : 'Super + Alt + E',
toggleMode: OSX ? 'Cmd + M' : 'Ctrl + M' toggleMode: OSX ? 'Command + M' : 'Ctrl + M'
}, },
ui: { ui: {
language: 'en', language: 'en',
@@ -182,6 +182,17 @@ function assignConfigValues (originalConfig, rcConfig) {
config.ui = Object.assign({}, DEFAULT_CONFIG.ui, originalConfig.ui, rcConfig.ui) config.ui = Object.assign({}, DEFAULT_CONFIG.ui, originalConfig.ui, rcConfig.ui)
config.editor = Object.assign({}, DEFAULT_CONFIG.editor, originalConfig.editor, rcConfig.editor) config.editor = Object.assign({}, DEFAULT_CONFIG.editor, originalConfig.editor, rcConfig.editor)
config.preview = Object.assign({}, DEFAULT_CONFIG.preview, originalConfig.preview, rcConfig.preview) config.preview = Object.assign({}, DEFAULT_CONFIG.preview, originalConfig.preview, rcConfig.preview)
rewriteHotkey(config)
return config
}
function rewriteHotkey (config) {
const keys = [...Object.keys(config.hotkey)]
keys.forEach(key => {
config.hotkey[key] = config.hotkey[key].replace(/Cmd/g, 'Command')
})
return config return config
} }

View File

@@ -37,7 +37,8 @@ function addStorage (input) {
key, key,
name: input.name, name: input.name,
type: input.type, type: input.type,
path: input.path path: input.path,
isOpen: false
} }
return Promise.resolve(newStorage) return Promise.resolve(newStorage)
@@ -48,7 +49,8 @@ function addStorage (input) {
key: newStorage.key, key: newStorage.key,
type: newStorage.type, type: newStorage.type,
name: newStorage.name, name: newStorage.name,
path: newStorage.path path: newStorage.path,
isOpen: false
}) })
localStorage.setItem('storages', JSON.stringify(rawStorages)) localStorage.setItem('storages', JSON.stringify(rawStorages))

View File

@@ -109,7 +109,7 @@ function migrateAttachments (renderedHTML, storagePath, noteKey) {
* @returns {String} postprocessed HTML in which all :storage references are mapped to the actual paths. * @returns {String} postprocessed HTML in which all :storage references are mapped to the actual paths.
*/ */
function fixLocalURLS (renderedHTML, storagePath) { function fixLocalURLS (renderedHTML, storagePath) {
return renderedHTML.replace(new RegExp(mdurl.encode(path.sep), 'g'), path.sep).replace(new RegExp(STORAGE_FOLDER_PLACEHOLDER, 'g'), 'file:///' + path.join(storagePath, DESTINATION_FOLDER)) return renderedHTML.replace(new RegExp(mdurl.encode(path.sep), 'g'), path.sep).replace(new RegExp('/?' + STORAGE_FOLDER_PLACEHOLDER, 'g'), 'file:///' + path.join(storagePath, DESTINATION_FOLDER))
} }
/** /**
@@ -195,7 +195,7 @@ function handlePastImageEvent (codeEditor, storageKey, noteKey, dataTransferItem
*/ */
function getAttachmentsInContent (markdownContent) { function getAttachmentsInContent (markdownContent) {
const preparedInput = markdownContent.replace(new RegExp(mdurl.encode(path.sep), 'g'), path.sep) const preparedInput = markdownContent.replace(new RegExp(mdurl.encode(path.sep), 'g'), path.sep)
const regexp = new RegExp(STORAGE_FOLDER_PLACEHOLDER + escapeStringRegexp(path.sep) + '?([a-zA-Z0-9]|-)*' + escapeStringRegexp(path.sep) + '[a-zA-Z0-9]+(\\.[a-zA-Z0-9]+)?', 'g') const regexp = new RegExp('/?' + STORAGE_FOLDER_PLACEHOLDER + '(' + escapeStringRegexp(path.sep) + '|/)' + '?([a-zA-Z0-9]|-)*' + '(' + escapeStringRegexp(path.sep) + '|/)' + '([a-zA-Z0-9]|\\.)+(\\.[a-zA-Z0-9]+)?', 'g')
return preparedInput.match(regexp) return preparedInput.match(regexp)
} }

View File

@@ -1,5 +1,6 @@
const dataApi = { const dataApi = {
init: require('./init'), init: require('./init'),
toggleStorage: require('./toggleStorage'),
addStorage: require('./addStorage'), addStorage: require('./addStorage'),
renameStorage: require('./renameStorage'), renameStorage: require('./renameStorage'),
removeStorage: require('./removeStorage'), removeStorage: require('./removeStorage'),

View File

@@ -8,7 +8,8 @@ function resolveStorageData (storageCache) {
key: storageCache.key, key: storageCache.key,
name: storageCache.name, name: storageCache.name,
type: storageCache.type, type: storageCache.type,
path: storageCache.path path: storageCache.path,
isOpen: storageCache.isOpen
} }
const boostnoteJSONPath = path.join(storageCache.path, 'boostnote.json') const boostnoteJSONPath = path.join(storageCache.path, 'boostnote.json')

View File

@@ -0,0 +1,28 @@
const _ = require('lodash')
const resolveStorageData = require('./resolveStorageData')
/**
* @param {String} key
* @param {Boolean} isOpen
* @return {Object} Storage meta data
*/
function toggleStorage (key, isOpen) {
let cachedStorageList
try {
cachedStorageList = JSON.parse(localStorage.getItem('storages'))
if (!_.isArray(cachedStorageList)) throw new Error('invalid storages')
} catch (err) {
console.log('error got')
console.error(err)
return Promise.reject(err)
}
const targetStorage = _.find(cachedStorageList, {key: key})
if (targetStorage == null) return Promise.reject('Storage')
targetStorage.isOpen = isOpen
localStorage.setItem('storages', JSON.stringify(cachedStorageList))
return resolveStorageData(targetStorage)
}
module.exports = toggleStorage

View File

@@ -3,7 +3,7 @@ import CM from 'browser/main/lib/ConfigManager'
import ee from 'browser/main/lib/eventEmitter' import ee from 'browser/main/lib/eventEmitter'
import { isObjectEqual } from 'browser/lib/utils' import { isObjectEqual } from 'browser/lib/utils'
require('mousetrap-global-bind') require('mousetrap-global-bind')
const functions = require('./shortcut') import functions from './shortcut'
let shortcuts = CM.get().hotkey let shortcuts = CM.get().hotkey

View File

@@ -4,8 +4,7 @@ import CSSModules from 'browser/lib/CSSModules'
import dataApi from 'browser/main/lib/dataApi' import dataApi from 'browser/main/lib/dataApi'
import i18n from 'browser/lib/i18n' import i18n from 'browser/lib/i18n'
import eventEmitter from 'browser/main/lib/eventEmitter' import eventEmitter from 'browser/main/lib/eventEmitter'
const { remote } = require('electron') import context from 'browser/lib/context'
const { Menu, MenuItem } = remote
class SnippetList extends React.Component { class SnippetList extends React.Component {
constructor (props) { constructor (props) {
@@ -21,18 +20,17 @@ class SnippetList extends React.Component {
} }
reloadSnippetList () { reloadSnippetList () {
dataApi.fetchSnippet().then(snippets => this.setState({snippets})) dataApi.fetchSnippet().then(snippets => {
this.setState({snippets})
this.props.onSnippetSelect(snippets[0])
})
} }
handleSnippetContextMenu (snippet) { handleSnippetContextMenu (snippet) {
const menu = new Menu() context.popup([{
menu.append(new MenuItem({
label: i18n.__('Delete snippet'), label: i18n.__('Delete snippet'),
click: () => { click: () => this.deleteSnippet(snippet)
this.deleteSnippet(snippet) }])
}
}))
menu.popup()
} }
deleteSnippet (snippet) { deleteSnippet (snippet) {
@@ -43,7 +41,7 @@ class SnippetList extends React.Component {
} }
handleSnippetClick (snippet) { handleSnippetClick (snippet) {
this.props.onSnippetClick(snippet) this.props.onSnippetSelect(snippet)
} }
createSnippet () { createSnippet () {
@@ -55,6 +53,16 @@ class SnippetList extends React.Component {
}).catch(err => { throw err }) }).catch(err => { throw err })
} }
defineSnippetStyleName (snippet) {
const { currentSnippet } = this.props
if (currentSnippet == null) return
if (currentSnippet.id === snippet.id) {
return 'snippet-item-selected'
} else {
return 'snippet-item'
}
}
render () { render () {
const { snippets } = this.state const { snippets } = this.state
return ( return (
@@ -70,7 +78,7 @@ class SnippetList extends React.Component {
{ {
snippets.map((snippet) => ( snippets.map((snippet) => (
<li <li
styleName='snippet-item' styleName={this.defineSnippetStyleName(snippet)}
key={snippet.id} key={snippet.id}
onContextMenu={() => this.handleSnippetContextMenu(snippet)} onContextMenu={() => this.handleSnippetContextMenu(snippet)}
onClick={() => this.handleSnippetClick(snippet)}> onClick={() => this.handleSnippetClick(snippet)}>

View File

@@ -25,7 +25,7 @@ class SnippetTab extends React.Component {
}, 500) }, 500)
} }
handleSnippetClick (snippet) { handleSnippetSelect (snippet) {
const { currentSnippet } = this.state const { currentSnippet } = this.state
if (currentSnippet === null || currentSnippet.id !== snippet.id) { if (currentSnippet === null || currentSnippet.id !== snippet.id) {
dataApi.fetchSnippet(snippet.id).then(changedSnippet => { dataApi.fetchSnippet(snippet.id).then(changedSnippet => {
@@ -66,8 +66,9 @@ class SnippetTab extends React.Component {
<div styleName='root'> <div styleName='root'>
<div styleName='header'>{i18n.__('Snippets')}</div> <div styleName='header'>{i18n.__('Snippets')}</div>
<SnippetList <SnippetList
onSnippetClick={this.handleSnippetClick.bind(this)} onSnippetSelect={this.handleSnippetSelect.bind(this)}
onSnippetDeleted={this.handleDeleteSnippet.bind(this)} /> onSnippetDeleted={this.handleDeleteSnippet.bind(this)}
currentSnippet={currentSnippet} />
<div styleName='snippet-detail' style={{visibility: currentSnippet ? 'visible' : 'hidden'}}> <div styleName='snippet-detail' style={{visibility: currentSnippet ? 'visible' : 'hidden'}}>
<div styleName='group-section'> <div styleName='group-section'>
<div styleName='group-section-label'>{i18n.__('Snippet name')}</div> <div styleName='group-section-label'>{i18n.__('Snippet name')}</div>

View File

@@ -122,6 +122,10 @@
&:hover &:hover
background darken(#f5f5f5, 5) background darken(#f5f5f5, 5)
.snippet-item-selected
@extend .snippet-list .snippet-item
background darken(#f5f5f5, 5)
.snippet-detail .snippet-detail
width 70% width 70%
height calc(100% - 200px) height calc(100% - 200px)
@@ -142,6 +146,8 @@ body[data-theme="default"], body[data-theme="white"]
background $ui-borderColor background $ui-borderColor
&:hover &:hover
background darken($ui-backgroundColor, 5) background darken($ui-backgroundColor, 5)
.snippet-item-selected
background darken($ui-backgroundColor, 5)
body[data-theme="dark"] body[data-theme="dark"]
.snippets .snippets
@@ -152,8 +158,12 @@ body[data-theme="dark"]
background $ui-dark-borderColor background $ui-dark-borderColor
&:hover &:hover
background darken($ui-dark-backgroundColor, 5) background darken($ui-dark-backgroundColor, 5)
.snippet-item-selected
background darken($ui-dark-backgroundColor, 5)
.snippet-detail .snippet-detail
color white color white
.group-control-button
colorDarkPrimaryButton()
body[data-theme="solarized-dark"] body[data-theme="solarized-dark"]
.snippets .snippets
@@ -164,8 +174,12 @@ body[data-theme="solarized-dark"]
background $ui-solarized-dark-borderColor background $ui-solarized-dark-borderColor
&:hover &:hover
background darken($ui-solarized-dark-backgroundColor, 5) background darken($ui-solarized-dark-backgroundColor, 5)
.snippet-item-selected
background darken($ui-solarized-dark-backgroundColor, 5)
.snippet-detail .snippet-detail
color white color white
.group-control-button
colorSolarizedDarkPrimaryButton()
body[data-theme="monokai"] body[data-theme="monokai"]
.snippets .snippets
@@ -176,5 +190,9 @@ body[data-theme="monokai"]
background $ui-monokai-borderColor background $ui-monokai-borderColor
&:hover &:hover
background darken($ui-monokai-backgroundColor, 5) background darken($ui-monokai-backgroundColor, 5)
.snippet-item-selected
background darken($ui-monokai-backgroundColor, 5)
.snippet-detail .snippet-detail
color white color white
.group-control-button
colorMonokaiPrimaryButton()

View File

@@ -11,6 +11,7 @@ import 'codemirror-mode-elixir'
import _ from 'lodash' import _ from 'lodash'
import i18n from 'browser/lib/i18n' import i18n from 'browser/lib/i18n'
import { getLanguages } from 'browser/lib/Languages' import { getLanguages } from 'browser/lib/Languages'
import normalizeEditorFontFamily from 'browser/lib/normalizeEditorFontFamily'
const OSX = global.process.platform === 'darwin' const OSX = global.process.platform === 'darwin'
@@ -164,7 +165,7 @@ class UiTab extends React.Component {
const { config, codemirrorTheme } = this.state const { config, codemirrorTheme } = this.state
const codemirrorSampleCode = 'function iamHappy (happy) {\n\tif (happy) {\n\t console.log("I am Happy!")\n\t} else {\n\t console.log("I am not Happy!")\n\t}\n};' const codemirrorSampleCode = 'function iamHappy (happy) {\n\tif (happy) {\n\t console.log("I am Happy!")\n\t} else {\n\t console.log("I am not Happy!")\n\t}\n};'
const enableEditRulersStyle = config.editor.enableRulers ? 'block' : 'none' const enableEditRulersStyle = config.editor.enableRulers ? 'block' : 'none'
const customCSS = config.preview.customCSS const fontFamily = normalizeEditorFontFamily(config.editor.fontFamily)
return ( return (
<div styleName='root'> <div styleName='root'>
<div styleName='group'> <div styleName='group'>
@@ -262,8 +263,16 @@ class UiTab extends React.Component {
}) })
} }
</select> </select>
<div styleName='code-mirror'> <div styleName='code-mirror' style={{fontFamily}}>
<ReactCodeMirror ref={e => (this.codeMirrorInstance = e)} value={codemirrorSampleCode} options={{ lineNumbers: true, readOnly: true, mode: 'javascript', theme: codemirrorTheme }} /> <ReactCodeMirror
ref={e => (this.codeMirrorInstance = e)}
value={codemirrorSampleCode}
options={{
lineNumbers: true,
readOnly: true,
mode: 'javascript',
theme: codemirrorTheme
}} />
</div> </div>
</div> </div>
</div> </div>
@@ -596,7 +605,19 @@ class UiTab extends React.Component {
type='checkbox' type='checkbox'
/>&nbsp; />&nbsp;
{i18n.__('Allow custom CSS for preview')} {i18n.__('Allow custom CSS for preview')}
<ReactCodeMirror onChange={e => this.handleUIChange(e)} ref={e => (this.customCSSCM = e)} value={config.preview.customCSS} options={{ lineNumbers: true, mode: 'css', theme: codemirrorTheme }} /> <div style={{fontFamily}}>
<ReactCodeMirror
width='400px'
height='400px'
onChange={e => this.handleUIChange(e)}
ref={e => (this.customCSSCM = e)}
value={config.preview.customCSS}
options={{
lineNumbers: true,
mode: 'css',
theme: codemirrorTheme
}} />
</div>
</div> </div>
</div> </div>

View File

@@ -360,6 +360,12 @@ function data (state = defaultDataMap(), action) {
state.storageMap = new Map(state.storageMap) state.storageMap = new Map(state.storageMap)
state.storageMap.set(action.storage.key, action.storage) state.storageMap.set(action.storage.key, action.storage)
return state return state
case 'EXPAND_STORAGE':
state = Object.assign({}, state)
state.storageMap = new Map(state.storageMap)
action.storage.isOpen = action.isOpen
state.storageMap.set(action.storage.key, action.storage)
return state
} }
return state return state
} }

View File

@@ -90,7 +90,7 @@ app.on('ready', function () {
mainWindow.setMenu(menu) mainWindow.setMenu(menu)
} }
// Check update every hour // Check update every day
setInterval(function () { setInterval(function () {
checkUpdate() checkUpdate()
}, 1000 * 60 * 60 * 24) }, 1000 * 60 * 60 * 24)
@@ -106,7 +106,7 @@ app.on('ready', function () {
checkUpdate() checkUpdate()
} }
}) })
}, 10000) }, 10 * 1000)
ipcServer = require('./ipcServer') ipcServer = require('./ipcServer')
ipcServer.server.start() ipcServer.server.start()
}) })

View File

@@ -141,17 +141,17 @@
"Portuguese": "Portugais", "Portuguese": "Portugais",
"Spanish": "Espagnol", "Spanish": "Espagnol",
"You have to save!": "Il faut sauvegarder !", "You have to save!": "Il faut sauvegarder !",
"Russian": "Russian", "Russian": "Russe",
"Command(⌘)": "Command(⌘)", "Command(⌘)": "Command(⌘)",
"Editor Rulers": "Editor Rulers", "Editor Rulers": "Règles dans l'éditeur",
"Enable": "Enable", "Enable": "Activer",
"Disable": "Disable", "Disable": "Désactiver",
"Allow preview to scroll past the last line": "Allow preview to scroll past the last line", "Allow preview to scroll past the last line": "Permettre de scroller après la dernière ligne dans l'aperçu",
"Sanitization": "Sanitization", "Sanitization": "Sanitization",
"Only allow secure html tags (recommended)": "Only allow secure html tags (recommended)", "Only allow secure html tags (recommended)": "N'accepter que les tags html sécurisés (recommandé)",
"Allow styles": "Allow styles", "Allow styles": "Accepter les styles",
"Allow dangerous html tags": "Allow dangerous html tags", "Allow dangerous html tags": "Accepter les tags html dangereux",
"Convert textual arrows to beautiful signs. ⚠ This will interfere with using HTML comments in your Markdown.": "Convert textual arrows to beautiful signs. ⚠ This will interfere with using HTML comments in your Markdown.", "Convert textual arrows to beautiful signs. ⚠ This will interfere with using HTML comments in your Markdown.": "Convertir des flèches textuelles en jolis signes. ⚠ Cela va interferérer avec les éventuels commentaires HTML dans votre Markdown.",
"⚠ You have pasted a link referring an attachment that could not be found in the storage location of this note. Pasting links referring attachments is only supported if the source and destination location is the same storage. Please Drag&Drop the attachment instead! ⚠": "⚠ You have pasted a link referring an attachment that could not be found in the storage location of this note. Pasting links referring attachments is only supported if the source and destination location is the same storage. Please Drag&Drop the attachment instead! ⚠", "⚠ You have pasted a link referring an attachment that could not be found in the storage location of this note. Pasting links referring attachments is only supported if the source and destination location is the same storage. Please Drag&Drop the attachment instead! ⚠": "⚠ Vous avez collé un lien qui référence une pièce-jointe qui n'a pas pu être récupéré dans le dossier de stockage de la note. Coller des liens qui font référence à des pièces-jointes ne fonctionne que si la source et la destination et la même. Veuillez plutôt utiliser du Drag & Drop ! ⚠",
"Disabled": "Disabled" "Disabled": "Disabled"
} }

View File

@@ -4,10 +4,10 @@
"Preferences": "偏好設定", "Preferences": "偏好設定",
"Make a note": "做點筆記", "Make a note": "做點筆記",
"Ctrl": "Ctrl", "Ctrl": "Ctrl",
"Ctrl(^)": "Ctrl", "Ctrl(^)": "Ctrl(^)",
"to create a new note": "新增筆記", "to create a new note": "新增筆記",
"Toggle Mode": "切換模式", "Toggle Mode": "切換模式",
"Trash": "廢紙簍", "Trash": "垃圾桶",
"MODIFICATION DATE": "修改時間", "MODIFICATION DATE": "修改時間",
"Words": "單字", "Words": "單字",
"Letters": "字數", "Letters": "字數",
@@ -20,8 +20,8 @@
".html": ".html", ".html": ".html",
"Print": "列印", "Print": "列印",
"Your preferences for Boostnote": "Boostnote 偏好設定", "Your preferences for Boostnote": "Boostnote 偏好設定",
"Storages": "本機儲存空間", "Storages": "儲存空間",
"Add Storage Location": "新增一個本機儲存位置", "Add Storage Location": "新增儲存位置",
"Add Folder": "新增資料夾", "Add Folder": "新增資料夾",
"Open Storage folder": "開啟儲存資料夾", "Open Storage folder": "開啟儲存資料夾",
"Unlink": "解除連結", "Unlink": "解除連結",
@@ -43,12 +43,12 @@
"Switch to Preview": "切回預覽頁面的時機", "Switch to Preview": "切回預覽頁面的時機",
"When Editor Blurred": "當編輯器失去焦點時", "When Editor Blurred": "當編輯器失去焦點時",
"When Editor Blurred, Edit On Double Click": "當編輯器失去焦點時,雙擊切換到編輯畫面", "When Editor Blurred, Edit On Double Click": "當編輯器失去焦點時,雙擊切換到編輯畫面",
"On Right Click": "點右鍵切換兩個頁面", "On Right Click": "點右鍵切換兩個頁面",
"Editor Keymap": "編輯器 Keymap", "Editor Keymap": "編輯器 Keymap",
"default": "預設", "default": "預設",
"vim": "vim", "vim": "vim",
"emacs": "emacs", "emacs": "emacs",
"⚠️ Please restart boostnote after you change the keymap": "⚠️ 請重新開啟 Boostnote 以完成設定。", "⚠️ Please restart boostnote after you change the keymap": "⚠️ 修改鍵盤配置請重新開啟 Boostnote ",
"Show line numbers in the editor": "在編輯器中顯示行號", "Show line numbers in the editor": "在編輯器中顯示行號",
"Allow editor to scroll past the last line": "允許編輯器捲軸捲動超過最後一行", "Allow editor to scroll past the last line": "允許編輯器捲軸捲動超過最後一行",
"Bring in web page title when pasting URL on editor": "在編輯器貼上網址的時候,自動加上網頁標題", "Bring in web page title when pasting URL on editor": "在編輯器貼上網址的時候,自動加上網頁標題",
@@ -79,7 +79,7 @@
"Analytics": "分析", "Analytics": "分析",
"Boostnote collects anonymous data for the sole purpose of improving the application, and strictly does not collect any personal information such the contents of your notes.": "Boostnote 收集匿名資料單純只為了提升軟體使用體驗,絕對不收集任何個人資料(包括筆記內容)", "Boostnote collects anonymous data for the sole purpose of improving the application, and strictly does not collect any personal information such the contents of your notes.": "Boostnote 收集匿名資料單純只為了提升軟體使用體驗,絕對不收集任何個人資料(包括筆記內容)",
"You can see how it works on ": "你可以看看它的程式碼是如何運作 ", "You can see how it works on ": "你可以看看它的程式碼是如何運作 ",
"You can choose to enable or disable this option.": "你可以選擇啟用或用這項功能", "You can choose to enable or disable this option.": "你可以選擇啟用或用這項功能",
"Enable analytics to help improve Boostnote": "允許數據分析以協助我們改進 Boostnote", "Enable analytics to help improve Boostnote": "允許數據分析以協助我們改進 Boostnote",
"Crowdfunding": "群眾募資", "Crowdfunding": "群眾募資",
"Dear everyone,": "親愛的用戶:", "Dear everyone,": "親愛的用戶:",
@@ -104,9 +104,9 @@
"Confirm": "確認", "Confirm": "確認",
"Cancel": "取消", "Cancel": "取消",
"Markdown Note": "Markdown 筆記", "Markdown Note": "Markdown 筆記",
"This format is for creating text documents. Checklists, code blocks and Latex blocks are available.": "建立文件、清單,也可以使用程式碼區塊甚至是 Latex 區塊。", "This format is for creating text documents. Checklists, code blocks and Latex blocks are available.": "建立文件、清單,也可以使用程式碼區塊 Latex 區塊。",
"Snippet Note": "程式碼片段筆記", "Snippet Note": "程式碼片段筆記",
"This format is for creating code snippets. Multiple snippets can be grouped into a single note.": "建立程式碼區塊片段。個程式碼區塊可以合在同一個筆記。", "This format is for creating code snippets. Multiple snippets can be grouped into a single note.": "建立程式碼區塊片段。個程式碼區塊可以分組爲同一個筆記。",
"Tab to switch format": "使用 Tab 鍵切換格式", "Tab to switch format": "使用 Tab 鍵切換格式",
"Updated": "依更新時間排序", "Updated": "依更新時間排序",
"Created": "依建立時間排序", "Created": "依建立時間排序",
@@ -117,12 +117,12 @@
"Blog Type": "部落格類型", "Blog Type": "部落格類型",
"Blog Address": "部落格網址", "Blog Address": "部落格網址",
"Save": "儲存", "Save": "儲存",
"Auth": "Auth", "Auth": "驗證",
"Authentication Method": "認證方法", "Authentication Method": "認證方法",
"JWT": "JWT", "JWT": "JWT",
"USER": "USER", "USER": "USER",
"Token": "Token", "Token": "Token",
"Storage": "本機儲存空間", "Storage": "儲存空間",
"Hotkeys": "快捷鍵", "Hotkeys": "快捷鍵",
"Show/Hide Boostnote": "顯示/隱藏 Boostnote", "Show/Hide Boostnote": "顯示/隱藏 Boostnote",
"Restore": "還原", "Restore": "還原",
@@ -144,7 +144,7 @@
"Russian": "Russian", "Russian": "Russian",
"Editor Rulers": "編輯器中顯示垂直尺規", "Editor Rulers": "編輯器中顯示垂直尺規",
"Enable": "啟用", "Enable": "啟用",
"Disable": "用", "Disable": "用",
"Sanitization": "過濾 HTML 程式碼", "Sanitization": "過濾 HTML 程式碼",
"Only allow secure html tags (recommended)": "只允許安全的 HTML 標籤 (建議)", "Only allow secure html tags (recommended)": "只允許安全的 HTML 標籤 (建議)",
"Allow styles": "允許樣式", "Allow styles": "允許樣式",

View File

@@ -1,7 +1,7 @@
{ {
"name": "boost", "name": "boost",
"productName": "Boostnote", "productName": "Boostnote",
"version": "0.11.6", "version": "0.11.7",
"main": "index.js", "main": "index.js",
"description": "Boostnote", "description": "Boostnote",
"license": "GPL-3.0", "license": "GPL-3.0",
@@ -17,7 +17,7 @@
"dev-start": "concurrently --kill-others \"npm run webpack\" \"npm run hot\"" "dev-start": "concurrently --kill-others \"npm run webpack\" \"npm run hot\""
}, },
"config": { "config": {
"electron-version": "1.8.7" "electron-version": "2.0.3"
}, },
"repository": { "repository": {
"type": "git", "type": "git",
@@ -53,11 +53,12 @@
"@rokt33r/season": "^5.3.0", "@rokt33r/season": "^5.3.0",
"aws-sdk": "^2.48.0", "aws-sdk": "^2.48.0",
"aws-sdk-mobile-analytics": "^0.9.2", "aws-sdk-mobile-analytics": "^0.9.2",
"codemirror": "^5.37.0", "codemirror": "^5.39.0",
"codemirror-mode-elixir": "^1.1.1", "codemirror-mode-elixir": "^1.1.1",
"electron-config": "^0.2.1", "electron-config": "^0.2.1",
"electron-gh-releases": "^2.0.2", "electron-gh-releases": "^2.0.2",
"escape-string-regexp": "^1.0.5", "escape-string-regexp": "^1.0.5",
"file-url": "^2.0.2",
"filenamify": "^2.0.0", "filenamify": "^2.0.0",
"flowchart.js": "^1.6.5", "flowchart.js": "^1.6.5",
"font-awesome": "^4.3.0", "font-awesome": "^4.3.0",
@@ -71,16 +72,14 @@
"lodash-move": "^1.1.1", "lodash-move": "^1.1.1",
"markdown-it": "^6.0.1", "markdown-it": "^6.0.1",
"markdown-it-admonition": "https://github.com/johannbre/markdown-it-admonition.git", "markdown-it-admonition": "https://github.com/johannbre/markdown-it-admonition.git",
"markdown-it-checkbox": "^1.1.0",
"markdown-it-emoji": "^1.1.1", "markdown-it-emoji": "^1.1.1",
"markdown-it-footnote": "^3.0.0", "markdown-it-footnote": "^3.0.0",
"markdown-it-imsize": "^2.0.1", "markdown-it-imsize": "^2.0.1",
"markdown-it-kbd": "^1.1.1", "markdown-it-kbd": "^1.1.1",
"markdown-it-multimd-table": "^2.0.1", "markdown-it-multimd-table": "^2.0.1",
"markdown-it-named-headers": "^0.0.4", "markdown-it-named-headers": "^0.0.4",
"markdown-it-plantuml": "^0.3.0", "markdown-it-plantuml": "^1.1.0",
"markdown-it-smartarrows": "^1.0.1", "markdown-it-smartarrows": "^1.0.1",
"md5": "^2.0.0",
"mdurl": "^1.0.1", "mdurl": "^1.0.1",
"moment": "^2.10.3", "moment": "^2.10.3",
"mousetrap": "^1.6.1", "mousetrap": "^1.6.1",
@@ -97,8 +96,6 @@
"sander": "^0.5.1", "sander": "^0.5.1",
"sanitize-html": "^1.18.2", "sanitize-html": "^1.18.2",
"striptags": "^2.2.1", "striptags": "^2.2.1",
"superagent": "^1.2.0",
"superagent-promise": "^1.0.3",
"typo-js": "^1.0.3", "typo-js": "^1.0.3",
"unique-slug": "2.0.0", "unique-slug": "2.0.0",
"uuid": "^3.2.1" "uuid": "^3.2.1"
@@ -121,7 +118,7 @@
"css-loader": "^0.19.0", "css-loader": "^0.19.0",
"devtron": "^1.1.0", "devtron": "^1.1.0",
"dom-storage": "^2.0.2", "dom-storage": "^2.0.2",
"electron": "2.0.2", "electron": "2.0.3",
"electron-packager": "^6.0.0", "electron-packager": "^6.0.0",
"eslint": "^3.13.1", "eslint": "^3.13.1",
"eslint-config-standard": "^6.2.1", "eslint-config-standard": "^6.2.1",

View File

@@ -25,7 +25,7 @@ Boostnote is an open source project. It's an independent project with its ongoin
## Community ## Community
- [Facebook Group](https://www.facebook.com/groups/boostnote/) - [Facebook Group](https://www.facebook.com/groups/boostnote/)
- [Twitter](https://twitter.com/boostnoteapp) - [Twitter](https://twitter.com/boostnoteapp)
- [Slack Group](https://join.slack.com/t/boostnote-group/shared_invite/enQtMzcwNDU3NDU3ODI0LTU1ZDgwZDNiZTNmN2RhOTY4OTM5ODY0ODUzMTRiNmQ0ZDMzZDRiYzg2YmQ5ZDYzZTQxYjMxYzBlNTM4NjcyYjM) - [Slack Group](https://join.slack.com/t/boostnote-group/shared_invite/enQtMzkxOTk4ODkyNzc0LThkNmMzY2VlZjVhYTNiYjE5YjQyZGVjNTJlYTY1OGMyZTFjNGU5YTUyYjUzOWZhYTU4OTVlNDYyNDFjYWMzNDM)
- [Blog](https://boostlog.io/tags/boostnote) - [Blog](https://boostlog.io/tags/boostnote)
- [Reddit](https://www.reddit.com/r/Boostnote/) - [Reddit](https://www.reddit.com/r/Boostnote/)

View File

@@ -200,7 +200,7 @@ it('should test that getAttachmentsInContent finds all attachments', function ()
' </body>\n' + ' </body>\n' +
'</html>' '</html>'
const actual = systemUnderTest.getAttachmentsInContent(testInput) const actual = systemUnderTest.getAttachmentsInContent(testInput)
const expected = [':storage' + path.sep + '9c9c4ba3-bc1e-441f-9866-c1e9a806e31c' + path.sep + '0.6r4zdgc22xp', ':storage' + path.sep + '9c9c4ba3-bc1e-441f-9866-c1e9a806e31c' + path.sep + '0.q2i4iw0fyx', ':storage' + path.sep + '9c9c4ba3-bc1e-441f-9866-c1e9a806e31c' + path.sep + 'd6c5ee92.jpg'] const expected = [':storage' + path.sep + '9c9c4ba3-bc1e-441f-9866-c1e9a806e31c' + path.sep + '0.6r4zdgc22xp.png', ':storage' + path.sep + '9c9c4ba3-bc1e-441f-9866-c1e9a806e31c' + path.sep + '0.q2i4iw0fyx.pdf', ':storage' + path.sep + '9c9c4ba3-bc1e-441f-9866-c1e9a806e31c' + path.sep + 'd6c5ee92.jpg']
expect(actual).toEqual(expect.arrayContaining(expected)) expect(actual).toEqual(expect.arrayContaining(expected))
}) })
@@ -225,8 +225,8 @@ it('should test that getAbsolutePathsOfAttachmentsInContent returns all absolute
' </body>\n' + ' </body>\n' +
'</html>' '</html>'
const actual = systemUnderTest.getAbsolutePathsOfAttachmentsInContent(testInput, dummyStoragePath) const actual = systemUnderTest.getAbsolutePathsOfAttachmentsInContent(testInput, dummyStoragePath)
const expected = [dummyStoragePath + path.sep + systemUnderTest.DESTINATION_FOLDER + path.sep + '9c9c4ba3-bc1e-441f-9866-c1e9a806e31c' + path.sep + '0.6r4zdgc22xp', const expected = [dummyStoragePath + path.sep + systemUnderTest.DESTINATION_FOLDER + path.sep + '9c9c4ba3-bc1e-441f-9866-c1e9a806e31c' + path.sep + '0.6r4zdgc22xp.png',
dummyStoragePath + path.sep + systemUnderTest.DESTINATION_FOLDER + path.sep + '9c9c4ba3-bc1e-441f-9866-c1e9a806e31c' + path.sep + '0.q2i4iw0fyx', dummyStoragePath + path.sep + systemUnderTest.DESTINATION_FOLDER + path.sep + '9c9c4ba3-bc1e-441f-9866-c1e9a806e31c' + path.sep + '0.q2i4iw0fyx.pdf',
dummyStoragePath + path.sep + systemUnderTest.DESTINATION_FOLDER + path.sep + '9c9c4ba3-bc1e-441f-9866-c1e9a806e31c' + path.sep + 'd6c5ee92.jpg'] dummyStoragePath + path.sep + systemUnderTest.DESTINATION_FOLDER + path.sep + '9c9c4ba3-bc1e-441f-9866-c1e9a806e31c' + path.sep + 'd6c5ee92.jpg']
expect(actual).toEqual(expect.arrayContaining(expected)) expect(actual).toEqual(expect.arrayContaining(expected))
}) })

View File

@@ -0,0 +1,38 @@
const test = require('ava')
const toggleStorage = require('browser/main/lib/dataApi/toggleStorage')
global.document = require('jsdom').jsdom('<body></body>')
global.window = document.defaultView
global.navigator = window.navigator
const Storage = require('dom-storage')
const localStorage = window.localStorage = global.localStorage = new Storage(null, { strict: true })
const path = require('path')
const _ = require('lodash')
const TestDummy = require('../fixtures/TestDummy')
const sander = require('sander')
const os = require('os')
const storagePath = path.join(os.tmpdir(), 'test/toggle-storage')
test.beforeEach((t) => {
t.context.storage = TestDummy.dummyStorage(storagePath)
localStorage.setItem('storages', JSON.stringify([t.context.storage.cache]))
})
test.serial('Toggle a storage location', (t) => {
const storageKey = t.context.storage.cache.key
return Promise.resolve()
.then(function doTest () {
return toggleStorage(storageKey, true)
})
.then(function assert (data) {
const cachedStorageList = JSON.parse(localStorage.getItem('storages'))
t.true(_.find(cachedStorageList, {key: storageKey}).isOpen === true)
})
})
test.after(function after () {
localStorage.clear()
sander.rimrafSync(storagePath)
})

View File

@@ -0,0 +1,16 @@
/**
* @fileoverview Unit test for browser/lib/normalizeEditorFontFamily
*/
import test from 'ava'
import normalizeEditorFontFamily from '../../browser/lib/normalizeEditorFontFamily'
import consts from '../../browser/lib/consts'
const defaultEditorFontFamily = consts.DEFAULT_EDITOR_FONT_FAMILY
test('normalizeEditorFontFamily() should return default font family (string[])', t => {
t.is(normalizeEditorFontFamily(), defaultEditorFontFamily.join(', '))
})
test('normalizeEditorFontFamily(["hoge", "huga"]) should return default font family connected with arg.', t => {
const arg = 'font1, font2'
t.is(normalizeEditorFontFamily(arg), `${arg}, ${defaultEditorFontFamily.join(', ')}`)
})

View File

@@ -28,16 +28,12 @@ var config = {
externals: [ externals: [
'node-ipc', 'node-ipc',
'electron', 'electron',
'md5',
'superagent',
'superagent-promise',
'lodash', 'lodash',
'markdown-it', 'markdown-it',
'moment', 'moment',
'markdown-it-emoji', 'markdown-it-emoji',
'fs-jetpack', 'fs-jetpack',
'@rokt33r/markdown-it-math', '@rokt33r/markdown-it-math',
'markdown-it-checkbox',
'markdown-it-kbd', 'markdown-it-kbd',
'markdown-it-plantuml', 'markdown-it-plantuml',
'markdown-it-admonition', 'markdown-it-admonition',

121
yarn.lock
View File

@@ -1574,10 +1574,6 @@ chalk@^2.0.0, chalk@^2.0.1, chalk@^2.3.0, chalk@^2.4.1:
escape-string-regexp "^1.0.5" escape-string-regexp "^1.0.5"
supports-color "^5.3.0" supports-color "^5.3.0"
charenc@~0.0.1:
version "0.0.2"
resolved "https://registry.yarnpkg.com/charenc/-/charenc-0.0.2.tgz#c0a1d2f3a7092e03774bfa83f14c0fc5790a8667"
chokidar@^1.0.0, chokidar@^1.4.2: chokidar@^1.0.0, chokidar@^1.4.2:
version "1.7.0" version "1.7.0"
resolved "https://registry.yarnpkg.com/chokidar/-/chokidar-1.7.0.tgz#798e689778151c8076b4b360e5edd28cda2bb468" resolved "https://registry.yarnpkg.com/chokidar/-/chokidar-1.7.0.tgz#798e689778151c8076b4b360e5edd28cda2bb468"
@@ -1731,10 +1727,14 @@ codemirror-mode-elixir@^1.1.1:
dependencies: dependencies:
codemirror "^5.20.2" codemirror "^5.20.2"
codemirror@^5.18.2, codemirror@^5.20.2, codemirror@^5.37.0: codemirror@^5.18.2, codemirror@^5.20.2:
version "5.38.0" version "5.38.0"
resolved "https://registry.yarnpkg.com/codemirror/-/codemirror-5.38.0.tgz#26a9551446e51dbdde36aabe60f72469724fd332" resolved "https://registry.yarnpkg.com/codemirror/-/codemirror-5.38.0.tgz#26a9551446e51dbdde36aabe60f72469724fd332"
codemirror@^5.39.0:
version "5.39.0"
resolved "https://registry.yarnpkg.com/codemirror/-/codemirror-5.39.0.tgz#4654f7d2f7e525e04a62e72d9482348ccb37dce5"
coffee-script@^1.10.0: coffee-script@^1.10.0:
version "1.12.7" version "1.12.7"
resolved "https://registry.yarnpkg.com/coffee-script/-/coffee-script-1.12.7.tgz#c05dae0cb79591d05b3070a8433a98c9a89ccc53" resolved "https://registry.yarnpkg.com/coffee-script/-/coffee-script-1.12.7.tgz#c05dae0cb79591d05b3070a8433a98c9a89ccc53"
@@ -1794,7 +1794,7 @@ colors@~1.1.2:
version "1.1.2" version "1.1.2"
resolved "https://registry.yarnpkg.com/colors/-/colors-1.1.2.tgz#168a4701756b6a7f51a12ce0c97bfa28c084ed63" resolved "https://registry.yarnpkg.com/colors/-/colors-1.1.2.tgz#168a4701756b6a7f51a12ce0c97bfa28c084ed63"
combined-stream@1.0.6, combined-stream@^1.0.5, combined-stream@~1.0.5: combined-stream@1.0.6, combined-stream@~1.0.5:
version "1.0.6" version "1.0.6"
resolved "https://registry.yarnpkg.com/combined-stream/-/combined-stream-1.0.6.tgz#723e7df6e801ac5613113a7e445a9b69cb632818" resolved "https://registry.yarnpkg.com/combined-stream/-/combined-stream-1.0.6.tgz#723e7df6e801ac5613113a7e445a9b69cb632818"
dependencies: dependencies:
@@ -1830,7 +1830,7 @@ compare-versions@^3.1.0:
version "3.2.1" version "3.2.1"
resolved "https://registry.yarnpkg.com/compare-versions/-/compare-versions-3.2.1.tgz#a49eb7689d4caaf0b6db5220173fd279614000f7" resolved "https://registry.yarnpkg.com/compare-versions/-/compare-versions-3.2.1.tgz#a49eb7689d4caaf0b6db5220173fd279614000f7"
component-emitter@^1.2.1, component-emitter@~1.2.0: component-emitter@^1.2.1:
version "1.2.1" version "1.2.1"
resolved "https://registry.yarnpkg.com/component-emitter/-/component-emitter-1.2.1.tgz#137918d6d78283f7df7a6b7c5a63e140e69425e6" resolved "https://registry.yarnpkg.com/component-emitter/-/component-emitter-1.2.1.tgz#137918d6d78283f7df7a6b7c5a63e140e69425e6"
@@ -1960,10 +1960,6 @@ cookie@0.3.1:
version "0.3.1" version "0.3.1"
resolved "https://registry.yarnpkg.com/cookie/-/cookie-0.3.1.tgz#e7e0a1f9ef43b4c8ba925c5c5a96e806d16873bb" resolved "https://registry.yarnpkg.com/cookie/-/cookie-0.3.1.tgz#e7e0a1f9ef43b4c8ba925c5c5a96e806d16873bb"
cookiejar@2.0.6:
version "2.0.6"
resolved "https://registry.yarnpkg.com/cookiejar/-/cookiejar-2.0.6.tgz#0abf356ad00d1c5a219d88d44518046dd026acfe"
copy-descriptor@^0.1.0: copy-descriptor@^0.1.0:
version "0.1.1" version "0.1.1"
resolved "https://registry.yarnpkg.com/copy-descriptor/-/copy-descriptor-0.1.1.tgz#676f6eb3c39997c2ee1ac3a924fd6124748f578d" resolved "https://registry.yarnpkg.com/copy-descriptor/-/copy-descriptor-0.1.1.tgz#676f6eb3c39997c2ee1ac3a924fd6124748f578d"
@@ -2015,10 +2011,6 @@ cross-spawn@^5.0.1:
shebang-command "^1.2.0" shebang-command "^1.2.0"
which "^1.2.9" which "^1.2.9"
crypt@~0.0.1:
version "0.0.2"
resolved "https://registry.yarnpkg.com/crypt/-/crypt-0.0.2.tgz#88d7ff7ec0dfb86f713dc87bbb42d044d3e6c41b"
cryptiles@2.x.x: cryptiles@2.x.x:
version "2.0.5" version "2.0.5"
resolved "https://registry.yarnpkg.com/cryptiles/-/cryptiles-2.0.5.tgz#3bdfecdc608147c1c67202fa291e7dca59eaa3b8" resolved "https://registry.yarnpkg.com/cryptiles/-/cryptiles-2.0.5.tgz#3bdfecdc608147c1c67202fa291e7dca59eaa3b8"
@@ -2206,7 +2198,7 @@ debug@*, debug@^3.0.1, debug@^3.1.0:
dependencies: dependencies:
ms "2.0.0" ms "2.0.0"
debug@2, debug@2.6.9, debug@^2.1.1, debug@^2.1.2, debug@^2.1.3, debug@^2.2.0, debug@^2.3.3, debug@^2.6.6, debug@^2.6.8, debug@^2.6.9: debug@2.6.9, debug@^2.1.1, debug@^2.1.2, debug@^2.1.3, debug@^2.2.0, debug@^2.3.3, debug@^2.6.6, debug@^2.6.8, debug@^2.6.9:
version "2.6.9" version "2.6.9"
resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.9.tgz#5d128515df134ff327e90a4c93f4e077a536341f" resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.9.tgz#5d128515df134ff327e90a4c93f4e077a536341f"
dependencies: dependencies:
@@ -2577,9 +2569,9 @@ electron-winstaller@^2.2.0:
lodash.template "^4.2.2" lodash.template "^4.2.2"
temp "^0.8.3" temp "^0.8.3"
electron@2.0.2: electron@2.0.3:
version "2.0.2" version "2.0.3"
resolved "https://registry.yarnpkg.com/electron/-/electron-2.0.2.tgz#b77e05f83419cc5ec921a2d21f35b55e4bfc3d68" resolved "https://registry.yarnpkg.com/electron/-/electron-2.0.3.tgz#8e591e820cae2ccdb0c3fd74c6d07834913fc133"
dependencies: dependencies:
"@types/node" "^8.0.24" "@types/node" "^8.0.24"
electron-download "^3.0.1" electron-download "^3.0.1"
@@ -3082,10 +3074,6 @@ extend-shallow@^3.0.0, extend-shallow@^3.0.2:
assign-symbols "^1.0.0" assign-symbols "^1.0.0"
is-extendable "^1.0.1" is-extendable "^1.0.1"
extend@3.0.0:
version "3.0.0"
resolved "https://registry.yarnpkg.com/extend/-/extend-3.0.0.tgz#5a474353b9f3353ddd8176dfd37b91c83a46f1d4"
extend@~3.0.1: extend@~3.0.1:
version "3.0.1" version "3.0.1"
resolved "https://registry.yarnpkg.com/extend/-/extend-3.0.1.tgz#a755ea7bc1adfcc5a31ce7e762dbaadc5e636444" resolved "https://registry.yarnpkg.com/extend/-/extend-3.0.1.tgz#a755ea7bc1adfcc5a31ce7e762dbaadc5e636444"
@@ -3206,6 +3194,10 @@ file-entry-cache@^2.0.0:
flat-cache "^1.2.1" flat-cache "^1.2.1"
object-assign "^4.0.1" object-assign "^4.0.1"
file-url@^2.0.2:
version "2.0.2"
resolved "https://registry.yarnpkg.com/file-url/-/file-url-2.0.2.tgz#e951784d79095127d3713029ab063f40818ca2ae"
filename-regex@^2.0.0: filename-regex@^2.0.0:
version "2.0.1" version "2.0.1"
resolved "https://registry.yarnpkg.com/filename-regex/-/filename-regex-2.0.1.tgz#c1c4b9bee3e09725ddb106b75c1e301fe2f18b26" resolved "https://registry.yarnpkg.com/filename-regex/-/filename-regex-2.0.1.tgz#c1c4b9bee3e09725ddb106b75c1e301fe2f18b26"
@@ -3351,14 +3343,6 @@ forever-agent@~0.6.0, forever-agent@~0.6.1:
version "0.6.1" version "0.6.1"
resolved "https://registry.yarnpkg.com/forever-agent/-/forever-agent-0.6.1.tgz#fbc71f0c41adeb37f96c577ad1ed42d8fdacca91" resolved "https://registry.yarnpkg.com/forever-agent/-/forever-agent-0.6.1.tgz#fbc71f0c41adeb37f96c577ad1ed42d8fdacca91"
form-data@1.0.0-rc3:
version "1.0.0-rc3"
resolved "https://registry.yarnpkg.com/form-data/-/form-data-1.0.0-rc3.tgz#d35bc62e7fbc2937ae78f948aaa0d38d90607577"
dependencies:
async "^1.4.0"
combined-stream "^1.0.5"
mime-types "^2.1.3"
form-data@~0.2.0: form-data@~0.2.0:
version "0.2.0" version "0.2.0"
resolved "https://registry.yarnpkg.com/form-data/-/form-data-0.2.0.tgz#26f8bc26da6440e299cbdcfb69035c4f77a6e466" resolved "https://registry.yarnpkg.com/form-data/-/form-data-0.2.0.tgz#26f8bc26da6440e299cbdcfb69035c4f77a6e466"
@@ -3375,10 +3359,6 @@ form-data@~2.3.1:
combined-stream "1.0.6" combined-stream "1.0.6"
mime-types "^2.1.12" mime-types "^2.1.12"
formidable@~1.0.14:
version "1.0.17"
resolved "https://registry.yarnpkg.com/formidable/-/formidable-1.0.17.tgz#ef5491490f9433b705faa77249c99029ae348559"
forwarded@~0.1.2: forwarded@~0.1.2:
version "0.1.2" version "0.1.2"
resolved "https://registry.yarnpkg.com/forwarded/-/forwarded-0.1.2.tgz#98c23dab1175657b8c0573e8ceccd91b0ff18c84" resolved "https://registry.yarnpkg.com/forwarded/-/forwarded-0.1.2.tgz#98c23dab1175657b8c0573e8ceccd91b0ff18c84"
@@ -4236,7 +4216,7 @@ is-binary-path@^1.0.0:
dependencies: dependencies:
binary-extensions "^1.0.0" binary-extensions "^1.0.0"
is-buffer@^1.1.5, is-buffer@~1.1.1: is-buffer@^1.1.5:
version "1.1.6" version "1.1.6"
resolved "https://registry.yarnpkg.com/is-buffer/-/is-buffer-1.1.6.tgz#efaa2ea9daa0d7ab2ea13a97b2b8ad51fefbe8be" resolved "https://registry.yarnpkg.com/is-buffer/-/is-buffer-1.1.6.tgz#efaa2ea9daa0d7ab2ea13a97b2b8ad51fefbe8be"
@@ -5392,12 +5372,6 @@ map-visit@^1.0.0:
version "1.0.2" version "1.0.2"
resolved "https://github.com/johannbre/markdown-it-admonition.git#e0c0fcd59e9119d6d60ed209aa3d0f1177ec0166" resolved "https://github.com/johannbre/markdown-it-admonition.git#e0c0fcd59e9119d6d60ed209aa3d0f1177ec0166"
markdown-it-checkbox@^1.1.0:
version "1.1.0"
resolved "https://registry.yarnpkg.com/markdown-it-checkbox/-/markdown-it-checkbox-1.1.0.tgz#20cff97f33d77d172f9dcf1bcfc92cecc5330fac"
dependencies:
underscore "^1.8.2"
markdown-it-emoji@^1.1.1: markdown-it-emoji@^1.1.1:
version "1.4.0" version "1.4.0"
resolved "https://registry.yarnpkg.com/markdown-it-emoji/-/markdown-it-emoji-1.4.0.tgz#9bee0e9a990a963ba96df6980c4fddb05dfb4dcc" resolved "https://registry.yarnpkg.com/markdown-it-emoji/-/markdown-it-emoji-1.4.0.tgz#9bee0e9a990a963ba96df6980c4fddb05dfb4dcc"
@@ -5426,9 +5400,9 @@ markdown-it-named-headers@^0.0.4:
dependencies: dependencies:
string "^3.0.1" string "^3.0.1"
markdown-it-plantuml@^0.3.0: markdown-it-plantuml@^1.1.0:
version "0.3.2" version "1.1.0"
resolved "https://registry.yarnpkg.com/markdown-it-plantuml/-/markdown-it-plantuml-0.3.2.tgz#f93a49bdfc8417b0df3c88700445f53487e57356" resolved "https://registry.yarnpkg.com/markdown-it-plantuml/-/markdown-it-plantuml-1.1.0.tgz#9ab8bfa09a02d80845e16e60f87a488edb50fdde"
markdown-it-smartarrows@^1.0.1: markdown-it-smartarrows@^1.0.1:
version "1.0.1" version "1.0.1"
@@ -5492,14 +5466,6 @@ md5-o-matic@^0.1.1:
version "0.1.1" version "0.1.1"
resolved "https://registry.yarnpkg.com/md5-o-matic/-/md5-o-matic-0.1.1.tgz#822bccd65e117c514fab176b25945d54100a03c3" resolved "https://registry.yarnpkg.com/md5-o-matic/-/md5-o-matic-0.1.1.tgz#822bccd65e117c514fab176b25945d54100a03c3"
md5@^2.0.0:
version "2.2.1"
resolved "https://registry.yarnpkg.com/md5/-/md5-2.2.1.tgz#53ab38d5fe3c8891ba465329ea23fac0540126f9"
dependencies:
charenc "~0.0.1"
crypt "~0.0.1"
is-buffer "~1.1.1"
mdurl@^1.0.1, mdurl@~1.0.1: mdurl@^1.0.1, mdurl@~1.0.1:
version "1.0.1" version "1.0.1"
resolved "https://registry.yarnpkg.com/mdurl/-/mdurl-1.0.1.tgz#fe85b2ec75a59037f2adfec100fd6c601761152e" resolved "https://registry.yarnpkg.com/mdurl/-/mdurl-1.0.1.tgz#fe85b2ec75a59037f2adfec100fd6c601761152e"
@@ -5561,7 +5527,7 @@ merge@^1.1.3:
version "1.2.0" version "1.2.0"
resolved "https://registry.yarnpkg.com/merge/-/merge-1.2.0.tgz#7531e39d4949c281a66b8c5a6e0265e8b05894da" resolved "https://registry.yarnpkg.com/merge/-/merge-1.2.0.tgz#7531e39d4949c281a66b8c5a6e0265e8b05894da"
methods@~1.1.1, methods@~1.1.2: methods@~1.1.2:
version "1.1.2" version "1.1.2"
resolved "https://registry.yarnpkg.com/methods/-/methods-1.1.2.tgz#5529a4d67654134edcc5266656835b0f851afcee" resolved "https://registry.yarnpkg.com/methods/-/methods-1.1.2.tgz#5529a4d67654134edcc5266656835b0f851afcee"
@@ -5609,7 +5575,7 @@ mime-db@~1.12.0:
version "1.12.0" version "1.12.0"
resolved "https://registry.yarnpkg.com/mime-db/-/mime-db-1.12.0.tgz#3d0c63180f458eb10d325aaa37d7c58ae312e9d7" resolved "https://registry.yarnpkg.com/mime-db/-/mime-db-1.12.0.tgz#3d0c63180f458eb10d325aaa37d7c58ae312e9d7"
mime-types@^2.1.12, mime-types@^2.1.3, mime-types@~2.1.17, mime-types@~2.1.18: mime-types@^2.1.12, mime-types@~2.1.17, mime-types@~2.1.18:
version "2.1.18" version "2.1.18"
resolved "https://registry.yarnpkg.com/mime-types/-/mime-types-2.1.18.tgz#6f323f60a83d11146f831ff11fd66e2fe5503bb8" resolved "https://registry.yarnpkg.com/mime-types/-/mime-types-2.1.18.tgz#6f323f60a83d11146f831ff11fd66e2fe5503bb8"
dependencies: dependencies:
@@ -5621,10 +5587,6 @@ mime-types@~2.0.1, mime-types@~2.0.3:
dependencies: dependencies:
mime-db "~1.12.0" mime-db "~1.12.0"
mime@1.3.4:
version "1.3.4"
resolved "https://registry.yarnpkg.com/mime/-/mime-1.3.4.tgz#115f9e3b6b3daf2959983cb38f149a2d40eb5d53"
mime@1.4.1: mime@1.4.1:
version "1.4.1" version "1.4.1"
resolved "https://registry.yarnpkg.com/mime/-/mime-1.4.1.tgz#121f9ebc49e3766f311a76e1fa1c8003c4b03aa6" resolved "https://registry.yarnpkg.com/mime/-/mime-1.4.1.tgz#121f9ebc49e3766f311a76e1fa1c8003c4b03aa6"
@@ -6779,10 +6741,6 @@ q@^1.1.2:
version "1.5.1" version "1.5.1"
resolved "https://registry.yarnpkg.com/q/-/q-1.5.1.tgz#7e32f75b41381291d04611f1bf14109ac00651d7" resolved "https://registry.yarnpkg.com/q/-/q-1.5.1.tgz#7e32f75b41381291d04611f1bf14109ac00651d7"
qs@2.3.3:
version "2.3.3"
resolved "https://registry.yarnpkg.com/qs/-/qs-2.3.3.tgz#e9e85adbe75da0bbe4c8e0476a086290f863b404"
qs@6.5.1: qs@6.5.1:
version "6.5.1" version "6.5.1"
resolved "https://registry.yarnpkg.com/qs/-/qs-6.5.1.tgz#349cdf6eef89ec45c12d7d5eb3fc0c870343a6d8" resolved "https://registry.yarnpkg.com/qs/-/qs-6.5.1.tgz#349cdf6eef89ec45c12d7d5eb3fc0c870343a6d8"
@@ -7030,15 +6988,6 @@ read-pkg@^2.0.0:
normalize-package-data "^2.3.2" normalize-package-data "^2.3.2"
path-type "^2.0.0" path-type "^2.0.0"
readable-stream@1.0.27-1:
version "1.0.27-1"
resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-1.0.27-1.tgz#6b67983c20357cefd07f0165001a16d710d91078"
dependencies:
core-util-is "~1.0.0"
inherits "~2.0.1"
isarray "0.0.1"
string_decoder "~0.10.x"
readable-stream@^1.1.8, readable-stream@~1.1.9: readable-stream@^1.1.8, readable-stream@~1.1.9:
version "1.1.14" version "1.1.14"
resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-1.1.14.tgz#7cf4c54ef648e3813084c636dd2079e166c081d9" resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-1.1.14.tgz#7cf4c54ef648e3813084c636dd2079e166c081d9"
@@ -7114,10 +7063,6 @@ redent@^1.0.0:
indent-string "^2.1.0" indent-string "^2.1.0"
strip-indent "^1.0.1" strip-indent "^1.0.1"
reduce-component@1.0.1:
version "1.0.1"
resolved "https://registry.yarnpkg.com/reduce-component/-/reduce-component-1.0.1.tgz#e0c93542c574521bea13df0f9488ed82ab77c5da"
reduce-css-calc@^1.2.6: reduce-css-calc@^1.2.6:
version "1.3.0" version "1.3.0"
resolved "https://registry.yarnpkg.com/reduce-css-calc/-/reduce-css-calc-1.3.0.tgz#747c914e049614a4c9cfbba629871ad1d2927716" resolved "https://registry.yarnpkg.com/reduce-css-calc/-/reduce-css-calc-1.3.0.tgz#747c914e049614a4c9cfbba629871ad1d2927716"
@@ -8043,26 +7988,6 @@ sumchecker@^1.2.0:
debug "^2.2.0" debug "^2.2.0"
es6-promise "^4.0.5" es6-promise "^4.0.5"
superagent-promise@^1.0.3:
version "1.1.0"
resolved "https://registry.yarnpkg.com/superagent-promise/-/superagent-promise-1.1.0.tgz#baf22d8bbdd439a9b07dd10f8c08f54fe2503533"
superagent@^1.2.0:
version "1.8.5"
resolved "https://registry.yarnpkg.com/superagent/-/superagent-1.8.5.tgz#1c0ddc3af30e80eb84ebc05cb2122da8fe940b55"
dependencies:
component-emitter "~1.2.0"
cookiejar "2.0.6"
debug "2"
extend "3.0.0"
form-data "1.0.0-rc3"
formidable "~1.0.14"
methods "~1.1.1"
mime "1.3.4"
qs "2.3.3"
readable-stream "1.0.27-1"
reduce-component "1.0.1"
supertap@^1.0.0: supertap@^1.0.0:
version "1.0.0" version "1.0.0"
resolved "https://registry.yarnpkg.com/supertap/-/supertap-1.0.0.tgz#bd9751c7fafd68c68cf8222a29892206a119fa9e" resolved "https://registry.yarnpkg.com/supertap/-/supertap-1.0.0.tgz#bd9751c7fafd68c68cf8222a29892206a119fa9e"
@@ -8406,10 +8331,6 @@ underscore.string@~2.4.0:
version "2.4.0" version "2.4.0"
resolved "https://registry.yarnpkg.com/underscore.string/-/underscore.string-2.4.0.tgz#8cdd8fbac4e2d2ea1e7e2e8097c42f442280f85b" resolved "https://registry.yarnpkg.com/underscore.string/-/underscore.string-2.4.0.tgz#8cdd8fbac4e2d2ea1e7e2e8097c42f442280f85b"
underscore@^1.8.2:
version "1.9.0"
resolved "https://registry.yarnpkg.com/underscore/-/underscore-1.9.0.tgz#31dbb314cfcc88f169cd3692d9149d81a00a73e4"
underscore@~1.4.x: underscore@~1.4.x:
version "1.4.4" version "1.4.4"
resolved "https://registry.yarnpkg.com/underscore/-/underscore-1.4.4.tgz#61a6a32010622afa07963bf325203cf12239d604" resolved "https://registry.yarnpkg.com/underscore/-/underscore-1.4.4.tgz#61a6a32010622afa07963bf325203cf12239d604"