Merge branch 'master' into jori/cache

This commit is contained in:
Jori Lallo
2017-07-16 19:49:50 -07:00
committed by GitHub
10 changed files with 84 additions and 111 deletions

View File

@ -204,8 +204,10 @@ type KeyData = {
onSave={this.props.onSave} onSave={this.props.onSave}
readOnly={this.props.readOnly} readOnly={this.props.readOnly}
/> />
{!this.props.readOnly && <ClickablePadding
<ClickablePadding onClick={this.focusAtEnd} grow />} onClick={!this.props.readOnly ? this.focusAtEnd : undefined}
grow
/>
</MaxWidth> </MaxWidth>
</Flex> </Flex>
); );
@ -225,6 +227,7 @@ const HeaderContainer = styled(Flex).attrs({
align: 'flex-end', align: 'flex-end',
})` })`
height: 100px; height: 100px;
flex-shrink: 0;
${({ readOnly }) => !readOnly && 'cursor: text;'} ${({ readOnly }) => !readOnly && 'cursor: text;'}
`; `;

View File

@ -1,20 +1,22 @@
// @flow // @flow
import React from 'react'; import React from 'react';
import classnames from 'classnames'; import styled from 'styled-components';
import styles from './ClickablePadding.scss';
type Props = { type Props = {
onClick: Function, onClick?: ?Function,
grow?: boolean, grow?: boolean,
}; };
const ClickablePadding = (props: Props) => { const ClickablePadding = (props: Props) => {
return ( return <Container grow={props.grow} onClick={props.onClick} />;
<div
className={classnames(styles.container, { [styles.grow]: props.grow })}
onClick={props.onClick}
/>
);
}; };
const Container = styled.div`
min-height: 150px;
padding-top: 50px;
cursor: ${({ onClick }) => (onClick ? 'text' : 'default')};
${({ grow }) => grow && `flex-grow: 1;`}
`;
export default ClickablePadding; export default ClickablePadding;

View File

@ -1,15 +0,0 @@
.container {
min-height: 150px;
padding-top: 50px;
cursor: text;
}
.grow {
flex-grow: 1;
}
@media all and (max-width: 960px) {
.container {
padding-top: 50px;
}
}

View File

@ -14,11 +14,12 @@ import { documentEditUrl, homeUrl, searchUrl } from 'utils/routeHelpers';
import { DropdownMenu, DropdownMenuItem } from 'components/DropdownMenu'; import { DropdownMenu, DropdownMenuItem } from 'components/DropdownMenu';
import { LoadingIndicatorBar } from 'components/LoadingIndicator'; import { LoadingIndicatorBar } from 'components/LoadingIndicator';
import Scrollable from 'components/Scrollable'; import Scrollable from 'components/Scrollable';
import KeyboardShortcuts from 'components/KeyboardShortcuts';
import Avatar from 'components/Avatar'; import Avatar from 'components/Avatar';
import Modal from 'components/Modal'; import Modal from 'components/Modal';
import AddIcon from 'components/Icon/AddIcon'; import AddIcon from 'components/Icon/AddIcon';
import CollectionNew from 'scenes/CollectionNew'; import CollectionNew from 'scenes/CollectionNew';
import KeyboardShortcuts from 'scenes/KeyboardShortcuts';
import Settings from 'scenes/Settings';
import SidebarCollection from './components/SidebarCollection'; import SidebarCollection from './components/SidebarCollection';
import SidebarCollectionList from './components/SidebarCollectionList'; import SidebarCollectionList from './components/SidebarCollectionList';
@ -78,6 +79,10 @@ type Props = {
this.modal = 'keyboard-shortcuts'; this.modal = 'keyboard-shortcuts';
} }
handleOpenSettings = () => {
this.modal = 'settings';
};
handleCreateCollection = () => { handleCreateCollection = () => {
this.modal = 'create-collection'; this.modal = 'create-collection';
}; };
@ -114,9 +119,9 @@ type Props = {
<LogoLink to="/">Atlas</LogoLink> <LogoLink to="/">Atlas</LogoLink>
</Flex> </Flex>
<DropdownMenu label={<Avatar src={user.user.avatarUrl} />}> <DropdownMenu label={<Avatar src={user.user.avatarUrl} />}>
<MenuLink to="/settings"> <DropdownMenuItem onClick={this.handleOpenSettings}>
<DropdownMenuItem>Settings</DropdownMenuItem> Settings
</MenuLink> </DropdownMenuItem>
<DropdownMenuItem onClick={this.handleOpenKeyboardShortcuts}> <DropdownMenuItem onClick={this.handleOpenKeyboardShortcuts}>
Keyboard shortcuts Keyboard shortcuts
</DropdownMenuItem> </DropdownMenuItem>
@ -176,6 +181,13 @@ type Props = {
> >
<KeyboardShortcuts /> <KeyboardShortcuts />
</Modal> </Modal>
<Modal
isOpen={this.modal === 'settings'}
onRequestClose={this.handleCloseModal}
title="Settings"
>
<Settings />
</Modal>
</Container> </Container>
); );
} }

