I had been playing around with Ory Kratos for quit...
# talk-kratos
d
I had been playing around with Ory Kratos for quite sometime. I have successfully integrated it with my Next.js frontend, and I am able to register, login, logout etc. Up next, I want to protect my Fastapi backend endpoints. I can follow the approach taken in this blog, where my backend receives a session token from the frontend, and then makes a
GET sessions/whoami
call to Kratos to validate the token. However, I am interested to know that is it possible that I can initiate an Ory Kratos client object in such a way, that I can do this validation without making a call to the Kratos server? May be, the sdk client can take secret, algorithm, and issuer during initialisation (which I can copy somewhere from the Ory console), and then can locally validate the incoming token's signature, issuer, expiry etc. etc. and can then extract the user's id and other stuff. I can do this by writing my own code in Python, but just curious, if there is already an easier helper available in Kratos' sdk that does this.
What am I trying to achieve? Basically, I don't want to make one extra http call everytime my fastapi server has to serve a resource. If I follow the blog's approach I need to make a network call to Kratos server on every call that's made to my protected fastapi endpoint. Instead, I would like to make use of the secret key and do the validation "natively" in my python code.
I would give this a shot later tonight. Meanwhile, checking if anyone has already attempted something like this.
I have one question: I was able to get a jwt token following the docs. This is the relevant code snippet I have added on one of the pages that I want to keep protected in my next.js application.
Copy code
// rest of the code...

const [session, setSession] = useState<Session | undefined>()
useEffect(() => {
        oryFrontend
            .toSession({
                "tokenizeAs": "my_template"
            })
            .then(async ({ data }) => {
                // User has a session!
                setSession(data)
            })
            .catch(() => {
                return router.push(basePath + "/ui/login");
            })
    }, [router])

if (!session) {
        // Still loading
        return null
}

// rest of the code...
The above works fine. However what I want to know is that, is there a way to have access to this data object(or just the jwt part) on the next.js server side? I need the token on next.js server side to make authenticated call to my fast-api backend. Of course, I can manually save the jwt inside cookies while logging in and then fetch the cookie on the server side, but I just wanted to know if there is a way where Ory Kratos itself takes care of putting this jwt in cookies while logging in and removing it from cookies while logging out, so that I have the access to the token throughout my application. Thanks in advance.
a
@damp-notebook-13395 I'd say the following response is, for the most part, also an answer to your question https://ory-community.slack.com/archives/C012RJ2MQ1H/p1698021397368199 tl;dr let Kratos set the browser cookie for you, and all your requests will be authenticated thereafter
d
checking
hmmm, I am already using the browser flows and redirects as I am developing using Ory's default UI. But having gone through the login documentation, my updated question is: By default, after successful login, this is what Ory Kratos responds with:
Copy code
HTTP/1.1 303 See Other
Cache-Control: 0
Location: <http://127.0.0.1:4455/>
Set-Cookie: csrf_token=b8OebRPTPr5ow23mA5gIZmFNLeuMbv8pZz1jT1Ex7ys=; Path=/; Domain=127.0.0.1; Max-Age=31536000; HttpOnly
Set-Cookie: ory_kratos_session=MTU5OTE2ODc2N3xEdi1CQkFFQ180SUFBUkFCRUFBQVJfLUNBQUVHYzNSeWFXNW5EQThBRFhObGMzTnBiMjVmZEc5clpXNEdjM1J5YVc1bkRDSUFJR055VlROMGRteHhSakJrUzBkbmRUUjBlVFY1V0RCRWFVTnJXVmR6V25oaHx2DICsB6IMbaHSQwnYITUZqr7Qx7CxUlnaneJWH495wQ==; Path=/; Expires=Fri, 04 Sep 2020 21:32:47 GMT; Max-Age=86400; HttpOnly; SameSite=Lax
Vary: Cookie
Date: Thu, 03 Sep 2020 21:32:47 GMT
Content-Length: 0
How do I configure Ory Kratos so that it sets one more cookie for me in the above response, whose value is the jwt token that I am currently fetching by making an explicit call to
/sessions/whoami?tokensie_as=mytemplate
. Once the jwt token is set in the cookie after login/registration, I won't have to make the recurring
whoami
calls everytime I need the jwt token.
a
I'm not aware of Kratos issuing any JWT, if you happen to know please share the link but so far as I know, the Kratos will set a cookie for you with
ory_kratos_session
as key and some random and long string as value that cookie will respond with an authenticated identity when doing
GET /sessions/whoami
but again, I'm not aware of any JWT issuance
d
following the above, I am able to get the jwt that I am expecting. My only worry is, currently, I have to make a explicit call to
sessions/whoami
everytime I need that jwt. Is there an easier way to configure Ory Kratos, so that it directly sets this jwt as a cookie after successful login/registration.
a
interesting, thanks I didn't know that also, let me take a closer look at the docs If I find anything that can help you, I'll share in this thread
d
sure thanks. I can of course, right manual code to do this^^ after successful login/registration, but I just wanted to know if there is a way where Kratos does it automatically. Anyway, thanks for looking into this πŸ™
a
surely, my pleasure BTW, I see that the endpoint in the docs is not covered in the HTTP API reference: https://www.ory.sh/docs/kratos/reference/api I guess that have been added recently and not yet released? or not yet documented perhaps!? πŸ€”
d
It's documented here @alert-advantage-94977: https://www.ory.sh/docs/reference/api Search for
Check Who the Current HTTP Session Belongs To
and see the query parameters.
tokenize_as
is listed there as a query param.
however, I can see it's not documented in the link that you have shared.. it's relatively new as I can make out from the github issue page.. so probably a miss
m
Hello all, the reason it is not included in the self-hosted API documentation is that this feature has not yet been released, see past releases here: https://github.com/ory/kratos/releases/ It is already merged on master in ory/kratos and in production in Ory Network. It will be included in the next open source release; cant say when that will come but we are on quarterly release schedule so should be soon.
I have to make a explicit call to
sessions/whoami
everytime I need that jwt.
@damp-notebook-13395 It should not be too many calls if the JWT has sufficient TTL, right? I guess it depends on your usage patterns and how β€œstale” the session data can be.
d
@magnificent-energy-493, it's not about token expiry. It's about who sets this jwt as a cookie so that I can easily fetch this token from the cookie throughout my application, instead of making a
whoami
api call. From how much I am able to figure out Ory Kratos doesn't set the jwt as a cookie automatically, and I would have to manually take care of setting it as a cookie post login/registration and also of unsetting it post logout. Correct me please if I am wrong.
m
@damp-notebook-13395 So you get an Ory Session cookie, transform that into a JWT and then transform it back into a cookie? Just use the Ory Session cookie if you want to use cookies. If you want to be able to check the session without calling whoami, use the JWT and verify it with a library, like this one for example.
d
Just use the Ory Session cookie if you want to use cookies.
I want to make http call to my fastapi backend and pass the jwt along. Without storing the jwt as cookie and without making a network call to
/whoami
, how do I do that?
a
Well, I couldn't find anything for you Vikas but my two cents, drop authentication logic from your backend, put Oathkeeper or Nginx in front of all your requests (i.e. proxy), query the Kratos for authentication and all the requests reaching your backend is considered authenticated and in trusted zone
d
yeah, my finding also indicates that for what I want, I would have to use Oathkeeper. I don't think I am going to take that route though. Will study how other auth solutions are designed. Thanks for all your help Meysam πŸ™