4

I'm trying to integrate my Meteor application with Facebook Open Graph, to publish actions in the timeline.

Facebook API works by defining object specific meta tags in the HTML head, that will be read by the API. For example:

<head prefix="og: http://ogp.me/ns# [YOUR_APP_NAMESPACE]: 
                     http://ogp.me/ns/apps/[YOUR_APP_NAMESPACE]#">
    <title>OG Tutorial App</title>
    <meta property="fb:app_id" content="[YOUR_APP_ID]" /> 
    <meta property="og:type" content="[YOUR_APP_NAMESPACE]:recipe" /> 
    <meta property="og:title" content="Stuffed Cookies" /> 
    <meta property="og:image" content="http://fbwerks.com:8000/zhen/cookie.jpg" /> 
    <meta property="og:description" content="The Turducken of Cookies" /> 
    <meta property="og:url" content="http://fbwerks.com:8000/zhen/cookie.html">
</head>

However, what Facebook API sees when inspecting any URL is something like this:

<!DOCTYPE html>
<html>
<head>
<link rel="stylesheet" href="/ed99236548322b46a7562b49cd6ee0e0f059e506.css">
  <script type="text/javascript" src="/c16ff21884b1f831d91ebf271236ef78b03b552e.js"></script>
  <title>Made with Meteor!</title>
</head>
<body>
</body>
</html>

What is the best way of integrating this meta tags, that may change depending on the URL, in the Meteor application?

joaomvalentim
  • 53
  • 1
  • 5
  • have you read this? http://meteor.com/faq/can-meteor-serve-static-html – Lloyd Jul 01 '12 at 15:29
  • Thanks Lloyd. But does this means that with the cuurent Meteor release (0.3.7), there's no way of achieving this? No workaround is possible? – joaomvalentim Jul 01 '12 at 16:24
  • Meteor does not serve static content in the `body` but your Open Graph `meta` tags should appear in the `head`. At least, it works for me. – Lloyd Jul 01 '12 at 16:37
  • Yes, but that meta tags content should be dynamic. For example the `og:title`, `og:description` and `og:url` depend on the content being served. – joaomvalentim Jul 01 '12 at 18:14
  • 1
    Still working on it, but the solution for now until Meteor implements proper server routing is to write our own routing logic (see http://stackoverflow.com/questions/10119777/can-i-mount-another-route-handler-through-meteor-bootstrap-app). – joaomvalentim Jul 06 '12 at 07:44
  • i see, thanks for the link.. i considered hacking server.js too but instead will live with client-side FB auth for now, i'm not using Open Graph so i'm not desperate.. – Lloyd Jul 06 '12 at 08:26
  • 1
    Just to point out that this is not hacked in server.js. Just add it on your `Meteor.startup()` on the server side. – joaomvalentim Jul 06 '12 at 08:36

3 Answers3

5

I encountered the same issue.

Two ways to deal with this:

  • A recent addition to the "spiderable" package (currently in "devel" branch) also lets you change the "head" tag in client code (append your og:title etc..) and have that "magically" served to Facebook from your server.

(NOTE: you will probably need to not use autopublish package with this solution, since "spiderable" stops the page rendering while relying on a flag that "autopublish" sets to "true" right on client startup)

  • A more light-weight solution would be the "headly" package for Meteor:

https://github.com/ayal/headly

After installation you use it like so:

Meteor.headly.config({tagsForRequest: function(req) {
  ... do something dynamic here, i.e get title from db based on url param ...
  return '<meta property="og:title" content="<DYNAMIC TITLE>" />';
}});
ayal gelles
  • 2,829
  • 1
  • 21
  • 18
  • If I am querying for a document based on `_id`, then this needs to go in the url. Is url param the right way to query database? – Prashant Mar 15 '13 at 13:23
  • 1
    @Prashant, yes I think it's quite common to have an id in the url (either as a query param or in the path) and query the db with it. – ayal gelles Mar 20 '13 at 10:15
  • Is there some problem with the headly package? Meteor crashes. – Prashant Dec 12 '13 at 06:05
1

Spiderable package is the way to go...

in your router do something like this... (this is coffee-sciprt)

#Spiderable stuff to set meta tags for crawl
$("meta[property='fb:app_id']").attr "content", "YOUR_APP_ID"
$("meta[property='og:type']").attr "content", "YOUR_APP:OPEN_GRAPH_CUSTOM_EVENT"
$("meta[property='og:url']").attr "content", "https://apps.facebook.com/YOURAPP"+ @canonicalPath
$("meta[property='og:title']").attr "content", "some title:
$("meta[property='og:description']").attr "content", "some description"
$("meta[property='og:image']").attr "content", "thumb image url"

you can test to see if the Facebook crawl of this page is working with their debug tool... just enter the URL for this page and check for errors etc..

https://developers.facebook.com/tools/debug

  • don't forget to add the stubbed out meta tags in the head of your layout! In jade... "meta(property='fb:app_id', content='foobar')" – adamwong246 Oct 08 '15 at 17:47
0

You need to meteor add spiderable.

As of meteor 0.4.2, with the spiderable package included, all you have to do is include the relevant <meta> elements in the client HTML's <head>.

<head>
  <meta property="og:type" content="website" />
  <title>HTML head test</title>
</head>
Dan Dascalescu
  • 143,271
  • 52
  • 317
  • 404
  • 5
    Hey Dan, just to emphasize - the question as I understand it is about *dynamically* setting the meta-tags in the head. Your solution would have worked even without using "spiderable" because a static head was included in what the server served anyhow. It would not have worked for dynamic og:title, og:image etc.. However there is a recent change to spiderable that would let you acheive that. (see my answer above) – ayal gelles Oct 30 '12 at 13:57