oficina / sheets Public

The Keymail continuation says where it's going, and is tested

Review (Fable): the notice rendered an empty status line and no test
reached the page. The render is a method now, tested directly.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Paul Campbell pushed by paul@keymail.dev 1657f59b175ed6ff08bc372c0a468d88303723b0 parent 91e7f8c
2 files changed, +33 −10
  • internal/sheets/home.go +14 −10
  • internal/sheets/signin_door_test.go +19 −0

CI passed — run details

CI log
amadan: .amadan/timeout: this job's budget is 15m0s (this runner allows up to 30m0s)
=== vet ===
CGO_ENABLED=0 go vet ./...
go: downloading github.com/carlosframework/rastrillo v0.23.0
go: downloading golang.org/x/crypto v0.55.0
go: downloading amadan.net/oficina/estilo.git v0.0.0-20260929185827-41201439fd22
go: downloading gorm.io/gorm v1.31.2
go: downloading github.com/xuri/excelize/v2 v2.11.0
go: downloading amadan.net/oficina/home/connect v0.0.0-20260923190447-01166fcfc0a9
go: downloading amadan.net/oficina/home/handoff v0.0.0-20260908102137-481d2d57f489
go: downloading amadan.net/rastrillo/native/server v0.0.0-20260923173546-2a5d07b2c8d3
go: downloading github.com/go-chi/chi/v5 v5.3.2
go: downloading amadan.net/rastrillo/rastrillo v0.26.1-0.20260908075707-29e4491631bd
go: downloading github.com/richardlehane/mscfb v1.0.7
go: downloading github.com/tiendc/go-deepcopy v1.7.2
go: downloading github.com/xuri/efp v0.0.1
go: downloading github.com/xuri/nfp v0.0.2-0.20250530014748-2ddeb826f9a9
go: downloading golang.org/x/net v0.57.0
go: downloading golang.org/x/text v0.41.0
go: downloading github.com/jinzhu/now v1.1.5
go: downloading github.com/go-json-experiment/json v0.0.0-20250725192818-e39067aee2d2
go: downloading modernc.org/sqlite v1.55.0
go: downloading gorm.io/plugin/dbresolver v1.6.2
go: downloading github.com/keymaildev/signin v0.1.1
go: downloading github.com/richardlehane/msoleps v1.0.6
go: downloading github.com/jinzhu/inflection v1.0.0
go: downloading golang.org/x/sys v0.47.0
go: downloading modernc.org/libc v1.74.1
go: downloading modernc.org/memory v1.11.0
go: downloading github.com/google/uuid v1.6.0
go: downloading modernc.org/mathutil v1.7.1
go: downloading github.com/dustin/go-humanize v1.0.1
go: downloading github.com/remyoudompheng/bigfft v0.0.0-20230129092748-24d4a6f8daec
=== fmt ===
=== build ===
CGO_ENABLED=0 go build ./...
=== migrations ===
rastrillo migration check
rastrillo migration check: models and migrations agree
=== go-test ===
CGO_ENABLED=0 go test -count=1 ./...
?   	amadan.net/oficina/sheets/cmd/sheets	[no test files]
ok  	amadan.net/oficina/sheets/internal/guardstest	0.089s
ok  	amadan.net/oficina/sheets/internal/sheets	11.399s
ok  	amadan.net/oficina/sheets/internal/sheets/calc	0.010s
ok  	amadan.net/oficina/sheets/internal/sheets/format	0.004s
ok  	amadan.net/oficina/sheets/internal/sheets/live	0.054s
ok  	amadan.net/oficina/sheets/internal/sheets/seal	0.003s
ok  	amadan.net/oficina/sheets/internal/sheets/sealtest	0.004s
ok  	amadan.net/oficina/sheets/internal/sheets/store	3.283s
ok  	amadan.net/oficina/sheets/internal/sheets/xlsx	0.336s
?   	amadan.net/oficina/sheets/tools/gencorpus	[no test files]
=== race ===
go test -race -count=1 ./internal/sheets/store/... ./internal/sheets/live/...
ok  	amadan.net/oficina/sheets/internal/sheets/store	50.286s
ok  	amadan.net/oficina/sheets/internal/sheets/live	1.060s
diff --git a/internal/sheets/home.go b/internal/sheets/home.go
index 219ab3a..32cea90 100644
--- a/internal/sheets/home.go
+++ b/internal/sheets/home.go
@@ -160,16 +160,20 @@ func (a *App) homeLocalComplete(w http.ResponseWriter, r *http.Request) {
a.homeRoutes.LocalComplete(w, r)
}
func (a *App) homeLocalBegin(w http.ResponseWriter, r *http.Request) {
- connect.OAuthContinuation(a.origin, a.handleBegin, func(w http.ResponseWriter, r *http.Request, destination string) {
- p := connect.OAuthPage(destination)
- // The page between the door and Keymail is the same card: the
- // refresh stays Home's (head), the body is the door's notice.
- a.render(w, r, "home_oauth", frame{parts: []string{p.Title}, signinPage: true}, http.StatusOK, homeOAuthView{
- Page: p,
- Door: chrome.SignInNotice{Icon: brand.Path("sheets"), App: "Sheets", Sky: sky.For(r.Host), Heading: p.Title,
- Link: &chrome.Link{Href: p.URL, Label: p.ActionLabel}},
- })
- })(w, r)
+ connect.OAuthContinuation(a.origin, a.handleBegin, a.renderHomeOAuth)(w, r)
+}
+
+// renderHomeOAuth is the page between the door and Keymail, and it is
+// the same card: the refresh stays Home's (head), the body is the
+// door's notice.
+func (a *App) renderHomeOAuth(w http.ResponseWriter, r *http.Request, destination string) {
+ p := connect.OAuthPage(destination)
+ a.render(w, r, "home_oauth", frame{parts: []string{p.Title}, signinPage: true}, http.StatusOK, homeOAuthView{
+ Page: p,
+ Door: chrome.SignInNotice{Icon: brand.Path("sheets"), App: "Sheets", Sky: sky.For(r.Host),
+ Heading: p.Title, Body: "Taking you to Keymail to finish signing in.",
+ Link: &chrome.Link{Href: p.URL, Label: p.ActionLabel}},
+ })
}
func (a *App) rejectDisabledHome(next http.Handler) http.Handler {
diff --git a/internal/sheets/signin_door_test.go b/internal/sheets/signin_door_test.go
index f74dc0a..37a78d5 100644
--- a/internal/sheets/signin_door_test.go
+++ b/internal/sheets/signin_door_test.go
@@ -1,6 +1,7 @@
package sheets
import (
+ "html"
"net/http"
"net/http/httptest"
"regexp"
@@ -37,3 +38,21 @@ func TestSignInPageIsTheDoor(t *testing.T) {
t.Error("sign-in page does not link sky.css")
}
}
+
+// The page between the door and Keymail is the door's notice, and still
+// carries Home's refresh to the destination.
+func TestKeymailContinuationIsTheDoor(t *testing.T) {
+ app := New(Config{})
+ const dest = "https://keymail.example.test/oauth/authorize?state=s"
+ rec := httptest.NewRecorder()
+ app.renderHomeOAuth(rec, httptest.NewRequest(http.MethodPost, "/signin", nil), dest)
+ body := html.UnescapeString(rec.Body.String())
+ for _, want := range []string{
+ `http-equiv="refresh"`, `content="0;url=` + dest + `"`, `href="` + dest + `"`,
+ "estilo-door", "estilo-sky-layer", "<span>Sheets</span>", "Taking you to Keymail",
+ } {
+ if !strings.Contains(body, want) {
+ t.Errorf("continuation lacks %q", want)
+ }
+ }
+}