FastAPI/Python API: Authorization Code Sample

This Python code sample demonstrates how to implement authorization in a FastAPI server using Auth0.

2 Likes

Hi, developers.
I’m was following the developers documentation on Auth0 for FastAPI but I wasn’t able to clone it. because it was asking for username and password. And I searched this repo on GitHub of Auth0 but this repo wasn’t there.

So, I guess the repo is private for now. But if you can make it public just let us know. :slightly_smiling_face:

1 Like

Hello, Sachin! Welcome to the Auth0 Community.

I apologize about that. The repo was left private but it’s not public :slight_smile: Please let us know if you have any questions on the code. Thanks for the heads up!

2 Likes

Hi developers, thanks to you I was able to integrate my FastAPI with Auth0.
But now I have come up with a different issue.

I have used the sample template provided by Auth0 for my FastAPI and Angular Integration to test it. But when I used it in my FastAPI and Angular code it is throwing

Access to XMLHttpRequest at ‘http://localhost:6060/robots/’ from origin ‘http://localhost:4040’ has been blocked by CORS policy: No ‘Access-Control-Allow-Origin’ header is present on the requested resource

GET http://localhost:6060/robots/ net::ERR_FAILED 500 (Internal Server Error)

I tried to log it then I found this

Here is a Sample code of my FastAPI and Angular.

app.module.ts

imports: [
    ....
    AuthModule.forRoot({
      ...environment.auth0,
      httpInterceptor: {
        allowedList: [`${environment.api.serverUrl}/robots/`]
      },
    }),
    .....
  ],
  providers: [
    {
      provide: HTTP_INTERCEPTORS,
      useClass: AuthHttpInterceptor,
      multi: true,
    },
  ],

environment.ts

export const environment = {
  production: false,
  auth0: {
    domain: 'xxx',
    clientId: 'xxx',
    authorizationParams: {
      audience: 'https://hello-world.example.com',
      redirect_uri: 'http://localhost:4040',
    },
    errorPath: '',
  },
  api: {
    serverUrl: 'http://localhost:6060',
  },
};

robot.service.ts

getAllRobotsRestricted = (): Observable<ApiResponseModel> => {
    const config: RequestConfigModel = {
      url: `${env.api.serverUrl}/robots/`,
      method: 'GET',
      headers: {
        'content-type': 'application/json',
      },
    };

    return this.externalAuth0Service.callExternalApi(config).pipe(
      mergeMap((response) => {
        const { data, error } = response;

        return of({
          data: data ? (data as RobotsModel) : null,
          error,
        });
      })
    );
  }

external api

callExternalApi = (config: RequestConfigModel): Observable<ApiResponseModel> => {
    return this.http
      .request<unknown>(config.method, config.url, config.headers)
      .pipe(
        mergeMap((data) => {
          return of({
            data: data,
            error: null,
          });
        }),
        catchError((err) => {
          if (err.error && err.status) {
            return of({
              data: null,
              error: err.error,
            });
          }

          return of({
            data: null,
            error: {
              message: err.message,
            },
          });
        })
      );
  };

So, can you help me with this?

Hi, @imsachinsingh10 I’m happy to hear that this code sample has helped you to integrate your FastAPI application with Auth0.

This error is related to how you set up CORS in your FastAPI application. FastAPI is restrictive by default, so you’ll need to explicitly enable particular origins, methods, or headers so browsers can be permitted to use them in a Cross-Domain context.

For example, in our case, the client applications, such as the Angular application, are running on http://localhost:4040, so we’ve explicitly enabled the FastAPI server to allow requests from the http://localhost:4040 origin by doing the following in the main.py file:

from fastapi.middleware.cors import CORSMiddleware

...

app = FastAPI(openapi_url=None)

...

app.add_middleware(
    CORSMiddleware,
    allow_origins=[settings.client_origin_url],
    allow_methods=["GET"],
    allow_headers=["Authorization", "Content-Type"],
    max_age=86400,
)

