@@ -22,11 +22,7 @@ export interface TimelineResponse {
2222 * Fetches the full packument server-side, extracts only the fields needed
2323 * for the timeline view, sorted by publish time (newest first).
2424 *
25- * Query params:
26- * - offset: number of versions to skip (default 0)
27- * - limit: number of versions to return (default 25)
28- *
29- * URL patterns:
25+ * Examples:
3026 * - /api/registry/timeline/packageName?offset=0&limit=25
3127 * - /api/registry/timeline/@scope/packageName?offset=0&limit=25
3228 */
@@ -37,7 +33,13 @@ export default defineCachedEventHandler(
3733 throw createError ( { statusCode : 404 , message : 'Package name is required' } )
3834 }
3935
40- const packageName = decodeURIComponent ( pkgParam )
36+ let packageName : string
37+ try {
38+ packageName = decodeURIComponent ( pkgParam )
39+ }
40+ catch {
41+ throw createError ( { statusCode : 400 , message : 'Invalid package name encoding' } )
42+ }
4143
4244 const query = getQuery ( event )
4345 const offset = Math . max ( 0 , Number ( query . offset ) || 0 )
@@ -88,7 +90,9 @@ export default defineCachedEventHandler(
8890 swr : true ,
8991 getKey : event => {
9092 const query = getQuery ( event )
91- return `timeline:v1:${ getRouterParam ( event , 'pkg' ) } :${ query . offset ?? 0 } :${ query . limit ?? DEFAULT_LIMIT } `
93+ const offset = Math . max ( 0 , Number ( query . offset ) || 0 )
94+ const limit = Math . max ( 1 , Math . min ( 100 , Number ( query . limit ) || DEFAULT_LIMIT ) )
95+ return `timeline:v1:${ getRouterParam ( event , 'pkg' ) } :${ offset } :${ limit } `
9296 } ,
9397 } ,
9498)
0 commit comments