Fix autoplay infinite loop
## Issue Closes 3661: Autoplay + Related go into loops ( infinite ) sometimes ## GUI Push the actual "next" item into the top of the list. ## History search 1. Skip if the next item is itself. 2. The URL stored in the history comes in various forms, so a direct comparison won't work. - There's also a weird case where the URL differs by just a little (p.09 vs p-09), but with the same claim ID: lbry://vacuum-tube-computer-p.09-–-building#5212bc8bc63c373e2bf1ebc5b765595ed7b6514d lbry://vacuum-tube-computer-p-09-–-building#5212bc8bc63c373e2bf1ebc5b765595ed7b6514d Check the claim_id as well to cover cases like these.
This commit is contained in:
parent
59b7975085
commit
ede83f358d
3 changed files with 39 additions and 4 deletions
|
@ -3,17 +3,19 @@ import { makeSelectClaimForUri, makeSelectClaimIsNsfw } from 'lbry-redux';
|
|||
import { doSearch } from 'redux/actions/search';
|
||||
import { makeSelectRecommendedContentForUri, selectIsSearching } from 'redux/selectors/search';
|
||||
import { selectUserVerifiedEmail } from 'redux/selectors/user';
|
||||
import { makeSelectNextUnplayedRecommended } from 'redux/selectors/content';
|
||||
import RecommendedVideos from './view';
|
||||
|
||||
const select = (state, props) => ({
|
||||
claim: makeSelectClaimForUri(props.uri)(state),
|
||||
mature: makeSelectClaimIsNsfw(props.uri)(state),
|
||||
recommendedContent: makeSelectRecommendedContentForUri(props.uri)(state),
|
||||
nextRecommendedUri: makeSelectNextUnplayedRecommended(props.uri)(state),
|
||||
isSearching: selectIsSearching(state),
|
||||
isAuthenticated: selectUserVerifiedEmail(state),
|
||||
});
|
||||
|
||||
const perform = dispatch => ({
|
||||
const perform = (dispatch) => ({
|
||||
search: (query, options) => dispatch(doSearch(query, options)),
|
||||
});
|
||||
|
||||
|
|
|
@ -15,6 +15,7 @@ type Props = {
|
|||
uri: string,
|
||||
claim: ?StreamClaim,
|
||||
recommendedContent: Array<string>,
|
||||
nextRecommendedUri: string,
|
||||
isSearching: boolean,
|
||||
search: (string, Options) => void,
|
||||
mature: boolean,
|
||||
|
@ -22,7 +23,7 @@ type Props = {
|
|||
};
|
||||
|
||||
export default function RecommendedContent(props: Props) {
|
||||
const { uri, claim, search, mature, recommendedContent, isSearching, isAuthenticated } = props;
|
||||
const { uri, claim, search, mature, recommendedContent, nextRecommendedUri, isSearching, isAuthenticated } = props;
|
||||
const isMobile = useIsMobile();
|
||||
const isMedium = useIsMediumScreen();
|
||||
|
||||
|
@ -43,6 +44,22 @@ export default function RecommendedContent(props: Props) {
|
|||
}
|
||||
}, [stringifiedClaim, mature, search]);
|
||||
|
||||
function reorderList(recommendedContent) {
|
||||
let newList = recommendedContent;
|
||||
if (newList) {
|
||||
const index = newList.indexOf(nextRecommendedUri);
|
||||
if (index === -1) {
|
||||
// This would be weird. Shouldn't happen since it is derived from the same list.
|
||||
} else if (index !== 0) {
|
||||
// Swap the "next" item to the top of the list
|
||||
const a = newList[0];
|
||||
newList[0] = nextRecommendedUri;
|
||||
newList[index] = a;
|
||||
}
|
||||
}
|
||||
return newList;
|
||||
}
|
||||
|
||||
React.useEffect(() => {
|
||||
getRecommendedContent();
|
||||
}, [uri, getRecommendedContent]);
|
||||
|
@ -57,7 +74,7 @@ export default function RecommendedContent(props: Props) {
|
|||
<ClaimList
|
||||
type="small"
|
||||
loading={isSearching}
|
||||
uris={recommendedContent}
|
||||
uris={reorderList(recommendedContent)}
|
||||
hideMenu={isMobile}
|
||||
injectedItem={
|
||||
SHOW_ADS && IS_WEB ? (
|
||||
|
|
|
@ -123,7 +123,23 @@ export const makeSelectNextUnplayedRecommended = (uri: string) =>
|
|||
continue;
|
||||
}
|
||||
|
||||
if (!history.some((item) => item.uri === recommendedForUri[i])) {
|
||||
const recommendedUriInfo = parseURI(recommendedUri);
|
||||
const recommendedUriShort = recommendedUriInfo.claimName + '#' + recommendedUriInfo.claimId.substring(0, 1);
|
||||
|
||||
if (claimsByUri[uri] && claimsByUri[uri].claim_id === recommendedUriInfo.claimId) {
|
||||
// Skip myself (same claim ID)
|
||||
continue;
|
||||
}
|
||||
|
||||
if (
|
||||
!history.some((h) => {
|
||||
const directMatch = h.uri === recommendedForUri[i];
|
||||
const shortUriMatch = h.uri.includes(recommendedUriShort);
|
||||
const idMatch = claimsByUri[h.uri] && claimsByUri[h.uri].claim_id === recommendedUriInfo.claimId;
|
||||
|
||||
return directMatch || shortUriMatch || idMatch;
|
||||
})
|
||||
) {
|
||||
return recommendedForUri[i];
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue