Introduction and first functions

There I will go to the search and try to find information about myself:

https://habr.com/ru/search/?q=yakvenalex&target_type=posts&order=relevance

Please note. I simply entered my login and clicked on search, but the line immediately generated path parameters (/ru/search/) and 3 query parameters at once:

  • q = yakvenalex

  • target_type = post

  • order = relevance

Now let's do the same with our students. Now for convenience, I will output the course to the query parameter, and then we will combine both the query parameter and the path parameter in one endpoint (function).

@app.get("/students")
def get_all_students(course: Optional[int] = None):
    students = json_to_dict_list(path_to_json)
    if course is None:
        return students
    else:
        return_list = []
        for student in students:
            if student["course"] == course:
                return_list.append(student)
        return return_list

Let's figure it out.

As you can see, I've rewritten our start endpoint. Now it doesn't just return all students, but allows you to use query parameters.

You can also see that I have used the course: Optional notation.[int] = None. Thanks to this, we not only specified that FastApi should expect an integer (int), but also allowed not to pass this parameter (query parameter) at all.

Next I wrote a simple handler. If the parameter was not there, then we returned all users, if the parameter was there, then we returned only students of a specific course.

In production projects, deeper and more detailed data validation is used using Pydantic, but we'll talk about that next time, if, in general, the topic of developing your own API via Python is interesting to you.

Let's look:

The link now looks like this: http://127.0.0.1:8000/students?course=1. If there were several parameters, we would call them through &.

If we do not pass any query parameters, we will get all students.If we do not pass any query parameters, we will get all students.

Now let's look at an example of a combination of path parameters and query parameters.

In our working example, let's pass the course in the path parameter, and the major (major) and year of admission (enrollment_year) in the query parameters.

@app.get("/students/{course}")
def get_all_students_course(course: int, major: Optional[str] = None, enrollment_year: Optional[int] = 2018):
    students = json_to_dict_list(path_to_json)
    filtered_students = []
    for student in students:
        if student["course"] == course:
            filtered_students.append(student)

    if major:
        filtered_students = [student for student in filtered_students if student['major'].lower() == major.lower()]

    if enrollment_year:
        filtered_students = [student for student in filtered_students if student['enrollment_year'] == enrollment_year]

    return filtered_students

Here it is necessary to use logic. I solved this problem like this.

First, we selected students of the course we needed, and then, we sorted by specialty, if there was one. And then, from the specialty, we sorted by year of admission.

I implemented the filter for the specialty and year of admission using a list generator. If you find it so difficult, you can use the standard for cycle. And in general, try to solve this problem in another way.

The link will now look like this:

http://127.0.0.1:8000/students/1?enrollment_year=2019&major=Psychology

The order in which the request parameters are passed does not matter. The main thing is not to violate the general syntax.

Let's look:

Please note. Despite the fact that I entered my request (Psychology) in Russian characters and with a capital letter in the address bar, the final link has changed its appearance. This is purely a question of the browser's operation. Don't let this scare you.

Testing our API

Of course, this is all extremely interesting, but the question is why? I will answer it for you now in a clear way.

I hope you have a basic understanding of the Python library requests. In short and simple, the main idea of ​​the library is to send HTTP requests. This allows you to easily interact with web services and APIs. It simplifies the execution of different types of requests, such as GET and POST, and the processing of responses, providing a convenient and understandable interface for working with HTTP.

As you understand, this is what we need, because we already have an API (somewhat).

import requests


def get_all_students():
    url = "http://127.0.0.1:8000/students"
    response = requests.get(url)
    return response.json()


students = get_all_students()
for i in students:
    print(i)

The requests library is not built-in, so be sure to install it.

Initially, we need a link to which we will execute our request. In this case, it is:

http://127.0.0.1:8000/students

Next we execute the request itself. In this case, it is enough to just pass the link.

And then you send a request to your server, transforming the response into JSON. The main beauty here is that we get a list of Python dictionaries, which allows you to easily work with your API.

