Supporting iframe embeds from different domains?

I’d like embed iframes from domains outside of instagram, youtube, etc. How would I go about doing that? I noticed some people talk about GitHub - discourse/onebox: A gem for turning URLs into website previews but it only supports html previews.

Thanks!
Syed

4 Likes

iframes can now be whitelisted through the allowed_iframes Site Setting. It accepts a list of iframe src domain prefixes that discourse can safely allow in posts. The whitelist-iframe plugin is no longer required.


What I have done is make a plugin that calls the Discourse.Markdown.whiteListIframe function. The plugin is very simple, The hard part is that you have to supply regular expressions to match any URLs you want to white-list. The code is here. https://github.com/scossar/whitelist-iframe

You can test any URLs you wish to whitelist in your web browser’s console window. For example, if you open the browser’s console from a Discourse forum and then enter the following line, you should be able to embed iframes from Freesound.

window.Discourse.Markdown.whiteListIframe(/^(https?:)\/\/www\.freesound\.org\/embed\/sound\/iframe\/.+/i);

There may be an easier way to do this. :slight_smile:

10 Likes

thanks! this looks super straightforward! I’ll try it out!

Syed

Will this support video embeds from the New York Times?

Trying to embed this video:

<iframe title="New York Times Video - Embed Player" width="480" height="321" frameborder="0" scrolling="no" allowfullscreen="true" marginheight="0" marginwidth="0" id="nyt_video_player" src="http://graphics8.nytimes.com/video/players/offsite/index.html?videoId=100000003764816"></iframe>

Yes it works if you add this line to iframe-whitelist.js :

Discourse.Markdown.whiteListIframe(/^(https?:)?\/\/graphics8\.nytimes\.com\/video\/players\/.+/i);

Thanks Simon. I’m not a software engineer (not even close - a business guy). Help me a little more with this please…

Where do I find the “iframe-whitelist.js”

Thanks!

Not that I know, I haven’t tried. but are you sure? It doesn’t look the same as I see here (i.e. the URL is not …/video/players/)

<iframe width="480" height="373" frameborder="0" scrolling="no" marginheight="0"
 marginwidth="0" id="nyt_video_player"
 title="New York Times Video - Embed Player"
 src="http://graphics8.nytimes.com/bcvideo/1.0/iframe/embed.html?videoId=1247467505934&playerType=embed">
</iframe>

Yes, I based it off the source that @BCHK supplied and it works. Maybe the regular expression I am using is too specific though. Would there be any risk in just using this?

Discourse.Markdown.whiteListIframe(/^(https?:)?\/\/graphics8\.nytimes\.com\/.+/i);

IMHO not any moreso than the other, They both end in “one or more anything characters”
i.e. It’s the “anything” that opens up the potential for problems, eg. If it is known that they always end with digits, I’d add that in.

Not that the problem would necessarily be a security risk. I think if someone posted a bad URL it would result in a broken link either way. Only difference is the onebox wouldn’t try with a bad URL

1 Like

Are you able to install plugins? If so, it is here:
https://github.com/scossar/whitelist-iframe
Right now I am just hardcoding urls into the plugin. It currently works for SoundCloud, FreeSound and now New York Times video. That’s not an ideal way to do it. It could probably be set up to allow acceptable urls to be added through the admin section.

Ah - haven’t done it yet - but probably time to learn. Thanks!

https://github.com/discourse/discourse/blob/b12ace5f9d867426172c0fa17e8107b3805e8901/app/assets/javascripts/discourse/lib/markdown.js#L223-L227

Hello, We need max width and length for iframe. What we can do, to realize this?
I have found this, but I’m not sure. I’m newbie in JS.
Somebody can help me?

Just learning to install plugins into Discourse. I got the plugin installed and it works! Now… How do you find the file in Digital Ocean so I can hardcode a new domain to whitelist? /var/discourse/plugins doesn’t exist…

To find the file on Digital Ocean, ssh into your droplet and then run:

$ cd /var/discourse
$ ./launcher enter app
$ cd var/www/discourse/plugins

The problem with changing things that way is that your changes will be overwritten every time you update Discourse. The right way to do it is to update the plugin file that is in the repository on github and then run launcher rebuild app in your droplet.

You can do that by cloning my repository on github and making the changes you want in your cloned version. You then need to change the url that you have added to the app.yml file so that it pulls from your new repository. If this isn’t clear, just let me know :slightly_smiling:

I can also just add the domain you want to whitelist to the plugin file that is in my repository.

5 Likes

Thanks @simon! I got it to work through cloning your repository :slight_smile:

1 Like

i installed the plugin and i try add my iframe of discord with command:

<iframe src="https://discordapp.com/widget?id=184421097603596288&theme=dark" width="350" height="500" allowtransparency="true" frameborder="0"></iframe>

but not happen, how to insert discordapp.com to whitelist?

You will need to cone the plugin to your own github repository and add something like this to the iframe-whitelist.js file:

(function() {
  Discourse.Markdown.whiteListIframe(/^(https?:)?\/\/www\.freesound\.org\/embed\/sound\/iframe\/.+/i);
  Discourse.Markdown.whiteListIframe(/^(https?:)?\/\/w\.soundcloud\.com\/player\/.+/i);
  Discourse.Markdown.whiteListIframe(/^(https?:)?\/\/graphics8\.nytimes\.com\/.+/i);
  Discourse.Markdown.whiteListIframe(/^(https?:)?\/\/www\.youtube\.com\/embed\/.+/i);

  // whitelist discordapp
  Discourse.Markdown.whiteListIframe(/^(https?:)?\/\/discordapp\.com\/.+/i);
})();

You will then need to use your own repository as the source for the plugin.

3 Likes

Nice, work perfectly, its amazing! Thanks!

@simon i rebuild app and inserted code again in iframe-whitelist.js file, but now, not working :pensive:

1 Like

Which github repo do you have in your app.yml file?

1 Like