Skip to content

Commit

Permalink
Added giphy plugin for liquid_tags
Browse files Browse the repository at this point in the history
A plugin that makes it easier to use gif images from giphy.com. you just
need the gif id and the rest will be get from the giphy api.
  • Loading branch information
xsteadfastx committed Sep 18, 2015
1 parent adea2d1 commit 06cc3e3
Show file tree
Hide file tree
Showing 5 changed files with 132 additions and 2 deletions.
8 changes: 8 additions & 0 deletions liquid_tags/Readme.md
Expand Up @@ -53,6 +53,14 @@ To insert a Flickr image to a post, follow these steps:

``{% flickr image_id [small|medium|large] ["alt text"|'alt text'] %}``

## Giphy Tag
To insert a gif from Giphy in your document by its id (such as ``aMSJFS6oFX0fC``), enable the ``liquid_tags.giphy`` plugin and use the following:

{% giphy gif_id ["alt text"|'alt text'] %}

IMPORTANT: You have to request a production API key from giphy [here](https://api.giphy.com/submit).
For the first runs you could also use the public beta key you can get [here](https://github.com/giphy/GiphyAPI).

## Soundcloud Tag
To insert a Soundcloud Widget to a post, follow these steps:

Expand Down
89 changes: 89 additions & 0 deletions liquid_tags/giphy.py
@@ -0,0 +1,89 @@
"""
Giphy Tag
---------
This implements a Liquid-style Giphy tag for Pelican.
IMPORTANT: You have to request a production API key from giphy `here <https://api.giphy.com/submit>`.
For the first runs you could also use the public beta key you can get `here <https://github.com/giphy/GiphyAPI>`.
Syntax
------
{% giphy gif_id ["alt text"|'alt text'] %}
Example
-------
{% giphy aMSJFS6oFX0fC 'ive had some free time' %}
Output
------
<a href="http://giphy.com/gifs/veronica-mars-aMSJFS6oFX0fC"><img src="http://media4.giphy.com/media/aMSJFS6oFX0fC/giphy.gif" alt="ive had some free time"></a>
"""
import json
import re
try:
from urllib.request import urlopen
except ImportError:
from urllib import urlopen
from .mdx_liquid_tags import LiquidTags


SYNTAX = '''{% giphy gif_id ["alt text"|'alt text'] %}'''
GIPHY = re.compile('''(?P<gif_id>[\S+]+)(?:\s+(['"]{0,1})(?P<alt>.+)(\\2))?''')


def get_gif(api_key, gif_id):
'''Returns dict with gif informations from the API.'''
url = 'http://api.giphy.com/v1/gifs/{}?api_key={}'.format(gif_id, api_key)
r = urlopen(url)

return json.loads(r.read().decode('utf-8'))


def create_html(api_key, attrs):
'''Returns complete html tag string.'''
gif = get_gif(api_key, attrs['gif_id'])

if 'alt' not in attrs.keys():
attrs['alt'] = 'source: {}'.format(gif['data']['source'])

html_out = '<a href="{}">'.format(gif['data']['url'])
html_out += '<img src="{}" alt="{}">'.format(
gif['data']['images']['original']['url'],
attrs['alt'])
html_out += '</a>'

return html_out


def main(api_key, markup):
'''Doing the regex parsing and running the create_html function.'''
match = GIPHY.search(markup)

attrs = None

if match:
attrs = dict(
[(key, value.strip())
for (key, value) in match.groupdict().items() if value])

else:
raise ValueError('Error processing input. '
'Expected syntax: {}'.format(SYNTAX))

return create_html(api_key, attrs)


@LiquidTags.register('giphy')
def giphy(preprocessor, tag, markup):
api_key = preprocessor.configs.getConfig('GIPHY_API_KEY')

if api_key is None:
raise ValueError('Please set GIPHY_API_KEY.')

return main(api_key, markup)


# ---------------------------------------------------
# This import allows image tag to be a Pelican plugin
from liquid_tags import register
6 changes: 4 additions & 2 deletions liquid_tags/mdx_liquid_tags.py
Expand Up @@ -21,11 +21,13 @@
EXTRACT_TAG = re.compile(r'(?:\s*)(\S+)(?:\s*)')
LT_CONFIG = { 'CODE_DIR': 'code',
'NOTEBOOK_DIR': 'notebooks',
'FLICKR_API_KEY': 'flickr'
'FLICKR_API_KEY': 'flickr',
'GIPHY_API_KEY': 'giphy'
}
LT_HELP = { 'CODE_DIR' : 'Code directory for include_code subplugin',
'NOTEBOOK_DIR' : 'Notebook directory for notebook subplugin',
'FLICKR_API_KEY': 'Flickr key for accessing the API'
'FLICKR_API_KEY': 'Flickr key for accessing the API',
'GIPHY_API_KEY': 'Giphy key for accessing the API'
}

class _LiquidTagsPreprocessor(markdown.preprocessors.Preprocessor):
Expand Down
2 changes: 2 additions & 0 deletions liquid_tags/test_data/giphy.json
@@ -0,0 +1,2 @@

{"data":{"type":"gif","id":"aMSJFS6oFX0fC","url":"http:\/\/giphy.com\/gifs\/veronica-mars-aMSJFS6oFX0fC","bitly_gif_url":"http:\/\/gph.is\/1hcFOSo","bitly_url":"http:\/\/gph.is\/1hcFOSo","embed_url":"http:\/\/giphy.com\/embed\/aMSJFS6oFX0fC","username":"","source":"http:\/\/www.tumblr.com","rating":"pg","caption":"","content_url":"","import_datetime":"2014-02-21 04:43:11","trending_datetime":"1970-01-01 00:00:00","images":{"fixed_height":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/200.gif","width":"350","height":"200","size":"296611","mp4":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/200.mp4","mp4_size":"64850","webp":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/200.webp","webp_size":"529942"},"fixed_height_still":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/200_s.gif","width":"350","height":"200"},"fixed_height_downsampled":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/200_d.gif","width":"350","height":"200","size":"243264","webp":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/200_d.webp","webp_size":"138300"},"fixed_width":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/200w.gif","width":"200","height":"114","size":"120246","mp4":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/200w.mp4","mp4_size":"96166","webp":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/200w.webp","webp_size":"210140"},"fixed_width_still":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/200w_s.gif","width":"200","height":"114"},"fixed_width_downsampled":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/200w_d.gif","width":"200","height":"114","size":"113909","webp":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/200w_d.webp","webp_size":"55084"},"fixed_height_small":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/100.gif","width":"175","height":"100","size":"296611","mp4":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/100.mp4","mp4_size":"243931","webp":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/100.webp","webp_size":"136098"},"fixed_height_small_still":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/100_s.gif","width":"175","height":"100"},"fixed_width_small":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/100w.gif","width":"100","height":"57","size":"120246","mp4":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/100w.mp4","mp4_size":"101604","webp":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/100w.webp","webp_size":"55480"},"fixed_width_small_still":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/100w_s.gif","width":"100","height":"57"},"downsized":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/giphy.gif","width":"245","height":"140","size":"487767"},"downsized_still":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/giphy_s.gif","width":"245","height":"140"},"downsized_large":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/giphy.gif","width":"245","height":"140","size":"487767"},"original":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/giphy.gif","width":"245","height":"140","size":"487767","frames":"23","mp4":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/giphy.mp4","mp4_size":"219528","webp":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/giphy.webp","webp_size":"272262"},"original_still":{"url":"http:\/\/media2.giphy.com\/media\/aMSJFS6oFX0fC\/giphy_s.gif","width":"245","height":"140"}}},"meta":{"status":200,"msg":"OK"}}
29 changes: 29 additions & 0 deletions liquid_tags/test_giphy.py
@@ -0,0 +1,29 @@
from . import giphy
try:
from unittest.mock import patch
except ImportError:
from mock import patch
import os
import pytest


PLUGIN_DIR = os.path.dirname(__file__)
TEST_DATA_DIR = os.path.join(PLUGIN_DIR, 'test_data')


@pytest.mark.parametrize('input,expected', [
(dict(gif_id='abc123'),
('<a href="http://giphy.com/gifs/veronica-mars-aMSJFS6oFX0fC">'
'<img src="http://media2.giphy.com/media/'
'aMSJFS6oFX0fC/giphy.gif" alt="source: http://www.tumblr.com"></a>')),
(dict(gif_id='abc123', alt='ive had some free time'),
('<a href="http://giphy.com/gifs/veronica-mars-aMSJFS6oFX0fC">'
'<img src="http://media2.giphy.com/media/'
'aMSJFS6oFX0fC/giphy.gif" alt="ive had some free time"></a>'))
])
@patch('liquid_tags.giphy.urlopen')
def test_create_html(mock_urlopen, input, expected):
with open(TEST_DATA_DIR + '/giphy.json', 'rb') as f:
mock_urlopen.return_value.read.return_value = f.read()

assert giphy.create_html('test_api_key', input) == expected

0 comments on commit 06cc3e3

Please sign in to comment.