Skip to content

Commit

Permalink
add support for new summaries and product clusters (#9)
Browse files Browse the repository at this point in the history
  • Loading branch information
jdpedrie authored May 3, 2024
1 parent 265c0f6 commit 345818b
Show file tree
Hide file tree
Showing 4 changed files with 162 additions and 16 deletions.
51 changes: 45 additions & 6 deletions brave.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,12 +9,13 @@ import (
)

const (
defaultBaseURL = "https://api.search.brave.com/res/v1/"
imageSearchPath = "images/search"
spellcheckPath = "spellcheck/search"
suggestSearchPath = "suggest/search"
videoSearchPath = "videos/search"
webSearchPath = "web/search"
defaultBaseURL = "https://api.search.brave.com/res/v1/"
imageSearchPath = "images/search"
spellcheckPath = "spellcheck/search"
suggestSearchPath = "suggest/search"
videoSearchPath = "videos/search"
webSearchPath = "web/search"
summarizerSearchPath = "summarizer/search"
)

// Brave is an interface for fetching results from the Brave Search API.
Expand Down Expand Up @@ -215,6 +216,8 @@ type searchOptions struct {
units UnitType
userAgent string
apiVersion string
summary bool
entityInfo bool
}

func (s searchOptions) getFreshness() string {
Expand Down Expand Up @@ -646,6 +649,10 @@ func WithLocPostalCode(v string) SearchOption {
}

// WithSpellcheck toggles spellchecking on or off.
//
// Refer to [Query Parameters] for more detail.
//
// [Query Parameters]: https://api.search.brave.com/app/documentation/query
func WithSpellcheck(v bool) SearchOption {
return func(o searchOptions) searchOptions {
o.spellcheck = &v
Expand All @@ -654,13 +661,45 @@ func WithSpellcheck(v bool) SearchOption {
}

// WithAPIVersion specifies the version of the API to use for a request.
//
// Refer to [Query Headers] for more detail.
//
// [Query Headers]: https://api.search.brave.com/app/documentation/headers
func WithAPIVersion(v string) SearchOption {
return func(o searchOptions) searchOptions {
o.apiVersion = v
return o
}
}

// WithSummary specifies whether a summary key should be requested.
//
// Applicable to [Brave.WebSearch].
//
// Refer to [Query Parameters] for more detail.
//
// [Query Parameters]: https://api.search.brave.com/app/documentation/query
func WithSummary(v bool) SearchOption {
return func(o searchOptions) searchOptions {
o.summary = v
return o
}
}

// WithEntityInfo specifies whether entity information should be returned
//
// Applicable to [Brave.SummarizerSearch].
//
// Refer to [Query Parameters] for more detail.
//
// [Query Parameters]: https://api.search.brave.com/app/documentation/query
func WithEntityInfo(v bool) SearchOption {
return func(o searchOptions) searchOptions {
o.entityInfo = v
return o
}
}

// ClientOption allows configuration of the API client.
type ClientOption func(clientOptions) clientOptions

Expand Down
49 changes: 47 additions & 2 deletions summary.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,54 @@ package brave

import (
"context"
"errors"
"net/http"

"github.com/google/go-querystring/query"
)

func (b *brave) SummarizerSearch(ctx context.Context, key string, options ...SearchOption) (*SummarizerSearchResult, error) {
return nil, errors.New("not implemented")
u := *b.baseURL
u.Path = u.Path + summarizerSearchPath

var opts searchOptions
applyOpts(&opts, options, nil)

var params summarizerSearchParams
params.fromSearchOptions(key, opts)

values, err := query.Values(params)
if err != nil {
return nil, err
}

u.RawQuery = values.Encode()

req, err := http.NewRequestWithContext(ctx, http.MethodGet, u.String(), nil)
if err != nil {
return nil, err
}

opts.applyRequestHeaders(b.subscriptionToken, req)

return handleRequest[SummarizerSearchResult](b.client, req)
}

type SummarizerSearchResult struct {
Type string `json:"type"`
Status string `json:"status"`
Title string `json:"title"`
Summary []SummaryMessage `json:"summary"`
Enrichments *SummaryEnrichments `json:"enrichments"`
Followups []string `json:"followups"`
EntitiesInfo map[string]any `json:"entities_info"`
}

type summarizerSearchParams struct {
Key string `url:"key"`
EntityInfo bool `url:"entity_info"`
}

func (s *summarizerSearchParams) fromSearchOptions(key string, options searchOptions) {
s.Key = key
s.EntityInfo = options.entityInfo
}
71 changes: 65 additions & 6 deletions types.go
Original file line number Diff line number Diff line change
Expand Up @@ -171,7 +171,7 @@ type SearchResult struct {
Rating *Rating `json:"rating"`
Article *Article `json:"article"`
// Product any `json:"product"`
// ProductCluster []any `json:"product_cluster"`
ProductCluster []Product `json:"product_cluster"`
ClusterType string `json:"cluster_type"`
Cluster []Result `json:"cluster"`
CreativeWork *CreativeWork `json:"creative_work"`
Expand Down Expand Up @@ -239,6 +239,7 @@ type Image struct {
Thumbnail *Thumbnail `json:"thumbnail"`
URL string `json:"url"`
Properties *ImageProperties `json:"properties"`
Text string `json:"text"`
}

type ImageProperties struct {
Expand Down Expand Up @@ -408,15 +409,15 @@ type Price struct {
type Article struct {
Author []Person `json:"author"`
Date string `json:"date"`
Publisher *Organization `json:"organization"`
Publisher *Organization `json:"publisher"`
Thumbnail *Thumbnail `json:"thumbnail"`
IsAccessibleForFree bool `json:"isAccessibleForFree"`
}

type Organization struct {
Person

Type string `json:"type"`
Type string `json:"type"`
Name string `json:"name"`
Thumbnail *Thumbnail `json:"thumbnail"`
}

type CreativeWork struct {
Expand Down Expand Up @@ -450,7 +451,49 @@ type Software struct {
IsPyPi bool `json:"is_pypi"`
}

type SummarizerSearchResult struct{}
type Summarizer struct {
Type string `json:"type"`
Key string `json:"key"`
}

type SummaryMessage struct {
Type string `json:"type"`
Data string `json:"data"`
}

type SummaryEnrichments struct {
Raw string `json:"raw"`
Images []Image `json:"images"`
QA []SummaryAnswer `json:"qa"`
Entities []SummaryEntity `json:"entities"`
Context []SummaryContext `json:"context"`
}

type SummaryAnswer struct {
Answer string `json:"answer"`
Score float32 `json:"score"`
Highlight *TextLocation `json:"highlight"`
}

type SummaryEntity struct {
UUID string `json:"uuid"`
Name string `json:"name"`
URL string `json:"url"`
Text string `json:"text"`
Images []Image `json:"images"`
Highlight []TextLocation `json:"highlight"`
}

type SummaryContext struct {
Title string `json:"title"`
URL string `json:"url"`
MetaURL *MetaURL `json:"meta_url"`
}

type TextLocation struct {
Start Number `json:"start"`
End Number `json:"end"`
}

type SuggestResult struct {
Query string `json:"string"`
Expand Down Expand Up @@ -499,6 +542,22 @@ type GraphInfoBox struct {
Movie *MovieData `json:"movie"`
}

type Product struct {
Type string `json:"type"`
Name string `json:"name"`
Price string `json:"price"`
Thumbnail *Thumbnail `json:"thumbnail"`
Description string `json:"description"`
Offers []Offer `json:"offers"`
Rating *Rating `json:"rating"`
}

type Offer struct {
URL string `json:"url"`
Price string `json:"price"`
PriceCurrency string `json:"priceCurrency"`
}

type ErrorResponse struct {
ID string `json:"id"`
Status int `json:"status"`
Expand Down
7 changes: 5 additions & 2 deletions web.go
Original file line number Diff line number Diff line change
Expand Up @@ -37,14 +37,15 @@ func (b *brave) WebSearch(ctx context.Context, term string, options ...SearchOpt
type WebSearchResult struct {
Type string `json:"type"`
Discussions *ResultContainer[DiscussionResult] `json:"discussions"`
FAQ any `json:"faq"`
FAQ *ResultContainer[QA] `json:"faq"`
InfoBox *ResultContainer[GraphInfoBox] `json:"infobox"`
Locations *Locations `json:"locations"`
Locations *ResultContainer[LocationResult] `json:"locations"`
Mixed *Mixed `json:"mixed"`
News *ResultContainer[NewsResult] `json:"news"`
Query *Query `json:"query"`
Videos *ResultContainer[VideoResult] `json:"videos"`
Web *ResultContainer[SearchResult] `json:"web"`
Summarizer *Summarizer `json:"summarizer"`
}

type webSearchParams struct {
Expand All @@ -62,6 +63,7 @@ type webSearchParams struct {
TextDecorations bool `url:"text_decorations,omitempty"`
UILang string `url:"ui_lang,omitempty"`
Units string `url:"units,omitempty"`
Summary bool `url:"summary,omitempty"`
}

func (w *webSearchParams) fromSearchOptions(term string, options searchOptions) {
Expand All @@ -79,4 +81,5 @@ func (w *webSearchParams) fromSearchOptions(term string, options searchOptions)
w.TextDecorations = options.textDecorations
w.UILang = options.uiLang
w.Units = options.units.String()
w.Summary = options.summary
}

0 comments on commit 345818b

Please sign in to comment.