View File

@ -28,7 +28,6 @@ import Starred from 'scenes/Starred';
import Collection from 'scenes/Collection'; import Collection from 'scenes/Collection';
import Document from 'scenes/Document'; import Document from 'scenes/Document';
import Search from 'scenes/Search'; import Search from 'scenes/Search';
import Settings from 'scenes/Settings';
import SlackAuth from 'scenes/SlackAuth'; import SlackAuth from 'scenes/SlackAuth';
import Flatpage from 'scenes/Flatpage'; import Flatpage from 'scenes/Flatpage';
import ErrorAuth from 'scenes/ErrorAuth'; import ErrorAuth from 'scenes/ErrorAuth';
@ -126,7 +125,7 @@ render(
<Route exact path="/search" component={Search} /> <Route exact path="/search" component={Search} />
<Route exact path="/search/:query" component={Search} /> <Route exact path="/search/:query" component={Search} />
<Route exact path="/settings" component={Settings} /> <Route exact path="/developers" component={Api} />
<Route path="/404" component={Error404} /> <Route path="/404" component={Error404} />
@ -140,9 +139,6 @@ render(
path="/collections/:id/new" path="/collections/:id/new"
component={DocumentNew} component={DocumentNew}
/> />
<Route exact path="/developers" component={Api} />
<Route component={notFoundSearch} /> <Route component={notFoundSearch} />
</Switch> </Switch>
</Layout> </Layout>

View File

@ -1,17 +1,17 @@
// @flow // @flow
import React from 'react'; import React from 'react';
import { observer } from 'mobx-react'; import { observer } from 'mobx-react';
import Flex from 'components/Flex'; import { Link } from 'react-router-dom';
import styled from 'styled-components';
import ApiKeyRow from './components/ApiKeyRow'; import ApiKeyRow from './components/ApiKeyRow';
import styles from './Settings.scss';
import SettingsStore from './SettingsStore'; import SettingsStore from './SettingsStore';
import { color } from 'styles/constants';
import Flex from 'components/Flex';
import Button from 'components/Button'; import Button from 'components/Button';
import Input from 'components/Input'; import Input from 'components/Input';
import CenteredContent from 'components/CenteredContent'; import HelpText from 'components/HelpText';
import SlackAuthLink from 'components/SlackAuthLink'; import SlackAuthLink from 'components/SlackAuthLink';
import PageTitle from 'components/PageTitle';
@observer class Settings extends React.Component { @observer class Settings extends React.Component {
store: SettingsStore; store: SettingsStore;
@ -25,15 +25,14 @@ import PageTitle from 'components/PageTitle';
const showSlackSettings = DEPLOYMENT === 'hosted'; const showSlackSettings = DEPLOYMENT === 'hosted';
return ( return (
<CenteredContent> <Flex column>
<PageTitle title="Settings" />
{showSlackSettings && {showSlackSettings &&
<div className={styles.section}> <Section>
<h2 className={styles.sectionHeader}>Slack</h2> <h2>Slack</h2>
<p> <HelpText>
Connect Atlas to your Slack to instantly search for your documents Connect Atlas to your Slack to instantly search for your documents
using <code>/atlas</code> command. using <code>/atlas</code> command.
</p> </HelpText>
<SlackAuthLink <SlackAuthLink
scopes={['commands']} scopes={['commands']}
@ -47,17 +46,17 @@ import PageTitle from 'components/PageTitle';
srcSet="https://platform.slack-edge.com/img/add_to_slack.png 1x, https://platform.slack-edge.com/img/add_to_slack@2x.png 2x" srcSet="https://platform.slack-edge.com/img/add_to_slack.png 1x, https://platform.slack-edge.com/img/add_to_slack@2x.png 2x"
/> />
</SlackAuthLink> </SlackAuthLink>
</div>} </Section>}
<div className={styles.section}> <Section>
<h2 className={styles.sectionHeader}>API access</h2> <h2>API access</h2>
<p> <HelpText>
Create API tokens to hack on your Atlas. Create API tokens to hack on your Atlas.
Learn more in <a href>API documentation</a>. Learn more in <Link to="/developers">API documentation</Link>.
</p> </HelpText>
{this.store.apiKeys && {this.store.apiKeys &&
<table className={styles.apiKeyTable}> <Table>
<tbody> <tbody>
{this.store.apiKeys && {this.store.apiKeys &&
this.store.apiKeys.map(key => ( this.store.apiKeys.map(key => (
@ -70,9 +69,7 @@ import PageTitle from 'components/PageTitle';
/> />
))} ))}
</tbody> </tbody>
</table>} </Table>}
<div>
<InlineForm <InlineForm
placeholder="Token name" placeholder="Token name"
buttonLabel="Create token" buttonLabel="Create token"
@ -82,9 +79,8 @@ import PageTitle from 'components/PageTitle';
onSubmit={this.store.createApiKey} onSubmit={this.store.createApiKey}
disabled={this.store.isFetching} disabled={this.store.isFetching}
/> />
</div> </Section>
</div> </Flex>
</CenteredContent>
); );
} }
} }
@ -148,4 +144,18 @@ class InlineForm extends React.Component {
} }
} }
const Section = styled.div`
margin-bottom: 40px;
`;
const Table = styled.table`
margin-bottom: 20px;
width: 100%;
td {
margin-right: 20px;
color: ${color.slate};
}
`;
export default Settings; export default Settings;

