处理PHP中FQL返回的大用户ID

时间:2010-05-25 19:20:24

标签: php json facebook facebook-fql

我正在使用FQL从Facebook检索用户列表。为了保持一致性,我将结果作为JSON。这会导致问题 - 因为返回的JSON将用户ID编码为数字,json_decode()会将这些数字转换为浮点值,因为有些数字太大而无法放入int中;当然,我需要这些ID作为字符串。

由于json_decode()在没有接受任何行为标志的情况下做了自己的事情,我感到很茫然。有关如何解决此问题的任何建议吗?

7 个答案:

答案 0 :(得分:28)

如果在函数调用中指定了一个标志,

json_decode()可以将大整数转换为字符串:

$array = json_decode($json, true, 512, JSON_BIGINT_AS_STRING)

答案 1 :(得分:20)

我已经通过在我的FQL API调用中添加 &format=json-strings 解决了这个问题,如下所示:

$myQuery = "SELECT uid2 FROM friend WHERE uid1=me()";
$facebook->api("/fql?q=" . urlencode($myQuery) . "&format=json-strings")

这告诉facebook用引号括起所有数字,这导致json_decode都不使用 int-s不是花车。

因为我担心这个问题不仅限于FQL,而是所有图形API调用都选择将某些ID表示为BIG-INTs,我已经修改了Facebook的PHP SDK,以迫使Facebook返回它的所有数字都是字符串。

我已将这一行添加到_graph函数中。 这将是facebook_base.php,版本3.1.1

中的第738行
$params['format'] = 'json-strings';

当然可以解决

答案 2 :(得分:8)

我遇到了类似的问题,其中json_decode将最近的推特/推文ID转换为指数数字。

如果你想让你的BIGINT变成一个字符串,那么Björn的答案很棒 - 而且还有PHP 5.3+。如果这些都不是真的,另一种选择是提高PHP的浮点精度。 这可以用不同的方式来完成......

  • 在php.ini中找到precision值并将其更改为precision = 20
  • ini_set('precision', 20);添加到您的PHP应用
  • php_value precision 20添加到您应用的.htaccess或虚拟主机文件

答案 3 :(得分:5)

快速而肮脏,似乎现在有效:

$sJSON = preg_replace('/:(\d+)/', ':"${1}"', $sJSON);

答案 4 :(得分:3)

我使用它并且它的效果非常好。

json_decode(preg_replace('/("\w+"):(\d+)/', '\\1:"\\2"', $jsonString), true)

当包含地理数据时,json会中断,例如。 {"lat":54.2341}会产生"lat":"54".2341

解决方案:

$json = preg_replace('/("\w+"):(\d+)(.\d+)?/', '\\1:"\\2\\3"', $json);

答案 5 :(得分:0)

(preg_replace('/("\w+"):(\d+)(.\d+)?/', '\\1:"\\2\\3"', $json);)对我有用(解析facebook api的结果)

答案 6 :(得分:0)

PHP 方面的一个主要疏忽是浏览器不会阻塞从 BigInt(64 位)开始的整数,而是在此之前(53 位)。当 JSON 不支持 BigInt 时,将 BigInt 引入现代浏览器并没有多大帮助。所以我正在努力解决这个问题。

我的方法是处理解码后的数组(在可能将其重新编码为字符串之前):

function fix_large_int(&$value)
 {
  if (is_int($value) && $value > 9007199254740991)
    $value = strval($value);
 }
$json_arr = json_decode($json_str, flags: JSON_BIGINT_AS_STRING | JSON_OBJECT_AS_ARRAY);
echo('before: ' . json_encode($json_arr) . '<br />' . PHP_EOL);
array_walk_recursive($json_arr, 'fix_large_int');
echo('after:  ' . json_encode($json_arr) . '<br />' . PHP_EOL);

数字 9007199254740991 是 JavaScript 的 Number.MAX_SAFE_INTEGER 值。在此处阅读:https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Number/MAX_SAFE_INTEGER

(顺便说一句,我来到这里是因为 Twitter API 的 stringify_idsblocks/ids 参数 friends/ids 对我不起作用。似乎在我能找到的任何地方都没有提到找到了。)