chore: add mentions

This commit is contained in:
xuu 2025-03-30 13:50:39 -06:00
parent 6579c50c09
commit fb957ed25d
Signed by: xuu
GPG Key ID: 8B3B0604F164E04F

164
http.go
View File

@ -26,10 +26,10 @@ var PREAMBLE_DOCS = func() lextwt.Comments {
c := add(nil, iAmTheWatcher)
c = add(c, "")
c = add(c,"Usage:")
c = add(c," %s/api/plain/users View list of users and latest twt date.", hostname)
c = add(c," %s/api/plain/twt View all twts in decending order.", hostname)
c = add(c," %s/api/plain/conv/:hash View all twts for a conversation subject.", hostname)
c = add(c," %s/api/plain/users View list of users and latest twt date.", hostname)
c = add(c," %s/api/plain/twt View all twts in decending order.", hostname)
c = add(c," %s/api/plain/mentions?uri=:uri View all mentions for uri in decending order.", hostname)
c = add(c," %s/api/plain/conv/:hash View all twts for a conversation subject.", hostname)
c = add(c,"")
c = add(c,"Options:")
c = add(c," uri Filter to show a specific users twts.")
@ -132,19 +132,24 @@ func httpServer(ctx context.Context, app *appState) error {
reg.WriteTo(w)
})
http.HandleFunc("/api/plain/twt", func(w http.ResponseWriter, r *http.Request) {
http.HandleFunc("/api/plain/mentions", func(w http.ResponseWriter, r *http.Request) {
ctx, span := otel.Span(r.Context())
defer span.End()
args := make([]any, 0, 3)
where := `where feed_id in (select feed_id from feeds where state != 'permanantly-dead')`
w.Header().Set("Content-Type", "text/plain; charset=utf-8")
uri := r.URL.Query().Get("uri")
if uri != "" {
feed_id := urlNS.UUID5(uri)
where = "where feed_id = ?"
args = append(args, feed_id)
if uri == ""{
reg := lextwt.NewTwtRegistry(PREAMBLE_DOCS, nil)
reg.WriteTo(w)
return
}
mention := urlNS.UUID5(uri).MarshalText()
args := make([]any, 0, 3)
args = append(args, mention)
limit := 100
if v, ok := strconv.Atoi(r.URL.Query().Get("limit")); ok == nil {
@ -158,8 +163,9 @@ func httpServer(ctx context.Context, app *appState) error {
var end int64
err = db.QueryRowContext(ctx, `
select count(*) n from twts `+where+``, args...).Scan(&end)
select count(*) n from twts, json_each(mentions) where value = ?`, args...).Scan(&end)
span.RecordError(err)
fmt.Println(mention, end, err)
if offset < 1 {
offset += end
@ -169,12 +175,6 @@ func httpServer(ctx context.Context, app *appState) error {
offset = max(1, offset)
args = append(args, limit, offset-int64(limit))
span.AddEvent("twts", trace.WithAttributes(
attribute.Int("limit", limit),
attribute.Int64("offset-end", offset),
attribute.Int64("offset-start", offset-int64(limit)),
attribute.Int64("max", end),
))
qry := `
SELECT
@ -191,15 +191,16 @@ func httpServer(ctx context.Context, app *appState) error {
) using (feed_id)
where rowid in (
select rowid from twts
` + where +`
where ulid in (select ulid from twts, json_each(mentions) where value = ?)
order by ulid asc
limit ?
offset ?
)
order by ulid asc`
order by ulid asc
`
fmt.Println(qry, args)
w.Header().Set("Content-Type", "text/plain; charset=utf-8")
rows, err := db.QueryContext(
ctx, qry, args...,
)
@ -226,9 +227,128 @@ func httpServer(ctx context.Context, app *appState) error {
return
}
twter := types.NewTwter(o.Nick, o.URI)
o.Text = strings.ReplaceAll(o.Text, "\n", "\u2028")
twt, _ := lextwt.ParseLine(o.Text, &twter)
twts = append(twts, twt)
}
preamble := add(PREAMBLE_DOCS, "twt range = 1 %d", end)
preamble = add(preamble, "self = %s/mentions%s", hostname, mkqry(uri, limit, offset))
if next := offset + int64(len(twts)); next < end {
preamble = add(preamble, "next = %s/mentions%s", hostname, mkqry(uri, limit, next))
}
if prev := offset - int64(limit); prev > 0 {
preamble = add(preamble, "prev = %s/mentions%s", hostname, mkqry(uri, limit, prev))
}
reg := lextwt.NewTwtRegistry(preamble, twts)
reg.WriteTo(w)
})
http.HandleFunc("/api/plain/twt", func(w http.ResponseWriter, r *http.Request) {
ctx, span := otel.Span(r.Context())
defer span.End()
uri := r.URL.Query().Get("uri")
limit := 100
if v, ok := strconv.Atoi(r.URL.Query().Get("limit")); ok == nil {
limit = v
}
var offset int64 = 0
if v, ok := strconv.ParseInt(r.URL.Query().Get("offset"), 10, 64); ok == nil {
offset = v
}
twts, end, err := func(uri string, limit int, offset int64, ) ([]types.Twt, int64, error) {
args := make([]any, 0, 3)
where := `where feed_id in (select feed_id from feeds where state != 'permanantly-dead')`
if uri != "" {
feed_id := urlNS.UUID5(uri)
where = "where feed_id = ?"
args = append(args, feed_id)
}
var end int64
err = db.QueryRowContext(ctx, `
select count(*) n from twts `+where+``, args...).Scan(&end)
span.RecordError(err)
if offset < 1 {
offset += end
}
limit = min(100, max(1, limit))
offset = max(1, offset)
args = append(args, limit, offset-int64(limit))
span.AddEvent("twts", trace.WithAttributes(
attribute.Int("limit", limit),
attribute.Int64("offset-end", offset),
attribute.Int64("offset-start", offset-int64(limit)),
attribute.Int64("max", end),
))
qry := `
SELECT
feed_id,
hash,
conv,
coalesce(nick, 'nobody') nick,
coalesce(uri, 'https://empty.txt') uri,
text
FROM twts
join (
select feed_id, nick, uri
from feeds
) using (feed_id)
where rowid in (
select rowid from twts
` + where +`
order by ulid asc
limit ?
offset ?
)
order by ulid asc`
fmt.Println(qry, args)
w.Header().Set("Content-Type", "text/plain; charset=utf-8")
rows, err := db.QueryContext(
ctx, qry, args...,
)
if err != nil {
span.RecordError(err)
return nil, 0, err
}
defer rows.Close()
var twts []types.Twt
for rows.Next() {
var o struct {
FeedID string
Hash string
Conv string
Dt string
Nick string
URI string
Text string
}
err = rows.Scan(&o.FeedID, &o.Hash, &o.Conv, &o.Nick, &o.URI, &o.Text)
if err != nil {
span.RecordError(err)
return nil, 0, err
}
twter := types.NewTwter(o.Nick, o.URI)
twt, _ := lextwt.ParseLine(o.Text, &twter)
twts = append(twts, twt)
}
return twts, end, err
} (uri, limit, offset)
span.RecordError(err)
preamble := add(PREAMBLE_DOCS, "twt range = 1 %d", end)
preamble = add(preamble, "self = %s/api/plain/twt%s", hostname, mkqry(uri, limit, offset))
if next := offset + int64(len(twts)); next < end {