@@ -503,6 +503,124 @@ final class StatsStoreV4Tests: XCTestCase {
503503 let storageTopEarnerStats = viewStorage. loadTopEarnerStats ( date: " 2020 " , granularity: StatGranularity . year. rawValue)
504504 XCTAssertEqual ( storageTopEarnerStats? . toReadOnly ( ) , expectedTopEarnerStats)
505505 }
506+
507+ // MARK: - StatsStoreV4.retrieveSiteSummaryStats
508+
509+ /// Verifies that `StatsActionV4.retrieveSiteSummaryStats` returns any retrieved SiteSummaryStats.
510+ ///
511+ func test_retrieveSiteSummaryStats_returns_retrieved_stats( ) throws {
512+ // Given
513+ let store = StatsStoreV4 ( dispatcher: dispatcher, storageManager: storageManager, network: network)
514+ network. simulateResponse ( requestUrlSuffix: " sites/ \( sampleSiteID) /stats/summary/ " , filename: " site-summary-stats " )
515+
516+ // When
517+ let result : Result < SiteSummaryStats , Error > = waitFor { promise in
518+ let action = StatsActionV4 . retrieveSiteSummaryStats ( siteID: self . sampleSiteID,
519+ period: . day,
520+ quantity: 1 ,
521+ latestDateToInclude: DateFormatter . dateFromString ( with: " 2022-12-09T17:06:55 " ) ) { result in
522+ promise ( result)
523+ }
524+ store. onAction ( action)
525+ }
526+
527+ // Then
528+ XCTAssertTrue ( result. isSuccess)
529+ let siteSummaryStats = try XCTUnwrap ( result) . get ( )
530+ XCTAssertEqual ( siteSummaryStats, sampleSiteSummaryStats ( ) )
531+ }
532+
533+ /// Verifies that `StatsActionV4.retrieveSiteSummaryStats` makes the expected alternate network request for multiple stats periods.
534+ ///
535+ func test_retrieveSiteSummaryStats_makes_expected_network_request_for_multiple_periods( ) throws {
536+ // Given
537+ let store = StatsStoreV4 ( dispatcher: dispatcher, storageManager: storageManager, network: network)
538+
539+ // When
540+ let _: Void = waitFor { promise in
541+ let action = StatsActionV4 . retrieveSiteSummaryStats ( siteID: self . sampleSiteID,
542+ period: . month,
543+ quantity: 3 ,
544+ latestDateToInclude: DateFormatter . dateFromString ( with: " 2022-12-31T17:06:55 " ) ) { _ in
545+ promise ( ( ) )
546+ }
547+ store. onAction ( action)
548+ }
549+
550+ // Then
551+ let request = try XCTUnwrap ( network. requestsForResponseData. first as? DotcomRequest )
552+ XCTAssertEqual ( request. path, " sites/ \( sampleSiteID) /stats/visits/ " )
553+ XCTAssertEqual ( request. parameters ? [ " date " ] as? String , " 2022-12-31 " )
554+ XCTAssertEqual ( request. parameters ? [ " unit " ] as? String , " month " )
555+ XCTAssertEqual ( request. parameters ? [ " quantity " ] as? String , " 3 " )
556+ }
557+
558+ /// Verifies that `StatsActionV4.retrieveSiteSummaryStats` converts and returns SiteSummaryStats for multiple periods.
559+ ///
560+ func test_retrieveSiteSummaryStats_returns_retrieved_quarter_stats( ) throws {
561+ // Given
562+ let store = StatsStoreV4 ( dispatcher: dispatcher, storageManager: storageManager, network: network)
563+ network. simulateResponse ( requestUrlSuffix: " sites/ \( sampleSiteID) /stats/visits/ " , filename: " site-visits-quarter " )
564+
565+ // When
566+ let result : Result < SiteSummaryStats , Error > = waitFor { promise in
567+ let action = StatsActionV4 . retrieveSiteSummaryStats ( siteID: self . sampleSiteID,
568+ period: . month,
569+ quantity: 3 ,
570+ latestDateToInclude: DateFormatter . dateFromString ( with: " 2022-12-31T17:06:55 " ) ) { result in
571+ promise ( result)
572+ }
573+ store. onAction ( action)
574+ }
575+
576+ // Then
577+ XCTAssertTrue ( result. isSuccess)
578+ let siteSummaryStats = try XCTUnwrap ( result) . get ( )
579+ XCTAssertEqual ( siteSummaryStats, sampleSiteSummaryStatsQuarter ( ) )
580+ }
581+
582+ /// Verifies that `StatsActionV4.retrieveSiteSummaryStats` returns an error whenever there is an error response from the backend.
583+ ///
584+ func test_retrieveSiteSummaryStats_returns_error_upon_response_error( ) {
585+ // Given
586+ let store = StatsStoreV4 ( dispatcher: dispatcher, storageManager: storageManager, network: network)
587+ network. simulateResponse ( requestUrlSuffix: " sites/ \( sampleSiteID) /stats/summary/ " , filename: " generic_error " )
588+
589+ // When
590+ let result : Result < SiteSummaryStats , Error > = waitFor { promise in
591+ let action = StatsActionV4 . retrieveSiteSummaryStats ( siteID: self . sampleSiteID,
592+ period: . day,
593+ quantity: 1 ,
594+ latestDateToInclude: DateFormatter . dateFromString ( with: " 2022-12-09T17:06:55 " ) ) { result in
595+ promise ( result)
596+ }
597+ store. onAction ( action)
598+ }
599+
600+ // Then
601+ XCTAssertTrue ( result. isFailure)
602+ }
603+
604+ /// Verifies that `StatsActionV4.retrieveSiteSummaryStats` returns an error whenever there is no backend response.
605+ ///
606+ func test_retrieveSiteSummaryStats_returns_error_upon_empty_response( ) {
607+ // Given
608+ let store = StatsStoreV4 ( dispatcher: dispatcher, storageManager: storageManager, network: network)
609+
610+ // When
611+ let result : Result < SiteSummaryStats , Error > = waitFor { promise in
612+ let action = StatsActionV4 . retrieveSiteSummaryStats ( siteID: self . sampleSiteID,
613+ period: . day,
614+ quantity: 1 ,
615+ latestDateToInclude: DateFormatter . dateFromString ( with: " 2022-12-09T17:06:55 " ) ) { result in
616+ promise ( result)
617+ }
618+ store. onAction ( action)
619+ }
620+
621+ // Then
622+ XCTAssertTrue ( result. isFailure)
623+ }
506624}
507625
508626
@@ -683,4 +801,22 @@ private extension StatsStoreV4Tests {
683801 currency: " " ,
684802 imageUrl: " https://dulces.mystagingwebsite.com/wp-content/uploads/2020/07/img_7472-scaled.jpeg " )
685803 }
804+
805+ // MARK: - Site Summary Stats Sample
806+
807+ func sampleSiteSummaryStats( ) -> Networking . SiteSummaryStats {
808+ return SiteSummaryStats ( siteID: sampleSiteID,
809+ date: " 2022-12-09 " ,
810+ period: . day,
811+ visitors: 12 ,
812+ views: 123 )
813+ }
814+
815+ func sampleSiteSummaryStatsQuarter( ) -> Networking . SiteSummaryStats {
816+ return SiteSummaryStats ( siteID: sampleSiteID,
817+ date: " 2022-12-09 " ,
818+ period: . month,
819+ visitors: 243 ,
820+ views: 486 )
821+ }
686822}
0 commit comments