Compare commits

..

No commits in common. "master" and "0.37-fixes" have entirely different histories.

26 changed files with 215 additions and 279 deletions

View file

@ -1,3 +1,4 @@
sudo: true
dist: xenial dist: xenial
#addons: #addons:
# apt: # apt:
@ -8,7 +9,7 @@ dist: xenial
# - mysql-client # - mysql-client
language: node_js language: node_js
node_js: node_js:
- "lts/dubnium" - "lts/*"
cache: cache:
directories: directories:
- "node_modules" - "node_modules"

View file

@ -1,6 +1,6 @@
The MIT License (MIT) The MIT License (MIT)
Copyright (c) 2017-2020 LBRY Inc. Copyright (c) 2017-2019 LBRY Inc.
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the
"Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish,

View file

@ -3,8 +3,6 @@
spee.ch provides a user-friendly, custom-designed, image and video hosting site backed by a decentralized network and spee.ch provides a user-friendly, custom-designed, image and video hosting site backed by a decentralized network and
blockchain ([LBRY](https://lbry.tech/)). Via just a small set of config files, you can spin your an entire spee.ch site back up including assets. blockchain ([LBRY](https://lbry.tech/)). Via just a small set of config files, you can spin your an entire spee.ch site back up including assets.
**Please note: the spee.ch code base and setup instructions are no longer actively maintained now that we have lbry.tv. Proceed at your own caution. Setup will require dev ops skills.**
![App GIF](https://spee.ch/e/speechgif.gif) ![App GIF](https://spee.ch/e/speechgif.gif)
For a completely open, unrestricted example of a spee.ch site, check out https://www.spee.ch. For a completely open, unrestricted example of a spee.ch site, check out https://www.spee.ch.
@ -107,7 +105,7 @@ $ npm run start
#### Customize your app #### Customize your app
Check out the [customization guide](https://github.com/lbryio/spee.ch/blob/master/customize.md) to change your app's appearance and components Check out the [customization guide](https://github.com/lbryio/spee.ch/blob/readme-update/customize.md) to change your app's appearance and components
#### (optional) add custom components and update the styles #### (optional) add custom components and update the styles

View file

@ -1,6 +1,6 @@
import Request from '../utils/request'; import Request from '../utils/request';
export function getLongClaimId(host, name, modifier) { export function getLongClaimId (host, name, modifier) {
let body = {}; let body = {};
// create request params // create request params
if (modifier) { if (modifier) {
@ -13,40 +13,40 @@ export function getLongClaimId(host, name, modifier) {
} }
body['claimName'] = name; body['claimName'] = name;
const params = { const params = {
method: 'POST', method : 'POST',
headers: { 'Content-Type': 'application/json' }, headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(body), body : JSON.stringify(body),
}; };
// create url // create url
const url = `${host}/api/claim/long-id`; const url = `${host}/api/claim/long-id`;
// return the request promise // return the request promise
return Request(url, params); return Request(url, params);
} };
export function getShortId(host, name, claimId) { export function getShortId (host, name, claimId) {
const url = `${host}/api/claim/short-id/${claimId}/${name}`; const url = `${host}/api/claim/short-id/${claimId}/${name}`;
return Request(url); return Request(url);
} };
export function getClaimData(host, name, claimId) { export function getClaimData (host, name, claimId) {
const url = `${host}/api/claim/data/${name}/${claimId}`; const url = `${host}/api/claim/data/${name}/${claimId}`;
return Request(url); return Request(url);
} };
export function checkClaimAvailability(claim) { export function checkClaimAvailability (claim) {
const url = `/api/claim/availability/${claim}`; const url = `/api/claim/availability/${claim}`;
return Request(url); return Request(url);
} }
export function getClaimViews(claimId) { export function getClaimViews (claimId) {
const url = `/api/claim/views/${claimId}`; const url = `/api/claim/views/${claimId}`;
return Request(url); return Request(url);
} }
export function doAbandonClaim(outpoint) { export function doAbandonClaim (claimId) {
const params = { const params = {
method: 'POST', method : 'POST',
body: JSON.stringify({ outpoint }), body : JSON.stringify({claimId}),
headers: new Headers({ headers: new Headers({
'Content-Type': 'application/json', 'Content-Type': 'application/json',
}), }),

View file

@ -16,7 +16,7 @@ import EditPage from '@pages/EditPage';
const App = () => { const App = () => {
return ( return (
<Switch> <Switch>
<Route exact path='/' component={AboutPage} /> <Route exact path='/' component={HomePage} />
<Route exact path='/about' component={AboutPage} /> <Route exact path='/about' component={AboutPage} />
<Route exact path='/tos' component={TosPage} /> <Route exact path='/tos' component={TosPage} />
<Route exact path='/faq' component={FaqPage} /> <Route exact path='/faq' component={FaqPage} />

View file

@ -22,30 +22,15 @@ export const makePublishRequestChannel = (fd, isUpdate) => {
xhr.upload.addEventListener('load', onLoad); xhr.upload.addEventListener('load', onLoad);
// set state change handler // set state change handler
xhr.onreadystatechange = () => { xhr.onreadystatechange = () => {
if (xhr.readyState === XMLHttpRequest.DONE) { if (xhr.readyState === 4) {
switch (xhr.status) { const response = JSON.parse(xhr.response);
case 413: if ((xhr.status === 200) && response.success) {
emitter({error: new Error("Unfortunately it appears this web server " +
"has been misconfigured, please inform the service administrators " +
"that they must set their nginx/apache request size maximums higher " +
"than their file size limits.")});
emitter(END);
break;
case 200:
var response = JSON.parse(xhr.response);
if (response.success) {
emitter({success: response}); emitter({success: response});
emitter(END); emitter(END);
} else { } else {
emitter({error: new Error(response.message)}); emitter({error: new Error(response.message)});
emitter(END); emitter(END);
} }
break;
default:
emitter({error: new Error("Received an unexpected response from " +
"server: " + xhr.status)});
emitter(END);
}
} }
}; };
// open and send // open and send

View file

@ -1,13 +1,32 @@
import React from 'react'; import React from 'react';
import Row from '@components/Row'; import Row from '@components/Row';
import {Link} from 'react-router-dom';
const AboutSpeechDetails = () => { const AboutSpeechDetails = () => {
return ( return (
<div> <div>
<Row> <Row>
<p className={'text--large'}> <p className={'text--large'}>
Spee.ch's journey may be on hold, but LBRY is still on mission. We'd like to thank all of our testers and early adopters for helping us explore this use case. <Link className={'link--primary'} to='/tos'>Terms of Service</Link>
We're really excited about <a className='link--primary' href='https://lbry.tv' target='_blank'>lbry.tv</a> and can't wait to see you over there for a fully featured experience. <br />
<Link className={'link--primary'} to='/faq'>Frequently Asked Questions</Link>
</p>
</Row>
<Row>
<p className={'text--large'}>
Spee.ch is a media-hosting site that reads from and publishes content to the <a className='link--primary' href='https://lbry.com'>LBRY</a> blockchain.
</p>
<p className={'text--large'}>
Spee.ch is a hosting service, but with the added benefit that it stores your content on a decentralized network of computers -- the <a className='link--primary' href='https://lbry.com/get'>LBRY</a> network. This means that your images are stored in multiple locations without a single point of failure.
</p>
</Row>
<Row>
<h3>Contribute</h3>
<p className={'text--large'}>
If you have an idea for your own spee.ch-like site on top of LBRY, fork our <a className='link--primary' href='https://github.com/lbryio/spee.ch'>github repo</a> and go to town!
</p>
<p className={'text--large'}>
If you want to improve spee.ch, join our <a className='link--primary' href='https://chat.lbry.com'>discord channel</a> or solve one of our <a className='link--primary' href='https://github.com/lbryio/spee.ch/issues'>github issues</a>.
</p> </p>
</Row> </Row>
</div> </div>

View file

@ -5,13 +5,14 @@ const AboutSpeechOverview = () => {
return ( return (
<div> <div>
<Row> <Row>
<p className={'text--extra-large'}>Lbry is no longer supporting Spee.ch. However, we're excited to show you <a className='link--primary' href='https://lbry.tv' target='_blank'>lbry.tv</a>!</p> <p className={'text--extra-large'}>Spee.ch is an open-source project. Please contribute to the existing site, or fork it and make your own.</p>
</Row> </Row>
<Row> <Row>
<div className={'text--large'}> <div className={'text--large'}>
<a className='link--primary' target='_blank' href='https://twitter.com/lbry'>TWITTER</a><br/> <a className='link--primary' target='_blank' href='https://twitter.com/spee_ch'>TWITTER</a><br/>
<a className='link--primary' target='_blank' href='https://github.com/lbryio/'>GITHUB</a><br/> <a className='link--primary' target='_blank' href='https://github.com/lbryio/spee.ch'>GITHUB</a><br/>
<a className='link--primary' target='_blank' href='https://discord.gg/YjYbwhS'>DISCORD CHANNEL</a><br/> <a className='link--primary' target='_blank' href='https://discord.gg/YjYbwhS'>DISCORD CHANNEL</a><br/>
<a className='link--primary' target='_blank' href='https://github.com/lbryio/spee.ch/blob/master/README.md'>DOCUMENTATION</a><br/>
</div> </div>
</Row> </Row>
</div> </div>

View file

@ -194,7 +194,7 @@ class AssetInfo extends React.Component {
<a <a
className={'link--primary'} className={'link--primary'}
target='_blank' target='_blank'
href={`https://lbry.com/dmca/${claimId}`} href='https://lbry.com/dmca'
> >
Report Report
</a> </a>

View file

@ -33,14 +33,14 @@ class NavigationLinks extends React.Component {
const { channelName, showPublish, closedRegistration } = this.props; const { channelName, showPublish, closedRegistration } = this.props;
return ( return (
<div className='navigation-links'> <div className='navigation-links'>
{/*{showPublish && <NavLink*/} {showPublish && <NavLink
{/* className='nav-bar-link link--nav'*/} className='nav-bar-link link--nav'
{/* activeClassName='link--nav-active'*/} activeClassName='link--nav-active'
{/* to='/'*/} to='/'
{/* exact*/} exact
{/*>*/} >
{/* Publish*/} Publish
{/*</NavLink>}*/} </NavLink>}
<NavLink <NavLink
className='nav-bar-link link--nav' className='nav-bar-link link--nav'
activeClassName='link--nav-active' activeClassName='link--nav-active'
@ -48,24 +48,24 @@ class NavigationLinks extends React.Component {
> >
About About
</NavLink> </NavLink>
{/*{ channelName ? (*/} { channelName ? (
{/* <NavBarChannelOptionsDropdown*/} <NavBarChannelOptionsDropdown
{/* channelName={this.props.channelName}*/} channelName={this.props.channelName}
{/* handleSelection={this.handleSelection}*/} handleSelection={this.handleSelection}
{/* defaultSelection={this.props.channelName}*/} defaultSelection={this.props.channelName}
{/* VIEW={VIEW}*/} VIEW={VIEW}
{/* LOGOUT={LOGOUT}*/} LOGOUT={LOGOUT}
{/* />*/} />
{/*) : !closedRegistration && (*/} ) : !closedRegistration && (
{/* <NavLink*/} <NavLink
{/* id='nav-bar-login-link'*/} id='nav-bar-login-link'
{/* className='nav-bar-link link--nav'*/} className='nav-bar-link link--nav'
{/* activeClassName='link--nav-active'*/} activeClassName='link--nav-active'
{/* to='/login'*/} to='/login'
{/* >*/} >
{/* Channel*/} Channel
{/* </NavLink>*/} </NavLink>
{/*)}*/} )}
</div> </div>
); );
} }

View file

@ -7,9 +7,6 @@ class PublishDisabledMessage extends React.Component {
<div className={'publish-disabled-message'}> <div className={'publish-disabled-message'}>
<div className={'message'}> <div className={'message'}>
<p className={'text--secondary'}>Publishing is currently disabled.</p> <p className={'text--secondary'}>Publishing is currently disabled.</p>
<p className={'text--secondary'}>
Try <a className='link--primary' href='https://lbry.tv' target='_blank'>lbry.tv</a>
</p>
<p className={'text--secondary'}>{message}</p> <p className={'text--secondary'}>{message}</p>
</div> </div>
</div> </div>

View file

@ -3,7 +3,7 @@ import ErrorPage from '@pages/ErrorPage';
import ShowAssetLite from '@pages/ShowAssetLite'; import ShowAssetLite from '@pages/ShowAssetLite';
import ShowAssetDetails from '@pages/ShowAssetDetails'; import ShowAssetDetails from '@pages/ShowAssetDetails';
import ShowChannel from '@pages/ShowChannel'; import ShowChannel from '@pages/ShowChannel';
import { withRouter, Redirect } from 'react-router-dom'; import { withRouter } from 'react-router-dom';
import { import {
CHANNEL, CHANNEL,
@ -15,24 +15,15 @@ import {
class ContentPageWrapper extends React.Component { class ContentPageWrapper extends React.Component {
componentDidMount () { componentDidMount () {
const { onHandleShowPageUri, match, homeChannel } = this.props; const { onHandleShowPageUri, match, homeChannel } = this.props;
//onHandleShowPageUri(homeChannel ? { claim: homeChannel } : match.params); onHandleShowPageUri(homeChannel ? { claim: homeChannel } : match.params);
} }
componentWillReceiveProps (nextProps) { componentWillReceiveProps (nextProps) {
if (nextProps.match.params !== this.props.match.params) { if (nextProps.match.params !== this.props.match.params) {
//this.props.onHandleShowPageUri(nextProps.match.params); this.props.onHandleShowPageUri(nextProps.match.params);
} }
} }
render () { render () {
const { error, requestType, match } = this.props; const { error, requestType } = this.props;
const { params } = match;
const { claim, identifier } = params;
if (identifier && claim) {
return <Redirect to={`https://lbry.tv/${identifier}/${claim}`} />;
} else if (identifier) {
// return <Redirect to={`https://lbry.tv/${identifier}/`} />
} else {
return <Redirect to={`https://lbry.tv/${claim}`} />;
}
if (error) { if (error) {
return ( return (
<ErrorPage error={error} /> <ErrorPage error={error} />
@ -40,13 +31,13 @@ class ContentPageWrapper extends React.Component {
} }
switch (requestType) { switch (requestType) {
case CHANNEL: case CHANNEL:
// return <ShowChannel />; return <ShowChannel />;
case ASSET_LITE: case ASSET_LITE:
// return <ShowAssetLite />; return <ShowAssetLite />;
case ASSET_DETAILS: case ASSET_DETAILS:
// return <ShowAssetDetails />; return <ShowAssetDetails />;
case SPECIAL_ASSET: case SPECIAL_ASSET:
// return <ShowChannel />; return <ShowChannel />;
default: default:
return <p>loading...</p>; return <p>loading...</p>;
} }

View file

@ -5,19 +5,17 @@ import { updatePublishStatus, clearFile } from '../actions/publish';
import { removeAsset } from '../actions/show'; import { removeAsset } from '../actions/show';
import { doAbandonClaim } from '../api/assetApi'; import { doAbandonClaim } from '../api/assetApi';
function* abandonClaim(action) { function * abandonClaim (action) {
const { claimData, history } = action.data; const { claimData, history } = action.data;
const { outpoint } = claimData; const { claimId } = claimData;
const confirm = window.confirm( const confirm = window.confirm('Are you sure you want to abandon this claim? This action cannot be undone.');
'Are you sure you want to abandon this claim? This action cannot be undone.'
);
if (!confirm) return; if (!confirm) return;
yield put(updatePublishStatus(publishStates.ABANDONING, 'Your claim is being abandoned...')); yield put(updatePublishStatus(publishStates.ABANDONING, 'Your claim is being abandoned...'));
try { try {
yield call(doAbandonClaim, outpoint); yield call(doAbandonClaim, claimId);
} catch (error) { } catch (error) {
return console.log('abandon error:', error.message); return console.log('abandon error:', error.message);
} }
@ -27,6 +25,6 @@ function* abandonClaim(action) {
return history.push('/'); return history.push('/');
} }
export function* watchAbandonClaim() { export function * watchAbandonClaim () {
yield takeLatest(actions.ABANDON_CLAIM, abandonClaim); yield takeLatest(actions.ABANDON_CLAIM, abandonClaim);
} };

View file

@ -1,6 +1,6 @@
# Configure your own spee.ch # Configure your own spee.ch
_note: this guide assumes you have done the [quickstart](https://github.com/lbryio/spee.ch/blob/master/README.md) or [fullstart](https://github.com/lbryio/spee.ch/blob/master/fullstart.md) guide and have a working spee.ch server_ _note: this guide assumes you have done the [quickstart](https://github.com/lbryio/spee.ch/blob/readme-update/README.md) or [fullstart](https://github.com/lbryio/spee.ch/blob/readme-update/fullstart.md) guide and have a working spee.ch server_
## Custom Components ## Custom Components
The components used by spee.ch are taken from the `client/` folder, but you can override those components by defining your own in the `site/custom/` folder. The components used by spee.ch are taken from the `client/` folder, but you can override those components by defining your own in the `site/custom/` folder.

170
package-lock.json generated
View file

@ -1729,7 +1729,7 @@
}, },
"util": { "util": {
"version": "0.10.3", "version": "0.10.3",
"resolved": "https://registry.npmjs.org/util/-/util-0.10.3.tgz", "resolved": "http://registry.npmjs.org/util/-/util-0.10.3.tgz",
"integrity": "sha1-evsa/lCAUkZInj23/g7TeTNqwPk=", "integrity": "sha1-evsa/lCAUkZInj23/g7TeTNqwPk=",
"dev": true, "dev": true,
"requires": { "requires": {
@ -1755,6 +1755,14 @@
"integrity": "sha1-WWZ/QfrdTyDMvCu5a41Pf3jsA2c=", "integrity": "sha1-WWZ/QfrdTyDMvCu5a41Pf3jsA2c=",
"dev": true "dev": true
}, },
"async": {
"version": "2.6.2",
"resolved": "https://registry.npmjs.org/async/-/async-2.6.2.tgz",
"integrity": "sha512-H1qVYh1MYhEEFLsP97cVKqCGo7KfCyTt6uEWqsTBr9SO84oK9Uwbyd/yCW+6rKJLHksBNUVWZDAjfS+Ccx0Bbg==",
"requires": {
"lodash": "^4.17.11"
}
},
"async-each": { "async-each": {
"version": "1.0.1", "version": "1.0.1",
"resolved": "https://registry.npmjs.org/async-each/-/async-each-1.0.1.tgz", "resolved": "https://registry.npmjs.org/async-each/-/async-each-1.0.1.tgz",
@ -1803,19 +1811,12 @@
"integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ==" "integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ=="
}, },
"axios": { "axios": {
"version": "0.18.1", "version": "0.18.0",
"resolved": "http://registry.npmjs.org/axios/-/axios-0.18.1.tgz", "resolved": "http://registry.npmjs.org/axios/-/axios-0.18.0.tgz",
"integrity": "sha512-0BfJq4NSfQXd+SkFdrvFbG7addhYSBA2mQwISr46pD6E5iqkWg02RAs8vyTT/j0RTnoYmeXauBuSv1qKwR179g==", "integrity": "sha1-MtU+SFHv3AoRmTts0AB4nXDAUQI=",
"requires": { "requires": {
"follow-redirects": "1.5.10", "follow-redirects": "^1.3.0",
"is-buffer": "^2.0.2" "is-buffer": "^1.1.5"
},
"dependencies": {
"is-buffer": {
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-2.0.3.tgz",
"integrity": "sha512-U15Q7MXTuZlrbymiz95PJpZxu8IlipAp4dtS3wOdgPXx3mqBnslrWU14kxfHB+Py/+2PVKSr37dMAgM2A4uArw=="
}
} }
}, },
"babel-eslint": { "babel-eslint": {
@ -2616,7 +2617,6 @@
"resolved": "http://registry.npmjs.org/bl/-/bl-1.2.2.tgz", "resolved": "http://registry.npmjs.org/bl/-/bl-1.2.2.tgz",
"integrity": "sha512-e8tQYnZodmebYDWGH7KMRvtzKXaJHx3BbilrgZCfvyLUYdKpK1t5PSPmpkny/SgiTSCnjfLW7v5rlONXVFkQEA==", "integrity": "sha512-e8tQYnZodmebYDWGH7KMRvtzKXaJHx3BbilrgZCfvyLUYdKpK1t5PSPmpkny/SgiTSCnjfLW7v5rlONXVFkQEA==",
"dev": true, "dev": true,
"optional": true,
"requires": { "requires": {
"readable-stream": "^2.3.5", "readable-stream": "^2.3.5",
"safe-buffer": "^5.1.1" "safe-buffer": "^5.1.1"
@ -3611,15 +3611,6 @@
"resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz",
"integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac="
}, },
"cors": {
"version": "2.8.5",
"resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz",
"integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==",
"requires": {
"object-assign": "^4",
"vary": "^1"
}
},
"cosmiconfig": { "cosmiconfig": {
"version": "5.0.7", "version": "5.0.7",
"resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-5.0.7.tgz", "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-5.0.7.tgz",
@ -3955,7 +3946,7 @@
"dependencies": { "dependencies": {
"pify": { "pify": {
"version": "2.3.0", "version": "2.3.0",
"resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", "resolved": "http://registry.npmjs.org/pify/-/pify-2.3.0.tgz",
"integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=",
"dev": true, "dev": true,
"optional": true "optional": true
@ -3967,7 +3958,6 @@
"resolved": "https://registry.npmjs.org/decompress-tar/-/decompress-tar-4.1.1.tgz", "resolved": "https://registry.npmjs.org/decompress-tar/-/decompress-tar-4.1.1.tgz",
"integrity": "sha512-JdJMaCrGpB5fESVyxwpCx4Jdj2AagLmv3y58Qy4GE6HMVjWz1FeVQk1Ct4Kye7PftcdOo/7U7UKzYBJgqnGeUQ==", "integrity": "sha512-JdJMaCrGpB5fESVyxwpCx4Jdj2AagLmv3y58Qy4GE6HMVjWz1FeVQk1Ct4Kye7PftcdOo/7U7UKzYBJgqnGeUQ==",
"dev": true, "dev": true,
"optional": true,
"requires": { "requires": {
"file-type": "^5.2.0", "file-type": "^5.2.0",
"is-stream": "^1.1.0", "is-stream": "^1.1.0",
@ -4002,7 +3992,6 @@
"resolved": "https://registry.npmjs.org/decompress-targz/-/decompress-targz-4.1.1.tgz", "resolved": "https://registry.npmjs.org/decompress-targz/-/decompress-targz-4.1.1.tgz",
"integrity": "sha512-4z81Znfr6chWnRDNfFNqLwPvm4db3WuZkqV+UgXQzSngG3CEKdBkw5jrv3axjjL96glyiiKjsxJG3X6WBZwX3w==", "integrity": "sha512-4z81Znfr6chWnRDNfFNqLwPvm4db3WuZkqV+UgXQzSngG3CEKdBkw5jrv3axjjL96glyiiKjsxJG3X6WBZwX3w==",
"dev": true, "dev": true,
"optional": true,
"requires": { "requires": {
"decompress-tar": "^4.1.1", "decompress-tar": "^4.1.1",
"file-type": "^5.2.0", "file-type": "^5.2.0",
@ -4024,14 +4013,14 @@
"dependencies": { "dependencies": {
"file-type": { "file-type": {
"version": "3.9.0", "version": "3.9.0",
"resolved": "https://registry.npmjs.org/file-type/-/file-type-3.9.0.tgz", "resolved": "http://registry.npmjs.org/file-type/-/file-type-3.9.0.tgz",
"integrity": "sha1-JXoHg4TR24CHvESdEH1SpSZyuek=", "integrity": "sha1-JXoHg4TR24CHvESdEH1SpSZyuek=",
"dev": true, "dev": true,
"optional": true "optional": true
}, },
"get-stream": { "get-stream": {
"version": "2.3.1", "version": "2.3.1",
"resolved": "https://registry.npmjs.org/get-stream/-/get-stream-2.3.1.tgz", "resolved": "http://registry.npmjs.org/get-stream/-/get-stream-2.3.1.tgz",
"integrity": "sha1-Xzj5PzRgCWZu4BUKBUFn+Rvdld4=", "integrity": "sha1-Xzj5PzRgCWZu4BUKBUFn+Rvdld4=",
"dev": true, "dev": true,
"optional": true, "optional": true,
@ -4042,7 +4031,7 @@
}, },
"pify": { "pify": {
"version": "2.3.0", "version": "2.3.0",
"resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", "resolved": "http://registry.npmjs.org/pify/-/pify-2.3.0.tgz",
"integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=",
"dev": true, "dev": true,
"optional": true "optional": true
@ -5158,7 +5147,7 @@
}, },
"external-editor": { "external-editor": {
"version": "2.2.0", "version": "2.2.0",
"resolved": "https://registry.npmjs.org/external-editor/-/external-editor-2.2.0.tgz", "resolved": "http://registry.npmjs.org/external-editor/-/external-editor-2.2.0.tgz",
"integrity": "sha512-bSn6gvGxKt+b7+6TKEv1ZycHleA7aHhRHyAqJyp5pbUFuYYNIzpZnQDk7AsYckyWdEnTeAnay0aCy2aV6iTk9A==", "integrity": "sha512-bSn6gvGxKt+b7+6TKEv1ZycHleA7aHhRHyAqJyp5pbUFuYYNIzpZnQDk7AsYckyWdEnTeAnay0aCy2aV6iTk9A==",
"requires": { "requires": {
"chardet": "^0.4.0", "chardet": "^0.4.0",
@ -5393,8 +5382,7 @@
"version": "5.2.0", "version": "5.2.0",
"resolved": "https://registry.npmjs.org/file-type/-/file-type-5.2.0.tgz", "resolved": "https://registry.npmjs.org/file-type/-/file-type-5.2.0.tgz",
"integrity": "sha1-LdvqfHP/42No365J3DOMBYwritY=", "integrity": "sha1-LdvqfHP/42No365J3DOMBYwritY=",
"dev": true, "dev": true
"optional": true
}, },
"fill-range": { "fill-range": {
"version": "4.0.0", "version": "4.0.0",
@ -5511,11 +5499,11 @@
} }
}, },
"follow-redirects": { "follow-redirects": {
"version": "1.5.10", "version": "1.5.7",
"resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.5.10.tgz", "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.5.7.tgz",
"integrity": "sha512-0V5l4Cizzvqt5D44aTXbFZz+FtyXV1vrDN6qrelxtfYQKW0KO0W2T/hkE8xvGa/540LkZlkaUjO4ailYTFtHVQ==", "integrity": "sha512-NONJVIFiX7Z8k2WxfqBjtwqMifx7X42ORLFrOZ2LTKGj71G3C0kfdyTqGqr8fx5zSX6Foo/D95dgGWbPUiwnew==",
"requires": { "requires": {
"debug": "=3.1.0" "debug": "^3.1.0"
} }
}, },
"for-in": { "for-in": {
@ -5592,8 +5580,7 @@
"version": "1.0.0", "version": "1.0.0",
"resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz",
"integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==", "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==",
"dev": true, "dev": true
"optional": true
}, },
"fs-extra": { "fs-extra": {
"version": "5.0.0", "version": "5.0.0",
@ -5626,7 +5613,8 @@
"fs.realpath": { "fs.realpath": {
"version": "1.0.0", "version": "1.0.0",
"resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz",
"integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=",
"dev": true
}, },
"fsevents": { "fsevents": {
"version": "1.2.4", "version": "1.2.4",
@ -5648,8 +5636,7 @@
"ansi-regex": { "ansi-regex": {
"version": "2.1.1", "version": "2.1.1",
"bundled": true, "bundled": true,
"dev": true, "dev": true
"optional": true
}, },
"aproba": { "aproba": {
"version": "1.2.0", "version": "1.2.0",
@ -6064,8 +6051,7 @@
"safe-buffer": { "safe-buffer": {
"version": "5.1.1", "version": "5.1.1",
"bundled": true, "bundled": true,
"dev": true, "dev": true
"optional": true
}, },
"safer-buffer": { "safer-buffer": {
"version": "2.1.2", "version": "2.1.2",
@ -6121,7 +6107,6 @@
"version": "3.0.1", "version": "3.0.1",
"bundled": true, "bundled": true,
"dev": true, "dev": true,
"optional": true,
"requires": { "requires": {
"ansi-regex": "^2.0.0" "ansi-regex": "^2.0.0"
} }
@ -6165,21 +6150,20 @@
"wrappy": { "wrappy": {
"version": "1.0.2", "version": "1.0.2",
"bundled": true, "bundled": true,
"dev": true, "dev": true
"optional": true
}, },
"yallist": { "yallist": {
"version": "3.0.2", "version": "3.0.2",
"bundled": true, "bundled": true,
"dev": true, "dev": true
"optional": true
} }
} }
}, },
"fstream": { "fstream": {
"version": "1.0.12", "version": "1.0.11",
"resolved": "https://registry.npmjs.org/fstream/-/fstream-1.0.12.tgz", "resolved": "https://registry.npmjs.org/fstream/-/fstream-1.0.11.tgz",
"integrity": "sha512-WvJ193OHa0GHPEL+AycEJgxvBEwyfRkN1vhjca23OaPVMCaLCXTd5qAu82AjTcgP1UJmytkOKb63Ypde7raDIg==", "integrity": "sha1-XB+x8RdHcRTwYyoOtLcbPLD9MXE=",
"dev": true,
"requires": { "requires": {
"graceful-fs": "^4.1.2", "graceful-fs": "^4.1.2",
"inherits": "~2.0.0", "inherits": "~2.0.0",
@ -6253,7 +6237,7 @@
}, },
"strip-ansi": { "strip-ansi": {
"version": "3.0.1", "version": "3.0.1",
"resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", "resolved": "http://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz",
"integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=",
"dev": true, "dev": true,
"requires": { "requires": {
@ -6440,7 +6424,7 @@
}, },
"pify": { "pify": {
"version": "2.3.0", "version": "2.3.0",
"resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", "resolved": "http://registry.npmjs.org/pify/-/pify-2.3.0.tgz",
"integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=",
"dev": true "dev": true
} }
@ -6533,21 +6517,16 @@
"dev": true "dev": true
}, },
"handlebars": { "handlebars": {
"version": "4.1.2", "version": "4.1.0",
"resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.1.2.tgz", "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.1.0.tgz",
"integrity": "sha512-nvfrjqvt9xQ8Z/w0ijewdD/vvWDTOweBUm96NTr66Wfvo1mJenBLwcYmPs3TIBP5ruzYGD7Hx/DaM9RmhroGPw==", "integrity": "sha512-l2jRuU1NAWK6AW5qqcTATWQJvNPEwkM7NEKSiv/gqOsoSQbVoWyqVEY5GS+XPQ88zLNmqASRpzfdm8d79hJS+w==",
"requires": { "requires": {
"neo-async": "^2.6.0", "async": "^2.5.0",
"optimist": "^0.6.1", "optimist": "^0.6.1",
"source-map": "^0.6.1", "source-map": "^0.6.1",
"uglify-js": "^3.1.4" "uglify-js": "^3.1.4"
}, },
"dependencies": { "dependencies": {
"neo-async": {
"version": "2.6.1",
"resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.1.tgz",
"integrity": "sha512-iyam8fBuCUpWeKPGpaNMetEocMt364qkCsfL9JuhjXX6dRnguRVOfk2GZaDpPjcOKiiXCPINZC1GczQ7iTq3Zw=="
},
"source-map": { "source-map": {
"version": "0.6.1", "version": "0.6.1",
"resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz",
@ -6822,7 +6801,7 @@
}, },
"http-errors": { "http-errors": {
"version": "1.6.3", "version": "1.6.3",
"resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", "resolved": "http://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz",
"integrity": "sha1-i1VoC7S+KDoLW/TqLjhYC+HZMg0=", "integrity": "sha1-i1VoC7S+KDoLW/TqLjhYC+HZMg0=",
"requires": { "requires": {
"depd": "~1.1.2", "depd": "~1.1.2",
@ -7723,9 +7702,9 @@
"integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==" "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ=="
}, },
"js-yaml": { "js-yaml": {
"version": "3.13.1", "version": "3.13.0",
"resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.13.1.tgz", "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.13.0.tgz",
"integrity": "sha512-YfbcO7jXDdyj0DGxYVSlSeQNHbD7XPWvrVWeVUujrQEoZzWJIRrCPoyk6kL6IAjAG2IolMK4T0hNUe0HOUs5Jw==", "integrity": "sha512-pZZoSxcCYco+DIKBTimr67J6Hy+EYGZDY/HCWC+iAEA9h1ByhMXAIVUXMcMFpOCxQ/xjXmPI2MkDL5HRm5eFrQ==",
"requires": { "requires": {
"argparse": "^1.0.7", "argparse": "^1.0.7",
"esprima": "^4.0.0" "esprima": "^4.0.0"
@ -8124,9 +8103,9 @@
} }
}, },
"lodash": { "lodash": {
"version": "4.17.13", "version": "4.17.11",
"resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.13.tgz", "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.11.tgz",
"integrity": "sha512-vm3/XWXfWtRua0FkUyEHBZy8kCPjErNBT9fJx8Zvs+U6zjqPbTUOpkaoum3O5uiA8sm+yNMHXfYkTUHFoMxFNA==" "integrity": "sha512-cQKh8igo5QUhZ7lg38DYWAxMvjSAKG0A8wGSVimP07SIUEK2UO+arSRKbRZWtelMtN5V0Hkwh5ryOto/SshYIg=="
}, },
"lodash.assign": { "lodash.assign": {
"version": "4.2.0", "version": "4.2.0",
@ -8158,9 +8137,9 @@
"dev": true "dev": true
}, },
"lodash.mergewith": { "lodash.mergewith": {
"version": "4.6.2", "version": "4.6.1",
"resolved": "https://registry.npmjs.org/lodash.mergewith/-/lodash.mergewith-4.6.2.tgz", "resolved": "https://registry.npmjs.org/lodash.mergewith/-/lodash.mergewith-4.6.1.tgz",
"integrity": "sha512-GK3g5RPZWTRSeLSpgP8Xhra+pnjBC56q9FZYe1d5RN3TJ35dbkGy3YqBSMbyCrlbi+CM9Z3Jk5yTL7RCsqboyQ==", "integrity": "sha512-eWw5r+PYICtEBgrBE5hhlT6aAa75f411bgDz/ZL2KZqYV03USvucsxcHUIlGTDTECs1eunpI7HOV7U+WLDvNdQ==",
"dev": true "dev": true
}, },
"lodash.tail": { "lodash.tail": {
@ -8403,7 +8382,7 @@
}, },
"load-json-file": { "load-json-file": {
"version": "1.1.0", "version": "1.1.0",
"resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-1.1.0.tgz", "resolved": "http://registry.npmjs.org/load-json-file/-/load-json-file-1.1.0.tgz",
"integrity": "sha1-lWkFcI1YtLq0wiYbBPWfMcmTdMA=", "integrity": "sha1-lWkFcI1YtLq0wiYbBPWfMcmTdMA=",
"dev": true, "dev": true,
"requires": { "requires": {
@ -8442,7 +8421,7 @@
}, },
"pify": { "pify": {
"version": "2.3.0", "version": "2.3.0",
"resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", "resolved": "http://registry.npmjs.org/pify/-/pify-2.3.0.tgz",
"integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=",
"dev": true "dev": true
}, },
@ -8614,9 +8593,9 @@
} }
}, },
"mixin-deep": { "mixin-deep": {
"version": "1.3.2", "version": "1.3.1",
"resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.2.tgz", "resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.1.tgz",
"integrity": "sha512-WRoDn//mXBiJ1H40rqa3vH0toePwSsGb45iInWlTySa+Uu4k3tYUSxa2v1KqAiLtvlrSzaExqS1gtk96A9zvEA==", "integrity": "sha512-8ZItLHeEgaqEvd5lYBXfm4EZSFCX29Jb9K+lAHhDKzReKBQKj3R+7NOF6tjqYi9t4oI8VUfaWITJQm86wnXGNQ==",
"dev": true, "dev": true,
"requires": { "requires": {
"for-in": "^1.0.2", "for-in": "^1.0.2",
@ -9003,7 +8982,7 @@
}, },
"semver": { "semver": {
"version": "5.3.0", "version": "5.3.0",
"resolved": "https://registry.npmjs.org/semver/-/semver-5.3.0.tgz", "resolved": "http://registry.npmjs.org/semver/-/semver-5.3.0.tgz",
"integrity": "sha1-myzl094C0XxgEq0yaqa00M9U+U8=", "integrity": "sha1-myzl094C0XxgEq0yaqa00M9U+U8=",
"dev": true "dev": true
} }
@ -9096,7 +9075,7 @@
}, },
"chalk": { "chalk": {
"version": "1.1.3", "version": "1.1.3",
"resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", "resolved": "http://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz",
"integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=",
"dev": true, "dev": true,
"requires": { "requires": {
@ -9133,7 +9112,7 @@
}, },
"strip-ansi": { "strip-ansi": {
"version": "3.0.1", "version": "3.0.1",
"resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", "resolved": "http://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz",
"integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=",
"dev": true, "dev": true,
"requires": { "requires": {
@ -10114,6 +10093,17 @@
"resolved": false, "resolved": false,
"integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8="
}, },
"fstream": {
"version": "1.0.11",
"resolved": false,
"integrity": "sha1-XB+x8RdHcRTwYyoOtLcbPLD9MXE=",
"requires": {
"graceful-fs": "^4.1.2",
"inherits": "~2.0.0",
"mkdirp": ">=0.5 0",
"rimraf": "2"
}
},
"gauge": { "gauge": {
"version": "2.7.4", "version": "2.7.4",
"resolved": false, "resolved": false,
@ -13868,6 +13858,7 @@
"version": "2.6.2", "version": "2.6.2",
"resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz", "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz",
"integrity": "sha512-lreewLK/BlghmxtfH36YYVg1i8IAce4TI7oao75I1g245+6BctqTVQiBP3YUJ9C6DQOXJmkYR9X9fCLtCOJc5w==", "integrity": "sha512-lreewLK/BlghmxtfH36YYVg1i8IAce4TI7oao75I1g245+6BctqTVQiBP3YUJ9C6DQOXJmkYR9X9fCLtCOJc5w==",
"dev": true,
"requires": { "requires": {
"glob": "^7.0.5" "glob": "^7.0.5"
}, },
@ -13876,6 +13867,7 @@
"version": "7.1.3", "version": "7.1.3",
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.3.tgz", "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.3.tgz",
"integrity": "sha512-vcfuiIxogLV4DlGBHIUOwI0IbrJ8HWPc4MU7HzviGeNho/UJDfi6B5p3sHeWIQ0KGIU0Jpxi5ZHxemQfLkkAwQ==", "integrity": "sha512-vcfuiIxogLV4DlGBHIUOwI0IbrJ8HWPc4MU7HzviGeNho/UJDfi6B5p3sHeWIQ0KGIU0Jpxi5ZHxemQfLkkAwQ==",
"dev": true,
"requires": { "requires": {
"fs.realpath": "^1.0.0", "fs.realpath": "^1.0.0",
"inflight": "^1.0.4", "inflight": "^1.0.4",
@ -14033,7 +14025,7 @@
}, },
"load-json-file": { "load-json-file": {
"version": "1.1.0", "version": "1.1.0",
"resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-1.1.0.tgz", "resolved": "http://registry.npmjs.org/load-json-file/-/load-json-file-1.1.0.tgz",
"integrity": "sha1-lWkFcI1YtLq0wiYbBPWfMcmTdMA=", "integrity": "sha1-lWkFcI1YtLq0wiYbBPWfMcmTdMA=",
"dev": true, "dev": true,
"requires": { "requires": {
@ -14046,7 +14038,7 @@
}, },
"os-locale": { "os-locale": {
"version": "1.4.0", "version": "1.4.0",
"resolved": "https://registry.npmjs.org/os-locale/-/os-locale-1.4.0.tgz", "resolved": "http://registry.npmjs.org/os-locale/-/os-locale-1.4.0.tgz",
"integrity": "sha1-IPnxeuKe00XoveWDsT0gCYA8FNk=", "integrity": "sha1-IPnxeuKe00XoveWDsT0gCYA8FNk=",
"dev": true, "dev": true,
"requires": { "requires": {
@ -14075,7 +14067,7 @@
}, },
"pify": { "pify": {
"version": "2.3.0", "version": "2.3.0",
"resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", "resolved": "http://registry.npmjs.org/pify/-/pify-2.3.0.tgz",
"integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=",
"dev": true "dev": true
}, },
@ -14113,7 +14105,7 @@
}, },
"strip-ansi": { "strip-ansi": {
"version": "3.0.1", "version": "3.0.1",
"resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", "resolved": "http://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz",
"integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=",
"dev": true, "dev": true,
"requires": { "requires": {
@ -14249,7 +14241,7 @@
"dependencies": { "dependencies": {
"commander": { "commander": {
"version": "2.8.1", "version": "2.8.1",
"resolved": "https://registry.npmjs.org/commander/-/commander-2.8.1.tgz", "resolved": "http://registry.npmjs.org/commander/-/commander-2.8.1.tgz",
"integrity": "sha1-Br42f+v9oMMwqh4qBy09yXYkJdQ=", "integrity": "sha1-Br42f+v9oMMwqh4qBy09yXYkJdQ=",
"dev": true, "dev": true,
"optional": true, "optional": true,
@ -15169,7 +15161,6 @@
"resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-1.6.2.tgz", "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-1.6.2.tgz",
"integrity": "sha512-rzS0heiNf8Xn7/mpdSVVSMAWAoy9bfb1WOTYC78Z0UQKeKa/CWS8FOq0lKGNa8DWKAn9gxjCvMLYc5PGXYlK2A==", "integrity": "sha512-rzS0heiNf8Xn7/mpdSVVSMAWAoy9bfb1WOTYC78Z0UQKeKa/CWS8FOq0lKGNa8DWKAn9gxjCvMLYc5PGXYlK2A==",
"dev": true, "dev": true,
"optional": true,
"requires": { "requires": {
"bl": "^1.0.0", "bl": "^1.0.0",
"buffer-alloc": "^1.2.0", "buffer-alloc": "^1.2.0",
@ -15432,8 +15423,7 @@
"version": "1.1.1", "version": "1.1.1",
"resolved": "https://registry.npmjs.org/to-buffer/-/to-buffer-1.1.1.tgz", "resolved": "https://registry.npmjs.org/to-buffer/-/to-buffer-1.1.1.tgz",
"integrity": "sha512-lx9B5iv7msuFYE3dytT+KE5tap+rNYw+K4jVkb9R/asAb+pbBSM17jtunHplhBe6RRJdZx3Pn2Jph24O32mOVg==", "integrity": "sha512-lx9B5iv7msuFYE3dytT+KE5tap+rNYw+K4jVkb9R/asAb+pbBSM17jtunHplhBe6RRJdZx3Pn2Jph24O32mOVg==",
"dev": true, "dev": true
"optional": true
}, },
"to-fast-properties": { "to-fast-properties": {
"version": "2.0.0", "version": "2.0.0",
@ -16608,7 +16598,7 @@
}, },
"strip-ansi": { "strip-ansi": {
"version": "3.0.1", "version": "3.0.1",
"resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", "resolved": "http://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz",
"integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=",
"dev": true, "dev": true,
"requires": { "requires": {
@ -16710,7 +16700,7 @@
"dependencies": { "dependencies": {
"async": { "async": {
"version": "1.0.0", "version": "1.0.0",
"resolved": "https://registry.npmjs.org/async/-/async-1.0.0.tgz", "resolved": "http://registry.npmjs.org/async/-/async-1.0.0.tgz",
"integrity": "sha1-+PwEyjoTeErenhZBr5hXjPvWR6k=" "integrity": "sha1-+PwEyjoTeErenhZBr5hXjPvWR6k="
} }
} }

View file

@ -36,12 +36,11 @@
"@fortawesome/fontawesome-svg-core": "^1.2.8", "@fortawesome/fontawesome-svg-core": "^1.2.8",
"@fortawesome/free-solid-svg-icons": "^5.5.0", "@fortawesome/free-solid-svg-icons": "^5.5.0",
"@fortawesome/react-fontawesome": "^0.1.3", "@fortawesome/react-fontawesome": "^0.1.3",
"axios": "^0.18.1", "axios": "^0.18.0",
"bcrypt": "^3.0.3", "bcrypt": "^3.0.3",
"body-parser": "^1.18.3", "body-parser": "^1.18.3",
"connect-multiparty": "^2.2.0", "connect-multiparty": "^2.2.0",
"cookie-session": "^2.0.0-beta.3", "cookie-session": "^2.0.0-beta.3",
"cors": "^2.8.5",
"express": "^4.16.4", "express": "^4.16.4",
"express-handlebars": "^3.0.0", "express-handlebars": "^3.0.0",
"express-http-context": "^1.2.0", "express-http-context": "^1.2.0",
@ -53,7 +52,7 @@
"inquirer": "^5.2.0", "inquirer": "^5.2.0",
"ip": "^1.1.5", "ip": "^1.1.5",
"isbot": "^2.2.1", "isbot": "^2.2.1",
"lodash": "^4.17.13", "lodash": "^4.17.11",
"make-dir": "^1.3.0", "make-dir": "^1.3.0",
"mime-types": "^2.1.21", "mime-types": "^2.1.21",
"module-alias": "^2.1.0", "module-alias": "^2.1.0",

View file

@ -82,7 +82,6 @@ export default (db, table, sequelize) => ({
}; };
const selectWhere = { const selectWhere = {
...whereClause, ...whereClause,
claim_type: 1,
publisher_id: channelClaimId, publisher_id: channelClaimId,
}; };
return await table return await table
@ -104,7 +103,6 @@ export default (db, table, sequelize) => ({
.findAll({ .findAll({
where: { where: {
name: claimName, name: claimName,
claim_type: 1,
publisher_id: channelClaimId, publisher_id: channelClaimId,
bid_state: { [sequelize.Op.or]: ['Controlling', 'Active', 'Accepted'] }, bid_state: { [sequelize.Op.or]: ['Controlling', 'Active', 'Accepted'] },
}, },
@ -203,10 +201,6 @@ export default (db, table, sequelize) => ({
} }
return claimArray[0]; return claimArray[0];
})
.catch(error => {
logger.verbose(`resolveClaim failed: ${error}`)
reject(error);
}); });
}, },
@ -216,7 +210,6 @@ export default (db, table, sequelize) => ({
.findAll({ .findAll({
where: { where: {
name: claimName, name: claimName,
claim_type: 1,
publisher_id: channelId, publisher_id: channelId,
}, },
}) })

View file

@ -9,28 +9,28 @@ const authenticateUser = require('../publish/authentication.js');
*/ */
const claimAbandon = async (req, res) => { const claimAbandon = async (req, res) => {
const { outpoint } = req.body; const {claimId} = req.body;
const { user } = req; const {user} = req;
try { try {
const [channel, claim] = await Promise.all([ const [channel, claim] = await Promise.all([
authenticateUser(user.channelName, null, null, user), authenticateUser(user.channelName, null, null, user),
db.Claim.findOne({ where: { outpoint } }), db.Claim.findOne({where: {claimId}}),
]); ]);
if (!claim) throw new Error('That channel does not exist'); if (!claim) throw new Error('That channel does not exist');
if (!channel.channelName) throw new Error("You don't own this channel"); if (!channel.channelName) throw new Error('You don\'t own this channel');
await abandonClaim({ outpoint }); await abandonClaim({claimId});
const file = await db.File.findOne({ where: { outpoint } }); const file = await db.File.findOne({where: {claimId}});
await Promise.all([ await Promise.all([
deleteFile(file.filePath), deleteFile(file.filePath),
db.File.destroy({ where: { outpoint } }), db.File.destroy({where: {claimId}}),
db.Claim.destroy({ where: { outpoint } }), db.Claim.destroy({where: {claimId}}),
]); ]);
logger.debug(`Claim abandoned: ${outpoint}`); logger.debug(`Claim abandoned: ${claimId}`);
res.status(200).json({ res.status(200).json({
success: true, success: true,
message: `Claim with outpoint ${outpoint} abandonded`, message: `Claim with id ${claimId} abandonded`,
}); });
} catch (error) { } catch (error) {
logger.error('abandon claim error:', error); logger.error('abandon claim error:', error);

View file

@ -64,19 +64,18 @@ const getClaimIdAndServeAsset = (
claimDataValues.outpoint || claimDataValues.outpoint ||
`${claimDataValues.transaction_hash_id}:${claimDataValues.vout}`; `${claimDataValues.transaction_hash_id}:${claimDataValues.vout}`;
logger.debug('Outpoint:', outpoint); logger.debug('Outpoint:', outpoint);
return db.Blocked.isNotBlocked(outpoint) return db.Blocked.isNotBlocked(outpoint).then(() => {
// .then(() => {
// If content was found, is approved, and not blocked - log a view. // If content was found, is approved, and not blocked - log a view.
// if (headers && headers['user-agent'] && /LBRY/.test(headers['user-agent']) === false) { if (headers && headers['user-agent'] && /LBRY/.test(headers['user-agent']) === false) {
// db.Views.create({ db.Views.create({
// time: Date.now(), time: Date.now(),
// isChannel: false, isChannel: false,
// claimId: claimDataValues.claim_id || claimDataValues.claimId, claimId: claimDataValues.claim_id || claimDataValues.claimId,
// publisherId: claimDataValues.publisher_id || claimDataValues.certificateId, publisherId: claimDataValues.publisher_id || claimDataValues.certificateId,
// ip, ip,
// }); });
// } }
// }); });
}) })
.then(() => { .then(() => {
return db.File.findOne({ return db.File.findOne({

View file

@ -20,7 +20,10 @@ const { setupBlockList } = require('./utils/blockList');
const speechPassport = require('./speechPassport'); const speechPassport = require('./speechPassport');
const processTrending = require('./utils/processTrending'); const processTrending = require('./utils/processTrending');
const { setRouteDataInContextMiddleware } = require('./middleware/httpContextMiddleware'); const {
logMetricsMiddleware,
setRouteDataInContextMiddleware,
} = require('./middleware/logMetricsMiddleware');
const { const {
details: { port: PORT, blockListEndpoint }, details: { port: PORT, blockListEndpoint },
@ -142,7 +145,7 @@ function Server() {
app[routeMethod]( app[routeMethod](
routePath, routePath,
// logMetricsMiddleware, logMetricsMiddleware,
setRouteDataInContextMiddleware(routePath, routeData), setRouteDataInContextMiddleware(routePath, routeData),
...controllers ...controllers
); );

View file

@ -73,14 +73,13 @@ module.exports = {
}); });
}); });
}, },
async abandonClaim({ outpoint }) { async abandonClaim({ claimId }) {
logger.debug(`lbryApi >> Abandon claim "${outpoint}"`); logger.debug(`lbryApi >> Abandon claim "${claimId}"`);
const gaStartTime = Date.now(); const gaStartTime = Date.now();
const [txid, nout] = outpoint.split(':');
try { try {
const abandon = await axios.post(lbrynetUri, { const abandon = await axios.post(lbrynetUri, {
method: 'stream_abandon', method: 'claim_abandon',
params: { txid: txid, nout: Number(nout) }, params: { claim_id: claimId },
}); });
sendGATimingEvent('lbrynet', 'abandonClaim', 'ABANDON_CLAIM', gaStartTime, Date.now()); sendGATimingEvent('lbrynet', 'abandonClaim', 'ABANDON_CLAIM', gaStartTime, Date.now());
return abandon.data; return abandon.data;

View file

@ -5,13 +5,11 @@ const {
publishing: { publishingChannelWhitelist }, publishing: { publishingChannelWhitelist },
} = require('@config/siteConfig'); } = require('@config/siteConfig');
const ipBanFile = './site/config/ipBan.txt'; const ipBanFile = './site/config/ipBan.txt';
const ipWhitelist = './site/config/ipWhitelist.txt';
const forbiddenMessage = const forbiddenMessage =
'<h1>Forbidden</h1>If you are seeing this by mistake, please contact us using <a href="https://chat.lbry.com/">https://chat.lbry.com/</a>'; '<h1>Forbidden</h1>If you are seeing this by mistake, please contact us using <a href="https://chat.lbry.com/">https://chat.lbry.com/</a>';
const maxPublishesInTenMinutes = 20;
let ipCounts = {}; let ipCounts = {};
let blockedAddresses = []; let blockedAddresses = [];
let whitelistedAddresses = [];
if (fs.existsSync(ipBanFile)) { if (fs.existsSync(ipBanFile)) {
const lineReader = require('readline').createInterface({ const lineReader = require('readline').createInterface({
@ -25,28 +23,9 @@ if (fs.existsSync(ipBanFile)) {
}); });
} }
// If a file called ipWhitelist.txt exists
// Please comment above each whitelisted IP why/who/when etc
// # Jim because he's awesome - January 2018
if (fs.existsSync(ipWhitelist)) {
const lineReader = require('readline').createInterface({
input: require('fs').createReadStream(ipWhitelist),
});
lineReader.on('line', line => {
if (line && line !== '' && line[0] !== '#') {
whitelistedAddresses.push(line);
}
});
}
const autoblockPublishMiddleware = (req, res, next) => { const autoblockPublishMiddleware = (req, res, next) => {
let ip = (req.headers['x-forwarded-for'] || req.connection.remoteAddress).split(/,\s?/)[0]; let ip = (req.headers['x-forwarded-for'] || req.connection.remoteAddress).split(/,\s?/)[0];
if (whitelistedAddresses.indexOf(ip) !== -1) {
next();
return;
}
if (blockedAddresses.indexOf(ip) !== -1) { if (blockedAddresses.indexOf(ip) !== -1) {
res.status(403).send(forbiddenMessage); res.status(403).send(forbiddenMessage);
res.end(); res.end();
@ -65,7 +44,7 @@ const autoblockPublishMiddleware = (req, res, next) => {
} }
}, 600000 /* 10 minute retainer */); }, 600000 /* 10 minute retainer */);
if (count === maxPublishesInTenMinutes) { if (count === 10) {
logger.error(`Banning IP: ${ip}`); logger.error(`Banning IP: ${ip}`);
blockedAddresses.push(ip); blockedAddresses.push(ip);
res.status(403).send(forbiddenMessage); res.status(403).send(forbiddenMessage);

View file

@ -1,13 +0,0 @@
const httpContext = require('express-http-context');
function setRouteDataInContextMiddleware(routePath, routeData) {
return function(req, res, next) {
httpContext.set('routePath', routePath);
httpContext.set('routeData', routeData);
next();
};
}
module.exports = {
setRouteDataInContextMiddleware,
};

View file

@ -25,7 +25,6 @@ const publishingConfig = require('../../controllers/api/config/site/publishing')
const getTorList = require('../../controllers/api/tor'); const getTorList = require('../../controllers/api/tor');
const getBlockedList = require('../../controllers/api/blocked'); const getBlockedList = require('../../controllers/api/blocked');
const getOEmbedData = require('../../controllers/api/oEmbed'); const getOEmbedData = require('../../controllers/api/oEmbed');
const cors = require('cors');
export default { export default {
// homepage routes // homepage routes
@ -44,10 +43,10 @@ export default {
'/api/claim/data/:claimName/:claimId' : { controller: [ torCheckMiddleware, claimData ] }, '/api/claim/data/:claimName/:claimId' : { controller: [ torCheckMiddleware, claimData ] },
'/api/claim/get/:name/:claimId' : { controller: [ torCheckMiddleware, claimGet ] }, '/api/claim/get/:name/:claimId' : { controller: [ torCheckMiddleware, claimGet ] },
'/api/claim/list/:name' : { controller: [ torCheckMiddleware, claimList ] }, '/api/claim/list/:name' : { controller: [ torCheckMiddleware, claimList ] },
'/api/claim/long-id' : { method: 'post', controller: [ cors(), torCheckMiddleware, claimLongId ] }, // note: should be a 'get' '/api/claim/long-id' : { method: 'post', controller: [ torCheckMiddleware, claimLongId ] }, // note: should be a 'get'
'/api/claim/publish' : { method: 'post', controller: [ cors(), torCheckMiddleware, autoblockPublishMiddleware, multipartMiddleware, autoblockPublishBodyMiddleware, claimPublish ] }, '/api/claim/publish' : { method: 'post', controller: [ torCheckMiddleware, autoblockPublishMiddleware, multipartMiddleware, autoblockPublishBodyMiddleware, claimPublish ] },
'/api/claim/update' : { method: 'post', controller: [ cors(), torCheckMiddleware, multipartMiddleware, claimUpdate ] }, '/api/claim/update' : { method: 'post', controller: [ torCheckMiddleware, multipartMiddleware, claimUpdate ] },
'/api/claim/abandon' : { method: 'post', controller: [ cors(), torCheckMiddleware, multipartMiddleware, claimAbandon ] }, '/api/claim/abandon' : { method: 'post', controller: [ torCheckMiddleware, multipartMiddleware, claimAbandon ] },
'/api/claim/resolve/:name/:claimId' : { controller: [ torCheckMiddleware, claimResolve ] }, '/api/claim/resolve/:name/:claimId' : { controller: [ torCheckMiddleware, claimResolve ] },
'/api/claim/short-id/:longId/:name' : { controller: [ torCheckMiddleware, claimShortId ] }, '/api/claim/short-id/:longId/:name' : { controller: [ torCheckMiddleware, claimShortId ] },
'/api/claim/views/:claimId' : { controller: [ torCheckMiddleware, claimViews ] }, '/api/claim/views/:claimId' : { controller: [ torCheckMiddleware, claimViews ] },
@ -56,7 +55,7 @@ export default {
// user routes // user routes
'/api/user/password/' : { method: 'put', controller: [ torCheckMiddleware, userPassword ] }, '/api/user/password/' : { method: 'put', controller: [ torCheckMiddleware, userPassword ] },
// configs // configs
'/api/config/site/publishing' : { controller: [ cors(), torCheckMiddleware, publishingConfig ] }, '/api/config/site/publishing' : { controller: [ torCheckMiddleware, publishingConfig ] },
// tor // tor
'/api/tor' : { controller: [ torCheckMiddleware, getTorList ] }, '/api/tor' : { controller: [ torCheckMiddleware, getTorList ] },
// blocked // blocked

View file

@ -2,6 +2,6 @@ module.exports = {
...require('./pages').default, ...require('./pages').default,
...require('./api').default, ...require('./api').default,
...require('./auth').default, ...require('./auth').default,
// ...require('./assets').default, ...require('./assets').default,
...require('./fallback').default, ...require('./fallback').default,
}; };

View file

@ -13,10 +13,8 @@ const awaitFileSize = (outpoint, size, interval, timeout) => {
function checkFileList() { function checkFileList() {
logger.debug('checkFileList'); logger.debug('checkFileList');
return getFileListFileByOutpoint(outpoint).then(result => { return getFileListFileByOutpoint(outpoint).then(result => {
const { items: fileInfos } = result; logger.debug('File List Result', result);
const fileInfo = fileInfos[0]; if (result[0]['completed'] === true || result[0]['written_bytes'] > size) {
logger.debug('File List Result', fileInfo);
if (fileInfo.completed === true || fileInfo.written_bytes > size) {
logger.debug('FILE READY'); logger.debug('FILE READY');
return 'ready'; return 'ready';
} else if (timeout !== 0 && Date.now() - start > timeout) { } else if (timeout !== 0 && Date.now() - start > timeout) {