11import dayjs from 'dayjs'
22import isoWeek from 'dayjs/plugin/isoWeek'
33import 'server-only'
4+ import { z } from 'zod'
45
56dayjs . extend ( isoWeek )
67
@@ -30,19 +31,33 @@ type RangeResponse = {
3031 } >
3132}
3233
34+ const rangeResponseSchema = z . object ( {
35+ downloads : z . array (
36+ z . object ( {
37+ downloads : z . number ( ) ,
38+ day : z . string ( )
39+ } )
40+ )
41+ } )
42+
3343async function getLastNDays ( pkg : string , n : number ) : Promise < Datum [ ] > {
3444 const start = dayjs ( ) . subtract ( n , 'day' ) . format ( 'YYYY-MM-DD' )
3545 const end = dayjs ( ) . subtract ( 1 , 'day' ) . endOf ( 'day' ) . format ( 'YYYY-MM-DD' )
3646 const url = `https://api.npmjs.org/downloads/range/${ start } :${ end } /${ pkg } `
37- const { downloads } = await get < RangeResponse > ( url )
38- const data = downloads . map ( d => ( {
39- date : d . day ,
40- downloads : d . downloads
41- } ) )
42- if ( data . at ( - 1 ) ?. downloads === 0 ) {
43- data . pop ( ) // Remove last day if it's zero (stats not available yet)
47+ try {
48+ const { downloads } = rangeResponseSchema . parse ( await get ( url ) )
49+ const data = downloads . map ( d => ( {
50+ date : d . day ,
51+ downloads : d . downloads
52+ } ) )
53+ if ( data . at ( - 1 ) ?. downloads === 0 ) {
54+ data . pop ( ) // Remove last day if it's zero (stats not available yet)
55+ }
56+ return data
57+ } catch ( e ) {
58+ console . error ( e )
59+ return [ ]
4460 }
45- return data
4661}
4762
4863async function getAllTime ( pkg : string ) : Promise < number > {
@@ -54,10 +69,15 @@ async function getAllTime(pkg: string): Promise<number> {
5469 const url = `https://api.npmjs.org/downloads/range/${ start . format (
5570 'YYYY-MM-DD'
5671 ) } :${ end . format ( 'YYYY-MM-DD' ) } /${ pkg } `
57- const res = await get < RangeResponse > ( url )
58- downloads += res . downloads . reduce ( ( sum , d ) => sum + d . downloads , 0 )
59- start = end
60- end = start . add ( 18 , 'month' )
72+ try {
73+ const res = rangeResponseSchema . parse ( await get < RangeResponse > ( url ) )
74+ downloads += res . downloads . reduce ( ( sum , d ) => sum + d . downloads , 0 )
75+ start = end
76+ end = start . add ( 18 , 'month' )
77+ } catch ( e ) {
78+ console . error ( e )
79+ break
80+ }
6181 }
6282 return downloads
6383}
0 commit comments