Check-in by ben on 2024-10-06 22:35:40

 Preserve search result sort order through page navigation.  To
 keep it simple, use one single sort order in the search results
 instead of nested sort orders.  For consistency with web site,
 sort by "creatorSorter", "date", and "titleSorter" instead of
 "creator", "publicdate", and "title".

 INSERTED    DELETED
       33         17 src/search/index.dcgi.m4
        2          2 src/sort/index.dcgi.m4
       35         19 TOTAL over 2 changed files

Index: src/search/index.dcgi.m4
==================================================================
--- src/search/index.dcgi.m4
+++ src/search/index.dcgi.m4
@@ -9,28 +9,39 @@
incl(src/api.awk)
incl(src/cgi.awk)
incl(src/util.awk)

function main(search,     cmd, count, creator, descr, field, fields, i, \
-    iaout, id, jsout, label, numfound, order, orders, page, rows,       \
-    searchstr, title, type, url)
+    iaout, id, jsout, label, numfound, order, order_names, page, rows,  \
+    searchstr, sort_param, title, type, url)
{
+    order_names["addeddate"] = "addeddate"
+    order_names["collection_size"] = "collection_size"
+    order_names["createddate"] = "createddate"
+    order_names["creator"] = "creatorSorter"
+    order_names["date"] = "date"
+    order_names["downloads"] = "downloads"
+    order_names["nav_order"] = "nav_order"
+    order_names["random"] = "random"
+    order_names["title"] = "titleSorter"
+    order_names["week"] = "week"
+
    rows = 15
    page = 1
-    delete order
-    orders = 0
+    order = ""

    # parse out page number and sort orders
    for (i in parts) {
        if (parts[i] ~ /^rows[0-9][0-9]*$/) {
            rows = substr(parts[i], 5)
        } else if (parts[i] ~ /^page[0-9][0-9]*$/) {
            page = substr(parts[i], 5)
        } else if (parts[i] ~ /^sort/) {
-            orders++
-            str = substr(parts[i], 5)
-            order[orders] = str
+            if (length(order) == 0) {
+                sort_param = parts[i]
+                order = substr(parts[i], 5)
+            }
        }
    }

    # special case for when the search term is an archive.org details URL
    if (match(search, /^https:\/\/(www\.)?archive\.org\/details\//)) {
@@ -40,18 +51,19 @@

    # remove quotes from search string, since it gets quoted later
    gsub(/"/, "", search)

    # default sort orders if none were specified
-    if (orders == 0) {
-        orders = 1
+    if (length(order) == 0) {
        if (search == "mediatype:collection" ||
            search == "mediatype:(collection)")
        {
-            order[1] = "collection_size desc"
+            order = "collection_size desc"
+            sort_param = "sort" order
        } else {
-            order[1] = "nav_order desc"
+            order = "nav_order desc"
+            sort_param = "sort" order
        }
    }

    iaout = gettemp()
    jsout = gettemp()
@@ -69,12 +81,14 @@
    searchstr = search
    gsub(/anyfield:/, "", searchstr)

    url = sprintf("%s/advancedsearch.php?q=%s&output=json&rows=%d&page=%d", \
        api_endpoint, searchstr, rows, page)
-    for (i = 1; i <= orders; i++) {
-        url = url sprintf("&sort%%5B%d%%5D=%s", i-1, order[i])
+    if (length(order) > 0) {
+        split(order, parts, " ")
+        url = url sprintf("&sort%%5B0%%5D=%s %s", order_names[parts[1]], \
+            parts[2])
    }
    for (i = 1; i <= fields; i++) {
        url = url sprintf("&fl%%5B%d%%5D=%s", i-1, field[i])
    }
    api_request(url, "GET", iaout)
@@ -163,18 +177,20 @@

    print ""

    # only show "page back" if the user is past page 1
    if (page > 1) {
-        printf "[1|[<<] Page %d|%s/search/page%d/rows%d/%%09%s|%s|%s]\n",
-            page - 1, cgipath, page - 1, rows, search, server, port
+        printf "[1|[<<] Page %d|%s/search/page%d/rows%d/%s%%09%s|%s|%s]\n",
+            page - 1, cgipath, page - 1, rows, sort_param, search,
+            server, port
    }

    # only show "next page" if the current page is completely full
    if (count == rows) {
-        printf "[1|[>>] Page %d|%s/search/page%d/rows%d/%%09%s|%s|%s]\n",
-            page + 1, cgipath, page + 1, rows, search, server, port
+        printf "[1|[>>] Page %d|%s/search/page%d/rows%d/%s%%09%s|%s|%s]\n",
+            page + 1, cgipath, page + 1, rows, sort_param, search,
+            server, port
    }

    # only show "sort" if there's more than one item to sort
    if (count > 1) {
        printf "[1|[^v] Sort|%s/sort/%%09%s|%s|%s]\n", cgipath, search,

Index: src/sort/index.dcgi.m4
==================================================================
--- src/sort/index.dcgi.m4
+++ src/sort/index.dcgi.m4
@@ -32,13 +32,13 @@
    lbl[11] = "Date created [^]"
    opt[11] = "createddate asc"
    lbl[12] = "Date created [v]"
    opt[12] = "createddate desc"
    lbl[13] = "Date published [^]"
-    opt[13] = "publicdate asc"
+    opt[13] = "date asc"
    lbl[14] = "Date published [v]"
-    opt[14] = "publicdate desc"
+    opt[14] = "date desc"
    lbl[15] = "Creator [^]"
    opt[15] = "creator asc"
    lbl[16] = "Creator [v]"
    opt[16] = "creator desc"
    lbl[17] = "Random"