Progress towards working publish
This commit is contained in:
parent
df954882bc
commit
8325828f6e
11 changed files with 1399 additions and 159 deletions
|
@ -15,6 +15,7 @@ import { selectBadgeNumber } from "selectors/app";
|
|||
import { selectTotalDownloadProgress } from "selectors/file_info";
|
||||
import setBadge from "util/setBadge";
|
||||
import setProgressBar from "util/setProgressBar";
|
||||
import { doFileList } from "actions/file_info";
|
||||
import batchActions from "util/batchActions";
|
||||
|
||||
const { ipcRenderer } = require("electron");
|
||||
|
@ -356,3 +357,92 @@ export function doFetchChannelListMine() {
|
|||
lbry.channel_list_mine().then(callback);
|
||||
};
|
||||
}
|
||||
|
||||
export function doCreateChannel(name, amount) {
|
||||
return function(dispatch, getState) {
|
||||
dispatch({
|
||||
type: types.CREATE_CHANNEL_STARTED,
|
||||
});
|
||||
|
||||
return new Promise((resolve, reject) => {
|
||||
lbry
|
||||
.channel_new({
|
||||
channel_name: name,
|
||||
amount: parseFloat(amount),
|
||||
})
|
||||
.then(
|
||||
channelClaim => {
|
||||
channelClaim.name = name;
|
||||
dispatch({
|
||||
type: types.CREATE_CHANNEL_COMPLETED,
|
||||
data: { channelClaim },
|
||||
});
|
||||
resolve(channelClaim);
|
||||
},
|
||||
err => {
|
||||
resolve(err);
|
||||
}
|
||||
);
|
||||
});
|
||||
};
|
||||
}
|
||||
|
||||
export function doPublish(params) {
|
||||
return function(dispatch, getState) {
|
||||
let uri;
|
||||
const { name, channel_name } = params;
|
||||
if (channel_name) {
|
||||
uri = lbryuri.build({ name: channel_name, path: name }, false);
|
||||
} else {
|
||||
uri = lbryuri.build({ name: name }, false);
|
||||
}
|
||||
const pendingPublish = {
|
||||
name,
|
||||
channel_name,
|
||||
claim_id: "pending_claim_" + uri,
|
||||
txid: "pending_" + uri,
|
||||
nout: 0,
|
||||
outpoint: "pending_" + uri + ":0",
|
||||
time: Date.now(),
|
||||
};
|
||||
|
||||
dispatch({
|
||||
type: types.PUBLISH_STARTED,
|
||||
data: {
|
||||
params,
|
||||
pendingPublish,
|
||||
},
|
||||
});
|
||||
|
||||
return new Promise((resolve, reject) => {
|
||||
const success = claim => {
|
||||
claim.name = params.name;
|
||||
claim.channel_name = params.channel_name;
|
||||
dispatch({
|
||||
type: types.PUBLISH_COMPLETED,
|
||||
data: {
|
||||
claim,
|
||||
uri,
|
||||
pendingPublish,
|
||||
},
|
||||
});
|
||||
dispatch(doFileList());
|
||||
resolve(claim);
|
||||
};
|
||||
const failure = error => {
|
||||
dispatch({
|
||||
type: types.PUBLISH_FAILED,
|
||||
data: {
|
||||
error,
|
||||
params,
|
||||
uri,
|
||||
pendingPublish,
|
||||
},
|
||||
});
|
||||
reject(error);
|
||||
};
|
||||
|
||||
lbry.publish(params).then(success, failure);
|
||||
});
|
||||
};
|
||||
}
|
||||
|
|
|
@ -42,6 +42,40 @@ export class TruncatedText extends React.PureComponent {
|
|||
}
|
||||
}
|
||||
|
||||
export class TruncatedMarkdown extends React.PureComponent {
|
||||
static propTypes = {
|
||||
lines: React.PropTypes.number,
|
||||
};
|
||||
|
||||
static defaultProps = {
|
||||
lines: null,
|
||||
};
|
||||
|
||||
transformMarkdown(text) {
|
||||
// render markdown to html string then trim html tag
|
||||
let htmlString = ReactDOMServer.renderToStaticMarkup(
|
||||
<ReactMarkdown source={this.props.children} />
|
||||
);
|
||||
var txt = document.createElement("textarea");
|
||||
txt.innerHTML = htmlString;
|
||||
return txt.value.replace(/<(?:.|\n)*?>/gm, "");
|
||||
}
|
||||
|
||||
render() {
|
||||
let content = this.props.children && typeof this.props.children === "string"
|
||||
? this.transformMarkdown(this.props.children)
|
||||
: this.props.children;
|
||||
return (
|
||||
<span
|
||||
className="truncated-text"
|
||||
style={{ WebkitLineClamp: this.props.lines }}
|
||||
>
|
||||
{content}
|
||||
</span>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
export class BusyMessage extends React.PureComponent {
|
||||
static propTypes = {
|
||||
message: React.PropTypes.string,
|
||||
|
|
|
@ -68,6 +68,11 @@ export const FETCH_CHANNEL_LIST_MINE_STARTED =
|
|||
"FETCH_CHANNEL_LIST_MINE_STARTED";
|
||||
export const FETCH_CHANNEL_LIST_MINE_COMPLETED =
|
||||
"FETCH_CHANNEL_LIST_MINE_COMPLETED";
|
||||
export const CREATE_CHANNEL_STARTED = "CREATE_CHANNEL_STARTED";
|
||||
export const CREATE_CHANNEL_COMPLETED = "CREATE_CHANNEL_COMPLETED";
|
||||
export const PUBLISH_STARTED = "PUBLISH_STARTED";
|
||||
export const PUBLISH_COMPLETED = "PUBLISH_COMPLETED";
|
||||
export const PUBLISH_FAILED = "PUBLISH_FAILED";
|
||||
|
||||
// Search
|
||||
export const SEARCH_STARTED = "SEARCH_STARTED";
|
||||
|
|
|
@ -203,6 +203,8 @@ lbryuri.build = function(uriObj, includeProto = true, allowExtraProps = false) {
|
|||
/* Takes a parseable LBRY URI and converts it to standard, canonical format (currently this just
|
||||
* consists of adding the lbry:// prefix if needed) */
|
||||
lbryuri.normalize = function(uri) {
|
||||
if (uri.match(/pending_claim/)) return uri;
|
||||
|
||||
const { name, path, bidPosition, claimSequence, claimId } = lbryuri.parse(
|
||||
uri
|
||||
);
|
||||
|
|
|
@ -13,6 +13,8 @@ import {
|
|||
doFetchClaimListMine,
|
||||
doFetchChannelListMine,
|
||||
doResolveUri,
|
||||
doCreateChannel,
|
||||
doPublish,
|
||||
} from "actions/content";
|
||||
import rewards from "rewards";
|
||||
import PublishPage from "./view";
|
||||
|
@ -33,6 +35,8 @@ const perform = dispatch => ({
|
|||
dispatch(doClaimRewardType(rewards.TYPE_FIRST_CHANNEL)),
|
||||
fetchChannelListMine: () => dispatch(doFetchChannelListMine()),
|
||||
resolveUri: uri => dispatch(doResolveUri(uri)),
|
||||
createChannel: (name, amount) => dispatch(doCreateChannel(name, amount)),
|
||||
publish: params => dispatch(doPublish(params)),
|
||||
});
|
||||
|
||||
export default connect(select, perform)(PublishPage);
|
||||
|
|
|
@ -125,16 +125,11 @@ class PublishPage extends React.PureComponent {
|
|||
publishArgs.file_path = this.refs.file.getValue();
|
||||
}
|
||||
|
||||
lbry.publishDeprecated(
|
||||
publishArgs,
|
||||
message => {
|
||||
this.handlePublishStarted();
|
||||
},
|
||||
null,
|
||||
error => {
|
||||
this.handlePublishError(error);
|
||||
}
|
||||
);
|
||||
const success = claim => {};
|
||||
const failure = error => this.handlePublishError(error);
|
||||
|
||||
this.handlePublishStarted();
|
||||
this.props.publish(publishArgs).then(success, failure);
|
||||
};
|
||||
|
||||
if (this.state.isFee) {
|
||||
|
@ -216,6 +211,10 @@ class PublishPage extends React.PureComponent {
|
|||
handleNameChange(event) {
|
||||
var rawName = event.target.value;
|
||||
|
||||
this.nameChanged(rawName);
|
||||
}
|
||||
|
||||
nameChanged(rawName) {
|
||||
if (!rawName) {
|
||||
this.setState({
|
||||
rawName: "",
|
||||
|
@ -233,15 +232,26 @@ class PublishPage extends React.PureComponent {
|
|||
return;
|
||||
}
|
||||
|
||||
let channel = "";
|
||||
if (this.state.channel !== "anonymous") channel = this.state.channel;
|
||||
|
||||
const name = rawName.toLowerCase();
|
||||
const uri = lbryuri.normalize(name);
|
||||
const uri = lbryuri.build({ contentName: name, channelName: channel });
|
||||
this.setState({
|
||||
rawName: rawName,
|
||||
name: name,
|
||||
uri,
|
||||
});
|
||||
|
||||
this.props.resolveUri(uri);
|
||||
if (this.resolveUriTimeout) {
|
||||
clearTimeout(this.resolveUriTimeout);
|
||||
this.resolveUriTimeout = undefined;
|
||||
}
|
||||
const resolve = () => this.props.resolveUri(uri);
|
||||
|
||||
this.resolveUriTimeout = setTimeout(resolve.bind(this), 500, {
|
||||
once: true,
|
||||
});
|
||||
}
|
||||
|
||||
handleBidChange(event) {
|
||||
|
@ -302,40 +312,12 @@ class PublishPage extends React.PureComponent {
|
|||
});
|
||||
}
|
||||
|
||||
handleChannelChange(event) {
|
||||
const channel = event.target.value;
|
||||
|
||||
handleChannelChange(channelName) {
|
||||
this.setState({
|
||||
channel: channel,
|
||||
});
|
||||
}
|
||||
|
||||
handleNewChannelNameChange(event) {
|
||||
const newChannelName = event.target.value.startsWith("@")
|
||||
? event.target.value
|
||||
: "@" + event.target.value;
|
||||
|
||||
if (
|
||||
newChannelName.length > 1 &&
|
||||
!lbryuri.isValidName(newChannelName.substr(1), false)
|
||||
) {
|
||||
this.refs.newChannelName.showError(
|
||||
__("LBRY channel names must contain only letters, numbers and dashes.")
|
||||
);
|
||||
return;
|
||||
} else {
|
||||
this.refs.newChannelName.clearError();
|
||||
}
|
||||
|
||||
this.setState({
|
||||
newChannelName: newChannelName,
|
||||
});
|
||||
}
|
||||
|
||||
handleNewChannelBidChange(event) {
|
||||
this.setState({
|
||||
newChannelBid: event.target.value,
|
||||
channel: channelName,
|
||||
});
|
||||
const nameChanged = () => this.nameChanged(this.state.rawName);
|
||||
setTimeout(nameChanged.bind(this), 500, { once: true });
|
||||
}
|
||||
|
||||
handleTOSChange(event) {
|
||||
|
@ -413,19 +395,26 @@ class PublishPage extends React.PureComponent {
|
|||
getNameBidHelpText() {
|
||||
if (
|
||||
this.state.uri &&
|
||||
this.props.resolvingUris.indexOf(this.state.uri) !== -1
|
||||
this.props.resolvingUris.indexOf(this.state.uri) !== -1 &&
|
||||
this.claim() === undefined
|
||||
) {
|
||||
return <BusyMessage />;
|
||||
} else if (!this.state.name) {
|
||||
return __("Select a URL for this publish.");
|
||||
} else if (!this.claim()) {
|
||||
return __("This URL is unused.");
|
||||
} else if (this.myClaimExists()) {
|
||||
return __(
|
||||
"You have already used this URL. Publishing to it again will update your previous publish."
|
||||
} else if (this.myClaimExists() && !this.state.prefillDone) {
|
||||
return (
|
||||
<Notice>
|
||||
{__("You already have a claim with this name.")}{" "}
|
||||
<Link
|
||||
label={__("Use data from my existing claim")}
|
||||
onClick={() => this.handlePrefillClicked()}
|
||||
/>
|
||||
</Notice>
|
||||
);
|
||||
} else if (this.state.topClaimValue) {
|
||||
if (this.state.topClaimValue === 1) {
|
||||
} else if (this.claim()) {
|
||||
if (this.topClaimValue() === 1) {
|
||||
return (
|
||||
<span>
|
||||
{__(
|
||||
|
@ -439,7 +428,7 @@ class PublishPage extends React.PureComponent {
|
|||
<span>
|
||||
{__(
|
||||
'A deposit of at least "%s" credits is required to win "%s". However, you can still get a permanent URL for any amount.',
|
||||
this.state.topClaimValue,
|
||||
this.topClaimValue(),
|
||||
this.state.name
|
||||
)}
|
||||
</span>
|
||||
|
@ -709,77 +698,11 @@ class PublishPage extends React.PureComponent {
|
|||
</div>
|
||||
</section>
|
||||
|
||||
<section className="card">
|
||||
<div className="card__title-primary">
|
||||
<h4>{__("Identity")}</h4>
|
||||
<div className="card__subtitle">
|
||||
{__("Who created this content?")}
|
||||
</div>
|
||||
</div>
|
||||
<div className="card__content">
|
||||
{this.props.fetchingChannels
|
||||
? <BusyMessage message="Fetching identities" />
|
||||
: <FormRow
|
||||
type="select"
|
||||
tabIndex="1"
|
||||
onChange={event => {
|
||||
this.handleChannelChange(event);
|
||||
}}
|
||||
value={this.state.channel}
|
||||
>
|
||||
<option key="anonymous" value="anonymous">
|
||||
{__("Anonymous")}
|
||||
</option>
|
||||
{this.props.channels.map(({ name }) =>
|
||||
<option key={name} value={name}>{name}</option>
|
||||
)}
|
||||
<option key="new" value="new">
|
||||
{__("New identity...")}
|
||||
</option>
|
||||
</FormRow>}
|
||||
</div>
|
||||
{this.state.channel == "new"
|
||||
? <div className="card__content">
|
||||
<FormRow
|
||||
label={__("Name")}
|
||||
type="text"
|
||||
onChange={event => {
|
||||
this.handleNewChannelNameChange(event);
|
||||
}}
|
||||
ref={newChannelName => {
|
||||
this.refs.newChannelName = newChannelName;
|
||||
}}
|
||||
value={this.state.newChannelName}
|
||||
/>
|
||||
<FormRow
|
||||
label={__("Deposit")}
|
||||
postfix={__("LBC")}
|
||||
step="0.01"
|
||||
min="0"
|
||||
type="number"
|
||||
helper={lbcInputHelp}
|
||||
onChange={event => {
|
||||
this.handleNewChannelBidChange(event);
|
||||
}}
|
||||
value={this.state.newChannelBid}
|
||||
/>
|
||||
<div className="form-row-submit">
|
||||
<Link
|
||||
button="primary"
|
||||
label={
|
||||
!this.state.creatingChannel
|
||||
? __("Create identity")
|
||||
: __("Creating identity...")
|
||||
}
|
||||
onClick={event => {
|
||||
this.handleCreateChannelClick(event);
|
||||
}}
|
||||
disabled={this.state.creatingChannel}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
: null}
|
||||
</section>
|
||||
<ChannelSection
|
||||
{...this.props}
|
||||
handleChannelChange={this.handleChannelChange.bind(this)}
|
||||
channel={this.state.channel}
|
||||
/>
|
||||
|
||||
<section className="card">
|
||||
<div className="card__title-primary">
|
||||
|
@ -795,7 +718,9 @@ class PublishPage extends React.PureComponent {
|
|||
</div>
|
||||
<div className="card__content">
|
||||
<FormRow
|
||||
prefix="lbry://"
|
||||
prefix={`lbry://${this.state.channel === "anonymous"
|
||||
? ""
|
||||
: `${this.state.channel}/`}`}
|
||||
type="text"
|
||||
ref="name"
|
||||
placeholder="myname"
|
||||
|
@ -907,4 +832,177 @@ class PublishPage extends React.PureComponent {
|
|||
}
|
||||
}
|
||||
|
||||
class ChannelSection extends React.PureComponent {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
|
||||
this.state = {
|
||||
newChannelName: "@",
|
||||
newChannelBid: 10,
|
||||
addingChannel: false,
|
||||
};
|
||||
}
|
||||
|
||||
handleChannelChange(event) {
|
||||
const channel = event.target.value;
|
||||
if (channel === "new") this.setState({ addingChannel: true });
|
||||
else {
|
||||
this.setState({ addingChannel: false });
|
||||
this.props.handleChannelChange(event.target.value);
|
||||
}
|
||||
}
|
||||
|
||||
handleNewChannelNameChange(event) {
|
||||
const newChannelName = event.target.value.startsWith("@")
|
||||
? event.target.value
|
||||
: "@" + event.target.value;
|
||||
|
||||
if (
|
||||
newChannelName.length > 1 &&
|
||||
!lbryuri.isValidName(newChannelName.substr(1), false)
|
||||
) {
|
||||
this.refs.newChannelName.showError(
|
||||
__("LBRY channel names must contain only letters, numbers and dashes.")
|
||||
);
|
||||
return;
|
||||
} else {
|
||||
this.refs.newChannelName.clearError();
|
||||
}
|
||||
|
||||
this.setState({
|
||||
newChannelName,
|
||||
});
|
||||
}
|
||||
|
||||
handleNewChannelBidChange(event) {
|
||||
this.setState({
|
||||
newChannelBid: event.target.value,
|
||||
});
|
||||
}
|
||||
|
||||
handleCreateChannelClick(event) {
|
||||
if (this.state.newChannelName.length < 5) {
|
||||
this.refs.newChannelName.showError(
|
||||
__("LBRY channel names must be at least 4 characters in length.")
|
||||
);
|
||||
return;
|
||||
}
|
||||
|
||||
this.setState({
|
||||
creatingChannel: true,
|
||||
});
|
||||
|
||||
const newChannelName = this.state.newChannelName;
|
||||
const amount = parseFloat(this.state.newChannelBid);
|
||||
this.setState({
|
||||
creatingChannel: true,
|
||||
});
|
||||
const success = (() => {
|
||||
this.setState({
|
||||
creatingChannel: false,
|
||||
addingChannel: false,
|
||||
channel: newChannelName,
|
||||
});
|
||||
this.props.handleChannelChange(newChannelName);
|
||||
}).bind(this);
|
||||
const failure = (err => {
|
||||
this.setState({
|
||||
creatingChannel: false,
|
||||
});
|
||||
this.refs.newChannelName.showError(
|
||||
__("Unable to create channel due to an internal error.")
|
||||
);
|
||||
}).bind(this);
|
||||
this.props.createChannel(newChannelName, amount).then(success, failure);
|
||||
}
|
||||
|
||||
render() {
|
||||
const lbcInputHelp = __(
|
||||
"This LBC remains yours and the deposit can be undone at any time."
|
||||
);
|
||||
|
||||
const { fetchingChannels, channels } = this.props;
|
||||
|
||||
let channelContent = [];
|
||||
if (channels.length > 0) {
|
||||
channelContent.push(
|
||||
<FormRow
|
||||
key="channel"
|
||||
type="select"
|
||||
tabIndex="1"
|
||||
onChange={this.handleChannelChange.bind(this)}
|
||||
value={this.props.channel}
|
||||
>
|
||||
<option key="anonymous" value="anonymous">
|
||||
{__("Anonymous")}
|
||||
</option>
|
||||
{this.props.channels.map(({ name }) =>
|
||||
<option key={name} value={name}>{name}</option>
|
||||
)}
|
||||
<option key="new" value="new">
|
||||
{__("New identity...")}
|
||||
</option>
|
||||
</FormRow>
|
||||
);
|
||||
if (fetchingChannels) {
|
||||
channelContent.push(
|
||||
<BusyMessage message="Updating channels" key="loading" />
|
||||
);
|
||||
}
|
||||
} else if (fetchingChannels) {
|
||||
channelContent.push(
|
||||
<BusyMessage message="Loading channels" key="loading" />
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<section className="card">
|
||||
<div className="card__title-primary">
|
||||
<h4>{__("Identity")}</h4>
|
||||
<div className="card__subtitle">
|
||||
{__("Who created this content?")}
|
||||
</div>
|
||||
</div>
|
||||
<div className="card__content">
|
||||
{channelContent}
|
||||
</div>
|
||||
{this.state.addingChannel &&
|
||||
<div className="card__content">
|
||||
<FormRow
|
||||
label={__("Name")}
|
||||
type="text"
|
||||
onChange={event => {
|
||||
this.handleNewChannelNameChange(event);
|
||||
}}
|
||||
value={this.state.newChannelName}
|
||||
/>
|
||||
<FormRow
|
||||
label={__("Deposit")}
|
||||
postfix="LBC"
|
||||
step="0.1"
|
||||
min="0"
|
||||
type="number"
|
||||
helper={lbcInputHelp}
|
||||
ref="newChannelName"
|
||||
onChange={this.handleNewChannelBidChange.bind(this)}
|
||||
value={this.state.newChannelBid}
|
||||
/>
|
||||
<div className="form-row-submit">
|
||||
<Link
|
||||
button="primary"
|
||||
label={
|
||||
!this.state.creatingChannel
|
||||
? __("Create identity")
|
||||
: __("Creating identity...")
|
||||
}
|
||||
onClick={this.handleCreateChannelClick.bind(this)}
|
||||
disabled={this.state.creatingChannel}
|
||||
/>
|
||||
</div>
|
||||
</div>}
|
||||
</section>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
export default PublishPage;
|
||||
|
|
|
@ -15,7 +15,13 @@ reducers[types.RESOLVE_URI_COMPLETED] = function(state, action) {
|
|||
byUri[uri] = claim.claim_id;
|
||||
} else if (claim === undefined && certificate !== undefined) {
|
||||
byId[certificate.claim_id] = certificate;
|
||||
byUri[uri] = certificate.claim_id;
|
||||
// Don't point URI at the channel certificate unless it actually is
|
||||
// a channel URI. This is brittle.
|
||||
if (!uri.split(certificate.name)[1].match(/\//)) {
|
||||
byUri[uri] = certificate.claim_id;
|
||||
} else {
|
||||
byUri[uri] = null;
|
||||
}
|
||||
} else {
|
||||
byUri[uri] = null;
|
||||
}
|
||||
|
@ -108,6 +114,34 @@ reducers[types.ABANDON_CLAIM_COMPLETED] = function(state, action) {
|
|||
});
|
||||
};
|
||||
|
||||
reducers[types.CREATE_CHANNEL_COMPLETED] = function(state, action) {
|
||||
const { channelClaim } = action.data;
|
||||
const byId = Object.assign({}, state.byId);
|
||||
const myChannelClaims = new Set(state.myChannelClaims);
|
||||
|
||||
byId[channelClaim.claim_id] = channelClaim;
|
||||
myChannelClaims.add(channelClaim.claim_id);
|
||||
|
||||
return Object.assign({}, state, {
|
||||
byId,
|
||||
myChannelClaims,
|
||||
});
|
||||
};
|
||||
|
||||
reducers[types.PUBLISH_COMPLETED] = function(state, action) {
|
||||
const { claim } = action.data;
|
||||
const byId = Object.assign({}, state.byId);
|
||||
const myClaims = new Set(state.myClaims);
|
||||
|
||||
byId[claim.claim_id] = claim;
|
||||
myClaims.add(claim.claim_id);
|
||||
|
||||
return Object.assign({}, state, {
|
||||
byId,
|
||||
myClaims,
|
||||
});
|
||||
};
|
||||
|
||||
export default function reducer(state = defaultState, action) {
|
||||
const handler = reducers[action.type];
|
||||
if (handler) return handler(state, action);
|
||||
|
|
|
@ -12,8 +12,9 @@ reducers[types.FILE_LIST_STARTED] = function(state, action) {
|
|||
|
||||
reducers[types.FILE_LIST_COMPLETED] = function(state, action) {
|
||||
const { fileInfos } = action.data;
|
||||
|
||||
const newByOutpoint = Object.assign({}, state.byOutpoint);
|
||||
const pendingByOutpoint = Object.assign({}, state.pendingByOutpoint);
|
||||
|
||||
fileInfos.forEach(fileInfo => {
|
||||
const { outpoint } = fileInfo;
|
||||
|
||||
|
@ -23,6 +24,7 @@ reducers[types.FILE_LIST_COMPLETED] = function(state, action) {
|
|||
return Object.assign({}, state, {
|
||||
isFileListPending: false,
|
||||
byOutpoint: newByOutpoint,
|
||||
pendingByOutpoint,
|
||||
});
|
||||
};
|
||||
|
||||
|
@ -136,6 +138,61 @@ reducers[types.LOADING_VIDEO_FAILED] = function(state, action) {
|
|||
});
|
||||
};
|
||||
|
||||
reducers[types.PUBLISH_STARTED] = function(state, action) {
|
||||
const { pendingPublish } = action.data;
|
||||
const pendingByOutpoint = Object.assign({}, state.pendingByOutpoint);
|
||||
|
||||
pendingByOutpoint[pendingPublish.outpoint] = pendingPublish;
|
||||
|
||||
return Object.assign({}, state, {
|
||||
pendingByOutpoint,
|
||||
});
|
||||
};
|
||||
|
||||
reducers[types.PUBLISH_COMPLETED] = function(state, action) {
|
||||
const { pendingPublish } = action.data;
|
||||
const pendingByOutpoint = Object.assign({}, state.pendingByOutpoint);
|
||||
|
||||
delete pendingByOutpoint[pendingPublish.outpoint];
|
||||
|
||||
return Object.assign({}, state, {
|
||||
pendingByOutpoint,
|
||||
});
|
||||
};
|
||||
|
||||
reducers[types.PUBLISH_FAILED] = function(state, action) {
|
||||
const { pendingPublish } = action.data;
|
||||
const pendingByOutpoint = Object.assign({}, state.pendingByOutpoint);
|
||||
|
||||
delete pendingByOutpoint[pendingPublish.outpoint];
|
||||
|
||||
return Object.assign({}, state, {
|
||||
pendingByOutpoint,
|
||||
});
|
||||
};
|
||||
|
||||
// reducers[types.PUBLISH_COMPLETED] = function(state, action) {
|
||||
// const { claim } = action.data;
|
||||
// const uri = lbryuri.build({
|
||||
// txid: claim.txId
|
||||
// })
|
||||
// const newPendingPublish = {
|
||||
// name,
|
||||
// channel_name,
|
||||
// claim_id: "pending_claim_" + uri,
|
||||
// txid: "pending_" + uri,
|
||||
// nout: 0,
|
||||
// outpoint: "pending_" + uri + ":0",
|
||||
// time: Date.now(),
|
||||
// };
|
||||
// const fileInfos = Object.assign({}, state.fileInfos)
|
||||
// fileInfos[newPendingPublish.outpoint] = newPendingPublish
|
||||
|
||||
// return Object.assign({}, state, {
|
||||
// fileInfos,
|
||||
// })
|
||||
// }
|
||||
|
||||
export default function reducer(state = defaultState, action) {
|
||||
const handler = reducers[action.type];
|
||||
if (handler) return handler(state, action);
|
||||
|
|
|
@ -69,6 +69,11 @@ export const makeSelectLoadingForUri = () => {
|
|||
return createSelector(selectLoadingForUri, loading => !!loading);
|
||||
};
|
||||
|
||||
export const selectFileInfosPendingPublish = createSelector(
|
||||
_selectState,
|
||||
state => Object.values(state.pendingByOutpoint || {})
|
||||
);
|
||||
|
||||
export const selectFileInfosDownloaded = createSelector(
|
||||
selectFileInfosByOutpoint,
|
||||
selectMyClaimsOutpoints,
|
||||
|
@ -87,24 +92,17 @@ export const selectFileInfosDownloaded = createSelector(
|
|||
}
|
||||
);
|
||||
|
||||
export const selectFileInfosPendingPublish = createSelector(
|
||||
_selectState,
|
||||
state => {
|
||||
return lbry.getPendingPublishes();
|
||||
}
|
||||
);
|
||||
|
||||
export const selectFileInfosPublished = createSelector(
|
||||
selectFileInfosByOutpoint,
|
||||
selectFileInfosPendingPublish,
|
||||
selectMyClaimsOutpoints,
|
||||
(byOutpoint, pendingFileInfos, outpoints) => {
|
||||
selectFileInfosPendingPublish,
|
||||
(byOutpoint, outpoints, pendingPublish) => {
|
||||
const fileInfos = [];
|
||||
outpoints.forEach(outpoint => {
|
||||
const fileInfo = byOutpoint[outpoint];
|
||||
if (fileInfo) fileInfos.push(fileInfo);
|
||||
});
|
||||
return [...fileInfos, ...pendingFileInfos];
|
||||
return fileInfos;
|
||||
}
|
||||
);
|
||||
|
||||
|
@ -133,7 +131,6 @@ export const selectFileInfosByUri = createSelector(
|
|||
if (fileInfo) fileInfos[uri] = fileInfo;
|
||||
}
|
||||
});
|
||||
|
||||
return fileInfos;
|
||||
}
|
||||
);
|
||||
|
|
|
@ -92,12 +92,16 @@ const saveClaimsFilter = createFilter("claims", [
|
|||
"myClaims",
|
||||
"myChannelClaims",
|
||||
]);
|
||||
const saveFileInfosFilter = createFilter("fileInfo", [
|
||||
"fileInfos",
|
||||
"pendingByOutpoint",
|
||||
]);
|
||||
|
||||
const persistOptions = {
|
||||
whitelist: ["claims"],
|
||||
whitelist: ["claims", "fileInfo"],
|
||||
// Order is important. Needs to be compressed last or other transforms can't
|
||||
// read the data
|
||||
transforms: [saveClaimsFilter, compressor],
|
||||
transforms: [saveClaimsFilter, saveFileInfosFilter, compressor],
|
||||
debounce: 1000,
|
||||
storage: localForage,
|
||||
};
|
||||
|
|
957
ui/yarn.lock
957
ui/yarn.lock
File diff suppressed because it is too large
Load diff
Loading…
Reference in a new issue