Notice that our FastAPI code sample reads the settings.client_origin_url value from an environment variable. You can leverage this example, pass the allowed origin directly, and adjust it to your needs. For more information on how you can configure CORS in FastAPI, you can check the official documentation:

To understand how CORS works here is an excellent blog post from Auth0 that you can also read What is CORS? Complete Tutorial on Cross-Origin Resource Sharing.

1 Like

Thank you so much for your response but I figured out the problem. Now it is working perfectly fine :grin:.

It was a minor issue from my side that I forgot to install one of the libraries Cryptography which is required along with other dependencies like PyJWT , secure.

So, if anyone faces the similar issue then they can keep a check of requirement.txt files as well.

Thanks! :grin:

2 Likes

Thanks for sharing it with the rest of community!

Hi there,

Thanks very much for making these tutorials available! I’m having a few issues getting it running locally though. I am using the FastAPI backend code linked in the original post and then I have continued the tutorial to try and integrate the React + JavaScript SPA (using the code from this repo: GitHub - auth0-developer-hub/spa_react-v17_javascript_hello-world_react-router-5).

I have both the frontend and backend up and running and have tested that when I change the public message in the backend those changes show up in the front end. However, there seems to be an issue with the Authorization header not being set correctly. Once I login via the login button I still get a message that Protected message requires authentication (and looking at the request header there is no Authorization header). I am able to see the Profile page however, since this seems to be handled entirely via the frontend code (there’s no route for that in main.py).

It seems the backend and frontend tutorials don’t entirely tie together. Any help you can give on how to set the Authorization header correctly so the private message is displayed correctly once I’m logged in via the React app login button would be great. Let me know if I should raise an issue in the GitHub instead but technically the code in that repo works fine, just not when used in conjunction with the React+JS SPA code.

1 Like

Hi @a_o, welcome to the Auth0 Community.
Thanks for sharing such a detailed response. You’ve identified the issue correctly. When the Client application does not send the Authorization header for a protected message, the API responds with a “Requires authentication” message. This issue could be because of the branch of the SPA you’re running. The main and basic-authentication branches only show how to implement user authentication.

To tie together the client and the API code samples, you should check out the basic-authentication-with-api-integration branch in the client. We have a full-stack page that can help you with the instructions to run both code samples together
React v17 with React Router 5 (JavaScript) + FastAPI (Python) Code Sample: Basic Access Control for Hello World Full-Stack App.

Also, if you would like to learn more in detail and step-by-step how to call a protected API from the React Client application, I recommend reading the “Integrate React with an API Server” section of our React by Example Developer Guide.

Let us know if that works for you or if you need further instructions to tie them together. We’re happy to help.

1 Like

Hi Byron,
Thanks for your quick response!

This was in fact the issue, I’m not sure if I was following a different version of the tutorial or if I just missed the step to change to the basic-authentication-with-api-integration branch but this is working locally for me now. I was a bit confused as to why I could see the Admin message as well but I found the related tutorial on RBAC (React v17 with React Router 5 (JavaScript) + FastAPI (Python) Code Sample: Basic Role-Based Access Control (RBAC) for Hello World Full-Stack App) which I will be following next to implement the read:admin-messages scope/permission.

Thanks again! :pray:

2 Likes

Thanks, @byron.motoche ! I am glad that it’s working now, @a_o ! We’ll have a “FastAPI Authorization By Example” guide in the near future :eyes: Stay tuned, please :pray:

Sounds good @dan-auth0 will keep my eyes peeled for that! :+1: If it’s still in development I’d love to make a request to have a FastAPI guide that uses vanilla JS for the frontend as opposed to a framework like React. It might make it easier to understand the nuts and bolts of what’s going on without all the extra framework specific stuff (especially for newer devs) - thanks! :pray:

1 Like

Thanks for your feedback. Our FastAPI guide will be independent of front-end implementation, just like the code sample. :slight_smile: