Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Test your API docs!

Sponsored · Your Podcast. Everywhere. Effortlessly. Share. Educate. Inspire. Entertain. You do you. We'll handle the rest.
Avatar for Honza Javorek Honza Javorek
February 04, 2018

Test your API docs!

Today many API docs are driven by API description formats, such as Swagger/OpenAPI, API Blueprint, and so on. I'm working on an Open Source tool (Dredd), which verifies whether the implementation is according to the description. This enables a whole new workflow to API designers - they can design before implementing, and then ensure the implementation is in sync with the design.

https://fosdem.org/2018/schedule/event/test_api_docs_with_dredd/

Avatar for Honza Javorek

Honza Javorek

February 04, 2018
Tweet

More Decks by Honza Javorek

Other Decks in Technology

Transcript

  1. import urllib2 gh_url = 'https://api.github.com' req = urllib2.Request(gh_url) password_manager =

    urllib2.HTTPPasswordMgrWithDefaultRealm() password_manager.add_password(None, gh_url, 'user', 'pass') auth_manager = urllib2.HTTPBasicAuthHandler(password_manager) opener = urllib2.build_opener(auth_manager) urllib2.install_opener(opener) handler = urllib2.urlopen(req) print handler.getcode() print handler.headers.getheader('content-type') Do you like this interface?
  2. >>> r = requests.get('https://api.github.com/user', ... auth=('user', 'pass')) >>> r.status_code 200

    >>> r.headers['content-type'] 'application/json; charset=utf8' >>> r.encoding 'utf-8' >>> r.text '{"type":"User"...' >>> r.json() {'disk_usage': 368627, 'private_gists': 484, ...} Do you like this interface?
  3. def test_basic_building(): req = requests.Request() req.url = 'http://kennethreitz.org/' req.data =

    {'life': '42'} pr = req.prepare() assert pr.url == req.url assert pr.body == 'life=42'
  4. test > RED > implement > test > GREEN req

    = requests.Request() req.url = 'http://kennethreitz.org/' req.data = {'life': '42'} pr = req.prepare() assert pr.url == req.url assert pr.body == 'life=42'
  5. Feature: Status code Background: Given you expect HTTP status code

    "200" Scenario: Different real response status When real status code is "500" Then Gavel will set some error for "status code" And Request or Response is NOT valid Scenario: Response status code match When real status code is "200" Then Gavel will NOT set any errors for "status code" And Request or Response is valid Gherkin / Cucumber
  6. Before I start writing a single line of code, I

    write the README and fill it with usage examples. I pretend that the module I want to build is already written and available, and I write some code with it. “ https://www.kennethreitz.org/essays/how-i-develop-things-and-why
  7. RDD

  8. # Requests The `requests` library allows you to perform HTTP

    requests from your Python code. ## Example ```python >>> r = requests.get('https://github.com') >>> r.status_code 200 ``` ## License MIT README.md
  9. Readme Driven Development • chance to think through the project

    first • docs are ready - no need to write them retroactively • your team can use the interface before it exists • easy to discuss the interface with everyone
  10. # Calendar API The API gives you various means to

    work with date and time. ## GET /now Provides you with current date and time. - Response 200 (application/json) ```json { "day": 29, "month": 2, "year": 2017, "hour": 11, "minute": 45, "second": 38 } ``` API.md
  11. language: "python" python: - "3.6" before_install: - "npm install -g

    dredd" script: - "dredd API.md http://localhost:8000" Continuous Integration
  12. Remember • think first, design first, docs first, test first

    • discuss the the interface design before implementing • use the interface before implementing (mocks, tests) • have your interface design as a single source of truth • test implementation against the design