Code sync, security fixes
This commit is contained in:
@@ -0,0 +1,115 @@
|
||||
package web
|
||||
|
||||
import (
|
||||
"net/http"
|
||||
|
||||
"github.com/andydixon/relata/internal/api"
|
||||
"github.com/andydixon/relata/internal/relationships"
|
||||
)
|
||||
|
||||
// publicBase carries what every public page needs.
|
||||
//
|
||||
// It deliberately does not embed `base`: the shared page context reads the
|
||||
// pending-review count from the database, and a page served to an anonymous
|
||||
// visitor must touch no workspace data at all.
|
||||
type publicBase struct {
|
||||
Title string
|
||||
Version string
|
||||
SignedIn bool
|
||||
OAuthEnabled bool
|
||||
LocalEnabled bool
|
||||
ProviderName string
|
||||
RequestID string
|
||||
}
|
||||
|
||||
func (h *Handlers) newPublicBase(r *http.Request, title string) publicBase {
|
||||
return publicBase{
|
||||
Title: title,
|
||||
Version: h.d.Version,
|
||||
SignedIn: api.PrincipalFrom(r.Context()) != nil,
|
||||
OAuthEnabled: h.oauthEnabled(),
|
||||
LocalEnabled: h.localLoginEnabled(),
|
||||
ProviderName: h.providerName(),
|
||||
}
|
||||
}
|
||||
|
||||
// LandingPage is the only dual-purpose route.
|
||||
//
|
||||
// Signed in, it is the dashboard. Signed out, it is a description of what
|
||||
// Relata does — served rather than redirected, so the front page of the site is
|
||||
// not a login form.
|
||||
func (h *Handlers) LandingPage(w http.ResponseWriter, r *http.Request) {
|
||||
if api.PrincipalFrom(r.Context()) != nil {
|
||||
h.Dashboard(w, r)
|
||||
return
|
||||
}
|
||||
|
||||
data := struct {
|
||||
publicBase
|
||||
Weights []publicWeightRow
|
||||
}{
|
||||
publicBase: h.newPublicBase(r, "Relata — a self-organising semantic document database"),
|
||||
Weights: publicWeightRows(),
|
||||
}
|
||||
h.d.Renderer.RenderPublic(w, r, "public_landing.html", http.StatusOK, data)
|
||||
}
|
||||
|
||||
// HowItWorksPage explains the pipeline and the scoring, without any data.
|
||||
func (h *Handlers) HowItWorksPage(w http.ResponseWriter, r *http.Request) {
|
||||
data := struct {
|
||||
publicBase
|
||||
Weights []publicWeightRow
|
||||
}{
|
||||
publicBase: h.newPublicBase(r, "How Relata works"),
|
||||
Weights: publicWeightRows(),
|
||||
}
|
||||
h.d.Renderer.RenderPublic(w, r, "public_how.html", http.StatusOK, data)
|
||||
}
|
||||
|
||||
// PublicAPIPage describes the API and how to authenticate against it.
|
||||
func (h *Handlers) PublicAPIPage(w http.ResponseWriter, r *http.Request) {
|
||||
data := struct {
|
||||
publicBase
|
||||
CallbackURL string
|
||||
}{
|
||||
publicBase: h.newPublicBase(r, "The Relata API"),
|
||||
CallbackURL: h.callbackURL(),
|
||||
}
|
||||
h.d.Renderer.RenderPublic(w, r, "public_api.html", http.StatusOK, data)
|
||||
}
|
||||
|
||||
// publicWeightRow is one signal weight, shown publicly because the scoring model is
|
||||
// part of what the product claims rather than something to be discovered.
|
||||
type publicWeightRow struct {
|
||||
Signal string
|
||||
Weight float64
|
||||
Means string
|
||||
}
|
||||
|
||||
func publicWeightRows() []publicWeightRow {
|
||||
explain := map[string]string{
|
||||
"content_hash_match": "Byte-identical content.",
|
||||
"semantic_similarity": "How alike the wording is, rebased so that ordinary similarity counts for little.",
|
||||
"shared_entity": "An exact entity match, discounted by how common that entity is.",
|
||||
"claim_support": "Two statements agree about the same subject.",
|
||||
"claim_contradiction": "Two statements disagree about the same subject.",
|
||||
"model_classification": "A language model's opinion. One signal, weighted below the storage " +
|
||||
"threshold, so it can never create a relationship on its own.",
|
||||
"shared_concept": "Overlapping concept vocabulary.",
|
||||
"alias_entity": "A match through an alias a person confirmed. Unconfirmed candidates count for nothing.",
|
||||
"temporal_proximity": "Created close together in time.",
|
||||
"shared_metadata": "Matching metadata you supplied.",
|
||||
"user_confirmation": "A person confirmed it. This dominates everything else.",
|
||||
"user_rejection": "A person rejected it. This drives the score to zero.",
|
||||
}
|
||||
|
||||
rows := make([]publicWeightRow, 0, len(relationships.Weights))
|
||||
for _, sig := range relationships.WeightOrder() {
|
||||
rows = append(rows, publicWeightRow{
|
||||
Signal: string(sig),
|
||||
Weight: relationships.Weights[sig],
|
||||
Means: explain[string(sig)],
|
||||
})
|
||||
}
|
||||
return rows
|
||||
}
|
||||
Reference in New Issue
Block a user