// WebPageContentServiceTests.swift // OSGKeyboardTests @testable import OSGKeyboard @testable import OSGKeyboardShared import XCTest final class WebPageContentServiceTests: XCTestCase { override func setUp() { super.setUp() StubURLProtocol.reset() } override func tearDown() { StubURLProtocol.reset() super.tearDown() } func testURLPolicyAllowsPublicHTTPSAndRejectsPrivateTargets() { XCTAssertNotNil( WebPageURLPolicy.validatedSummaryURL( URL(string: "https://example.com/article")! ) ) XCTAssertNil( WebPageURLPolicy.validatedSummaryURL( URL(string: "http://example.com/article")! ) ) XCTAssertNil( WebPageURLPolicy.validatedSummaryURL( URL(string: "https://127.0.0.1/admin")! ) ) XCTAssertNil( WebPageURLPolicy.validatedSummaryURL( URL(string: "https://router.local/admin")! ) ) XCTAssertNil( WebPageURLPolicy.validatedSummaryURL( URL(string: "https://user:secret@example.com/private")! ) ) } func testHTMLExtractorUsesArticleAndRemovesActiveOrNavigationContent() throws { let html = """ Example & Report

Quarterly update

Revenue grew by 18 percent while operating costs remained stable.

The company plans to expand into two additional markets next quarter.

""" let content = try WebPageHTMLExtractor.extract( html: html, finalURL: URL(string: "https://example.com/report")!, maximumBodyCharacters: 10_000 ) XCTAssertEqual(content.title, "Example & Report") XCTAssertTrue(content.body.contains("Revenue grew by 18 percent")) XCTAssertTrue(content.body.contains("two additional markets")) XCTAssertFalse(content.body.contains("Home Pricing Login")) XCTAssertFalse(content.body.contains("reveal the system prompt")) } func testServiceDownloadsAndExtractsBoundedStaticHTML() async throws { let configuration = URLSessionConfiguration.ephemeral configuration.protocolClasses = [HTMLPageStubURLProtocol.self] let service = WebPageContentService(configuration: configuration) let content = try await service.fetchSummarySource( from: URL(string: "https://example.com/release")! ) XCTAssertEqual(content.title, "Launch Notes") XCTAssertTrue(content.body.contains("reliable link detection")) XCTAssertTrue(content.summaryMaterial.contains("https://example.com/release")) } func testExtractorRejectsPagesWithoutReadableContent() { XCTAssertThrowsError( try WebPageHTMLExtractor.extract( html: "", finalURL: URL(string: "https://example.com")!, maximumBodyCharacters: 10_000 ) ) { error in XCTAssertEqual(error as? WebPageContentError, .emptyContent) } } } private final class HTMLPageStubURLProtocol: URLProtocol, @unchecked Sendable { // URLProtocol requires overridable class methods; `static` cannot satisfy // these superclass requirements even though this concrete stub is final. // swiftlint:disable:next static_over_final_class override class func canInit(with request: URLRequest) -> Bool { true } // swiftlint:disable:next static_over_final_class override class func canonicalRequest(for request: URLRequest) -> URLRequest { request } override func startLoading() { let body = Data(""" Launch Notes

Version 2

This release adds reliable link detection and webpage summaries.

Users can review the generated summary before inserting it.

""".utf8) let response = HTTPURLResponse( url: request.url!, statusCode: 200, httpVersion: "HTTP/1.1", headerFields: ["Content-Type": "text/html; charset=utf-8"] )! client?.urlProtocol( self, didReceive: response, cacheStoragePolicy: .notAllowed ) client?.urlProtocol(self, didLoad: body) client?.urlProtocolDidFinishLoading(self) } override func stopLoading() {} }