View File

@ -1,19 +0,0 @@
@import '~styles/constants.scss';
.section {
margin-bottom: 40px;
}
.sectionHeader {
border-bottom: 1px solid #eee;
}
.apiKeyTable {
margin-bottom: 20px;
width: 100%;
td {
margin-right: 20px;
color: #969696;
}
}

View File

@ -9,9 +9,9 @@
"build": "npm run clean && npm run build:webpack", "build": "npm run clean && npm run build:webpack",
"start": "node index.js", "start": "node index.js",
"dev": "NODE_ENV=development DEBUG=sql,cache,presenters ./node_modules/.bin/nodemon --watch server index.js", "dev": "NODE_ENV=development DEBUG=sql,cache,presenters ./node_modules/.bin/nodemon --watch server index.js",
"lint": "npm run lint:js && npm run lint:flow", "lint": "npm run lint:flow && npm run lint:js",
"lint:js": "eslint frontend", "lint:js": "eslint frontend",
"lint:flow": "flow check", "lint:flow": "flow",
"deploy": "git push heroku master", "deploy": "git push heroku master",
"heroku-postbuild": "npm run build && npm run sequelize:migrate", "heroku-postbuild": "npm run build && npm run sequelize:migrate",
"sequelize:create-migration": "sequelize migration:create", "sequelize:create-migration": "sequelize migration:create",
@ -22,35 +22,19 @@
"precommit": "lint-staged" "precommit": "lint-staged"
}, },
"lint-staged": { "lint-staged": {
"*.js": [ "*.js": ["eslint --fix", "git add"]
"eslint --fix",
"git add"
]
}, },
"jest": { "jest": {
"verbose": false, "verbose": false,
"roots": [ "roots": ["frontend"],
"frontend"
],
"moduleNameMapper": { "moduleNameMapper": {
"^.*[.](s?css|css)$": "<rootDir>/__mocks__/styleMock.js", "^.*[.](s?css|css)$": "<rootDir>/__mocks__/styleMock.js",
"^.*[.](gif|ttf|eot|svg)$": "<rootDir>/__test__/fileMock.js" "^.*[.](gif|ttf|eot|svg)$": "<rootDir>/__test__/fileMock.js"
}, },
"moduleFileExtensions": [ "moduleFileExtensions": ["js", "jsx", "json"],
"js", "moduleDirectories": ["node_modules"],
"jsx", "modulePaths": ["frontend"],
"json" "setupFiles": ["<rootDir>/setupJest.js", "<rootDir>/__mocks__/window.js"]
],
"moduleDirectories": [
"node_modules"
],
"modulePaths": [
"frontend"
],
"setupFiles": [
"<rootDir>/setupJest.js",
"<rootDir>/__mocks__/window.js"
]
}, },
"engines": { "engines": {
"node": ">= 7.6" "node": ">= 7.6"