Web Service and Open Data
By Lélia Blin - ProgRes lelia.blin@lip6.fr
Thanks to Quentin Bramas
Create an API with Python
Create an API
• Django: Powerful web framework with a lot of modules. Great to build a complete website.
• Flask: Small Framework to build simple website.
• Bottle: Similar to Flask, but even simpler. Perfect to build an API
Available library/framework in python:
Create an API
The Bottle Framework (single file module, no dependencies)
• Routing: Requests to function-call mapping with support for clean and dynamic URLs.
• Templates: Fast and pythonic built-in template engine
• Utilities: Convenient access to form data, file uploads, cookies, headers and other HTTP-related metadata.
• Server: Built-in HTTP development server and
support for other WSGI capable HTTP server. (WSGI is the
Web Server Gateway Interface, which is a specification for web server in python)
Create an API
from bottle import route, run
@route('/hello') def hello():
return 'Hello world'
run(host='localhost', port=8080)
Hello world example:
>python3 07_Hello.py
Bottle v0.12.13 server starting up (using WSGIRefServer())...
Listening on http://localhost:8080/
Hit Ctrl-C to quit.
http://localhost:8080/hello
Id in URL
from bottle import route, run, template
@route('/hello/<name>') def hello(name):
return 'Hello ' + name
run(host='localhost', port=8080)
File: 08_HelloName.py
URL: http://localhost:8080/hello/Marie
Id in URL
Exemple: The user chose the langage: english, french, spanish
File: 09_HelloPL.py
Variables in URL
from bottle import Bottle, run, view, request app = Bottle()
@app.route('/jemesure') def jemesure():
return "Je mesure " + request.params.taille + " cm"
run(app, host='localhost', port=8080)#, reloader=True)
File: 11_Taille.py
URL: http://localhost:8080/jemesure?taille=133
Variables in URL
The response depends on the content of the variable
File: 10_Taille.py
URL: http://localhost:8080/jemesure?taille=133
Static content
#!/usr/bin/env python
# -*- coding: utf-8 -*-
from bottle import Bottle, run, static_file app = Bottle()
@app.route('/static/<filename:path>') def server_static(filename):
return static_file(filename, root='.')
run(app, host='localhost', port=8080, reloader=True)
File: 12_Img.py
URL: http://localhost:8080/static/cube.png
Template
Bottle comes with a fast, powerful and easy to learn built-in template engine called SimpleTemplate or stpl for short.
page.tpl
<!doctype html>
<!-- page.tpl -->
<HTML lang="fr">
<HEAD>
<TITLE>{{title}}</TITLE>
<meta charset="UTF-8">
</HEAD>
<body>
<h1>{{title}}</h1>
{{!body}}
<hr/>
<font size="-1"><i>Page réalisée avec Bottle</i></font>
</body>
</html>
La présence du ! Devant Body permet d'indiquer à bottle de ne pas échapper les caractères de balisage HTML dans la chaîne body.
Elle pourra donc contenir des balises.
Template
import bottle import datetime
@bottle.route("/time")
@bottle.view("page.tpl") def index() :
heure = datetime.datetime.now().strftime("<p>Nous sommes le %d/%m/
%Y, il est %H:%M:%S</p>")
return {"title":"Horloge", "body" : heure}
bottle.run(bottle.app(), host='localhost', port=8080, debug= True, reloader=True)
exo14
Template
@bottle.route("/qui")
@bottle.view("page.tpl") def qui() :
stri = """
<form method='post' action='bonjour'>
<input type='text' name='nom' placeholder='Votre nom ?'/>
<input type='submit' value='Bonjour bottle !'/>
</form>
"""
return {"title":"Présentez-vous", "body" : stri}
@bottle.route("/bonjour", method='POST')
@bottle.view("page.tpl") def bonjour() :
nom = bottle.request.forms.get('nom')
stri = "Bonjour mon(a) che(è)r(e) {}".format(nom) return {"title":"Bonjour", "body" : stri}
Accents
# -*- coding: utf-8 -*- import bottle import requests
from html.entities import codepoint2name def htmlCoding(stringToCode):
return ''.join( '&%s;' % codepoint2name[ord(oneChar)]
if ord(oneChar) in codepoint2name else oneChar for oneChar in stringToCode )
@bottle.route("/qui") def qui() : stri = """
<form method='post' action='bonjour'>
<input type='text' name='nom' placeholder='Votre nom ?'/>
<input type='submit' value='Validez !'/>
</form>
"""
return stri
@bottle.route("/bonjour", method='POST') def bonjour() :
nom = bottle.request.forms.nom return "Bonjour " + htmlCoding(nom)
bottle.run(bottle.app(), host='localhost', port=8080, debug= True, reloader=True)