Let's look:

Output the result to the console

Output the result to the console

Everything worked perfectly!

Now let's execute a query with a query parameter (let's not touch the path parameter for now).

def get_students_with_param_requests(course: int):
    url = "http://127.0.0.1:8000/students"
    response = requests.get(url, params={"course": course})
    return response.json()


students = get_students_with_param_requests(course=2)
for student in students:
    print(student)

In this example, you can see that there is a special attribute that takes parameters (params) in the form of a Python dictionary.

Let's see:

Received by 2 students

Received by 2 students

We got the students we needed, but what about the path parameters?

Let's get all the second year students using the path parameter.

def get_students_with_param_path(course: int):
    url = f"http://127.0.0.1:8000/students/{course}"
    response = requests.get(url)
    return response.json()


students = get_students_with_param_path(2)
for student in students:
    print(student)

Please note: The path parameter is passed in the link. We did not pass any other parameters.

Let's look:

Why only 1 student!?

Why only 1 student!?

An attentive reader will ask. Why did we get only one student when we have 2 students in the second year! But here everything is simple, we set the year of admission to 2018 by default. And from 2018 we have 1 student in the second year.

Mixing path parameters and query parameters.

def get_students_with_param_mix(course: int, major: str, enrollment_year: int):
    url = f"http://127.0.0.1:8000/students/{course}"
    response = requests.get(url, params={"major": major, "enrollment_year": enrollment_year})
    return response.json()


students = get_students_with_param_mix(2, major=None, enrollment_year=2018)
print(students)

Let's look:

I printed it out as a list, knowing that I only have 1 such student.

Теперь небольшое задание.

Write 2 methods yourself that will accept a student ID and return it. Let the first method work through the request parameter, and the second through the path parameter.

I will write these functions, but their implementation, as well as the full source code from this article, you will find in my telegram channel.

What about the documentation?

You will be surprised, but FastApi documentation has already been written for us. Moreover, this framework has also created a sandbox with forms for entering parameters.

To verify this, you need to follow the link: http://127.0.0.1:8000/docs

Isn't this a song? ;)

Isn't this a song? 😉

Every function we wrote was not only displayed here, but we also got the opportunity to click on it (sandbox). Let's take a look.

Here we see the entry “No parameters”. It is not surprising, because the endpoint of the main page of the site (function) itself does not accept any parameters.

When you click on “Try it out”, the script does not start, but you only enter the parameters.

To execute the script itself, you must then click on “Execute”

After executing the query we see the following result:

I don’t know about you, but when I first encountered this functionality, I was delighted.

Now let's try to execute a query with parameters.

We see that the parameter input form has been formed. In addition, FastApi highlighted the required parameters (asterisk) and added a comment that this is a path parameter (path), in addition, the framework indicated the parameter that is used by default (Default value: 2018) and did not set the asterisk next to major, since this is not a required parameter.

Let's execute the request.

Tap on "Try it out" and enter the request parameters.

Tap on “Try it out” and enter the request parameters.

Please note. FastApi also generated a curl request. What it is and how to work with it will be discussed next time.

Conclusion

Our introduction to FastAPI has come to an end. Today we have become familiar with some of the capabilities of this framework, but this amount of information is not enough to create full-fledged projects.

I have intentionally simplified the article to make the material accessible to everyone. However, understanding the basic concepts of API, HTTP requests, and practical application of FastAPI will lay a solid foundation for developing your own API in the future.

Let me remind you that this was a pilot article. Your likes, subscriptions, participation in voting under this article and comments will help you understand how interesting and useful this content is for you and, in general, the feasibility of writing such articles.

The source code and solution to the problem with endpoints to get information about a specific student can be found in my Telegram channel.

That's all for now. I hope this article won't be the last in my series of materials about FastAPI.

Similar Posts

Leave a Reply

Your email address will not be published. Required fields are marked *