Skip to content

Instantly share code, notes, and snippets.

@boxmein
Last active August 29, 2015 14:18
Show Gist options
  • Select an option

  • Save boxmein/588c5caa163c87e594e7 to your computer and use it in GitHub Desktop.

Select an option

Save boxmein/588c5caa163c87e594e7 to your computer and use it in GitHub Desktop.
Tiny Flask/Pillow-based HTTP image gallery server
# Tiny Flask/PIL/Pillow based HTTP image gallery server
# Wow, uh, that was a mouthful. Okay, here's what this is all about.
# It serves image galleries. Download it, launch the script in an image folder, and
# this baby will make your image folder look like a fancy image gallery page. Magic
# huh?
#
# It uses arcane rarely-available technologies such as Flexbox and HTML. It auto-
# generates and stores thumbnails from the entire directory, making the first load
# of a directory listing *really* slow. Left as an exercise to the reader. I wanted
# the gallery quickly built, not decently!
#
# Oh also the HTML it generates has a bit too many image tags, so a silly hack was
# used to hide the tags that are broken. Also an exercise to the reader.
#
# Other than that, feel free serving this on port 8000 and then applying some
# ngrok or localtunnel magic to give a quick HTTP overview of your image gallery
# to anyone on the internet!
#
# MIT license. boxmein 2015. blah blah blah.
from flask import Flask, send_file, render_template, abort
from PIL import Image
import sys
import os
DEBUG = os.environ['DEBUG'] if 'DEBUG' in os.environ else False
PORT = os.environ['PORT'] if 'PORT' in os.environ else 8000
THUMBSIZE=(200, 200)
app = Flask(__name__)
@app.route("/favicon.ico")
def favicon():
abort(404)
@app.route("/", defaults={"path": "."})
@app.route("/<path:path>")
def route_everything(path):
if os.path.isfile(path):
return send_file(path)
elif os.path.isdir(path):
names = [x for x in os.listdir(path) if '.thumbnail' not in x]
dirs = [x for x in names if os.path.isdir(path + '/' + x)]
print(list(dirs))
thumbs = {}
# generate thumbnails as needed
for f in names:
if not os.path.exists(path + '/' + f + '.thumbnail'):
try:
im = Image.open(path + '/' + f)
im.thumbnail(THUMBSIZE)
im.save(path + '/' + f + '.thumbnail', 'JPEG')
except OSError:
print ('warn: ' + f + ' was not an image')
return render_template('directory.html', path=os.listdir(path), wd=path, directories=list(dirs))
else:
abort(404)
if __name__ == '__main__':
app.run(port=PORT, debug=DEBUG)
<!doctype html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>/{{wd}} | -server</title>
<style>
body {
max-width: 800px;
margin: 0 auto;
font-family: sans-serif;
}
.imglist {
display: flex;
display: -webkit-flex;
flex-direction: row;
flex-wrap: wrap;
}
.imgthing {
margin: 0.1em;
transition: 0.1s ease;
}
.imgthing:hover {
box-shadow: 1px 1px 20px #999;
}
</style>
</head>
<body>
<h1>directory listing for /{{wd}} | -server</h1>
<div class="dirlist">
<h2>subdirs:</h2>
<ul>
{% for sd in directories %}
<li><a href="{{wd}}/{{sd}}">{{sd}}</a></li>
{% endfor %}
</ul>
</div>
<div class="imglist">
{% for file in path %}
<div class="imgthing">
<a href="{{wd}}/{{file}}">
<img src="{{wd}}/{{file}}.thumbnail" type="image/jpeg" onerror="this.style.display='none';">
</a>
</div>
{% endfor %}
</div>
</body>
</html>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment