├── .devcontainer └── devcontainer.json ├── .github └── workflows │ └── learnpack-audit.yml ├── .gitignore ├── .gitpod.Dockerfile ├── .gitpod.yml ├── .vscode └── settings.json ├── README.es.md ├── README.md ├── assets ├── preview.png └── traversion_json.png ├── exercises ├── 00-welcome │ ├── README.es.md │ └── README.md ├── 01-creating-a-request │ ├── README.es.md │ ├── README.md │ ├── app.py │ ├── solution.hide.py │ └── test.py ├── 02-random-status │ ├── README.es.md │ ├── README.md │ ├── app.py │ ├── solution.hide.py │ └── test.py ├── 03-response-body │ ├── README.es.md │ ├── README.md │ ├── app.py │ ├── solution.hide.py │ └── test.py ├── 04-response-body-json │ ├── README.es.md │ ├── README.md │ ├── app.py │ ├── solution.hide.py │ └── test.py ├── 05-project-name │ ├── README.es.md │ ├── README.md │ ├── app.py │ ├── solution.hide.py │ └── test.py ├── 06-project-list │ ├── README.es.md │ ├── README.md │ ├── app.py │ ├── solution.hide.py │ └── test.py ├── 07-project-list-image │ ├── README.es.md │ ├── README.md │ ├── app.py │ ├── solution.hide.py │ └── test.py ├── 08-blog-post-author │ ├── README.es.md │ ├── README.md │ ├── app.py │ ├── solution.hide.py │ └── test.py ├── 09-list-of-blog-titles │ ├── README.es.md │ ├── README.md │ ├── app.py │ ├── solution.hide.py │ └── test.py ├── 10-get-post-tags │ ├── README.es.md │ ├── README.md │ ├── app.py │ ├── solution.hide.py │ └── test.py ├── 11-get-attachment-by-id │ ├── README.es.md │ ├── README.md │ ├── app.py │ ├── solution.hide.py │ └── test.py ├── 12-post-request │ ├── README.es.md │ ├── README.md │ ├── app.py │ ├── solution.hide.py │ └── test.py └── 13-post-request-body │ ├── README.es.md │ ├── README.md │ ├── app.py │ ├── solution.hide.py │ └── test.py ├── learn.json └── preview.png /.devcontainer/devcontainer.json: -------------------------------------------------------------------------------- 1 | 2 | // For format details, see https://aka.ms/devcontainer.json. For config options, see the 3 | // README at: https://github.com/devcontainers/templates/tree/main/src/python 4 | { 5 | "name": "Python 3", 6 | // Or use a Dockerfile or Docker Compose file. More info: https://containers.dev/guide/dockerfile 7 | "image": "mcr.microsoft.com/devcontainers/python:0-3.10", 8 | "features": { 9 | "ghcr.io/devcontainers/features/node:1": { 10 | "nodeGypDependencies": true, 11 | "version": "16" 12 | } 13 | }, 14 | "customizations": { 15 | "vscode": { 16 | "settings": { 17 | "editor.defaultFormatter": "esbenp.prettier-vscode", 18 | "workbench.editorAssociations": { 19 | "*.md": "vscode.markdown.preview.editor" 20 | } 21 | }, 22 | "extensions": ["learn-pack.learnpack-vscode"] 23 | } 24 | }, 25 | "onCreateCommand": "pip3 install pytest==6.2.5 pytest-testdox mock toml requests && npm i @learnpack/learnpack@5.0.19 -g && learnpack plugins:install @learnpack/python@1.0.6" 26 | 27 | // Features to add to the dev container. More info: https://containers.dev/features. 28 | // "features": {}, 29 | 30 | // Use 'forwardPorts' to make a list of ports inside the container available locally. 31 | // "forwardPorts": [], 32 | 33 | // Use 'postCreateCommand' to run commands after the container is created. 34 | // "postCreateCommand": "pip3 install --user -r requirements.txt", 35 | 36 | // Configure tool-specific properties. 37 | // "customizations": {}, 38 | 39 | // Uncomment to connect as root instead. More info: https://aka.ms/dev-containers-non-root. 40 | // "remoteUser": "root" 41 | } 42 | -------------------------------------------------------------------------------- /.github/workflows/learnpack-audit.yml: -------------------------------------------------------------------------------- 1 | # This workflow will do a clean install of node dependencies, cache/restore them, build the source code and run tests across different versions of node 2 | # For more information see: https://help.github.com/actions/language-and-framework-guides/using-nodejs-with-github-actions 3 | 4 | name: Learnpack audit 5 | 6 | on: 7 | push: 8 | branches: [ main ] 9 | pull_request: 10 | branches: [ main ] 11 | 12 | jobs: 13 | build: 14 | 15 | runs-on: ubuntu-latest 16 | 17 | strategy: 18 | matrix: 19 | node-version: [20.x] 20 | # See supported Node.js release schedule at https://nodejs.org/en/about/releases/ 21 | 22 | steps: 23 | - uses: actions/checkout@v2 24 | - name: Use Node.js ${{ matrix.node-version }} 25 | uses: actions/setup-node@v2 26 | with: 27 | node-version: ${{ matrix.node-version }} 28 | - run: npm install @learnpack/learnpack@latest -g 29 | - run: learnpack audit -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Ignore everything 2 | /* 3 | 4 | !.gitignore 5 | !.devcontainer 6 | !.devcontainer/* 7 | !.gitpod.yml 8 | !.gitpod.Dockerfile 9 | !bc.json 10 | !learn.json 11 | !README.md 12 | !README.es.md 13 | !.vscode 14 | 15 | !/exercises 16 | !/exercises/* 17 | exercises/*/__pycache__/ 18 | 19 | !/.learn 20 | /.learn/** 21 | !/.learn/resets 22 | !/.learn/resets/** 23 | !/.learn/assets 24 | !/.learn/assets/** 25 | 26 | __pycache_ -------------------------------------------------------------------------------- /.gitpod.Dockerfile: -------------------------------------------------------------------------------- 1 | FROM gitpod/workspace-full:latest 2 | 3 | SHELL ["/bin/bash", "-c"] 4 | 5 | RUN sudo apt-get update \ 6 | && sudo apt-get update \ 7 | && sudo apt-get clean \ 8 | && sudo rm -rf /var/cache/apt/* /var/lib/apt/lists/* /tmp/* 9 | 10 | # That Gitpod install pyenv for me? no, thanks 11 | WORKDIR /home/gitpod/ 12 | RUN rm .pyenv -Rf 13 | RUN rm .gp_pyenv.d -Rf 14 | RUN curl https://pyenv.run | bash 15 | 16 | 17 | RUN pyenv update && pyenv install 3.10.7 && pyenv global 3.10.7 18 | RUN pip install pipenv 19 | 20 | # remove PIP_USER environment 21 | USER gitpod 22 | RUN if ! grep -q "export PIP_USER=no" "$HOME/.bashrc"; then printf '%s\n' "export PIP_USER=no" >> "$HOME/.bashrc"; fi 23 | RUN echo "" >> $HOME/.bashrc 24 | RUN echo "unset DATABASE_URL" >> $HOME/.bashrc 25 | RUN echo "export DATABASE_URL" >> $HOME/.bashrc 26 | 27 | RUN pip3 install pytest==6.2.5 pytest-testdox mock requests toml 28 | RUN npm i @learnpack/learnpack@2.1.39 -g && learnpack plugins:install @learnpack/python@1.0.3 29 | -------------------------------------------------------------------------------- /.gitpod.yml: -------------------------------------------------------------------------------- 1 | image: 2 | file: .gitpod.Dockerfile 3 | 4 | ports: 5 | - port: 3000 6 | onOpen: ignore 7 | 8 | vscode: 9 | extensions: 10 | - learn-pack.learnpack-vscode 11 | 12 | github: 13 | prebuilds: 14 | # enable for the master/default branch (defaults to true) 15 | master: true 16 | # enable for pull requests coming from this repo (defaults to true) 17 | pullRequests: false 18 | # add a "Review in Gitpod" button as a comment to pull requests (defaults to true) 19 | addComment: false 20 | -------------------------------------------------------------------------------- /.vscode/settings.json: -------------------------------------------------------------------------------- 1 | { 2 | "files.autoSave": "afterDelay", 3 | "files.autoSaveDelay": 700, 4 | "editor.minimap.enabled": false, 5 | "workbench.editorAssociations": { 6 | "*.md": "vscode.markdown.preview.editor" 7 | } 8 | } -------------------------------------------------------------------------------- /README.es.md: -------------------------------------------------------------------------------- 1 | 2 | # 🐍 Tutorial y Ejercicios de Python API Requests 3 | 4 | Por @alesanchezr y otros contribuidores de 4Geeks Academy 5 | 6 | 7 | En esta serie, aprenderás HTTP (*Hypertext Transfer Protocol*) y cómo usar el **package requests** de Python para crear solicitudes HTTP GET, POST, PUT, DELETE. 8 | 9 | Todo el tutorial es 👆 interactivo, ✅ calificado automáticamente y con 📹 videos tutoriales. 10 | 11 | Estos ejercicios son colaborativos, ¡te necesitamos! Si encuentras algún error o falta de ortografía, por favor contribuye y repórtalo. 12 | 13 | 14 | 15 | ## Instalación en un clic (recomendado) 16 | 17 | Puedes empezar estos ejercicios en pocos segundos haciendo clic en: [Abrir en Codespaces](https://codespaces.new/?repo=4GeeksAcademy/python-http-requests-api-tutorial-exercises) (recomendado) o [Abrir en Gitpod](https://gitpod.io#https://github.com/4GeeksAcademy/python-http-requests-api-tutorial-exercises). 18 | 19 | > Una vez ya tengas abierto VSCode los ejercicios de LearnPack deberían empezar automáticamente, si esto no sucede puedes intentar empezar los ejercicios escribiendo este comando en tu terminal: `$ learnpack start` 20 | 21 | ### Instalación local: 22 | 23 | Clona el repositorio en tu ambiente local y sigue los siguientes pasos: 24 | 25 | 1. Asegúrate de instalar [LearnPack](https://www.learnpack.co/), node.js versión 14+ y Python versión 3+. Este es el comando para instalar LearnPack: 26 | 27 | ```bash 28 | $ npm i learnpack -g 29 | $ learnpack plugins:install learnpack-python 30 | ``` 31 | 32 | 2. Comienza con los ejercicios ejecutando el siguiente comando al mismo nivel que tu archivo `learn.json`: 33 | 34 | ```bash 35 | $ pip3 install pytest==6.2.5 pytest-testdox mock requests toml 36 | $ learnpack start 37 | ``` 38 | 39 | 40 | ## ¿Cómo están organizados los ejercicios? 41 | 42 | Cada ejercicio es un pequeño proyecto en Python que contiene los siguientes archivos: 43 | 44 | 1. **app.py:** representa el archivo de entrada de Python que será ejecutado en el computador. 45 | 2. **README.md:** contiene las instrucciones del ejercicio. 46 | 3. **test.py:** no tienes que abrir este archivo. Contiene los scripts de pruebas del ejercicio. 47 | 48 | > Nota: Estos ejercicios tienen calificación automática. Los tests son muy rígidos y estrictos, mi recomendación es que no prestes demasiada atención a los tests y los uses solo como una sugerencia o podrías frustrarte. 49 | 50 | ## Colaboradores 51 | 52 | Gracias a estas personas maravillosas ([emoji key](https://github.com/kentcdodds/all-contributors#emoji-key)): 53 | 54 | 1. [Alejandro Sanchez (alesanchezr)](https://github.com/alesanchezr), contribución: (programador) 💻, (idea) 🤔, (build-tests) ⚠️, (pull-request-review) 👀, (build-tutorial) ✅, (documentación) 📖 55 | 56 | 2. [Paolo (plucodev)](https://github.com/plucodev), contribución: (bug reports) 🐛, (programador) 💻, (traducción) 🌎 57 | 58 | Este proyecto sigue la especificación [all-contributors](https://github.com/kentcdodds/all-contributors). ¡Todas las contribuciones son bienvenidas! 59 | 60 | Este y otros ejercicios son usados para [aprender a programar](https://4geeksacademy.com/es/aprender-a-programar/aprender-a-programar-desde-cero) por parte de los alumnos de 4Geeks Academy [Coding Bootcamp](https://4geeksacademy.com/es/inicio) realizado por [Alejandro Sánchez](https://twitter.com/alesanchezr) y muchos otros contribuyentes. Conoce más sobre nuestros [Cursos de Programación](https://4geeksacademy.com/es/curso-de-programacion-desde-cero?lang=es) para convertirte en [Full Stack Developer](https://4geeksacademy.com/es/coding-bootcamps/desarrollador-full-stack/?lang=es), o nuestro [Data Science Bootcamp](https://4geeksacademy.com/es/coding-bootcamps/curso-datascience-machine-learning). 61 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | 2 | # 🐍 Python API Requests Tutorial and Exercises 3 | 4 | By @alesanchezr and other contributors at 4Geeks Academy. 5 | 6 | *Estas instrucciones [están disponibles en 🇪🇸 español](https://github.com/4GeeksAcademy/python-http-requests-api-tutorial-exercises/blob/master/README.es.md) :es:* 7 | 8 | 9 | 10 | In this series you will Learn HTTP (*Hypertext Transfer Protocol*) and how to use the Python **requests package** to create HTTP requests GET, POST, PUT, DELETE. 11 | 12 | The entire tutorial is 👆 interactive, ✅ auto-graded and with 📹 video tutorials. 13 | 14 | These exercises were built in collaboration, we need you! If you find any bugs or misspells, please contribute and report them. 15 | 16 | 17 | ## One click installation (recommended): 18 | 19 | You can open these exercises in just a few seconds by clicking: [Open in Codespaces](https://codespaces.new/?repo=4GeeksAcademy/python-http-requests-api-tutorial-exercises) (recommended) or [Open in Gitpod](https://gitpod.io#https://github.com/4GeeksAcademy/python-http-requests-api-tutorial-exercises). 20 | 21 | > Once you have VSCode open, the LearnPack exercises should start automatically. If the exercises don't run automatically, you can try typing on your terminal: `$ learnpack start` 22 | 23 | ## Local Installation 24 | 25 | Clone the repository in your local environment and follow the steps below: 26 | 27 | 1. Make sure you install [LearnPack](https://www.learnpack.co/), node.js version 14+, and Python version 3+. This is the command to install LearnPack: 28 | 29 | ```bash 30 | $ npm i learnpack -g 31 | $ learnpack plugins:install learnpack-python 32 | ``` 33 | 34 | 2. Start the tutorial/exercises by running the following command at the same level your `learn.json` file is: 35 | 36 | ```bash 37 | $ pip3 install pytest==6.2.5 pytest-testdox mock requests toml 38 | $ learnpack start 39 | ``` 40 | 41 | 42 | ## How are the exercises organized? 43 | 44 | Each exercise is a small react application containing the following files: 45 | 46 | 1. **app.py:** represents the entry python file that will be executed by the computer. 47 | 2. **README.md:** contains exercise instructions. 48 | 3. **test.py:** you don't have to open this file, it contains the testing script for the exercise. 49 | 50 | > Note: The exercises have automatic grading, but they're very rigid and strict, my recommendation is to not take the tests too serious and use them only as a suggestion, or you may get frustrated. 51 | 52 | ## Contributors 53 | 54 | Thanks goes to these wonderful people ([emoji key](https://github.com/kentcdodds/all-contributors#emoji-key)): 55 | 56 | 1. [Alejandro Sanchez (alesanchezr)](https://github.com/alesanchezr), contribution: (coder) 💻, (idea) 🤔, (build-tests) ⚠️, (pull-request-review) 👀, (build-tutorial) ✅, (documentation) 📖 57 | 58 | 2. [Paolo (plucodev)](https://github.com/plucodev), contribution: (bug reports) 🐛, contribution: (coder) 💻, (translation) 🌎 59 | 60 | This project follows the [all-contributors](https://github.com/kentcdodds/all-contributors) specification. Contributions of any kind are welcome! 61 | 62 | This and many other exercises are built by students as part of the 4Geeks Academy [Coding Bootcamp](https://4geeksacademy.com/us/coding-bootcamp) by [Alejandro Sánchez](https://twitter.com/alesanchezr) and many other contributors. Find out more about our [Full Stack Developer Course](https://4geeksacademy.com/us/coding-bootcamps/part-time-full-stack-developer), and [Data Science Bootcamp](https://4geeksacademy.com/us/coding-bootcamps/datascience-machine-learning). 63 | -------------------------------------------------------------------------------- /assets/preview.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/4GeeksAcademy/python-http-requests-api-tutorial-exercises/f90a785f2d248c29bf0fe9b35c392c53be8d805b/assets/preview.png -------------------------------------------------------------------------------- /assets/traversion_json.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/4GeeksAcademy/python-http-requests-api-tutorial-exercises/f90a785f2d248c29bf0fe9b35c392c53be8d805b/assets/traversion_json.png -------------------------------------------------------------------------------- /exercises/00-welcome/README.es.md: -------------------------------------------------------------------------------- 1 | --- 2 | intro: "https://www.youtube.com/watch?v=6H4Gn6-lpLI" 3 | --- 4 | 5 | # `00` Welcome to Python API Requests! 6 | 7 | Python Requests es una herramienta potente y ampliamente utilizada para interactuar con APIs y realizar solicitudes HTTP en aplicaciones Python. Simplifica el proceso de enviar solicitudes HTTP y manejar respuestas, convirtiéndose en una herramienta favorita entre los desarrolladores para integrarse con servicios web y obtener datos de APIs. 8 | 9 | Con Python Requests, puedes hacer fácilmente solicitudes GET, POST, PUT, DELETE para comunicarte con servidores web y obtener datos. Admite el manejo de autenticación, encabezados, cookies y sesiones, permitiendo una integración sin problemas con diversos servicios web. 10 | 11 | Aquí aprenderás: 12 | 13 | 1. ¿Cómo hacer solicitudes GET? 14 | 2. ¿Cómo obtener propiedades de datos e información? 15 | 3. ¿Cómo configurar request headers? 16 | 4. ¿Cómo configurar request content-type? 17 | 5. ¿Cómo hacer solicitudes POST? 18 | 19 | Haga clic en el botón `Next →` en la esquina superior derecha para continuar. 20 | -------------------------------------------------------------------------------- /exercises/00-welcome/README.md: -------------------------------------------------------------------------------- 1 | # `00` Welcome to Python API Requests! 2 | 3 | Python Requests is a powerful and widely-used package for interacting with APIs and performing HTTP requests in Python applications. It simplifies the process of sending HTTP requests and handling responses, making it a favorite tool among developers for integrating with web services and fetching data from APIs. 4 | 5 | With Python Requests, you can easily make GET, POST, PUT, DELETE, to communicate with web servers and retrieve data. It supports handling authentication, headers, cookies, and sessions, allowing for seamless integration with various web services. 6 | 7 | Here you will learn: 8 | 9 | 1. How to do GET requests? 10 | 2. How to fetch data properties and information? 11 | 3. How to set request headers? 12 | 4. How to set request content-type? 13 | 5. How to do POST requests? 14 | 15 | Click the `Next →` button on the top right to continue. 16 | -------------------------------------------------------------------------------- /exercises/01-creating-a-request/README.es.md: -------------------------------------------------------------------------------- 1 | --- 2 | tutorial: "https://www.youtube.com/watch?v=eZ_5p3vyYFY" 3 | --- 4 | 5 | # `01` Creating a Request 6 | 7 | Python tiene integrado un [paquete de solicitudes (*requests package*)](https://requests.readthedocs.io/en/master/) eso permite a los desarrolladores crear solicitudes HTTP con bastante facilidad. 8 | 9 | Así es como en Python hacemos una solicitud HTTP GET: 10 | 11 | ```python 12 | response = requests.get('') 13 | print(response.status_code) 14 | ``` 15 | 16 | ## 📝 Instrucciones: 17 | 18 | Actualiza la variable `url` para que solicite a esta dirección: 19 | 20 | ```bash 21 | https://assets.breatheco.de/apis/fake/sample/hello.php 22 | ``` 23 | 24 | > Nota: La consola debe imprimir un código de estado 200. -------------------------------------------------------------------------------- /exercises/01-creating-a-request/README.md: -------------------------------------------------------------------------------- 1 | # `01` Creating a Request 2 | 3 | Python has a [requests package](https://requests.readthedocs.io/en/master/) that allows developers to create HTTP request pretty easily. 4 | 5 | In python this is how we make an HTTP GET request: 6 | 7 | ```python 8 | response = requests.get('') 9 | print(response.status_code) 10 | ``` 11 | 12 | ## 📝 Instructions: 13 | 14 | Update the `url` variable to make it request to this address: 15 | 16 | ```text 17 | https://assets.breatheco.de/apis/fake/sample/hello.php 18 | ``` 19 | 20 | > Note: The console should print a 200 status code. -------------------------------------------------------------------------------- /exercises/01-creating-a-request/app.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | url = "https://assets.breatheco.de/apis/fake/sample/404-example.php" 4 | # url = "https://assets.breatheco.de/apis/fake/sample/hello.php" 5 | response = requests.get(url) 6 | 7 | print("The response status is: "+str(response.status_code)) -------------------------------------------------------------------------------- /exercises/01-creating-a-request/solution.hide.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | url = "https://assets.breatheco.de/apis/fake/sample/hello.php" 4 | response = requests.get(url) 5 | 6 | print("The response status is: "+str(response.status_code)) -------------------------------------------------------------------------------- /exercises/01-creating-a-request/test.py: -------------------------------------------------------------------------------- 1 | import json, pytest 2 | from mock import patch 3 | 4 | @pytest.mark.it("Update the url to hello.php") 5 | def test_url(app): 6 | with patch('requests.get') as mock_request: 7 | app() 8 | url = "https://assets.breatheco.de/apis/fake/sample/hello.php" 9 | assert mock_request.call_args.args[0] == url -------------------------------------------------------------------------------- /exercises/02-random-status/README.es.md: -------------------------------------------------------------------------------- 1 | --- 2 | tutorial: "https://www.youtube.com/watch?v=La95dYo4xOs" 3 | --- 4 | 5 | # `02` Handle Response Status 6 | 7 | La siguiente solicitud GET siempre devuelve un código de status diferente, nunca se sabe qué respuesta está recibiendo del servidor. 8 | 9 | ## 📝 Instrucciones: 10 | 11 | Crea una condición para imprimir en la consola los siguientes mensajes según el status de respuesta: 12 | 13 | | Status | Mensaje | 14 | | ----- | ----- | 15 | | 404 | The URL you asked for is not found | 16 | | 503 | Unavailable right now | 17 | | 200 | Everything went perfect | 18 | | 400 | Something is wrong with the request params | 19 | | Otro código de status | Unknown status code | -------------------------------------------------------------------------------- /exercises/02-random-status/README.md: -------------------------------------------------------------------------------- 1 | # `02` Handle Response Status 2 | 3 | The following GET request is always returning a different status code; you never know what response you are getting from the server. 4 | 5 | ## 📝 Instructions: 6 | 7 | Create a condition to print on the console the following messages, depending on the response status: 8 | 9 | | Status | Message | 10 | | ----- | ----- | 11 | | 404 | The URL you asked for is not found | 12 | | 503 | Unavailable right now | 13 | | 200 | Everything went perfect | 14 | | 400 | Something is wrong with the request params | 15 | | Any other code | Unknown status code | -------------------------------------------------------------------------------- /exercises/02-random-status/app.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | response = requests.get("https://assets.breatheco.de/apis/fake/sample/random-status.php") 4 | -------------------------------------------------------------------------------- /exercises/02-random-status/solution.hide.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | response = requests.get("https://assets.breatheco.de/apis/fake/sample/random-status.php") 4 | 5 | if response.status_code == 404: 6 | print("The URL you asked for is not found") 7 | elif response.status_code == 503: 8 | print("Unavailable right now") 9 | elif response.status_code == 200: 10 | print("Everything went perfect") 11 | elif response.status_code == 400: 12 | print("Something is wrong with the request params") 13 | else: 14 | print("Unknown status code") -------------------------------------------------------------------------------- /exercises/02-random-status/test.py: -------------------------------------------------------------------------------- 1 | import json, pytest 2 | from mock import patch 3 | 4 | @pytest.mark.it("requests.get has to be called for the random-status.php url") 5 | def test_url_call(capsys, app): 6 | with patch('requests.get') as mock_request: 7 | app() 8 | mock_request.assert_called_once_with("https://assets.breatheco.de/apis/fake/sample/random-status.php") 9 | 10 | 11 | @pytest.mark.it("Testing for 200: Everything went perfect") 12 | def test_url_200(capsys, app): 13 | with patch('requests.get') as mock_request: 14 | mock_request.return_value.status_code = 200 15 | app() 16 | captured = capsys.readouterr() 17 | assert "Everything went perfect\n" == captured.out 18 | 19 | @pytest.mark.it("Testing for 404: The URL you asked for is not found'") 20 | def test_url_404(capsys, app): 21 | with patch('requests.get') as mock_request: 22 | mock_request.return_value.status_code = 404 23 | app() 24 | captured = capsys.readouterr() 25 | assert "The URL you asked for is not found\n" == captured.out 26 | 27 | @pytest.mark.it("Testing for 503: Unavailable right now") 28 | def test_url_503(capsys, app): 29 | with patch('requests.get') as mock_request: 30 | mock_request.return_value.status_code = 503 31 | app() 32 | captured = capsys.readouterr() 33 | assert "Unavailable right now\n" == captured.out 34 | 35 | @pytest.mark.it("Testing for 400: Something is wrong with the request params") 36 | def test_url_400(capsys, app): 37 | with patch('requests.get') as mock_request: 38 | mock_request.return_value.status_code = 400 39 | app() 40 | captured = capsys.readouterr() 41 | assert "Something is wrong with the request params\n" == captured.out 42 | 43 | @pytest.mark.it("Testing for any other code: Unknown status code") 44 | def test_url_generic_response(capsys, app): 45 | with patch('requests.get') as mock_request: 46 | mock_request.return_value.status_code = 500 # For example, using status code 500 for generic response 47 | app() 48 | captured = capsys.readouterr() 49 | assert "Unknown status code\n" == captured.out -------------------------------------------------------------------------------- /exercises/03-response-body/README.es.md: -------------------------------------------------------------------------------- 1 | --- 2 | tutorial: "https://www.youtube.com/watch?v=kQGUUW4ycDQ" 3 | --- 4 | 5 | # `03` Response Body 6 | 7 | Haga clic en este enlace para ver la respuesta que esta solicitud GET está dando en el body: 8 | [https://assets.breatheco.de/apis/fake/sample/random-status.php](https://assets.breatheco.de/apis/fake/sample/random-status.php) 9 | 10 | Ahora, si deseas obtener el *body* de la respuesta (texto/contenido), todo lo que tienes que hacer es: 11 | 12 | ```py 13 | print(response.text) 14 | ``` 15 | 16 | ## 📝 Instrucciones: 17 | 18 | Imprime en la consola el *body* de la respuesta solo para solicitudes con status `200`, para el resto imprime: 19 | 20 | ```text 21 | "Something went wrong" 22 | ``` -------------------------------------------------------------------------------- /exercises/03-response-body/README.md: -------------------------------------------------------------------------------- 1 | # `03` Response Body 2 | 3 | Click on this link to see the response body that this GET request is giving: 4 | [https://assets.breatheco.de/apis/fake/sample/random-status.php](https://assets.breatheco.de/apis/fake/sample/random-status.php) 5 | 6 | Now, if you want to get that response body (text/content) all you have to do is this: 7 | 8 | ```py 9 | print(response.text) 10 | ``` 11 | 12 | ## 📝 Instructions: 13 | 14 | Print on the console the response body for status code `200`, for all the other print: 15 | 16 | ```text 17 | "Something went wrong" 18 | ``` -------------------------------------------------------------------------------- /exercises/03-response-body/app.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | url = "https://assets.breatheco.de/apis/fake/sample/random-status.php" 4 | -------------------------------------------------------------------------------- /exercises/03-response-body/solution.hide.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | url = "https://assets.breatheco.de/apis/fake/sample/random-status.php" 4 | 5 | response = requests.get(url) 6 | 7 | if response.status_code == 200: 8 | print(response.text) 9 | else: 10 | print("Something went wrong") -------------------------------------------------------------------------------- /exercises/03-response-body/test.py: -------------------------------------------------------------------------------- 1 | import json, pytest 2 | from mock import patch 3 | 4 | @pytest.mark.it("requests.get has to be called for the random-status.php url") 5 | def test_url_call(capsys, app): 6 | with patch('requests.get') as mock_request: 7 | app() 8 | mock_request.assert_called_once_with("https://assets.breatheco.de/apis/fake/sample/random-status.php") 9 | 10 | @pytest.mark.it("Testing for 200: Ok") 11 | def test_url_200(capsys, app): 12 | with patch('requests.get') as mock_request: 13 | mock_request.return_value.status_code = 200 14 | mock_request.return_value.text = "something" 15 | app() 16 | captured = capsys.readouterr() 17 | assert "something\n" == captured.out 18 | 19 | @pytest.mark.it("Testing for any other code: Something went wrong") 20 | def test_url_404(capsys, app): 21 | with patch('requests.get') as mock_request: 22 | mock_request.return_value.status_code = 404 23 | app() 24 | captured = capsys.readouterr() 25 | assert "Something went wrong\n" == captured.out -------------------------------------------------------------------------------- /exercises/04-response-body-json/README.es.md: -------------------------------------------------------------------------------- 1 | --- 2 | tutorial: "https://www.youtube.com/watch?v=si3N6peHdjM" 3 | --- 4 | 5 | # `04` Response JSON 6 | 7 | Pero tener una respuesta basada en texto no es muy útil, es por eso que las API normalmente responden en formato CSV, JSON, YAML o XML. 8 | 9 | ## 📝 Instrucciones: 10 | 11 | El siguiente endpoint devuelve la hora actual en un formato JSON cada vez que se solicita utilizando el método GET. 12 | 13 | | | | 14 | | --- | --- | 15 | | method | GET | 16 | | endpoint | https://assets.breatheco.de/apis/fake/sample/time.php | 17 | | content-type | application/json | 18 | 19 | Response body: 20 | 21 | ```python 22 | { 23 | "hours": "07", 24 | "minutes": "29", 25 | "seconds": "35" 26 | } 27 | ``` 28 | 29 | 1. Haz una solicitud GET a ese endpoint e imprime la hora en la consola con este formato: 30 | 31 | ```bash 32 | Current time: 17 hrs 06 min and 23 sec 33 | ``` 34 | 35 | ## 💡 Pistas: 36 | 37 | + Usa el [metodo .json()](https://www.w3schools.com/python/ref_requests_response.asp) para obtener el response body como un diccionario y almacenarlo en una variable. 38 | + Obtenga las propiedades `hours`, `minutes` y `seconds` del diccionario. 39 | + Concatenar todo de esta manera: `Hora actual: 17 h 06 min y 23 seg`. 40 | 41 | -------------------------------------------------------------------------------- /exercises/04-response-body-json/README.md: -------------------------------------------------------------------------------- 1 | # `04` Response JSON 2 | 3 | But having a text based response is not very useful, that is why APIs normally respond in CSV, JSON, YAML or XML format. 4 | 5 | ## 📝 Instructions: 6 | 7 | The following endpoint returns the current time in a JSON format every time it is requested using the GET method. 8 | 9 | | | | 10 | | --- | --- | 11 | | method | GET | 12 | | endpoint | https://assets.breatheco.de/apis/fake/sample/time.php | 13 | | content-type | application/json | 14 | 15 | Response body: 16 | 17 | ```python 18 | { 19 | "hours": "07", 20 | "minutes": "29", 21 | "seconds": "35" 22 | } 23 | ``` 24 | 25 | 1. Please do a GET request to that endpoint and print the time on the console with this format: 26 | 27 | ```text 28 | Current time: 17 hrs 06 min and 23 sec 29 | ``` 30 | 31 | ## 💡 Hints: 32 | 33 | + Use the [.json() method](https://www.w3schools.com/python/ref_requests_response.asp) to get the response body as a dictionary and store it in a variable. 34 | + Get the `hours`, `minutes` and `seconds` properties from the dictionary. 35 | + Concatenate everything together like this: `Current time: 17 hrs 06 min and 23 sec`. 36 | 37 | -------------------------------------------------------------------------------- /exercises/04-response-body-json/app.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | response = requests.get("https://assets.breatheco.de/apis/fake/sample/time.php") 4 | print(response.text) -------------------------------------------------------------------------------- /exercises/04-response-body-json/solution.hide.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | response = requests.get("https://assets.breatheco.de/apis/fake/sample/time.php") 4 | 5 | if response.status_code == 200: 6 | # Parsing JSON response 7 | time_data = response.json() 8 | 9 | # Extracting hours, minutes, and seconds 10 | hours = time_data["hours"] 11 | minutes = time_data["minutes"] 12 | seconds = time_data["seconds"] 13 | 14 | print(f"Current time: {hours} hrs {minutes} min and {seconds} sec") 15 | else: 16 | print("Failed to fetch current time.") -------------------------------------------------------------------------------- /exercises/04-response-body-json/test.py: -------------------------------------------------------------------------------- 1 | import json, pytest 2 | from mock import patch 3 | 4 | class FakeResponse(object): 5 | # default response attributes 6 | status_code = 200 7 | content = '{"hours":"19","minutes":"45","seconds":"06"}' 8 | def json(self): 9 | return {"hours":"19","minutes":"45","seconds":"06"} 10 | 11 | @pytest.mark.it("requests.get has to be called for the time.php url") 12 | def test_url_call(capsys, app): 13 | with patch('requests.get') as mock_request: 14 | app() 15 | mock_request.assert_called_once_with("https://assets.breatheco.de/apis/fake/sample/time.php") 16 | 17 | @pytest.mark.it("You should print on the console a string like: Current time: 19 hrs 45 min and 06 sec") 18 | def test_url_output(capsys, app): 19 | with patch('requests.get') as mock_request: 20 | mock_request.return_value = FakeResponse() 21 | app() 22 | captured = capsys.readouterr() 23 | assert "Current time: 19 hrs 45 min and 06 sec\n" == captured.out -------------------------------------------------------------------------------- /exercises/05-project-name/README.es.md: -------------------------------------------------------------------------------- 1 | --- 2 | tutorial: "https://www.youtube.com/watch?v=sMA0NjIiVNs" 3 | --- 4 | 5 | 6 | # `05` Project name 7 | 8 | El siguiente endpoint es ideal para recuperar proyectos de estudiantes: 9 | 10 | GET [https://assets.breatheco.de/apis/fake/sample/project1.php](https://assets.breatheco.de/apis/fake/sample/project1.php) 11 | 12 | ```json 13 | { 14 | "name": "Coursera eLearning", 15 | "thumb": "https://unsplash.it/450/320?image=178", 16 | "description": "The coolest eLearning site on the planet", 17 | "images": [ 18 | "https://unsplash.it/450/320?image=178", 19 | "https://unsplash.it/450/320?image=179", 20 | "https://unsplash.it/450/320?image=180", 21 | "https://unsplash.it/450/320?image=181" 22 | ] 23 | } 24 | ``` 25 | 26 | ## 📝 Instrucciones: 27 | 28 | 1. Llama al endpoint e imprime el nombre del proyecto en el terminal (solo el nombre del proyecto). 29 | 30 | Ejemplo de salida: 31 | 32 | ```text 33 | Coursera eLearning 34 | ``` 35 | 36 | ## 💡 Pistas: 37 | 38 | + Haz una solicitud GET al endpoint. 39 | + Usa el [metodo .json()](https://www.w3schools.com/python/ref_requests_response.asp) para obtener el response body como un diccionario (igual que en el último ejercicio). 40 | + Imprime el nombre del proyecto, puedes acceder al nombre de la propiedad en el diccionario de respuestas. 41 | 42 | -------------------------------------------------------------------------------- /exercises/05-project-name/README.md: -------------------------------------------------------------------------------- 1 | # `05` Project name 2 | 3 | The following endpoint is ideal to retrieve student projects: 4 | 5 | GET [https://assets.breatheco.de/apis/fake/sample/project1.php](https://assets.breatheco.de/apis/fake/sample/project1.php) 6 | 7 | ```json 8 | { 9 | "name": "Coursera eLearning", 10 | "thumb": "https://unsplash.it/450/320?image=178", 11 | "description": "The coolest eLearning site on the planet", 12 | "images": [ 13 | "https://unsplash.it/450/320?image=178", 14 | "https://unsplash.it/450/320?image=179", 15 | "https://unsplash.it/450/320?image=180", 16 | "https://unsplash.it/450/320?image=181" 17 | ] 18 | } 19 | ``` 20 | 21 | ## 📝 Instructions: 22 | 23 | 1. Please call the endpoint and print the project name on the terminal (only the project name). 24 | 25 | Example output: 26 | 27 | ```text 28 | Coursera eLearning 29 | ``` 30 | 31 | ## 💡 Hints: 32 | 33 | + Make a GET request to the endpoint. 34 | + Use the [.json() method](https://www.w3schools.com/python/ref_requests_response.asp) to get the response body as a dictionary (same as you did on the last exercise). 35 | + Print the project name; you can access the property name in the response dictionary. 36 | 37 | -------------------------------------------------------------------------------- /exercises/05-project-name/app.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | # Your code here -------------------------------------------------------------------------------- /exercises/05-project-name/solution.hide.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | # Your code here 4 | response = requests.get("https://assets.breatheco.de/apis/fake/sample/project1.php") 5 | 6 | if response.status_code == 200: 7 | # Parsing JSON response 8 | project_data = response.json() 9 | 10 | # Extracting project name 11 | project_name = project_data["name"] 12 | 13 | print(project_name) 14 | else: 15 | print("Failed to fetch project data.") -------------------------------------------------------------------------------- /exercises/05-project-name/test.py: -------------------------------------------------------------------------------- 1 | import json, pytest 2 | from mock import patch 3 | 4 | class FakeResponse(object): 5 | # default response attributes 6 | status_code = 200 7 | def json(self): 8 | return { 9 | "name": "Sample Project", 10 | "thumb": "https://unsplash.it/450/320?image=178", 11 | "description": "The coolest eLearning site on the planet", 12 | "images": [ 13 | "https://unsplash.it/450/320?image=178", 14 | "https://unsplash.it/450/320?image=179", 15 | "https://unsplash.it/450/320?image=180", 16 | "https://unsplash.it/450/320?image=181" 17 | ] 18 | } 19 | 20 | @pytest.mark.it("requests.get has to be called for the project.php url") 21 | def test_url_call(capsys, app): 22 | with patch('requests.get') as mock_request: 23 | app() 24 | mock_request.assert_called_once_with("https://assets.breatheco.de/apis/fake/sample/project1.php") 25 | 26 | 27 | @pytest.mark.it("You should print the name of the project on the console") 28 | def test_url_output(capsys, app): 29 | with patch('requests.get') as mock_request: 30 | mock_request.return_value = FakeResponse() 31 | app() 32 | captured = capsys.readouterr() 33 | assert "Sample Project\n" == captured.out -------------------------------------------------------------------------------- /exercises/06-project-list/README.es.md: -------------------------------------------------------------------------------- 1 | --- 2 | tutorial: "https://www.youtube.com/watch?v=S2qXbTLRyGA" 3 | --- 4 | 5 | # `06` Project List 6 | 7 | El siguiente endpoint devuelve una respuesta en formato JSON con varios proyectos en una lista: 8 | 9 | GET: [https://assets.breatheco.de/apis/fake/sample/project_list.php](https://assets.breatheco.de/apis/fake/sample/project_list.php) 10 | 11 | Cada uno de los proyectos tiene el siguiente formato (ejemplo): 12 | 13 | ```json 14 | { 15 | "name": "Coursera eLearning", 16 | "thumb": "https://unsplash.it/450/320?image=178", 17 | "description": "The coolest eLearning site on the planet", 18 | "images": [ 19 | "https://unsplash.it/450/320?image=178", 20 | "https://unsplash.it/450/320?image=179", 21 | "https://unsplash.it/450/320?image=180", 22 | "https://unsplash.it/450/320?image=181" 23 | ] 24 | } 25 | ``` 26 | 27 | ## 📝 Instrucciones: 28 | 29 | 1. Llama al endpoint e imprime el nombre del **SEGUNDO** proyecto en la lista: 30 | 31 | Ejemplo de salida: 32 | 33 | ```text 34 | Coursera eLearning 35 | ``` 36 | 37 | ## 💡 Pistas: 38 | 39 | + Abre el endpoint en tu navegador y analiza la respuesta que se encuentra en el body, necesitas saber qué esperar, cuál será la estructura de los datos (response body) que devuelve el servidor. 40 | + En este caso, el response body comienza con un corchete `[`, es una lista, debes acceder al segundo proyecto utilizando posiciones numéricas. 41 | + Haz una solicitud GET al endpoint. 42 | + Usa el [metodo .json()](https://www.w3schools.com/python/ref_requests_response.asp) para obtener el response body como un diccionario. 43 | + Encuentra el segundo proyecto de la lista. 44 | + Imprime el nombre del proyecto, puedes acceder a la propiedad `name` del diccionario del proyecto. 45 | + No necesitas hacer un bucle (loop), solo accede al segundo elemento como una lista usando la posición. 46 | 47 | -------------------------------------------------------------------------------- /exercises/06-project-list/README.md: -------------------------------------------------------------------------------- 1 | # `06` Project List 2 | 3 | The following endpoint returns a JSON formatted response with several projects in a list: 4 | 5 | GET: [https://assets.breatheco.de/apis/fake/sample/project_list.php](https://assets.breatheco.de/apis/fake/sample/project_list.php) 6 | 7 | Each of the projects has the following format (example): 8 | 9 | ```json 10 | { 11 | "name": "Coursera eLearning", 12 | "thumb": "https://unsplash.it/450/320?image=178", 13 | "description": "The coolest eLearning site on the planet", 14 | "images": [ 15 | "https://unsplash.it/450/320?image=178", 16 | "https://unsplash.it/450/320?image=179", 17 | "https://unsplash.it/450/320?image=180", 18 | "https://unsplash.it/450/320?image=181" 19 | ] 20 | } 21 | ``` 22 | 23 | ## 📝 Instructions: 24 | 25 | 1. Please call the endpoint and print the name of the **SECOND** project on the list: 26 | 27 | Example output: 28 | ```text 29 | Coursera eLearning 30 | ``` 31 | 32 | ## 💡 Hints: 33 | 34 | + Open the endpoint on your browser and analyze the response body, you need to know what to expect, what is going to be the structure of the data (response body) coming back from the server. 35 | + In this case, the response body starts with a square bracket `[`, it's a list, and you have to access the second project by using numerical positions. 36 | + Make a GET request to the endpoint. 37 | + Use the [.json() method](https://www.w3schools.com/python/ref_requests_response.asp) to get the response body as a dictionary. 38 | + Find the second project on the list. 39 | + Print the project name, you can access the property `name` of the project dictionary. 40 | + You don't need to loop, just access the second item like a list using the position. 41 | 42 | -------------------------------------------------------------------------------- /exercises/06-project-list/app.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | # Your code here -------------------------------------------------------------------------------- /exercises/06-project-list/solution.hide.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | # Your code here 4 | response = requests.get("https://assets.breatheco.de/apis/fake/sample/project_list.php") 5 | 6 | if response.status_code == 200: 7 | # Parsing JSON response 8 | project_list = response.json() 9 | 10 | # Extracting the name of the second project 11 | second_project_name = project_list[1]["name"] 12 | 13 | print(second_project_name) 14 | else: 15 | print("Failed to fetch project list.") -------------------------------------------------------------------------------- /exercises/06-project-list/test.py: -------------------------------------------------------------------------------- 1 | import json, pytest 2 | from mock import patch 3 | 4 | class FakeResponse(object): 5 | # default response attributes 6 | status_code = 200 7 | def json(self): 8 | return [{ 9 | "name": "Starbucks for milkshakes", 10 | "thumb": "https://unsplash.it/450/320?image=178", 11 | "description": "", 12 | "images": [ 13 | "https://unsplash.it/450/320?image=178", 14 | "https://unsplash.it/450/320?image=179", 15 | "https://unsplash.it/450/320?image=180", 16 | "https://unsplash.it/450/320?image=181" 17 | ] 18 | }, 19 | { 20 | "name": "Uber for trucks", 21 | "thumb": "https://unsplash.it/450/320?image=178", 22 | "description": "", 23 | "images": [ 24 | "https://unsplash.it/450/320?image=178", 25 | "https://unsplash.it/450/320?image=179", 26 | "https://unsplash.it/450/320?image=180", 27 | "https://unsplash.it/450/320?image=181" 28 | ] 29 | }, 30 | { 31 | "name": "McDonalds for tacos", 32 | "thumb": "https://unsplash.it/450/320?image=178", 33 | "description": "", 34 | "images": [ 35 | "https://unsplash.it/450/320?image=178", 36 | "https://unsplash.it/450/320?image=179", 37 | "https://unsplash.it/450/320?image=180", 38 | "https://unsplash.it/450/320?image=181" 39 | ] 40 | } 41 | ] 42 | 43 | @pytest.mark.it("requests.get has to be called for the project_list.php url") 44 | def test_url_call(capsys, app): 45 | with patch('requests.get') as mock_request: 46 | app() 47 | mock_request.assert_called_once_with("https://assets.breatheco.de/apis/fake/sample/project_list.php") 48 | 49 | @pytest.mark.it("The printed position should be 1 (not 2 because lists indexes start at 0)") 50 | def test_url_output2(capsys, app): 51 | with patch('requests.get') as mock_request: 52 | mock_request.return_value = FakeResponse() 53 | app() 54 | captured = capsys.readouterr() 55 | assert "McDonalds for tacos\n" != captured.out 56 | 57 | @pytest.mark.it("Make sure you are printing the project name") 58 | def test_url_output1(capsys, app): 59 | with patch('requests.get') as mock_request: 60 | mock_request.return_value = FakeResponse() 61 | app() 62 | captured = capsys.readouterr() 63 | assert "Uber for trucks\n" == captured.out 64 | -------------------------------------------------------------------------------- /exercises/07-project-list-image/README.es.md: -------------------------------------------------------------------------------- 1 | --- 2 | tutorial: "https://www.youtube.com/watch?v=U7vhqOETpqk" 3 | --- 4 | 5 | # `07` Project List Image 6 | 7 | ## 📝 Instrucciones: 8 | 9 | 1. Haz una solicitud GET a la misma URL que en el ejercicio anterior, imprime la **última** URL de las imagenes del **último** proyecto. 10 | 11 | Ejemplo: 12 | 13 | ```text 14 | https://image.shutterstock.com/image-vector/trophy-cup-award-vector-icon-260nw-592525184.jpg 15 | ``` 16 | 17 | ## 💡 Pistas: 18 | 19 | + Haz una solicitud GET al endpoint. 20 | + Usa el [metodo .json()](https://www.w3schools.com/python/ref_requests_response.asp) para obtener el response body como un diccionario. 21 | + Encuentra el último proyecto en la lista. 22 | + Encuentra la última imagen de ese proyecto. 23 | + Imprime la URL de esa imagen en la consola. 24 | + No es necesario realizar un bucle, solo usa las posiciones numéricas (índice/index) para acceder a la información. 25 | 26 | -------------------------------------------------------------------------------- /exercises/07-project-list-image/README.md: -------------------------------------------------------------------------------- 1 | # `07` Project List Image 2 | 3 | ## 📝 Instructions: 4 | 5 | 1. Do a GET request to the same URL as in the previous exercise, print the **last** image URL in the **last** project. 6 | 7 | Example output: 8 | 9 | ```text 10 | https://image.shutterstock.com/image-vector/trophy-cup-award-vector-icon-260nw-592525184.jpg 11 | ``` 12 | 13 | ## 💡 Hints: 14 | 15 | + Do a GET request to the endpoint. 16 | + Use the [.json() method](https://www.w3schools.com/python/ref_requests_response.asp) to get the response body as a dictionary. 17 | + Find the last project on the list. 18 | + Find the last image of that project. 19 | + Print the image URL on the console. 20 | + No need to loop, just use the numerical positions (index) to access the information. 21 | 22 | -------------------------------------------------------------------------------- /exercises/07-project-list-image/app.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | # Your code here -------------------------------------------------------------------------------- /exercises/07-project-list-image/solution.hide.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | # Your code here 4 | response = requests.get("https://assets.breatheco.de/apis/fake/sample/project_list.php") 5 | 6 | if response.status_code == 200: 7 | # Parsing JSON response 8 | project_list = response.json() 9 | 10 | # Extracting the last project 11 | last_project = project_list[-1] 12 | 13 | # Extracting the last image URL 14 | last_image_url = last_project["images"][-1] 15 | 16 | # Printing the last image URL 17 | print(last_image_url) 18 | else: 19 | print("Failed to fetch project list.") -------------------------------------------------------------------------------- /exercises/07-project-list-image/test.py: -------------------------------------------------------------------------------- 1 | import json, pytest 2 | from mock import patch 3 | 4 | class FakeResponse(object): 5 | # default response attributes 6 | status_code = 200 7 | def json(self): 8 | return [ 9 | { 10 | "name" : "Amazon eCommerce", 11 | "thumb" : "https://unsplash.it/450/320?image=778", 12 | "description" : "This website is an eCommerce made to sell books online", 13 | "images" : [ 14 | "https://unsplash.it/450/320?image=778", 15 | "https://unsplash.it/450/320?image=779", 16 | ] 17 | }, 18 | { 19 | "name" : "Coursera eLearning", 20 | "thumb" : "https://unsplash.it/450/320?image=178", 21 | "description" : "The coolest eLearning site on the planet", 22 | "images" : [ 23 | "https://unsplash.it/450/320?image=178", 24 | "https://unsplash.it/450/320?image=179", 25 | "https://unsplash.it/450/320?image=180", 26 | "https://unsplash.it/450/320?image=181" 27 | ] 28 | }, 29 | { 30 | "name" : "Company Website", 31 | "thumb" : "https://unsplash.it/450/320?image=278", 32 | "description" : "Super boring company portfolio website with the typical about us, home, and contact us sections", 33 | "images" : [ 34 | "https://unsplash.it/450/320?image=278", 35 | "https://unsplash.it/450/320?image=280", 36 | "https://image.shutterstock.com/image-vector/trophy-cup-award-vector-icon-260nw-592525184.jpg" 37 | ] 38 | } 39 | ] 40 | 41 | @pytest.mark.it("requests.get has to be called for the project_list.php url") 42 | def test_url_call(capsys, app): 43 | with patch('requests.get') as mock_request: 44 | app() 45 | mock_request.assert_called_once_with("https://assets.breatheco.de/apis/fake/sample/project_list.php") 46 | 47 | @pytest.mark.it("Make sure you are printing the LAST image of the LAST project") 48 | def test_url_output1(capsys, app): 49 | with patch('requests.get') as mock_request: 50 | mock_request.return_value = FakeResponse() 51 | app() 52 | captured = capsys.readouterr() 53 | assert "https://image.shutterstock.com/image-vector/trophy-cup-award-vector-icon-260nw-592525184.jpg\n" == captured.out 54 | -------------------------------------------------------------------------------- /exercises/08-blog-post-author/README.es.md: -------------------------------------------------------------------------------- 1 | --- 2 | tutorial: "https://www.youtube.com/watch?v=NZMkq0cIIlU" 3 | --- 4 | 5 | # `08` Post blog author 6 | 7 | Tómate un momento para comprender el response body al hacer una solicitud GET a este endpoint: 8 | [https://assets.breatheco.de/apis/fake/sample/weird_portfolio.php](https://assets.breatheco.de/apis/fake/sample/weird_portfolio.php) 9 | 10 | > 👉🏼 [Aquí hay una breve explicación en video.](https://www.youtube.com/watch?v=fwfBYVrvSk0) 11 | 12 | ![explicación del json](https://github.com/4GeeksAcademy/python-http-requests-api-tutorial-exercises/blob/master/assets/traversion_json.png?raw=true) 13 | 14 | ## 📝 Instrucciones: 15 | 16 | 1. Obtén el nombre del autor de la primera publicación. 17 | 18 | ## 💡 Pistas: 19 | 20 | + Haz una solicitud GET al endpoint. 21 | + Usa el [metodo .json()](https://www.w3schools.com/python/ref_requests_response.asp) para obtener el response body como un diccionario. 22 | + Encuentra la primera publicación. 23 | + Obtén el diccionario `author`. 24 | + Imprime el nombre del autor. 25 | + No necesitas hacer un bucle, solo usa las posiciones (índice/index). 26 | 27 | -------------------------------------------------------------------------------- /exercises/08-blog-post-author/README.md: -------------------------------------------------------------------------------- 1 | # `08` Post blog author 2 | 3 | Take a moment to understand the response body when doing a GET request to this endpoint: 4 | [https://assets.breatheco.de/apis/fake/sample/weird_portfolio.php](https://assets.breatheco.de/apis/fake/sample/weird_portfolio.php) 5 | 6 | > 👉🏼 [Here is a brief video explanation.](https://www.youtube.com/watch?v=fwfBYVrvSk0) 7 | 8 | ![json explanation](https://github.com/4GeeksAcademy/python-http-requests-api-tutorial-exercises/blob/master/assets/traversion_json.png?raw=true) 9 | 10 | ## 📝 Instructions: 11 | 12 | 1. Get the author name of the first post. 13 | 14 | ## 💡 Hints: 15 | 16 | + Do a GET request to the endpoint. 17 | + Use the [.json() method](https://www.w3schools.com/python/ref_requests_response.asp) to get the response body as a dictionary. 18 | + Find the first post. 19 | + Get the `author` dictionary. 20 | + Print the author name. 21 | + You don't need to loop, just use the positions (index). 22 | 23 | -------------------------------------------------------------------------------- /exercises/08-blog-post-author/app.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | # Your code here -------------------------------------------------------------------------------- /exercises/08-blog-post-author/solution.hide.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | # Your code here 4 | response = requests.get("https://assets.breatheco.de/apis/fake/sample/weird_portfolio.php") 5 | 6 | if response.status_code == 200: 7 | # Parsing JSON response 8 | data = response.json() 9 | 10 | # Getting the first post 11 | first_post = data["posts"][0] 12 | 13 | # Getting the author dictionary 14 | author_dict = first_post["author"] 15 | 16 | # Getting the author name 17 | author_name = author_dict["name"] 18 | 19 | print(author_name) 20 | else: 21 | print("Failed to fetch data from the endpoint.") -------------------------------------------------------------------------------- /exercises/08-blog-post-author/test.py: -------------------------------------------------------------------------------- 1 | import json, pytest 2 | from mock import patch 3 | 4 | class FakeResponse(object): 5 | # default response attributes 6 | status_code = 200 7 | def json(self): 8 | return { 9 | "posts": [ 10 | { "author": { "name": "octabio", "id": "12" } } 11 | ] 12 | } 13 | 14 | @pytest.mark.it("requests.get has to be called for the weird_portfolio.php url") 15 | def test_url_call(capsys, app): 16 | with patch('requests.get') as mock_request: 17 | app() 18 | mock_request.assert_called_once_with("https://assets.breatheco.de/apis/fake/sample/weird_portfolio.php") 19 | 20 | @pytest.mark.it("Make sure you are printing the author name of the FIRST post") 21 | def test_url_output1(capsys, app): 22 | with patch('requests.get') as mock_request: 23 | mock_request.return_value = FakeResponse() 24 | app() 25 | captured = capsys.readouterr() 26 | assert "octabio\n" == captured.out 27 | -------------------------------------------------------------------------------- /exercises/09-list-of-blog-titles/README.es.md: -------------------------------------------------------------------------------- 1 | --- 2 | tutorial: "https://www.youtube.com/watch?v=SWgyGk3d3yk" 3 | --- 4 | 5 | # `09` List of blog titles 6 | 7 | ## 📝 Instrucciones: 8 | 9 | 1. Usando el mismo endpoint del ejercicio anterior, crea una función `get_titles` que retorne los títulos de todas las publicaciones encontradas en el response body. 10 | 11 | ## 💡 Pistas: 12 | 13 | + Crea una función `get_titles`. 14 | + Declara una lista vacía llamada `titles`. 15 | + Haz el request del API adentro de la función. 16 | + realiza un bucle que itere para cada publicación. 17 | + Agregue cada título a la nueva lista. 18 | + Retorna la lista `titles`. 19 | 20 | La salida de la consola debería verse parecido a esto: 21 | 22 | ```python 23 | ['title 1', 'title 2', 'title 3'] 24 | ``` -------------------------------------------------------------------------------- /exercises/09-list-of-blog-titles/README.md: -------------------------------------------------------------------------------- 1 | # `09` List of blog titles 2 | 3 | ## 📝 Instructions: 4 | 5 | 1. Using the same endpoint from the previous exercise, create a function `get_titles` that returns the titles of all the posts found in the response body. 6 | 7 | ## 💡 Hints: 8 | 9 | + Create the function `get_titles`. 10 | + Declare a new empty list called `titles`. 11 | + Do the request to the endpoint inside the function. 12 | + Loop each post from the list of posts. 13 | + Get the title of each post. 14 | + Add that title to the new list. 15 | + Return the `titles` list. 16 | 17 | The console output should be something similar to this: 18 | 19 | ```python 20 | ['title 1', 'title 2', 'title 3'] 21 | ``` -------------------------------------------------------------------------------- /exercises/09-list-of-blog-titles/app.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | def get_titles(): 4 | # Your code here 5 | return None 6 | 7 | 8 | print(get_titles()) -------------------------------------------------------------------------------- /exercises/09-list-of-blog-titles/solution.hide.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | def get_titles(): 4 | # Your code here 5 | url = "https://assets.breatheco.de/apis/fake/sample/weird_portfolio.php" 6 | 7 | titles = [] 8 | 9 | response = requests.get(url) 10 | 11 | if response.status_code == 200: 12 | # Parsing JSON response 13 | data = response.json() 14 | 15 | for post in data["posts"]: 16 | title = post["title"] 17 | if title: 18 | titles.append(title) 19 | else: 20 | print("Failed to fetch data from the endpoint.") 21 | 22 | return titles 23 | 24 | 25 | print(get_titles()) -------------------------------------------------------------------------------- /exercises/09-list-of-blog-titles/test.py: -------------------------------------------------------------------------------- 1 | import json, pytest 2 | from mock import patch 3 | 4 | class FakeResponse(object): 5 | # default response attributes 6 | status_code = 200 7 | def json(self): 8 | return { 9 | "posts": [ 10 | {"title": 'R.I.P. Ruby on Rails. Thanks for everything.'}, 11 | {"title": 'The fraud behind the C.A. of digital certificates is over'}, 12 | {"title": 'Manteniendo las raices'}, 13 | {"title": 'DF Tech Meetup, ya es una realidad'} 14 | ] 15 | } 16 | 17 | @pytest.mark.it("You seem to be returning None or not returning anything") 18 | def test_for_null(app): 19 | with patch('requests.get') as mock_request: 20 | from app import get_titles 21 | mock_request.return_value = FakeResponse() 22 | resp = get_titles() 23 | assert resp is not None 24 | 25 | @pytest.mark.it("The function should have returned a list but returned something different") 26 | def test_return_type(app): 27 | with patch('requests.get') as mock_request: 28 | from app import get_titles 29 | mock_request.return_value = FakeResponse() 30 | tags = get_titles() 31 | assert isinstance(tags, list) 32 | 33 | @pytest.mark.it("Return a list of post titles like: ['title 1', 'title 2', 'title 3']") 34 | def test_array_content(app): 35 | with patch('requests.get') as mock_request: 36 | from app import get_titles 37 | mock_request.return_value = FakeResponse() 38 | titles = ['R.I.P. Ruby on Rails. Thanks for everything.', 'The fraud behind the C.A. of digital certificates is over', 'Manteniendo las raices', 'DF Tech Meetup, ya es una realidad'] 39 | assert titles == get_titles() 40 | -------------------------------------------------------------------------------- /exercises/10-get-post-tags/README.es.md: -------------------------------------------------------------------------------- 1 | --- 2 | tutorial: "https://www.youtube.com/watch?v=l9e-lSsYNOI" 3 | --- 4 | 5 | # `10` Get post tags 6 | 7 | ## 📝 Instrucciones: 8 | 9 | 1. Usando el mismo endpoint del ejercicio anterior, crea una función `get_post_tags` que retorne el arreglo de etiquetas (tags) de un `post_id` dado. 10 | 11 | ## 💡 Pistas: 12 | 13 | + Crea la función `get_post_tags`. 14 | + Obtén todas las publicaciones (post) haciendo la solicitud GET al endpoint. 15 | + Declare la variable para almacenar el body serializado. 16 | + Usando el parámetro `post_id`, recorre con un loop todas las publicaciones y compara sus ID para ver si coinciden con el `post_id`. 17 | + Cuando encuentres la publicación que deseas, devuelve una lista de etiquetas (tags). 18 | 19 | -------------------------------------------------------------------------------- /exercises/10-get-post-tags/README.md: -------------------------------------------------------------------------------- 1 | # `10` Get post tags 2 | 3 | ## 📝 Instructions: 4 | 5 | 1. Using the same endpoint from the previous exercise, create a function `get_post_tags` that returns the array of tags of a given `post_id` 6 | 7 | ## 💡 Hints: 8 | 9 | + Create the function `get_post_tags`. 10 | + GET all the posts by sending a GET request to the endpoint. 11 | + Declare the variable to store the serialized body 12 | + Using the `post_id` parameter, loop all the posts and compare their `id`s to see if they match the `post_id`. 13 | + When you find the post you want, return its list of tags. 14 | 15 | -------------------------------------------------------------------------------- /exercises/10-get-post-tags/app.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | def get_post_tags(post_id): 4 | # Your code here 5 | return None 6 | 7 | 8 | print(get_post_tags(146)) -------------------------------------------------------------------------------- /exercises/10-get-post-tags/solution.hide.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | def get_post_tags(post_id): 4 | # Your code here 5 | url = "https://assets.breatheco.de/apis/fake/sample/weird_portfolio.php" 6 | 7 | response = requests.get(url) 8 | 9 | if response.status_code == 200: 10 | # Parsing JSON response 11 | data = response.json() 12 | 13 | # Loop through each post to find the one with matching post_id 14 | for post in data["posts"]: 15 | if post["id"] == post_id: 16 | return post["tags"] 17 | print("No post found") 18 | 19 | else: 20 | print("Failed to fetch data from the endpoint.") 21 | 22 | 23 | print(get_post_tags(146)) -------------------------------------------------------------------------------- /exercises/10-get-post-tags/test.py: -------------------------------------------------------------------------------- 1 | import json, pytest 2 | from mock import patch 3 | 4 | class FakeResponse(object): 5 | # default response attributes 6 | status_code = 200 7 | def json(self): 8 | return { 9 | "posts": [ 10 | { "id": 234, "tags": [ 11 | { "id": 25, "title": "programming" }, 12 | { "id": 26, "title": "software development"} 13 | ] 14 | }, 15 | { "id": 224, 16 | "tags": [ 17 | { "id": 23, "title": "react" }, 18 | { "id": 11, "title": "cooking"} 19 | ] 20 | }, 21 | { "id": 14, "tags": [] }, 22 | { "id": 34, "tags": [] }, 23 | { "id": 24, "tags": [] }, 24 | ] 25 | } 26 | 27 | @pytest.mark.it("You seem to be returning None or not retuning anything") 28 | def test_for_null(app): 29 | with patch('requests.get') as mock_request: 30 | from app import get_post_tags 31 | mock_request.return_value = FakeResponse() 32 | tags = get_post_tags(224) 33 | assert tags is not None 34 | 35 | @pytest.mark.it("The function should have returned a list but returned something different") 36 | def test_return_type(app): 37 | with patch('requests.get') as mock_request: 38 | from app import get_post_tags 39 | mock_request.return_value = FakeResponse() 40 | tags = get_post_tags(224) 41 | assert isinstance(tags, list) 42 | 43 | @pytest.mark.it("Given the post id, return a list with the post tags given") 44 | def test_array_content(app): 45 | with patch('requests.get') as mock_request: 46 | from app import get_post_tags 47 | mock_request.return_value = FakeResponse() 48 | 49 | tags = get_post_tags(224) 50 | 51 | assert len(tags) == 2 52 | assert tags[0]["id"] == 23 53 | assert tags[1]["id"] == 11 54 | -------------------------------------------------------------------------------- /exercises/11-get-attachment-by-id/README.es.md: -------------------------------------------------------------------------------- 1 | --- 2 | tutorial: "https://www.youtube.com/watch?v=TR0PYXJUEPY" 3 | --- 4 | 5 | # `11` Get attachment by id 6 | 7 | ## 📝 Instrucciones: 8 | 9 | 1. Usando el mismo endpoint del ejercicio anterior, crea una función `get_attachment_by_id` que retorne el título de los archivos adjuntos (attachments) que corresponden con el `id` dado. 10 | 11 | ## 💡 Pistas: 12 | 13 | + Crea la función `get_attachment_by_id` que reciba el `attachment_id` como un parámetro. 14 | + Recorre con un bucle todos los posts. 15 | + Recorre con un bucle todos los archivos adjuntos (attachments) de cada post. 16 | + Si el archivo adjunto (attachment) tiene el `attachment_id` dado en el parámetro de la función, devuélvelo. 17 | 18 | -------------------------------------------------------------------------------- /exercises/11-get-attachment-by-id/README.md: -------------------------------------------------------------------------------- 1 | # `11` Get attachment by id 2 | 3 | ## 📝 Instructions: 4 | 5 | 1. Using the same endpoint from the previous exercise, create a function `get_attachment_by_id` that returns the title of the attachment that corresponds to the given `id`. 6 | 7 | ## 💡 Hints: 8 | 9 | + Create the function `get_attachment_by_id` that receives the `attachment_id` as a parameter. 10 | + Loop all the posts. 11 | + Loop all the `attachments` for each post. 12 | + If the attachment has the given `attachment_id` in the function parameter, return it. 13 | 14 | -------------------------------------------------------------------------------- /exercises/11-get-attachment-by-id/app.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | def get_attachment_by_id(attachment_id): 4 | # Your code here 5 | return None 6 | 7 | print(get_attachment_by_id(137)) -------------------------------------------------------------------------------- /exercises/11-get-attachment-by-id/solution.hide.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | def get_attachment_by_id(attachment_id): 4 | # Your code here 5 | url = "https://assets.breatheco.de/apis/fake/sample/weird_portfolio.php" 6 | 7 | response = requests.get(url) 8 | 9 | if response.status_code == 200: 10 | # Parsing JSON response 11 | data = response.json() 12 | 13 | for post in data["posts"]: 14 | # Check if the post has attachments 15 | if "attachments" in post: 16 | # Loop through each attachment 17 | for attachment in post["attachments"]: 18 | if attachment["id"] == attachment_id: 19 | return attachment["title"] 20 | 21 | print("No attachment found") 22 | else: 23 | print("Failed to fetch data from the endpoint.") 24 | 25 | print(get_attachment_by_id(137)) -------------------------------------------------------------------------------- /exercises/11-get-attachment-by-id/test.py: -------------------------------------------------------------------------------- 1 | import json, pytest 2 | from mock import patch 3 | 4 | class FakeResponse(object): 5 | # default response attributes 6 | status_code = 200 7 | def json(self): 8 | return { 9 | "posts": [ 10 | { "attachments": [{ "id": 22, "title": "Invoice" }] }, 11 | { "attachments": [{ "id": 137, "title": "Training Certificate" }] }, 12 | { "attachments": [{ "id": 11, "title": "Presentation Slides" }] }, 13 | { "attachments": [{ "id": 40, "title": "Meeting Agenda" }] }, 14 | { "attachments": [{ "id": 314, "title": "Project Proposal" }] }, 15 | ] 16 | } 17 | 18 | @pytest.mark.it("You seem to be returning None or not returning anything on the function") 19 | def test_for_null(app): 20 | with patch('requests.get') as mock_request: 21 | from app import get_attachment_by_id 22 | mock_request.return_value = FakeResponse() 23 | att = get_attachment_by_id(137) 24 | assert att is not None 25 | 26 | @pytest.mark.it("The function should have returned a string (the attachment title) but returned something different") 27 | def test_return_type(app): 28 | with patch('requests.get') as mock_request: 29 | from app import get_attachment_by_id 30 | mock_request.return_value = FakeResponse() 31 | title = get_attachment_by_id(137) 32 | assert isinstance(title, str) 33 | 34 | @pytest.mark.it("Return the attachment title") 35 | def test_array_content(app): 36 | with patch('requests.get') as mock_request: 37 | from app import get_attachment_by_id 38 | mock_request.return_value = FakeResponse() 39 | title = get_attachment_by_id(137) 40 | assert title == "Training Certificate" 41 | -------------------------------------------------------------------------------- /exercises/12-post-request/README.es.md: -------------------------------------------------------------------------------- 1 | --- 2 | tutorial: "https://www.youtube.com/watch?v=1WsxHQ-_E1w" 3 | --- 4 | 5 | # `12` POST request 6 | 7 | Las solicitudes POST están destinadas a la creación, por ejemplo, si tu negocio es un e-commerce de camisetas, es probable que desees tener una forma de agregar nuevos clientes. 8 | 9 | Una solicitud de POST (*POST request*) generalmente tiene: 10 | 11 | | | | 12 | | ---- | ---- | 13 | | Method | POST | 14 | | Content-Type | application/json | 15 | | Body (payload) | JSON string | 16 | 17 | ## 📝 Instrucciones: 18 | 19 | 1. Envía una solitud POST al siguiente URL: 20 | 21 | POST: https://assets.breatheco.de/apis/fake/sample/post.php 22 | 23 | 2. Imprime la respuesta (response text) en la consola. 24 | 25 | ## 💡 Pista: 26 | 27 | + Usa el método POST del paquete *requests*: https://www.w3schools.com/python/ref_requests_post.asp 28 | 29 | -------------------------------------------------------------------------------- /exercises/12-post-request/README.md: -------------------------------------------------------------------------------- 1 | # `12` POST request 2 | 3 | POST requests are meant for creation, for example, if your business is a t-shirt e-commerce you probably want to have a way to add new clients. 4 | 5 | A POST request usually has: 6 | 7 | | | | 8 | | ---- | ---- | 9 | | Method | POST | 10 | | Content-Type | application/json | 11 | | Body (payload) | JSON string | 12 | 13 | ## 📝 Instructions: 14 | 15 | 1. Send a POST request to the following URL: 16 | 17 | POST: https://assets.breatheco.de/apis/fake/sample/post.php 18 | 19 | 2. And print the response text on the console. 20 | 21 | ## 💡 Hint: 22 | 23 | + Use the requests package POST method: https://www.w3schools.com/python/ref_requests_post.asp 24 | 25 | -------------------------------------------------------------------------------- /exercises/12-post-request/app.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | # Your code here -------------------------------------------------------------------------------- /exercises/12-post-request/solution.hide.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | # Your code here 4 | url = "https://assets.breatheco.de/apis/fake/sample/post.php" 5 | 6 | response = requests.post(url) 7 | 8 | print(response.text) -------------------------------------------------------------------------------- /exercises/12-post-request/test.py: -------------------------------------------------------------------------------- 1 | import json, pytest 2 | from mock import patch 3 | 4 | @pytest.mark.it("Make a POST request to the specified endpoint") 5 | def test_url(app): 6 | with patch('requests.post') as mock_request: 7 | app() 8 | url = "https://assets.breatheco.de/apis/fake/sample/post.php" 9 | assert mock_request.call_args.args[0] == url 10 | 11 | @pytest.mark.it("Print the response text in the console") 12 | def test_print(capsys, app): 13 | with patch('requests.get') as mock_request: 14 | app() 15 | captured = capsys.readouterr() 16 | assert captured.out.find("Excelent") > 0 -------------------------------------------------------------------------------- /exercises/13-post-request-body/README.es.md: -------------------------------------------------------------------------------- 1 | --- 2 | tutorial: "https://www.youtube.com/watch?v=x5k6pOmxmWc" 3 | --- 4 | 5 | # `13` POST request body 6 | 7 | ## 📝 Instrucciones: 8 | 9 | 1. Envía una solitud POST al siguiente URL: 10 | 11 | ```text 12 | https://assets.breatheco.de/apis/fake/sample/save-project-json.php 13 | ``` 14 | 15 | 2. Con `Content-Type: application/json` 16 | 17 | 3. Con el siguiente request body como texto JSON: 18 | 19 | ```json 20 | { 21 | "id": 2323, 22 | "title": "Very big project" 23 | } 24 | ``` 25 | 26 | ## 💡 Pista: 27 | 28 | + Usa el método POST del paquete *requests*: https://www.w3schools.com/python/ref_requests_post.asp 29 | 30 | -------------------------------------------------------------------------------- /exercises/13-post-request-body/README.md: -------------------------------------------------------------------------------- 1 | # `13` POST request body 2 | 3 | ## 📝 Instructions: 4 | 5 | 1. Send a POST request to the following URL: 6 | 7 | ```text 8 | https://assets.breatheco.de/apis/fake/sample/save-project-json.php 9 | ``` 10 | 11 | 2. With `Content-Type: application/json` 12 | 13 | 3. With the following request body as JSON text: 14 | 15 | ```json 16 | { 17 | "id": 2323, 18 | "title": "Very big project" 19 | } 20 | ``` 21 | 22 | ## 💡 Hint: 23 | 24 | + Use the requests package post method: https://www.w3schools.com/python/ref_requests_post.asp 25 | 26 | -------------------------------------------------------------------------------- /exercises/13-post-request-body/app.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | response = requests.post("https://assets.breatheco.de/apis/fake/sample/save-project-json.php") 4 | print(response.text) -------------------------------------------------------------------------------- /exercises/13-post-request-body/solution.hide.py: -------------------------------------------------------------------------------- 1 | import requests 2 | 3 | url = "https://assets.breatheco.de/apis/fake/sample/save-project-json.php" 4 | 5 | data = { 6 | "id": 2323, 7 | "title": "Very big project" 8 | } 9 | 10 | # Setting the headers 11 | headers = { 12 | "Content-Type": "application/json" 13 | } 14 | 15 | # Sending POST request with dictionary data 16 | response = requests.post(url, json=data, headers=headers) 17 | 18 | print(response.text) -------------------------------------------------------------------------------- /exercises/13-post-request-body/test.py: -------------------------------------------------------------------------------- 1 | import json, pytest 2 | from mock import patch 3 | 4 | @pytest.mark.it("Make a POST request to the specified endpoint") 5 | def test_url(app): 6 | with patch('requests.post') as mock_request: 7 | app() 8 | url = "https://assets.breatheco.de/apis/fake/sample/save-project-json.php" 9 | assert mock_request.call_args.args[0] == url 10 | 11 | @pytest.mark.it("Request header content-type must be application/json") 12 | def test_headers(app): 13 | with patch('requests.post') as mock_request: 14 | app() 15 | assert "headers" in mock_request.call_args.kwargs 16 | assert "Content-Type" in mock_request.call_args.kwargs["headers"] or "content-type" in mock_request.call_args.kwargs["headers"] 17 | 18 | headers = mock_request.call_args.kwargs["headers"] 19 | if "Content-Type" in headers: 20 | assert headers["Content-Type"].lower() == "application/json" 21 | if "content-type" in headers: 22 | assert headers["content-type"].lower() == "application/json" 23 | 24 | @pytest.mark.it("Request body must be a json object with id and title") 25 | def test_body(app): 26 | with patch('requests.post') as mock_request: 27 | app() 28 | assert "json" in mock_request.call_args.kwargs 29 | 30 | body = mock_request.call_args.kwargs["json"] 31 | assert "id" in body 32 | assert "title" in body -------------------------------------------------------------------------------- /learn.json: -------------------------------------------------------------------------------- 1 | 2 | { 3 | "language": "python", 4 | "title": { 5 | "us": "Learn how to build HTTP requests with Python", 6 | "es": "Aprende a hacer requests HTTP con Python" 7 | }, 8 | "slug": "python-http-requests-api-tutorial-exercises", 9 | "description": { 10 | "us": "Learn interactively to consume and create HTTP requests to APIs using Python", 11 | "es": "Aprende interactivamente cómo consumir APIs y hacer requests HTTP con Python" 12 | }, 13 | "repository": "https://github.com/4GeeksAcademy/python-http-requests-api-tutorial-exercises", 14 | "duration": 4, 15 | "videoSolutions": false, 16 | "difficulty": "easy", 17 | "preview": "https://github.com/4GeeksAcademy/python-http-requests-api-tutorial-exercises/blob/master/preview.png?raw=true", 18 | "repository": "https://github.com/4GeeksAcademy/python-http-requests-api-tutorial-exercises", 19 | "projectType": "tutorial", 20 | "autoPlay": true, 21 | "bugsLink": "https://github.com/learnpack/learnpack/issues/new", 22 | "editor": { 23 | "version": "5.0" 24 | }, 25 | "telemetry": { 26 | "batch": "https://breathecode.herokuapp.com/v1/assignment/me/telemetry?asset_id=1111" 27 | } 28 | } 29 | -------------------------------------------------------------------------------- /preview.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/4GeeksAcademy/python-http-requests-api-tutorial-exercises/f90a785f2d248c29bf0fe9b35c392c53be8d805b/preview.png --------------------------------------------------------------------------------