mirror of
https://github.com/naturalcrit/homebrewery.git
synced 2026-01-03 17:02:40 +00:00
Initial Commit. All seems to be working...?
EditPage.jsx and GoogleActions.js need to be cleaned up and shortened...
This commit is contained in:
BIN
client/homebrew/googleDrive.png
Normal file
BIN
client/homebrew/googleDrive.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 305 KiB |
BIN
client/homebrew/googleDriveMono.png
Normal file
BIN
client/homebrew/googleDriveMono.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 17 KiB |
@@ -2,17 +2,33 @@ const React = require('react');
|
||||
const createClass = require('create-react-class');
|
||||
const Nav = require('naturalcrit/nav/nav.jsx');
|
||||
|
||||
module.exports = function(props){
|
||||
if(global.account){
|
||||
return <Nav.item href={`/user/${global.account.username}`} color='yellow' icon='fa-user'>
|
||||
{global.account.username}
|
||||
const Account = createClass({
|
||||
|
||||
getInitialState : function() {
|
||||
return {
|
||||
url : ''
|
||||
};
|
||||
},
|
||||
|
||||
componentDidMount : function(){
|
||||
if(typeof window !== 'undefined'){
|
||||
this.setState({
|
||||
url : window.location.href
|
||||
});
|
||||
}
|
||||
},
|
||||
|
||||
render : function(){
|
||||
if(global.account){
|
||||
return <Nav.item href={`/user/${global.account.username}`} color='yellow' icon='fa-user'>
|
||||
{global.account.username}
|
||||
</Nav.item>;
|
||||
}
|
||||
|
||||
return <Nav.item href={`http://naturalcrit.com/login?redirect=${this.state.url}`} color='teal' icon='fa-sign-in'>
|
||||
login
|
||||
</Nav.item>;
|
||||
}
|
||||
let url = '';
|
||||
if(typeof window !== 'undefined'){
|
||||
url = window.location.href;
|
||||
}
|
||||
return <Nav.item href={`http://naturalcrit.com/login?redirect=${url}`} color='teal' icon='fa-sign-in'>
|
||||
login
|
||||
</Nav.item>;
|
||||
};
|
||||
});
|
||||
|
||||
module.exports = Account;
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
/* eslint-disable max-lines */
|
||||
require('./editPage.less');
|
||||
const React = require('react');
|
||||
const createClass = require('create-react-class');
|
||||
@@ -20,8 +21,10 @@ const BrewRenderer = require('../../brewRenderer/brewRenderer.jsx');
|
||||
|
||||
const Markdown = require('naturalcrit/markdown.js');
|
||||
|
||||
const SAVE_TIMEOUT = 3000;
|
||||
const googleDriveActive = require('../../googleDrive.png');
|
||||
const googleDriveInactive = require('../../googleDriveMono.png');
|
||||
|
||||
const SAVE_TIMEOUT = 3000;
|
||||
|
||||
const EditPage = createClass({
|
||||
getDefaultProps : function() {
|
||||
@@ -32,6 +35,7 @@ const EditPage = createClass({
|
||||
editId : null,
|
||||
createdAt : null,
|
||||
updatedAt : null,
|
||||
gDrive : false,
|
||||
|
||||
title : '',
|
||||
description : '',
|
||||
@@ -49,13 +53,19 @@ const EditPage = createClass({
|
||||
|
||||
isSaving : false,
|
||||
isPending : false,
|
||||
saveGoogle : this.props.brew.googleId ? true : false,
|
||||
errors : null,
|
||||
htmlErrors : Markdown.validate(this.props.brew.text),
|
||||
url : ''
|
||||
};
|
||||
},
|
||||
savedBrew : null,
|
||||
|
||||
componentDidMount : function(){
|
||||
this.setState({
|
||||
url : window.location.href
|
||||
});
|
||||
|
||||
this.trySave();
|
||||
window.onbeforeunload = ()=>{
|
||||
if(this.state.isSaving || this.state.isPending){
|
||||
@@ -74,7 +84,6 @@ const EditPage = createClass({
|
||||
document.removeEventListener('keydown', this.handleControlKeys);
|
||||
},
|
||||
|
||||
|
||||
handleControlKeys : function(e){
|
||||
if(!(e.ctrlKey || e.metaKey)) return;
|
||||
const S_KEY = 83;
|
||||
@@ -126,7 +135,13 @@ const EditPage = createClass({
|
||||
}
|
||||
},
|
||||
|
||||
save : function(){
|
||||
toggleGoogleStorage : function(){
|
||||
this.setState((prevState)=>({
|
||||
saveGoogle : !prevState.saveGoogle
|
||||
}));
|
||||
},
|
||||
|
||||
save : async function(){
|
||||
if(this.debounceSave && this.debounceSave.cancel) this.debounceSave.cancel();
|
||||
|
||||
this.setState((prevState)=>({
|
||||
@@ -135,22 +150,104 @@ const EditPage = createClass({
|
||||
htmlErrors : Markdown.validate(prevState.brew.text)
|
||||
}));
|
||||
|
||||
request
|
||||
.put(`/api/${this.props.brew.editId}`)
|
||||
.send(this.state.brew)
|
||||
.end((err, res)=>{
|
||||
if(err){
|
||||
this.setState({
|
||||
errors : err,
|
||||
});
|
||||
} else {
|
||||
this.savedBrew = res.body;
|
||||
this.setState({
|
||||
isPending : false,
|
||||
isSaving : false,
|
||||
});
|
||||
}
|
||||
});
|
||||
const transfer = this.state.saveGoogle == _.isNil(this.state.brew.googleId);
|
||||
|
||||
if(this.state.saveGoogle) {
|
||||
if(transfer) {
|
||||
const res = await request
|
||||
.post('/api/newGoogle/')
|
||||
.send(this.state.brew)
|
||||
.catch((err)=>{
|
||||
console.log(err.status === 401
|
||||
? 'Not signed in!'
|
||||
: 'Error Saving to Google!');
|
||||
this.setState({ errors: err });
|
||||
});
|
||||
|
||||
if(!res) { return; }
|
||||
|
||||
console.log('Deleting Local Copy');
|
||||
await request.delete(`/api/${this.state.brew.editId}`)
|
||||
.send()
|
||||
.catch((err)=>{
|
||||
console.log('Error deleting Local Copy');
|
||||
});
|
||||
|
||||
this.savedBrew = res.body;
|
||||
history.replaceState(null, null, `/edit/${this.savedBrew.googleId}${this.savedBrew.editId}`); //update URL to match doc ID
|
||||
} else {
|
||||
const res = await request
|
||||
.put(`/api/updateGoogle/${this.state.brew.editId}`)
|
||||
.send(this.state.brew)
|
||||
.catch((err)=>{
|
||||
console.log(err.status === 401
|
||||
? 'Not signed in!'
|
||||
: 'Error Saving to Google!');
|
||||
this.setState({ errors: err });
|
||||
return;
|
||||
});
|
||||
|
||||
this.savedBrew = res.body.brew;
|
||||
}
|
||||
} else {
|
||||
console.log('Saving Locally');
|
||||
if(transfer) {
|
||||
console.log('Moving to Local Storage');
|
||||
const res = await request.post('/api')
|
||||
.send(this.state.brew)
|
||||
.catch((err)=>{
|
||||
console.log('Error creating Local Copy');
|
||||
this.setState({ errors: err });
|
||||
return;
|
||||
});
|
||||
|
||||
await request.get(`/api/removeGoogle/${this.state.brew.googleId}${this.state.brew.editId}`)
|
||||
.send()
|
||||
.catch((err)=>{
|
||||
console.log('Error Deleting Google Brew');
|
||||
});
|
||||
|
||||
console.log('GOT THIS SAVED BREW:');
|
||||
console.log(res);
|
||||
this.savedBrew = res.body;
|
||||
history.replaceState(null, null, `/edit/${this.savedBrew.editId}`); //update URL to match doc ID
|
||||
} else {
|
||||
console.log('Updating existing local copy');
|
||||
const res = await request
|
||||
.put(`/api/update/${this.state.brew.editId}`)
|
||||
.send(this.state.brew)
|
||||
.catch((err)=>{
|
||||
console.log('Error Updating Local Brew');
|
||||
this.setState({ errors: err });
|
||||
return;
|
||||
});
|
||||
|
||||
this.savedBrew = res.body;
|
||||
}
|
||||
}
|
||||
|
||||
console.log('Finished saving. About to merge saved brew with current');
|
||||
this.setState((prevState)=>({
|
||||
brew : _.merge({}, prevState.brew, {
|
||||
googleId : this.savedBrew.googleId ? this.savedBrew.googleId : null,
|
||||
editId : this.savedBrew.editId,
|
||||
}),
|
||||
isPending : false,
|
||||
isSaving : false,
|
||||
}));
|
||||
},
|
||||
|
||||
renderGoogleDriveIcon : function(){
|
||||
if(this.state.saveGoogle) {
|
||||
return <Nav.item className='googleDriveStorage' onClick={this.toggleGoogleStorage}>
|
||||
<img src={googleDriveActive} alt='googleDriveActive' />
|
||||
</Nav.item>;
|
||||
} else {
|
||||
return <Nav.item className='googleDriveStorage' onClick={this.toggleGoogleStorage}>
|
||||
<img src={googleDriveInactive} alt='googleDriveInactive' />
|
||||
</Nav.item>;
|
||||
}
|
||||
|
||||
},
|
||||
|
||||
renderSaveButton : function(){
|
||||
@@ -161,6 +258,19 @@ const EditPage = createClass({
|
||||
errMsg += `\`\`\`\n${JSON.stringify(this.state.errors.response.error, null, ' ')}\n\`\`\``;
|
||||
} catch (e){}
|
||||
|
||||
if(this.state.errors.status == '401'){
|
||||
return <Nav.item className='save error' icon='fa-warning'>
|
||||
Oops!
|
||||
<div className='errorContainer'>
|
||||
You must be signed in to a Google account
|
||||
to save this to Google Drive!<br />
|
||||
Sign in <a target='_blank' rel='noopener noreferrer'
|
||||
href={`http://naturalcrit.com/login?redirect=${this.state.url}`}>
|
||||
here</a>.
|
||||
</div>
|
||||
</Nav.item>;
|
||||
}
|
||||
|
||||
return <Nav.item className='save error' icon='fa-warning'>
|
||||
Oops!
|
||||
<div className='errorContainer'>
|
||||
@@ -183,6 +293,7 @@ const EditPage = createClass({
|
||||
return <Nav.item className='save saved'>saved.</Nav.item>;
|
||||
}
|
||||
},
|
||||
|
||||
renderNavbar : function(){
|
||||
return <Navbar>
|
||||
<Nav.section>
|
||||
@@ -190,6 +301,7 @@ const EditPage = createClass({
|
||||
</Nav.section>
|
||||
|
||||
<Nav.section>
|
||||
{this.renderGoogleDriveIcon()}
|
||||
{this.renderSaveButton()}
|
||||
<ReportIssue />
|
||||
<Nav.item newTab={true} href={`/share/${this.props.brew.shareId}`} color='teal' icon='fa-share-alt'>
|
||||
|
||||
@@ -15,8 +15,8 @@
|
||||
top : 29px;
|
||||
left : -20px;
|
||||
z-index : 1000;
|
||||
width : 120px;
|
||||
padding : 8px;
|
||||
width : 135px;
|
||||
padding : 6px;
|
||||
background-color : #333;
|
||||
a{
|
||||
color : @teal;
|
||||
@@ -24,4 +24,9 @@
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
.googleDriveStorage img{
|
||||
height : 20px;
|
||||
padding : 0px;
|
||||
margin : -5px;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -24,6 +24,7 @@ const NewPage = createClass({
|
||||
getInitialState : function() {
|
||||
return {
|
||||
metadata : {
|
||||
gDrive : false,
|
||||
title : '',
|
||||
description : '',
|
||||
tags : '',
|
||||
@@ -32,11 +33,13 @@ const NewPage = createClass({
|
||||
systems : []
|
||||
},
|
||||
|
||||
text : '',
|
||||
isSaving : false,
|
||||
errors : []
|
||||
text : '',
|
||||
isSaving : false,
|
||||
saveGoogle : (global.account.googleId ? true : false),
|
||||
errors : []
|
||||
};
|
||||
},
|
||||
|
||||
componentDidMount : function() {
|
||||
const storage = localStorage.getItem(KEY);
|
||||
if(storage){
|
||||
@@ -80,12 +83,30 @@ const NewPage = createClass({
|
||||
localStorage.setItem(KEY, text);
|
||||
},
|
||||
|
||||
save : function(){
|
||||
save : async function(){
|
||||
this.setState({
|
||||
isSaving : true
|
||||
});
|
||||
|
||||
request.post('/api')
|
||||
console.log('saving new brew');
|
||||
|
||||
if(this.state.saveGoogle) {
|
||||
const res = await request
|
||||
.post('/api/newGoogle/')
|
||||
.send(_.merge({}, this.state.metadata, { text: this.state.text }))
|
||||
.catch((err)=>{
|
||||
console.log(err.status === 401
|
||||
? 'Not signed in!'
|
||||
: 'Error Creating New Google Brew!');
|
||||
this.setState({ isSaving: false });
|
||||
return;
|
||||
});
|
||||
|
||||
const brew = res.body;
|
||||
localStorage.removeItem(KEY);
|
||||
window.location = `/edit/${brew.googleId}${brew.editId}`;
|
||||
} else {
|
||||
request.post('/api')
|
||||
.send(_.merge({}, this.state.metadata, {
|
||||
text : this.state.text
|
||||
}))
|
||||
@@ -101,6 +122,8 @@ const NewPage = createClass({
|
||||
localStorage.removeItem(KEY);
|
||||
window.location = `/edit/${brew.editId}`;
|
||||
});
|
||||
}
|
||||
|
||||
},
|
||||
|
||||
renderSaveButton : function(){
|
||||
|
||||
@@ -45,6 +45,17 @@ const SharePage = createClass({
|
||||
}
|
||||
},
|
||||
|
||||
renderSourceButton : function() {
|
||||
let shareLink = this.props.brew.shareId;
|
||||
if(this.props.brew.googleId) {
|
||||
shareLink = this.props.brew.googleId + shareLink;
|
||||
}
|
||||
|
||||
return <Nav.item href={`/source/${shareLink}`} color='teal' icon='fa-code'>
|
||||
source
|
||||
</Nav.item>;
|
||||
},
|
||||
|
||||
render : function(){
|
||||
return <div className='sharePage page'>
|
||||
<Meta name='robots' content='noindex, nofollow' />
|
||||
@@ -55,9 +66,7 @@ const SharePage = createClass({
|
||||
|
||||
<Nav.section>
|
||||
<PrintLink shareId={this.props.brew.shareId} />
|
||||
<Nav.item href={`/source/${this.props.brew.shareId}`} color='teal' icon='fa-code'>
|
||||
source
|
||||
</Nav.item>
|
||||
{this.renderSourceButton()}
|
||||
<RecentNavItem brew={this.props.brew} storageKey='view' />
|
||||
<Account />
|
||||
</Nav.section>
|
||||
|
||||
@@ -6,6 +6,8 @@ const cx = require('classnames');
|
||||
const moment = require('moment');
|
||||
const request = require('superagent');
|
||||
|
||||
const googleDriveIcon = require('../../../googleDrive.png');
|
||||
|
||||
const BrewItem = createClass({
|
||||
getDefaultProps : function() {
|
||||
return {
|
||||
@@ -27,11 +29,19 @@ const BrewItem = createClass({
|
||||
if(!confirm('Are you REALLY sure? You will lose editor access to this document.')) return;
|
||||
}
|
||||
|
||||
request.delete(`/api/${this.props.brew.editId}`)
|
||||
.send()
|
||||
.end(function(err, res){
|
||||
location.reload();
|
||||
});
|
||||
if(this.props.brew.googleId) {
|
||||
request.get(`/api/removeGoogle/${this.props.brew.googleId}${this.props.brew.editId}`)
|
||||
.send()
|
||||
.end(function(err, res){
|
||||
location.reload();
|
||||
});
|
||||
} else {
|
||||
request.delete(`/api/${this.props.brew.editId}`)
|
||||
.send()
|
||||
.end(function(err, res){
|
||||
location.reload();
|
||||
});
|
||||
}
|
||||
},
|
||||
|
||||
renderDeleteBrewLink : function(){
|
||||
@@ -41,14 +51,41 @@ const BrewItem = createClass({
|
||||
<i className='fa fa-trash' />
|
||||
</a>;
|
||||
},
|
||||
|
||||
renderEditLink : function(){
|
||||
if(!this.props.brew.editId) return;
|
||||
|
||||
return <a href={`/edit/${this.props.brew.editId}`} target='_blank' rel='noopener noreferrer'>
|
||||
let editLink = this.props.brew.editId;
|
||||
if(this.props.brew.googleId) {
|
||||
editLink = this.props.brew.googleId + editLink;
|
||||
}
|
||||
|
||||
return <a href={`/edit/${editLink}`} target='_blank' rel='noopener noreferrer'>
|
||||
<i className='fa fa-pencil' />
|
||||
</a>;
|
||||
},
|
||||
|
||||
renderShareLink : function(){
|
||||
if(!this.props.brew.shareId) return;
|
||||
|
||||
let shareLink = this.props.brew.shareId;
|
||||
if(this.props.brew.googleId) {
|
||||
shareLink = this.props.brew.googleId + shareLink;
|
||||
}
|
||||
|
||||
return <a href={`/share/${shareLink}`} target='_blank' rel='noopener noreferrer'>
|
||||
<i className='fa fa-share-alt' />
|
||||
</a>;
|
||||
},
|
||||
|
||||
renderGoogleDriveIcon : function(){
|
||||
if(!this.props.brew.gDrive) return;
|
||||
|
||||
return <span>
|
||||
<img className='googleDriveIcon' src={googleDriveIcon} alt='googleDriveIcon' />
|
||||
</span>;
|
||||
},
|
||||
|
||||
render : function(){
|
||||
const brew = this.props.brew;
|
||||
return <div className='brewItem'>
|
||||
@@ -66,12 +103,11 @@ const BrewItem = createClass({
|
||||
<span>
|
||||
<i className='fa fa-refresh' /> {moment(brew.updatedAt).fromNow()}
|
||||
</span>
|
||||
{this.renderGoogleDriveIcon()}
|
||||
</div>
|
||||
|
||||
<div className='links'>
|
||||
<a href={`/share/${brew.shareId}`} target='_blank' rel='noopener noreferrer'>
|
||||
<i className='fa fa-share-alt' />
|
||||
</a>
|
||||
{this.renderShareLink()}
|
||||
{this.renderEditLink()}
|
||||
{this.renderDeleteBrewLink()}
|
||||
</div>
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
box-sizing : border-box;
|
||||
overflow : hidden;
|
||||
width : 48%;
|
||||
min-height : 80px;
|
||||
margin-right : 15px;
|
||||
margin-bottom : 15px;
|
||||
padding : 5px 15px 5px 8px;
|
||||
@@ -55,6 +56,14 @@
|
||||
&:hover{
|
||||
opacity : 1;
|
||||
}
|
||||
i{
|
||||
cursor : pointer;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
.googleDriveIcon {
|
||||
height : 20px;
|
||||
padding : 0px;
|
||||
margin : -5px;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -22,8 +22,9 @@ const BrewItem = require('./brewItem/brewItem.jsx');
|
||||
const UserPage = createClass({
|
||||
getDefaultProps : function() {
|
||||
return {
|
||||
username : '',
|
||||
brews : []
|
||||
username : '',
|
||||
brews : [],
|
||||
googleBrews : []
|
||||
};
|
||||
},
|
||||
|
||||
|
||||
Reference in New Issue
Block a user