通过开放图形向Facebook提交对象不起作用,但是在Facebook的对象调试器中测试URL之后可以正常工作吗?

时间:2011-11-02 03:25:01

标签: facebook facebook-graph-api meta-tags

我想允许我的网络应用的用户能够从一个页面(main_page)将多个对象发布到他们的时间轴。

我已经存储了用户的访问令牌。

我尝试提交的页面上的标签,网址是page_url:

<meta property="fb:app_id"      content="my_app_id" /> 
<meta property="og:type"        content="my_namespace:my_object" /> 
<meta property="og:title"       content="some string" /> 
<meta property="og:description" content="some other string" /> 
<meta property="og:image"       content="some_image_url" />
<meta property="og:locale"      content="en_US" />
<meta property="og:url"         content="page_url" />   

Rails代码提交url,从main_page触发:

begin
    fb_post = RestClient.post 'https://graph.facebook.com/me/my_namespace:do', :access_token=>user.get_facebook_auth_token, :my_object=>"page_url"
rescue StandardError => e
    p 'e.response is'
    p e.response
end

输出

2011-11-02T02:42:14+00:00 app[web.1]: "e.response is"
2011-11-02T02:42:14+00:00 app[web.1]: "{\"error\":{\"message\":\"(#3502) Object at URL page_url has og:type of 'website'. The property 'my_object' requires an object of og:type 'my_namespace:my_object'.\",\"type\":\"OAuthException\"}}"

真正奇怪的是,在收到此错误后,如果我在Object Debugger上测试page_url,它会在没有任何错误/警告的情况下通过,og:type是正确的类型并注意{{ 1}},然后运行与上面相同的Rails代码将正常工作

我在没有'website'标记的情况下尝试过它,同样的事情发生了。

更新:

根据Igy的回答,我尝试从动作创建过程中分离对象抓取过程。因此,在为全新对象提交操作之前,我使用og:url在对象上运行update

scrape=true

输出

begin
    p 'doing fb_update'
    fb_update = RestClient.post 'https://graph.facebook.com', :id=>page_url, :scrape => true
    p 'fb_update is'
    p fb_update
rescue StandardError => e
    p 'e.response is'
    p e.response
end

奇怪的是类型是2011-11-05T13:27:40+00:00 app[web.1]: "doing fb_update" 2011-11-05T13:27:50+00:00 app[web.1]: "fb_update is" 2011-11-05T13:27:50+00:00 app[web.1]: "{\"url\":\page_url,\"type\":\"website\",\"title\":\page_url,\"updated_time\":\"2011-11-05T13:27:50+0000\",\"id\":\id_here}" ,标题是页面的网址。我再次检查了HTML和Facebook调试器,并且类型和标题都是正确的。

3 个答案:

答案 0 :(得分:26)

我遇到了同样的问题。

only 方式我已经能够成功发布我定义的自定义对象类型的操作,用{{3}手动测试对象网址首先,然后通过我的应用程序在该对象上发布操作。

即使使用linter API - Facebook建议Object Debugger - 也会给我一个错误。

curl -X POST \
     -F "id=my_custom_object_url" \
     -F "scrape=true" \
     "https://graph.facebook.com"

只有调试工具似乎才能正确地抓取页面。

请注意,在使用预定义的对象类型时,我没有遇到此问题,例如“网站”:

<meta property="og:type" content="website" />

由于某种原因,此问题似乎只会影响自定义对象类型。

更新(解决方案):

我终于弄明白了。问题实际上是由于我的应用程序无法处理两个同时发生的HTTP请求。 (仅供参考:我正在使用Heroku来部署我的Rails应用程序。)当您向Facebook API发出请求以在对象URL上发布操作(请求#1)时,Facebook将立即尝试抓取您指定的对象URL(请求#2),并根据它能够成功获取的内容,它返回对原始请求的响应。如果我同步运行请求#1,那将占用我在Heroku上的Web进程,使我的应用程序无法同时处理请求#2。换句话说,Facebook无法成功访问它需要抓取的对象URL;相反,它返回一些默认值,包括对象类型“网站”。有趣的是,即使我在Heroku上启动了多个Web进程,也会发生这种情况。该应用程序旨在使用相同的Web进程来处理这两个请求。

我通过将所有Facebook API请求作为后台作业处理(使用here)解决了这个问题。在Heroku上,这需要启动至少一个Web进程和一个工作进程。如果你能做到这一点,那么在后台运行API请求无论如何都是一个好主意,因为它不会为用户占用你的网站,使他们等待几秒钟才能做任何事情。

顺便说一句,我建议运行两个后台作业。第一个应该通过POST来简单地抓取对象URL: delayed_job {object_url}&安培;刮=真

第一个作业成功完成后,启动另一个后台作业,将操作发布到时间轴: https://graph.facebook.com?id= {app_namespace}:{ACTION_NAME} =的access_token {user_access_token}

更新近期更新

根据评论中的建议,使用Unicorn也可以在不需要delayed_job的情况下完成任务。如果您使用Heroku,请在此处查看更多信息:
https://graph.facebook.com/me/

答案 1 :(得分:6)

The Object creation documents说它应该在你第一次创建对象时刮掉一个对象,但也要说

  

在您创建对象并同时发布到Facebook的某些托管和开发平台中,您可能会收到错误消息,指出该对象不存在。这是由于某些系统中存在竞争条件。

     

我们建议您(a)在发布操作之前验证对象是否已复制,或者(b)引入一个小延迟来解决复制滞后(例如,15-30秒)。

基于此,我认为您需要在初始调用中添加&scrape=true以强制立即刮,然后尝试稍后创建操作。 (我相信您收到的错误消息可能是因为该页面尚未被缓存/删除。)

答案 2 :(得分:5)

从我所看到的情况来看,Facebook Debugger Page是最好的(并且,在大多数实际目的中,)方式强制Facebook的缓存来刷新给定页面的OpenGraph信息。否则,您将花费最多一周等待他们已经删除的网页的缓存信息。

基本上,你应该

  1. 重写您的网页以按您的意愿行事
  2. 将相关网址传递到调试程序页面(看他们验证,刷新缓存),然后
  3. 允许“正常”提供网页以查看您的更改。
  4. 可能有其他方法迫使Facebook缓存过期;有关可能的解决方案,请参阅this Stackoverflow page。我还没有尝试过,但它们可能会有所帮助。