test: content descriptors, journal-tag type and translated slugs
The descriptor matrix for posts, categories and tags: Describe per locale with and without Polish unprefixed, Match exact and inexact per locale, Records paging and cursors, host patterns, unknown and malformed ids; journal-tag with tag_pages by default, on and off; translated slugs in menu items and matching, including a changed Polish slug.
This commit is contained in:
@@ -249,3 +249,147 @@ func TestJournalTagType(t *testing.T) {
|
||||
t.Fatalf("tag resolved without tag pages: %+v %v", got, err)
|
||||
}
|
||||
}
|
||||
|
||||
// TestContentDescriptorsMatrix (D-93, D-20c, D-58): the descriptor matrix
|
||||
// for posts, categories and tags: Describe per locale with and without an
|
||||
// unprefixed locale, Match exact and inexact per locale, Records paging,
|
||||
// host patterns, and unknown or malformed ids.
|
||||
func TestContentDescriptorsMatrix(t *testing.T) {
|
||||
requirePostgres(t)
|
||||
ctx := context.Background()
|
||||
|
||||
t.Run("describe and match with Polish unprefixed", func(t *testing.T) {
|
||||
_, gdb, reg := bootMenuItemTypes(t, map[string]string{})
|
||||
s := seedContent(t, gdb)
|
||||
for _, tc := range []struct{ key, id, want string }{
|
||||
{classes.MenuTypePost, id(s.hello.ID), "en=/en/blog/hello pl=/blog/witaj"},
|
||||
{classes.MenuTypeCategory, id(s.news.ID), "en=/en/blog/category/news pl=/blog/category/wiadomosci"},
|
||||
{classes.MenuTypeTag, id(s.tag.ID), "en=/en/blog/tag/mushrooms pl=/blog/tag/mushrooms"},
|
||||
} {
|
||||
rec, err := reg.Describe(ctx, tc.key, tc.id, "pl")
|
||||
if err != nil || rec == nil || localeURLs(rec) != tc.want {
|
||||
t.Fatalf("Describe(%s) = %+v, %v; want %s", tc.key, rec, err, tc.want)
|
||||
}
|
||||
}
|
||||
for _, tc := range []struct {
|
||||
path, key, locale string
|
||||
exact bool
|
||||
}{
|
||||
{"/blog/witaj", classes.MenuTypePost, "pl", true},
|
||||
{"/en/blog/hello", classes.MenuTypePost, "en", true},
|
||||
{"/pl/blog/witaj", classes.MenuTypePost, "pl", false},
|
||||
{"/blog/hello", classes.MenuTypePost, "pl", false},
|
||||
{"/blog/category/wiadomosci", classes.MenuTypeCategory, "pl", true},
|
||||
{"/en/blog/category/news", classes.MenuTypeCategory, "en", true},
|
||||
{"/blog/category/news", classes.MenuTypeCategory, "pl", false},
|
||||
{"/blog/tag/mushrooms", classes.MenuTypeTag, "pl", true},
|
||||
{"/en/blog/tag/mushrooms", classes.MenuTypeTag, "en", true},
|
||||
} {
|
||||
key, res, err := reg.MatchPath(ctx, tc.path, "pl")
|
||||
if err != nil || key != tc.key || res == nil || res.Locale != tc.locale || res.Exact != tc.exact {
|
||||
t.Fatalf("MatchPath(%s, pl) = %q %+v %v, want %s %s exact=%v", tc.path, key, res, err, tc.key, tc.locale, tc.exact)
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("match per locale without an unprefixed locale", func(t *testing.T) {
|
||||
_, gdb, reg := bootMenuItemTypes(t, map[string]string{})
|
||||
s := seedContent(t, gdb)
|
||||
for _, tc := range []struct {
|
||||
path, key, locale string
|
||||
exact bool
|
||||
}{
|
||||
{"/blog/category/wiadomosci", classes.MenuTypeCategory, "en", false},
|
||||
{"/pl/blog/category/news", classes.MenuTypeCategory, "pl", false},
|
||||
{"/en/blog/category/news", classes.MenuTypeCategory, "en", false},
|
||||
{"/pl/blog/tag/mushrooms", classes.MenuTypeTag, "pl", true},
|
||||
} {
|
||||
key, res, err := reg.MatchPath(ctx, tc.path, "")
|
||||
if err != nil || key != tc.key || res == nil || res.Locale != tc.locale || res.Exact != tc.exact {
|
||||
t.Fatalf("MatchPath(%s) = %q %+v %v, want %s %s exact=%v", tc.path, key, res, err, tc.key, tc.locale, tc.exact)
|
||||
}
|
||||
}
|
||||
for _, path := range []string{"/pl/blog/draft", "/blog/tag/missing", "/blog/category/missing", "/blog/category/news/extra", "/blog/tag/"} {
|
||||
if key, res, err := reg.MatchPath(ctx, path, ""); err != nil || res != nil {
|
||||
t.Fatalf("MatchPath(%s) = %q %+v %v, want no match", path, key, res, err)
|
||||
}
|
||||
}
|
||||
for _, tc := range []struct{ key, id string }{
|
||||
{classes.MenuTypePost, "999999"}, {classes.MenuTypePost, "abc"},
|
||||
{classes.MenuTypeCategory, "999999"}, {classes.MenuTypeTag, "999999"}, {classes.MenuTypeTag, ""},
|
||||
} {
|
||||
if rec, err := reg.Describe(ctx, tc.key, tc.id, ""); err != nil || rec != nil {
|
||||
t.Fatalf("Describe(%s, %q) = %+v, %v; want nothing", tc.key, tc.id, rec, err)
|
||||
}
|
||||
}
|
||||
draft, err := reg.Describe(ctx, classes.MenuTypePost, id(s.draft.ID), "")
|
||||
if err != nil || draft == nil || draft.Published || localeURLs(draft) != "en=/blog/draft pl=/pl/blog/draft" {
|
||||
t.Fatalf("Describe draft = %+v, %v", draft, err)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("records paging", func(t *testing.T) {
|
||||
_, gdb, reg := bootMenuItemTypes(t, map[string]string{})
|
||||
s := seedContent(t, gdb)
|
||||
second := models.Tag{Name: "Forest", Slug: "forest"}
|
||||
if err := gdb.Create(&second).Error; err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
all, err := reg.Records(ctx, classes.MenuTypePost, "", 0, "")
|
||||
if err != nil || len(all.Records) != 2 || all.Next != "" {
|
||||
t.Fatalf("limit 0 = %+v, %v", all, err)
|
||||
}
|
||||
if again, err := reg.Records(ctx, classes.MenuTypePost, "not-an-id", 0, ""); err != nil || len(again.Records) != 2 {
|
||||
t.Fatalf("a malformed cursor = %+v, %v; want the first page", again, err)
|
||||
}
|
||||
if end, err := reg.Records(ctx, classes.MenuTypePost, id(s.draft.ID), 10, ""); err != nil || len(end.Records) != 0 || end.Next != "" {
|
||||
t.Fatalf("after the last post = %+v, %v", end, err)
|
||||
}
|
||||
first, err := reg.Records(ctx, classes.MenuTypeTag, "", 1, "")
|
||||
if err != nil || len(first.Records) != 1 || first.Records[0].ID != id(s.tag.ID) || first.Next != id(s.tag.ID) {
|
||||
t.Fatalf("first tag page = %+v, %v", first, err)
|
||||
}
|
||||
next, err := reg.Records(ctx, classes.MenuTypeTag, first.Next, 1, "")
|
||||
if err != nil || len(next.Records) != 1 || next.Records[0].ID != id(second.ID) || next.Next != "" {
|
||||
t.Fatalf("second tag page = %+v, %v", next, err)
|
||||
}
|
||||
if got := localeURLs(&next.Records[0]); got != "en=/blog/tag/forest pl=/pl/blog/tag/forest" {
|
||||
t.Fatalf("paged tag URLs = %s", got)
|
||||
}
|
||||
if !all.Records[0].Published || all.Records[1].Published {
|
||||
t.Fatalf("published flags = %v %v", all.Records[0].Published, all.Records[1].Published)
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("host patterns", func(t *testing.T) {
|
||||
_, gdb, reg := bootMenuItemTypes(t, map[string]string{"menu_items.yaml": "patterns:\n journal-category: /c/:slug\n journal-tag: /t/:slug\n journal-post: /:category/:slug\n"})
|
||||
s := seedContent(t, gdb)
|
||||
for _, tc := range []struct{ key, id, want string }{
|
||||
{classes.MenuTypeCategory, id(s.news.ID), "en=/c/news pl=/pl/c/wiadomosci"},
|
||||
{classes.MenuTypeTag, id(s.tag.ID), "en=/t/mushrooms pl=/pl/t/mushrooms"},
|
||||
{classes.MenuTypePost, id(s.hello.ID), "en=/news/hello pl=/pl/wiadomosci/witaj"},
|
||||
} {
|
||||
rec, err := reg.Describe(ctx, tc.key, tc.id, "")
|
||||
if err != nil || rec == nil || localeURLs(rec) != tc.want {
|
||||
t.Fatalf("Describe(%s) = %+v, %v; want %s", tc.key, rec, err, tc.want)
|
||||
}
|
||||
}
|
||||
for _, tc := range []struct {
|
||||
path, key string
|
||||
exact bool
|
||||
}{
|
||||
{"/c/news", classes.MenuTypeCategory, true},
|
||||
{"/t/mushrooms", classes.MenuTypeTag, true},
|
||||
{"/news/hello", classes.MenuTypePost, true},
|
||||
{"/pl/wiadomosci/witaj", classes.MenuTypePost, true},
|
||||
} {
|
||||
key, res, err := reg.MatchPath(ctx, tc.path, "")
|
||||
if err != nil || key != tc.key || res == nil || res.Exact != tc.exact {
|
||||
t.Fatalf("MatchPath(%s) = %q %+v %v", tc.path, key, res, err)
|
||||
}
|
||||
}
|
||||
if key, res, err := reg.MatchPath(ctx, "/blog/category/news", ""); err != nil || res != nil {
|
||||
t.Fatalf("the default pattern still matched: %q %+v %v", key, res, err)
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
@@ -247,3 +247,89 @@ func resolve(t *testing.T, reg *signpost.Registry, key, ref, pattern string, nes
|
||||
}
|
||||
return got
|
||||
}
|
||||
|
||||
// TestJournalTagTypePages (D-102, P-11): journal-tag with tag_pages on
|
||||
// (the default and set explicitly) and off: references, Resolve, Describe
|
||||
// and Match by slug, by id pattern and under the Polish prefix.
|
||||
func TestJournalTagTypePages(t *testing.T) {
|
||||
requirePostgres(t)
|
||||
ctx := context.Background()
|
||||
for _, tc := range []struct {
|
||||
name string
|
||||
files map[string]string
|
||||
on bool
|
||||
}{
|
||||
{"default", map[string]string{}, true},
|
||||
{"explicitly on", map[string]string{"golem15.yaml": "journal:\n tag_pages: true\n"}, true},
|
||||
{"off", map[string]string{"golem15.yaml": "journal:\n tag_pages: false\n"}, false},
|
||||
} {
|
||||
t.Run(tc.name, func(t *testing.T) {
|
||||
_, gdb, reg := bootMenuItemTypes(t, tc.files)
|
||||
s := seedContent(t, gdb)
|
||||
refs, err := signpost.ReferenceOptions(ctx, reg, classes.MenuTypeTag)
|
||||
if err != nil || len(refs.Options) != 1 || refs.Options[0].Value != id(s.tag.ID) {
|
||||
t.Fatalf("references = %+v, %v (listed whether or not the site has tag pages)", refs, err)
|
||||
}
|
||||
item, err := reg.Resolve(ctx, classes.MenuTypeTag, id(s.tag.ID), "", false, "")
|
||||
if err != nil || (item != nil) != tc.on || (tc.on && (item.URL != "/blog/tag/mushrooms" || altString(item.Alternates) != "en=/blog/tag/mushrooms pl=/pl/blog/tag/mushrooms")) {
|
||||
t.Fatalf("Resolve = %+v, %v", item, err)
|
||||
}
|
||||
rec, err := reg.Describe(ctx, classes.MenuTypeTag, id(s.tag.ID), "")
|
||||
want := "en= pl="
|
||||
if tc.on {
|
||||
want = "en=/blog/tag/mushrooms pl=/pl/blog/tag/mushrooms"
|
||||
}
|
||||
if err != nil || rec == nil || localeURLs(rec) != want || rec.Locales[0].Title != "Mushrooms" {
|
||||
t.Fatalf("Describe = %+v, %v; want %s", rec, err, want)
|
||||
}
|
||||
typ, _ := reg.ContentType(classes.MenuTypeTag)
|
||||
for _, m := range []pact.ContentMatch{
|
||||
{Path: "/blog/tag/mushrooms", Pattern: classes.DefaultTagPattern},
|
||||
{Path: "/pl/blog/tag/mushrooms", Pattern: classes.DefaultTagPattern},
|
||||
{Path: "/t/" + id(s.tag.ID), Pattern: "/t/:id"},
|
||||
} {
|
||||
res, err := typ.Content.Match(ctx, m)
|
||||
if err != nil || (res != nil) != tc.on || (tc.on && (!res.Exact || res.ID != id(s.tag.ID))) {
|
||||
t.Fatalf("Match(%s) = %+v, %v", m.Path, res, err)
|
||||
}
|
||||
}
|
||||
if res, err := typ.Content.Match(ctx, pact.ContentMatch{Path: "/t/abc", Pattern: "/t/:id"}); err != nil || res != nil {
|
||||
t.Fatalf("a malformed id matched: %+v %v", res, err)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
// TestTranslatedSlugMenuItems (D-58): a post and a category resolve and
|
||||
// match through their translated slugs in each locale, and the default
|
||||
// slug stays the English address.
|
||||
func TestTranslatedSlugMenuItems(t *testing.T) {
|
||||
requirePostgres(t)
|
||||
ctx := context.Background()
|
||||
_, gdb, reg := bootMenuItemTypes(t, map[string]string{})
|
||||
s := seedContent(t, gdb)
|
||||
post := resolve(t, reg, classes.MenuTypePost, id(s.hello.ID), "", false)
|
||||
if altString(post.Alternates) != "en=/blog/hello pl=/pl/blog/witaj" {
|
||||
t.Fatalf("post alternates = %s", altString(post.Alternates))
|
||||
}
|
||||
cat := resolve(t, reg, classes.MenuTypeCategory, id(s.news.ID), "", false)
|
||||
if altString(cat.Alternates) != "en=/blog/category/news pl=/pl/blog/category/wiadomosci" {
|
||||
t.Fatalf("category alternates = %s", altString(cat.Alternates))
|
||||
}
|
||||
unprefixed := resolve(t, reg, classes.MenuTypePost, id(s.hello.ID), "", false, "pl")
|
||||
if altString(unprefixed.Alternates) != "en=/en/blog/hello pl=/blog/witaj" {
|
||||
t.Fatalf("unprefixed pl alternates = %s", altString(unprefixed.Alternates))
|
||||
}
|
||||
if key, res, err := reg.MatchPath(ctx, "/pl/blog/witaj", ""); err != nil || key != classes.MenuTypePost || res == nil || !res.Exact || res.ID != id(s.hello.ID) {
|
||||
t.Fatalf("the translated slug = %q %+v %v", key, res, err)
|
||||
}
|
||||
if err := translate.SetTranslated(ctx, gdb, &s.hello, "slug", "pl", "witamy"); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if key, res, err := reg.MatchPath(ctx, "/pl/blog/witamy", ""); err != nil || key != classes.MenuTypePost || res == nil || !res.Exact {
|
||||
t.Fatalf("a changed translated slug = %q %+v %v", key, res, err)
|
||||
}
|
||||
if _, res, err := reg.MatchPath(ctx, "/pl/blog/witaj", ""); err != nil || res != nil {
|
||||
t.Fatalf("the old translated slug still matches: %+v %v", res, err)
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user