95 lines
2.4 KiB
Go
95 lines
2.4 KiB
Go
package royalroad
|
|
|
|
import (
|
|
"context"
|
|
"net/http"
|
|
"net/http/httptest"
|
|
"testing"
|
|
"time"
|
|
)
|
|
|
|
func TestParseJSONLD(t *testing.T) {
|
|
tests := []struct {
|
|
name string
|
|
body string
|
|
want Story
|
|
wantErr bool
|
|
}{
|
|
{
|
|
name: "Success",
|
|
body: `<html><script type="application/ld+json">{"name":"Test Story","dateModified":"2023-07-06T17:47:41Z"}</script></html>`,
|
|
want: Story{
|
|
Name: "Test Story",
|
|
DateModified: time.Date(2023, 7, 6, 17, 47, 41, 0, time.UTC),
|
|
},
|
|
wantErr: false,
|
|
},
|
|
{
|
|
name: "Missing Script",
|
|
body: `<html><body>No JSON-LD here</body></html>`,
|
|
wantErr: true,
|
|
},
|
|
{
|
|
name: "Malformed JSON",
|
|
body: `<script type="application/ld+json">{invalid json}</script>`,
|
|
wantErr: true,
|
|
},
|
|
{
|
|
name: "Missing Name",
|
|
body: `<script type="application/ld+json">{"dateModified":"2023-07-06T17:47:41Z"}</script>`,
|
|
wantErr: true,
|
|
},
|
|
{
|
|
name: "Invalid Date",
|
|
body: `<script type="application/ld+json">{"name":"Story","dateModified":"not-a-date"}</script>`,
|
|
wantErr: true,
|
|
},
|
|
}
|
|
|
|
s := NewScraper()
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
got, err := s.parseJSONLD([]byte(tt.body))
|
|
if (err != nil) != tt.wantErr {
|
|
t.Errorf("parseJSONLD() error = %v, wantErr %v", err, tt.wantErr)
|
|
return
|
|
}
|
|
if !tt.wantErr && got != tt.want {
|
|
t.Errorf("parseJSONLD() = %v, want %v", got, tt.want)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestFetchStory_NonRoyalRoadHost(t *testing.T) {
|
|
s := NewScraper()
|
|
_, err := s.FetchStory(context.Background(), "https://google.com/fiction/123")
|
|
if err == nil {
|
|
t.Error("Expected error for non-RoyalRoad host, got nil")
|
|
}
|
|
}
|
|
|
|
func TestFetchStory_ChapterURL(t *testing.T) {
|
|
s := NewScraper()
|
|
_, err := s.FetchStory(context.Background(), "https://www.royalroad.com/fiction/123/chapter/456")
|
|
if err == nil {
|
|
t.Error("Expected error for chapter URL, got nil")
|
|
}
|
|
}
|
|
|
|
func TestFetchStory_HTTPError(t *testing.T) {
|
|
ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
|
w.WriteHeader(http.StatusNotFound)
|
|
}))
|
|
defer ts.Close()
|
|
|
|
s := NewScraper()
|
|
// We can't easily mock the host check for the server URL without custom logic,
|
|
// but we can verify that a non-RR URL (the test server) fails at the host check
|
|
// before it even hits the server.
|
|
_, err := s.FetchStory(context.Background(), ts.URL+"/fiction/123")
|
|
if err == nil {
|
|
t.Error("Expected error for non-RoyalRoad host, got nil")
|
|
}
|
|
}
|