我遇到了打印并返回所有vidDuration
值的异步方法的问题,然后为每个videoId放置了viewCount
个值,但vidDuration
只重复了最后一个值收到并将其分配给明显错误的所有videoId
。
我尝试在循环中设置一个名为tempArray
的临时数组,用于存储它所执行的每个vidDuration
值,然后将它们打印到每个vidDuration
,但是又一次,它在输出中循环,但是阵列中有许多值并且复制了视频,这是我不想要的。我评论了涉及tempArray
的行并恢复了工作问题。
根据我的理解,异步方法打印了所有持续时间值而没有输出,就像它被卡在那里直到它完成并解决然后它循环viewCount
并输出完全正常。我想知道如何以编程逻辑的方式解决这个问题?
脚本:
var channelName = 'ExampleChannel';
var vidWidth = 500;
var vidHeight = 400;
var vidResults = 15; /* # of videos to show at once - max 50 */
var vidDuration = "";
var viewCount = 0;
var videoId = "";
$(document).ready(function() {
$.get( // get channel name and load data
"https://www.googleapis.com/youtube/v3/channels",
{
part: 'contentDetails',
forUsername: channelName,
key: 'XXXXXXXX'
},
function(data)
{
$.each(data.items,
function(i, item) {
console.log(item); // log all items to console
var playlistId = item.contentDetails.relatedPlaylists.uploads;
getPlaylists(playlistId);
})
}
);
// function that gets the playlists
function getPlaylists(playlistId)
{
$.get(
"https://www.googleapis.com/youtube/v3/playlistItems",
{
part: 'snippet',
maxResults: vidResults,
playlistId: playlistId,
key: 'XXXXXXXX'
},
// print the results
function(data)
{
var output;
/*var tempArray = new Array();*/ // temporary array for storing video duration values
$.each(data.items,
function(i, item) {
console.log(item);
var vidTitle = item.snippet.title; // video title
var vidDesc = item.snippet.description; // video description
var videoId = item.snippet.resourceId.videoId; // video id
// check if description is empty
if(vidDesc == null || vidDesc == "")
{
vidDesc = "No description was written."; // FIX: test msg to see where it still shows up
$('#desc').remove(); // remove video description
}
else vidDesc = item.snippet.description;
getVideoDuration(videoId).done(function(r){
vidDuration = r;
console.log(r);
/*tempArray[i] = r;*/ // store value into each array index
/*console.log("Array:", tempArray[i], tempArray);*/ // log to console
/*i++;*/ // increment
getViewCount(videoId).done(function(r){
viewCount = r;
console.log(r);
//vidDuration = getVideoDuration(videoId);
//viewCount = getViewCount(videoId);
// temp array index to loop thru array
/*$.each(tempArray, function(i){
vidDuration = tempArray[i]; // assign index value to vidDuration
console.log("In Each vidDuration: ", vidDuration);
i++;
});*/
console.log("id: " + videoId + " duration: " + vidDuration + " viewCount: " + viewCount); // return value in console
output = '<li><iframe height="' + vidHeight + '" width="' + vidWidth + '" src=\"//www.youtube.com/embed/' + videoId + '\"></iframe></li><div id="title">' + vidTitle + '</div><div id="desc">' + vidDesc + '</div><div id="duration">Length: ' + vidDuration + '</div><div id="stats">View Count: ' + viewCount + '</div>';
// Append results to list tag
$('#results').append(output);
}); // end of getVideoDuration(videoId).done
}); // end of getViewCount(videoId).done
});
/*console.log("TEMPARRAY[]",tempArray);*/ // print entire array
}
);
}
// return video duration
function getVideoDuration(videoId)
{
var defer1 = $.Deferred();
var r = '';
$.get(
"https://www.googleapis.com/youtube/v3/videos",
{
part: 'contentDetails',
id: videoId,
key: 'XXXXXXXX',
},
function(data)
{
$.each(data.items,
function(i, item) {
r = item.contentDetails.duration;
defer1.resolve(r);
console.log("in vidDuration func", r);
});
}
);
return defer1.promise();
}
// return video view count
function getViewCount(videoId)
{
var defer2 = $.Deferred();
var r = '';
$.get(
"https://www.googleapis.com/youtube/v3/videos",
{
part: 'contentDetails, statistics',
id: videoId,
key: 'XXXXXXXX',
},
function(data)
{
$.each(data.items,
function(i, item) {
r = item.statistics.viewCount;
defer2.resolve(r);
console.log("in viewCount func", r);
});
}
);
return defer2.promise();
}
});
屏幕截图结果(正常刷新):
屏幕截图结果(使用调试器):
这是使用调试器控制台逐步完成结果的屏幕截图。 (为什么结果与页面正常加载时的结果不同?这是异步方法的典型操作吗?我该如何解决这个问题?)
答案 0 :(得分:1)
事实上,第二个承诺是错误的,第二个承诺已解决 AFTER 第一个承诺的所有承诺都已解决,因此最后一个值是保存。逻辑
现在,如果你解决了第一个承诺 WHEN ,那么你可以逐一解决问题。
var view = 0;
r = item.contentDetails.duration; // video duration
getViewCount(videoId).done(function(t){
view = t;
dfrd1.resolve(r, view);
});
我改变了一些代码来解决问题。
var channelName = 'example';
var vidWidth = 500;
var vidHeight = 400;
var vidResults = 15; /* # of videos to show at once - max 50 */
var vidDuration = "";
var viewCount = 0;
var videoId = "";
$(document).ready(function() {
$.get( // get channel name and load data
"https://www.googleapis.com/youtube/v3/channels",
{
part: 'contentDetails',
forUsername: channelName,
key: 'xxx'
},
function(data)
{
$.each(data.items,
function(i, item) {
//console.log(item); // log all items to console
var playlistId = item.contentDetails.relatedPlaylists.uploads;
//var viewCount = console.log(item.statistics.viewCount);
getPlaylists(playlistId);
});
}
);
// function that gets the playlists
function getPlaylists(playlistId)
{
$.get(
"https://www.googleapis.com/youtube/v3/playlistItems",
{
part: 'snippet',
maxResults: vidResults,
playlistId: playlistId,
key: 'xxx'
},
// print the results
function(data)
{
var output;
$.each(data.items,
function(i, item) {
console.log(item);
var vidTitle = item.snippet.title; // video title
var vidDesc = item.snippet.description; // video description
var videoId = item.snippet.resourceId.videoId; // video id
// check if description is empty
if(vidDesc == null || vidDesc == "")
{
vidDesc = "No description was written."; // FIX: test msg to see where it still shows up
$('#desc').remove(); // remove video description
}
else vidDesc = item.snippet.description;
getVideoDuration(videoId).done(function(d, v){
vidDuration = d;
//console.log(r);
viewCount = v;
document.write("id: " + videoId + " duration: " + vidDuration + " viewCount: " + viewCount); // return value in console
document.write("<br>");
output = '<li><iframe height="' + vidHeight + '" width="' + vidWidth + '" src=\"//www.youtube.com/embed/' + videoId + '\"></iframe></li><div id="title">' + vidTitle + '</div><div id="desc">' + vidDesc + '</div><div id="duration">Length: ' + vidDuration + '</div><div id="stats">View Count: ' + viewCount + '</div>';
// Append results to list tag
$('#results').append(output);
});
});
}
);
}
// return video duration
function getVideoDuration(videoId)
{
var dfrd1 = $.Deferred();
var r = '';
$.get(
"https://www.googleapis.com/youtube/v3/videos",
{
part: 'contentDetails',
id: videoId,
key: 'xxx',
},
function(data)
{
$.each(data.items,
function(i, item) {
//videoId = item.snippet.resourceId.videoId;
var view = 0;
r = item.contentDetails.duration; // video duration
getViewCount(videoId).done(function(t){
view = t;
dfrd1.resolve(r, view);
});
//alert(videoId);
});
}
);
return dfrd1.promise();
}
// return video view count
function getViewCount(videoId)
{
var dfrd2 = $.Deferred();
var r = '';
$.get(
"https://www.googleapis.com/youtube/v3/videos",
{
part: 'contentDetails, statistics',
id: videoId,
key: 'xxx',
},
function(data)
{
$.each(data.items,
function(i, item) {
//videoId = item.snippet.resourceId.videoId;
r = item.statistics.viewCount; // view count
//alert(videoId);
dfrd2.resolve(r);
// console.log("in", r);
});
}
);
return dfrd2.promise();
}
});