@@ -17,49 +17,99 @@ const DEFAULT_KEY = `${STORAGE_KEY}-${CLIENT_ID}`
1717const encoded = encodeURIComponent ( JSON . stringify ( validSession ) )
1818
1919describe ( 'getSessionFromCookies' , ( ) => {
20- it ( 'parses a session from a Next.js cookies() store using clientId' , ( ) => {
20+ it ( 'parses a session from a Next.js cookies() store using clientId' , async ( ) => {
2121 const cookiesStore = {
2222 get ( name : string ) {
2323 return name === DEFAULT_KEY ? { name, value : encoded } : undefined
2424 }
2525 }
2626 expect (
27- getSessionFromCookies ( cookiesStore , { clientId : CLIENT_ID } )
27+ await getSessionFromCookies ( cookiesStore , { clientId : CLIENT_ID } )
2828 ) . toEqual ( validSession )
2929 } )
3030
31- it ( 'parses a session from a plain object map using clientId' , ( ) => {
31+ it ( 'parses a session from a plain object map using clientId' , async ( ) => {
3232 const cookiesStore = { [ DEFAULT_KEY ] : encoded }
3333 expect (
34- getSessionFromCookies ( cookiesStore , { clientId : CLIENT_ID } )
34+ await getSessionFromCookies ( cookiesStore , { clientId : CLIENT_ID } )
3535 ) . toEqual ( validSession )
3636 } )
3737
38- it ( 'honours a custom storageKey override' , ( ) => {
38+ it ( 'honours a custom storageKey override' , async ( ) => {
3939 const customKey = `mi-prefix-${ CLIENT_ID } `
4040 const cookiesStore = { [ customKey ] : encoded }
4141 expect (
42- getSessionFromCookies ( cookiesStore , {
42+ await getSessionFromCookies ( cookiesStore , {
4343 clientId : CLIENT_ID ,
4444 storageKey : 'mi-prefix'
4545 } )
4646 ) . toEqual ( validSession )
4747 } )
4848
49- it ( 'returns null when the cookie is absent' , ( ) => {
49+ it ( 'returns null when the cookie is absent' , async ( ) => {
5050 expect (
51- getSessionFromCookies ( { get : ( ) => undefined } , { clientId : CLIENT_ID } )
51+ await getSessionFromCookies (
52+ { get : ( ) => undefined } ,
53+ {
54+ clientId : CLIENT_ID
55+ }
56+ )
5257 ) . toBeNull ( )
53- expect ( getSessionFromCookies ( { } , { clientId : CLIENT_ID } ) ) . toBeNull ( )
58+ expect ( await getSessionFromCookies ( { } , { clientId : CLIENT_ID } ) ) . toBeNull ( )
5459 } )
5560
56- it ( 'returns null when the cookie value is malformed JSON' , ( ) => {
61+ it ( 'returns null when the cookie value is malformed JSON' , async ( ) => {
5762 const cookiesStore = { [ DEFAULT_KEY ] : encodeURIComponent ( '{not-json' ) }
5863 expect (
59- getSessionFromCookies ( cookiesStore , { clientId : CLIENT_ID } )
64+ await getSessionFromCookies ( cookiesStore , { clientId : CLIENT_ID } )
6065 ) . toBeNull ( )
6166 } )
6267
68+ // Next.js 15 made `cookies()` async — callers may pass the un-awaited
69+ // Promise. Before this was async-aware the duck-typing missed `.get` on the
70+ // Promise and returned null silently.
71+ describe ( 'Next.js 15 async cookies()' , ( ) => {
72+ it ( 'awaits a Promise-wrapped cookies() store' , async ( ) => {
73+ const cookiesStore = {
74+ get ( name : string ) {
75+ return name === DEFAULT_KEY ? { name, value : encoded } : undefined
76+ }
77+ }
78+ expect (
79+ await getSessionFromCookies ( Promise . resolve ( cookiesStore ) , {
80+ clientId : CLIENT_ID
81+ } )
82+ ) . toEqual ( validSession )
83+ } )
84+
85+ it ( 'awaits a Promise-wrapped plain object map' , async ( ) => {
86+ const store = { [ DEFAULT_KEY ] : encoded }
87+ expect (
88+ await getSessionFromCookies ( Promise . resolve ( store ) , {
89+ clientId : CLIENT_ID
90+ } )
91+ ) . toEqual ( validSession )
92+ } )
93+
94+ it ( 'returns null for a Promise resolving to no session' , async ( ) => {
95+ expect (
96+ await getSessionFromCookies ( Promise . resolve ( { } ) , {
97+ clientId : CLIENT_ID
98+ } )
99+ ) . toBeNull ( )
100+ } )
101+
102+ // Backward compatibility: a non-thenable store must still return
103+ // synchronously so existing Next.js ≤14 callers that don't `await` keep
104+ // working (a Promise here would be truthy and silently "always logged in").
105+ it ( 'stays synchronous for a non-Promise store' , ( ) => {
106+ const store = { [ DEFAULT_KEY ] : encoded }
107+ const result = getSessionFromCookies ( store , { clientId : CLIENT_ID } )
108+ expect ( result ) . not . toBeInstanceOf ( Promise )
109+ expect ( result ) . toEqual ( validSession )
110+ } )
111+ } )
112+
63113 describe ( 'chunked cookies' , ( ) => {
64114 const split = ( str : string , size : number ) : string [ ] => {
65115 const out : string [ ] = [ ]
@@ -68,7 +118,7 @@ describe('getSessionFromCookies', () => {
68118 return out
69119 }
70120
71- it ( 'reassembles `key.0`, `key.1`, … from a Next.js cookies() store' , ( ) => {
121+ it ( 'reassembles `key.0`, `key.1`, … from a Next.js cookies() store' , async ( ) => {
72122 const chunks = split ( encoded , 50 )
73123 const store = {
74124 get ( name : string ) {
@@ -78,30 +128,30 @@ describe('getSessionFromCookies', () => {
78128 return idx < chunks . length ? { name, value : chunks [ idx ] } : undefined
79129 }
80130 }
81- expect ( getSessionFromCookies ( store , { clientId : CLIENT_ID } ) ) . toEqual (
82- validSession
83- )
131+ expect (
132+ await getSessionFromCookies ( store , { clientId : CLIENT_ID } )
133+ ) . toEqual ( validSession )
84134 } )
85135
86- it ( 'reassembles chunks from a plain object map' , ( ) => {
136+ it ( 'reassembles chunks from a plain object map' , async ( ) => {
87137 const chunks = split ( encoded , 50 )
88138 const store : Record < string , string > = { }
89139 chunks . forEach ( ( c , i ) => {
90140 store [ `${ DEFAULT_KEY } .${ i } ` ] = c
91141 } )
92- expect ( getSessionFromCookies ( store , { clientId : CLIENT_ID } ) ) . toEqual (
93- validSession
94- )
142+ expect (
143+ await getSessionFromCookies ( store , { clientId : CLIENT_ID } )
144+ ) . toEqual ( validSession )
95145 } )
96146
97- it ( 'prefers a single un-chunked cookie when both shapes are present' , ( ) => {
147+ it ( 'prefers a single un-chunked cookie when both shapes are present' , async ( ) => {
98148 const store = {
99149 [ DEFAULT_KEY ] : encoded ,
100150 [ `${ DEFAULT_KEY } .0` ] : 'stale-garbage'
101151 }
102- expect ( getSessionFromCookies ( store , { clientId : CLIENT_ID } ) ) . toEqual (
103- validSession
104- )
152+ expect (
153+ await getSessionFromCookies ( store , { clientId : CLIENT_ID } )
154+ ) . toEqual ( validSession )
105155 } )
106156 } )
107157} )
0 commit comments