2017-04-19 36 views
0

我有问题,我想用我的wiki中所有页面的名称填充一个列表。我的脚本:list = allpages不能提供所有页面

$TitleList = []; 
$nsList = []; 

$nsURL= 'wiki/api.php?action=query&meta=siteinfo& siprop=namespaces|namespacealiases&format=json'; 
$nsJson = file_get_contents($nsURL); 
$nsJsonD = json_decode($nsJson, true); 
foreach ($nsJsonD['query']['namespaces'] as $ns) 
{ 
    if ($ns['id'] >= 0) 
    array_push ($nsList, $ns['id']);  
} 

# populate the list of all pages in each namespace 
foreach ($nsList as $n) 
{ 
    $urlGET = 'wiki/api.php?action=query&list=allpages&apnamespace='.$n.'&format=json'; 
    $json = file_get_contents($urlGET); 
    $json_b = json_decode($json ,true); 

    foreach ($json_b['query']['allpages'] as $page) 
    {  
    echo("\n".$page['title']); 
    array_push($TitleList, $page["title"]); 
    } 
} 

但仍有35次%的页面丢失,我可以在我的wiki访问(“随机现场”测试)。有谁知道,为什么会发生这种情况?

+0

跟踪这种情况下'如果($ NS [” id']> = 0)' – diavolic

+0

当连接到'apnamespace =' –

回答

1

MediaWiki API不会一次返回所有结果,但可以批量处理。 默认批次只有10页;您可以指定aplimit更改该值(用户最多500个,机器人最多5,000个)。

要获得下一批,您需要指定continue=参数;在每批中,您还将在返回的数据中获得一个continue属性,您可以使用该属性请求下一批。要获取所有页面,只要继续元素存在,就必须循环。

例如,在英文维基百科,这将是第一个API调用: https://en.wikipedia.org/w/api.php?action=query&list=allpages&apnamespace=0&format=json&aplimit=500&continue=

...和continue对象将是这样的: "continue":{ "apcontinue":"\"Cigar\"_Daisey", "continue":"-||" }

(更新根据由OP评论与示例代码)

您现在想使用扁平化continue阵列到URL参数,例如'

在这里看到更完整的解释: https://www.mediawiki.org/wiki/API:Query#Continuing_queries

你的代码的工作版本应该(测试用维基百科有一个略有不同的代码):

# populate the list of all pages in each namespace 

    $baseUrl = 'wiki/api.php?action=query&list=allpages&apnamespace='.$n.'&format=json&limit=500&'; // Increase limit if you are using a bot, up to 5,000 
foreach ($nsList as $n) { 
    $next = ''; 
    while (isset($next)) { 
    $urlGET = $baseUrl . $next; 
    $json = file_get_contents($urlGET); 
    $json_b = json_decode($json, true); 
    foreach ($json_b['query']['allpages'] as $page) 
    { 
     echo("\n".$page['title']); 
     array_push($TitleList, $page["title"]); 
    } 

    if (isset($json_b['continue'])) { 
     $next = http_build_query($json_b['continue']); 
    } 
    } 
} 
+0

感谢您的帮助时,id的-2(Media)和-1(Special)会返回一个错误。当我进行下一次API调用时,出现“badcontinue”错误。所以我只是将参数保存在变量'$ continue = result ['continue'] ['apcontinue']'中。在下一个循环中,我将这个变量添加到'&continue = $ continue',这导致错误“badcontinue”。当我只传递'$ continue = result ['continue']' –

+0

时,它不起作用。因此,你需要做的是平坦化返回的“continue”元素并将其每个密钥对添加到查询URL。你可以使用像'http_build_query($ json_b ['continue']);''这样的方法来实现。我会更新我的答案。 –

+0

谢谢,你的回答对我来说是一个很大的帮助。它终于有效!我非常感谢。 –

相关问题