@@ -91,6 +91,46 @@ describe("resolveRejectionSignaled (#5132)", () => {
9191 expect ( text ) . not . toHaveBeenCalled ( ) ;
9292 } ) ;
9393
94+ it ( "ignores a non-numeric content-length header and falls through to reading the body" , async ( ) => {
95+ const fetchImpl = routedFetch ( {
96+ "AI-USAGE.md" : ( ) => ( {
97+ ok : true ,
98+ status : 200 ,
99+ headers : new Headers ( { "content-length" : "not-a-number" } ) ,
100+ json : async ( ) : Promise < unknown > => {
101+ throw new Error ( "json() is unused by resolveRejectionSignaled" ) ;
102+ } ,
103+ text : async ( ) => "No AI-generated pull requests, please." ,
104+ } ) ,
105+ "CONTRIBUTING.md" : ( ) => textResponse ( "Welcome, contributors!" ) ,
106+ } ) ;
107+
108+ const result = await resolveRejectionSignaled ( "acme/widgets" , { fetchImpl } ) ;
109+
110+ expect ( result ) . toBe ( true ) ;
111+ } ) ;
112+
113+ it ( "treats an oversized non-streamed policy document as absent" , async ( ) => {
114+ const oversizedText = "a" . repeat ( 129 * 1024 ) ;
115+ const fetchImpl = routedFetch ( {
116+ "AI-USAGE.md" : ( ) => ( {
117+ ok : true ,
118+ status : 200 ,
119+ headers : new Headers ( ) ,
120+ json : async ( ) : Promise < unknown > => {
121+ throw new Error ( "json() is unused by resolveRejectionSignaled" ) ;
122+ } ,
123+ text : async ( ) => oversizedText ,
124+ } ) ,
125+ "CONTRIBUTING.md" : ( ) => textResponse ( "Do not submit AI-generated code." ) ,
126+ } ) ;
127+
128+ const result = await resolveRejectionSignaled ( "acme/widgets" , { fetchImpl } ) ;
129+
130+ // AI-USAGE.md is treated as absent (oversized), so the verdict falls through to CONTRIBUTING.md's ban.
131+ expect ( result ) . toBe ( true ) ;
132+ } ) ;
133+
94134 it ( "cancels a streamed policy document once it exceeds the byte limit" , async ( ) => {
95135 let canceled = false ;
96136 const chunk = new Uint8Array ( 65 * 1024 ) ;
@@ -125,6 +165,36 @@ describe("resolveRejectionSignaled (#5132)", () => {
125165 expect ( canceled ) . toBe ( true ) ;
126166 } ) ;
127167
168+ it ( "reads a streamed policy document to completion when it stays within the byte limit" , async ( ) => {
169+ const encoder = new TextEncoder ( ) ;
170+ const stream = new ReadableStream ( {
171+ start ( controller ) {
172+ controller . enqueue ( encoder . encode ( "No AI-generated " ) ) ;
173+ controller . enqueue ( encoder . encode ( "pull requests, please." ) ) ;
174+ controller . close ( ) ;
175+ } ,
176+ } ) ;
177+ const fetchImpl = routedFetch ( {
178+ "AI-USAGE.md" : ( ) => ( {
179+ ok : true ,
180+ status : 200 ,
181+ headers : new Headers ( ) ,
182+ body : stream ,
183+ json : async ( ) : Promise < unknown > => {
184+ throw new Error ( "json() is unused by resolveRejectionSignaled" ) ;
185+ } ,
186+ text : async ( ) => {
187+ throw new Error ( "streaming responses should not call text()" ) ;
188+ } ,
189+ } ) ,
190+ "CONTRIBUTING.md" : ( ) => textResponse ( "Welcome, contributors!" ) ,
191+ } ) ;
192+
193+ const result = await resolveRejectionSignaled ( "acme/widgets" , { fetchImpl } ) ;
194+
195+ expect ( result ) . toBe ( true ) ;
196+ } ) ;
197+
128198 it ( "fails open to false when both docs 404" , async ( ) => {
129199 const fetchImpl = routedFetch ( { } ) ;
130200 const result = await resolveRejectionSignaled ( "acme/widgets" , { fetchImpl } ) ;
0 commit comments