Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
32 changes: 20 additions & 12 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,35 +23,43 @@ var jsdom = require('jsdom'),
url = 'http://www.imdb.com/title/tt0068646/'

jsdom.env({ html: url, done: function(error, window) {

// 3. pass window as the only argument to ogp.parse method
var ogData = ogp.parse(window)

// 5. Profit!
console.log('Open Graph data', ogData)
// 3. pass window as the only argument to ogp.parse method
var ogData = ogp.parse(window)

// ogp.parse can also parse Open Graph properties for any namespaces desired.
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If namespaces argument omitted then 'og' will be default.

//
// To match og and fb namespaces the following could be done:
// var ogData = ogp.parse(window, 'og fb')
// or:
// var ogData = ogp.parse(wondow, ['og', 'fb'])

// 5. Profit!
console.log('Open Graph data', ogData)
}})
```

This will put next structure into stdout:

```javascript
{ url: 'http://www.imdb.com/title/tt0068646/',
title: 'The Godfather (1972)',
type: 'video.movie',
image: 'http://ia.media-imdb.com/images/M/MV5BMTIyMTIxNjI5NF5BMl5BanBnXkFtZTcwNzQzNDM5MQ@@._V1._SX97_SY140_.jpg',
site_name: 'IMDb' }
{ 'og:url': 'http://www.imdb.com/title/tt0068646/',
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Updated to show namespaced results.

'og:title': 'The Godfather (1972)',
'og:type': 'video.movie',
'og:image': 'http://ia.media-imdb.com/images/M/MV5BMTIyMTIxNjI5NF5BMl5BanBnXkFtZTcwNzQzNDM5MQ@@._V1._SX97_SY140_.jpg',
'og:site_name': 'IMDb' }
```

In case if some of OpenGraph tags were presented multiple times (few image tags for example, output structure field related to that tag will be converted into array:

```javascript
{ image: ['image1.png', 'image2.png']}
{ 'og:image': ['image1.png', 'image2.png']}
```

## Credits

Written and maintained by [Yury Proshchenko](mailto:spect.man@gmail.com).

Multiple namespace support by [Cody Craven](http://github.com/codycraven).

## License

The MIT License
Expand Down
77 changes: 43 additions & 34 deletions lib/ogp.js
Original file line number Diff line number Diff line change
@@ -1,35 +1,44 @@
exports.parse = function(window) {
var ns
for (var i = 0; i < window.document.documentElement.attributes.length; ++i) {
var attr = window.document.documentElement.attributes[i]
if (attr.nodeValue.toLowerCase() !== 'http://opengraphprotocol.org/schema/') continue

ns = attr.nodeName.substring(6)
if (ns) break
}

if (!ns) return {}

var result = {},
metaTags = window.document.getElementsByTagName('meta')

for (var i = 0; i < metaTags.length; ++i) {
var tag = metaTags[i],
propertyAttr = tag.attributes['property']

if (!propertyAttr || propertyAttr.nodeValue.substring(0, ns.length) !== ns)
continue

var property = tag.attributes['property'].nodeValue.substring(ns.length+1),
content = tag.attributes['content'].nodeValue

if (!result[property])
result[property] = content
else if (result[property].push)
result[property].push(content)
else
result[property] = [result[property], content]
}

return result
exports.parse = function(window, namespaces) {
var result = {},
metaTags = window.document.getElementsByTagName('meta'),
propertyRegex = /^([a-z]+):/;

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This namespace prefix declaration does not match current http://ogp.me/ specifications and as such prevented the script from working on Open Graph valid pages. I removed this requirement all together as I know of at least three different implementations the Open Graph protocol has declared.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

whey don't keep this check and just add conditional for new namespace?

// If undefined set as "og" namespace (OGP default).
if (!namespaces)
namespaces = ['og'];
// If string convert to an array, accepts comma separated.
else if (typeof namespaces === 'string') {
namespaces = namespaces.split(' ');
}

for (var i = 0; i < metaTags.length; ++i) {
var tag = metaTags[i],
propertyAttr = tag.attributes['property']

// All OG meta tags contain property attribute.
if (!propertyAttr) {
continue
}
else {
var matches = propertyRegex.exec(propertyAttr.nodeValue);
// Verify OG property is found in our acceptable namespaces.
if (!matches[1] || namespaces.indexOf(matches[1]) == -1)
continue
}

var property = tag.attributes['property'].nodeValue,
content = tag.attributes['content'].nodeValue

// If the property does not already exist, assign it.
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I kept the results as close to the prior script's results as possible, except og namespaced properties now include "og:' such as 'og:title'.

if (!result[property])
result[property] = content
// Else if result[property] is already an array then push it.
else if (result[property].push)
result[property].push(content)
// Else convert string to array.
else
result[property] = [result[property], content]
}

return result
}
5 changes: 3 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
@@ -1,10 +1,11 @@
{
"name": "ogp",
"description": "Parse Open Graph meta tags from jsdom generated DOM",
"version": "0.0.2",
"version": "1.0.0",
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Updated major revision since results of parse would break existing implementations due to multiple namespace/prefix support.

"author": "Yury Proshchenko <spect.man@gmail.com>",
"contributors": [
{ "name": "Yury Proshchenko", "email": "spect.man@gmail.com" }
{ "name": "Yury Proshchenko", "email": "spect.man@gmail.com" },
{ "name": "Cody Craven", "email": "cody@cravencode.com", "url": "https://github.com/codycraven" }
],
"keywords": ["open graph", "opengraph", "ogp"],
"main": "./lib/ogp.js",
Expand Down