" ~ tf.fn ~ "; "),
);
}
return tip;
}
form = format(q"┃
┃",
_cfg.cgi_filename,
(post_value("ec") == "checked") ? post_value("sf", "field") : "",
provide_tip,
search_note,
the_can(post_value("sf", "field")),
cv.db_selected,
post_value("rt", "box", "idx"),
post_value("rt", "box", "txt"),
post_value("sml", "box", "1000"),
post_value("sml", "box", "2500"),
post_value("ec"),
post_value("url"),
post_value("se"),
post_value("sql"),
);
{
string set_value(string field_name, string default_val) {
string val;
if (field_name in cgi.post) {
val = cgi.post[field_name];
} else if (field_name in cgi.get) {
val = cgi.get[field_name];
} else { val = default_val; }
return val;
}
bool set_bool(string field_name) {
bool val;
if (field_name in cgi.post
&& cgi.post[field_name] == "on") {
val = true;
} else if (field_name in cgi.get
&& cgi.get[field_name] == "on") {
val = true;
} else { val = false; }
return val;
}
cv.db_selected = set_value("selected_db", _cfg.db_sqlite_filename); // selected_db_name == db (spine.search.db or whatever)
/+ ↓ selected_db names a file in the configured db directory, never a path
a value carrying a directory separator, a parent reference or a leading
dot is discarded in favour of the configured default
+/
cv.db_selected = db_filename_sanitised(cv.db_selected, _cfg.db_sqlite_filename);
cv.sql_match_limit = set_value("sml", "1000");
cv.sql_match_offset = set_value("smo", "0");
cv.search_text = set_value("sf", "");
cv.results_type = set_value("rt", "idx");
cv.checked_echo = set_bool("ec");
cv.checked_stats = set_bool("sts");
cv.checked_url = set_bool("url");
cv.checked_searched = set_bool("se");
cv.checked_tip = set_bool("tip");
cv.checked_sql = set_bool("sql");
tf = text_fields;
}
}
{
cgi.write(header);
cgi.write(table);
cgi.write(form);
// cgi.write(previous_next);
{ // debug environment
// foreach (k, d; environment.toAA) {
// cgi.write(k ~ ": " ~ d ~ "
");
// }
}
{ // debug cgi info:
// cgi.write("db with path: " ~ conf.db_path ~ "/" ~ cv.db_selected ~ "
\n");
// cgi.write("http url: " ~ conf.http_url ~ "
\n");
// cgi.write("query base url: " ~ conf.query_base_url ~ "
\n");
// cgi.write("db_selected: " ~ cv.db_selected ~ "
\n");
// cgi.write("search_text: " ~ cv.search_text ~ "
\n");
// cgi.write("sql_match_limit: " ~ cv.sql_match_limit ~ ";\n");
// cgi.write("sql_match_offset: " ~ cv.sql_match_offset ~ ";\n");
// cgi.write("results_type: " ~ cv.results_type ~ "
\n");
// cgi.write("cv.checked_echo: " ~ (cv.checked_echo ? "checked" : "off") ~ "; \n");
// cgi.write("cv.checked_stats: " ~ (cv.checked_stats ? "checked" : "off") ~ "; \n");
// cgi.write("cv.checked_url: " ~ (cv.checked_url ? "checked" : "off") ~ "; \n");
// cgi.write("cv.checked_searched: " ~ (cv.checked_searched ? "checked" : "off") ~ ";
\n");
// cgi.write("cv.checked_tip: " ~ (cv.checked_tip ? "checked" : "off") ~ "; \n");
// cgi.write("cv.checked_sql: " ~ (cv.checked_sql ? "checked" : "off") ~ "
\n");
}
}
string db_file_with_path = conf.db_path ~ "/" ~ cv.db_selected;
/+ ↓ report a missing db rather than let sqlite create an empty one +/
if (!(db_file_with_path.exists && db_file_with_path.isFile)) {
cgi.write("
search database not found: "
~ cv.db_selected
~ "
\n\n");
return;
}
/+ ↓ the search form only ever reads, open read only +/
auto db = Database(db_file_with_path, SQLITE_OPEN_READONLY);
{ /+ ↓ a db that carries neither of the tables searched is not a spine search db +/
long _tables_found = 0;
try {
_tables_found = db.execute(
"SELECT count(*) FROM sqlite_master WHERE type = 'table'"
~ " AND name IN ('metadata_and_text', 'doc_objects');"
).oneValue!long;
} catch (Exception) {
_tables_found = 0;
}
if (_tables_found < 2) {
cgi.write("
not a spine search database: "
~ cv.db_selected
~ "
expected tables metadata_and_text and doc_objects;"
~ " build the database with: spine --sqlite-db-recreate ... then"
~ " spine --sqlite-update ...
\n\n");
db.close;
return;
}
}
{ /+ ↓ db schema version, as stamped by spine in PRAGMA user_version +/
int _schema_version = 0;
try {
_schema_version = db.execute("PRAGMA user_version;").oneValue!int;
} catch (Exception) {
_schema_version = 0;
}
if (_schema_version != 0
&& _schema_version != sqlite_db_schema_version_expected) {
cgi.write("
search database schema version "
~ _schema_version.to!string
~ ", this search form expects version "
~ sqlite_db_schema_version_expected.to!string
~ "
the database needs to be rebuilt by a matching spine:
"
~ "spine --sqlite-db-recreate --sqlite-db-path=... --sqlite-db-filename=...
"
~ "spine --sqlite-update ...
\n