159 lines
4.8 KiB
Go
159 lines
4.8 KiB
Go
|
package query
|
||
|
|
||
|
import (
|
||
|
"encoding/json"
|
||
|
"fmt"
|
||
|
"io"
|
||
|
"net/http"
|
||
|
"strings"
|
||
|
|
||
|
"git.yetaga.in/alazyreader/library/media"
|
||
|
)
|
||
|
|
||
|
type GoogleBooks struct{}
|
||
|
|
||
|
type googleBookResult struct {
|
||
|
Kind string `json:"kind"`
|
||
|
TotalItems int `json:"totalItems"`
|
||
|
Items []item `json:"items"`
|
||
|
}
|
||
|
|
||
|
type industryIdentifier struct {
|
||
|
Type string `json:"type"`
|
||
|
Identifier string `json:"identifier"`
|
||
|
}
|
||
|
|
||
|
type readingMode struct {
|
||
|
Text bool `json:"text"`
|
||
|
Image bool `json:"image"`
|
||
|
}
|
||
|
|
||
|
type panelizationSummary struct {
|
||
|
ContainsEpubBubbles bool `json:"containsEpubBubbles"`
|
||
|
ContainsImageBubbles bool `json:"containsImageBubbles"`
|
||
|
}
|
||
|
|
||
|
type imageLink struct {
|
||
|
SmallThumbnail string `json:"smallThumbnail"`
|
||
|
Thumbnail string `json:"thumbnail"`
|
||
|
}
|
||
|
|
||
|
type volumeInfo struct {
|
||
|
Title string `json:"title"`
|
||
|
Subtitle string `json:"subtitle"`
|
||
|
Authors []string `json:"authors"`
|
||
|
Publisher string `json:"publisher"`
|
||
|
PublishedDate string `json:"publishedDate"`
|
||
|
Description string `json:"description"`
|
||
|
IndustryIdentifiers []industryIdentifier `json:"industryIdentifiers"`
|
||
|
ReadingModes readingMode `json:"readingModes"`
|
||
|
PageCount int `json:"pageCount"`
|
||
|
PrintType string `json:"printType"`
|
||
|
Categories []string `json:"categories"`
|
||
|
AverageRating int `json:"averageRating"`
|
||
|
RatingsCount int `json:"ratingsCount"`
|
||
|
MaturityRating string `json:"maturityRating"`
|
||
|
AllowAnonLogging bool `json:"allowAnonLogging"`
|
||
|
ContentVersion string `json:"contentVersion"`
|
||
|
PanelizationSummary panelizationSummary `json:"panelizationSummary"`
|
||
|
ImageLinks imageLink `json:"imageLinks"`
|
||
|
Language string `json:"language"`
|
||
|
PreviewLink string `json:"previewLink"`
|
||
|
InfoLink string `json:"infoLink"`
|
||
|
CanonicalVolumeLink string `json:"canonicalVolumeLink"`
|
||
|
}
|
||
|
|
||
|
type saleInfo struct {
|
||
|
Country string `json:"country"`
|
||
|
Saleability string `json:"saleability"`
|
||
|
IsEbook bool `json:"isEbook"`
|
||
|
}
|
||
|
|
||
|
type epub struct {
|
||
|
IsAvailable bool `json:"isAvailable"`
|
||
|
}
|
||
|
|
||
|
type pdf struct {
|
||
|
IsAvailable bool `json:"isAvailable"`
|
||
|
}
|
||
|
|
||
|
type accessInfo struct {
|
||
|
Country string `json:"country"`
|
||
|
Viewability string `json:"viewability"`
|
||
|
Embeddable bool `json:"embeddable"`
|
||
|
PublicDomain bool `json:"publicDomain"`
|
||
|
TextToSpeechPermission string `json:"textToSpeechPermission"`
|
||
|
Epub epub `json:"epub"`
|
||
|
Pdf pdf `json:"pdf"`
|
||
|
WebReaderLink string `json:"webReaderLink"`
|
||
|
AccessViewStatus string `json:"accessViewStatus"`
|
||
|
QuoteSharingAllowed bool `json:"quoteSharingAllowed"`
|
||
|
}
|
||
|
|
||
|
type searchInfo struct {
|
||
|
TextSnippet string `json:"textSnippet"`
|
||
|
}
|
||
|
|
||
|
type item struct {
|
||
|
Kind string `json:"kind"`
|
||
|
ID string `json:"id"`
|
||
|
Etag string `json:"etag"`
|
||
|
SelfLink string `json:"selfLink"`
|
||
|
VolumeInfo volumeInfo `json:"volumeInfo"`
|
||
|
SaleInfo saleInfo `json:"saleInfo"`
|
||
|
AccessInfo accessInfo `json:"accessInfo"`
|
||
|
SearchInfo searchInfo `json:"searchInfo"`
|
||
|
}
|
||
|
|
||
|
func (g *GoogleBooks) GetByISBN(isbn string) (*media.Book, error) {
|
||
|
client := &http.Client{}
|
||
|
resp, err := client.Get(fmt.Sprintf("https://www.googleapis.com/books/v1/volumes?q=isbn:%s", isbn))
|
||
|
|
||
|
if err != nil {
|
||
|
return nil, err
|
||
|
}
|
||
|
defer resp.Body.Close()
|
||
|
|
||
|
if resp.StatusCode != http.StatusOK {
|
||
|
return nil, fmt.Errorf("received non-200 status code: %d", resp.StatusCode)
|
||
|
}
|
||
|
|
||
|
var result googleBookResult
|
||
|
b, err := io.ReadAll(resp.Body)
|
||
|
if err != nil {
|
||
|
return nil, err
|
||
|
}
|
||
|
if err = json.Unmarshal(b, &result); err != nil {
|
||
|
return nil, err
|
||
|
}
|
||
|
|
||
|
if len(result.Items) == 0 {
|
||
|
return nil, fmt.Errorf("no book found")
|
||
|
}
|
||
|
|
||
|
return googleToBook(result.Items[0]), nil
|
||
|
}
|
||
|
|
||
|
func googleToBook(i item) *media.Book {
|
||
|
return &media.Book{
|
||
|
Title: buildTitle(i.VolumeInfo.Title, i.VolumeInfo.Subtitle),
|
||
|
Authors: i.VolumeInfo.Authors,
|
||
|
SortAuthor: strings.ToLower(getLastName(tryGetFirst(i.VolumeInfo.Authors))),
|
||
|
ISBN10: getIdentifierType(i.VolumeInfo.IndustryIdentifiers, "ISBN_10"),
|
||
|
ISBN13: getIdentifierType(i.VolumeInfo.IndustryIdentifiers, "ISBN_13"),
|
||
|
Publisher: i.VolumeInfo.Publisher,
|
||
|
Year: strings.Split(i.VolumeInfo.PublishedDate, "-")[0],
|
||
|
Description: i.VolumeInfo.Description,
|
||
|
Genre: tryGetFirst(i.VolumeInfo.Categories),
|
||
|
}
|
||
|
}
|
||
|
|
||
|
func getIdentifierType(iis []industryIdentifier, typename string) string {
|
||
|
for _, ident := range iis {
|
||
|
if ident.Type == typename {
|
||
|
return ident.Identifier
|
||
|
}
|
||
|
}
|
||
|
return ""
|
||
|
}
|