building an api with django and django rest framework

Post on 13-Apr-2017

958 Views

Category:

Software

5 Downloads

Preview:

Click to see full reader

TRANSCRIPT

Building an API with Django and Django REST Framework

PyTennessee 2016

2

Hi, I’m Chris Foresman

• Senior Systems Engineer at Vokal• Python mentor to all ages• Learned to program in BASIC on a

TRS-80 circa 1986• Love: karaoke, bourbon, brunch• I have a 3-yr-old at home

@foresmac

3

Hi, I’m Adam Bain

• Systems Engineer at Vokal• Rehabilitated Java engineer via

Python• Learned to program in BASIC circa

94• Likes: Hockey, Craft Beer• I referee robotics competitions

@adam_bain

4

Let’s build an API!

5

With Python!

6

Who’s with us so far?

7

If you want to follow along:

• terminal access• a text editor: SublimeText, Atom, vim• or IDE, like PyCharm• ideally have virtualenv (or venv)• git

8

If you want to follow along:

• mkdir ~/tutorial• virtualenv ~/tutorial• cd ~/tutorial• source bin/activate• pip install django djangorestframework• git clone https://github.com/vokal/deckbuilder-api.git• git checkout -b base base

9

Ok, let’s get started.

10

Planning

11

Planning

• sketch out your data models• how will different things be represented?• think about what actions your API needs to support• will you be strictly RESTful, supporting only CRUD?• or, will your API be more expressive?• it’s up to you to strike a balance!

12

Wait, isn’t CRUD bad? And why do I need REST already?

13

CRUD

• your basic database operations:• CREATE• READ• UPDATE• DELETE

14

HTTP

• your basic HTTP request methods:• POST• GET• PUT (and/or PATCH)• DELETE

15

REST in a nutshell

• your basic RESTful API:• CREATE = POST• READ = GET• UPDATE = PUT (and/or PATCH)• DELETE = DELETE

FYI: REST stands for Representational State Transfer

16

Common RESTful pattern

• /object• POST data to this endpoint to create a new object• GET this endpoint to retrieve a list of objects

• /object/:id• GET this endpoint to get details about a particular object• PUT or PATCH data to this endpoint to update that object • DELETE this endpoint to delete the object

17

Pragmatic, not-strictly-RESTful patterns

• /object/:id/action• Either POST data to this endpoint to perform some action,

particularly if it results in new data being created, or• PUT to this endpoint to perform some action that doesn’t require

any additional data, and typically modifies existing data but does not create new data objects

• /object/noun• GET this endpoint to get some specific grouping or set of the

objects

18

Be as logically consistent as humanly possible

19

Models

git checkout -b models models

20

Models

• define objects that represent your data• map fields to database column types• handle DB magic for you (for the most part)• strive for “fat” models and “thin” views

• give your models methods• for complicated creation, updating, etc, use managers

21

Models

• know your field types• CharField• IntegerField• BooleanField• DatetimeField• etc

• fields also have parameters that affect database table creation and data validation• null=True, max_length=255, etc

22

Serializers

git checkout -b serializers serializers

23

Serializers

• this is the main gateway between your API and the world• typically:

• validates input• converts JSON to Python dict• converts model instances to Python dicts

• which can then be passed to model instances and saved to the database

24

Generic Views

git checkout -b generic_view generic_view

25

Generic Views

• class-based views• can be configured with basic attributes:

• serializer• permissions_classes• queryset

• or can use more dynamic config:• get_queryset()• get_serializer()• etc

26

Generic Views

• basic GenericAPIView• composable with mixins• most common options pre-defined:

• ListCreateView• RetrieveUpdateDestroyView• others...

27

View Sets

git checkout -b view_set view_set

28

View Sets

• great for straightforward CRUD operations• can be extended with additional “detail” views• automagically handle URL routing generation• a lot of functionality for a little bit of code

29

URL Routing

30

URL Routing

• just match a URL regex with a corresponding view• call as_view() on it, like so:

url(r’^/card/?$’, ListCreateCardView.as_view(), name=’list-create-card’)

31

URL Routing

• if you’re using ViewSets, do the following:

router = routers.DefaultRouter()router.register(r'card', CardViewSet)urlpatterns = router.urls

32

“Browsable” API

git checkout -b browsable_api browsable_api

33

“Browseable” API

• Let’s you experiment with your API via a browser

34

Testing

35

Testing

• why does everyone hate it?• trust us, you’ll thank yourself later• generally “integration” tests cover most code• additional unit tests cover everything else• for Pete’s sake, learn to use mock

36

You’ve got questions?

37

We’ve got answers.

38

(Hopefully)

39

Resources

• http://www.django-rest-framework.org• https://docs.djangoproject.com• https://virtualenv.readthedocs.org• https://github.com/vokal/deckbuilder-api

Thank you!

PyTennessee 2016

top related