From d1fae6b26e0820dee76e396c540bb1de90038917 Mon Sep 17 00:00:00 2001 From: Boris Kolpackov Date: Tue, 22 Sep 2015 12:31:42 +0200 Subject: Implement package version detals page --- brep/package | 12 +- brep/package-search.cxx | 45 ++----- brep/package-version-details.cxx | 222 ++++++++++++++++++++++++++++++-- brep/package-version-search.cxx | 67 ++++------ brep/package.cxx | 7 +- brep/page | 34 +++-- brep/page.cxx | 54 ++++---- loader/loader.cxx | 72 +++++++---- tests/loader/driver.cxx | 78 +++++++---- tests/loader/external/1/misc/packages | 8 ++ tests/loader/internal/1/math/packages | 17 ++- tests/loader/internal/1/stable/packages | 6 +- web/xhtml | 3 + 13 files changed, 429 insertions(+), 196 deletions(-) diff --git a/brep/package b/brep/package index 75920c4..ddfc179 100644 --- a/brep/package +++ b/brep/package @@ -348,7 +348,7 @@ namespace brep dependencies_type, requirements_type, optional location, - odb::lazy_shared_ptr); + std::shared_ptr); // Manifest data. // @@ -446,10 +446,8 @@ namespace brep set(_set (this.requirements, (?))) \ id_column("") key_column("") value_column("id") - #pragma db member(external_repositories) \ - id_column("") \ - value_column("repository") \ - value_not_null + #pragma db member(external_repositories) \ + id_column("") value_column("repository") value_not_null private: friend class odb::access; @@ -479,6 +477,8 @@ namespace brep get() set(_id (std::move (?))) }; + // Find the latest version of an internal package. + // #pragma db view object(package_version = version) \ object(package_version = v: \ version::id.data.package == v::id.data.package && \ @@ -492,7 +492,7 @@ namespace brep object(package inner: version::id.data.package == package::name && \ version::internal_repository.is_not_null () && \ v::id.data.package.is_null ()) - struct internal_package + struct latest_internal_package_version { using package_type = brep::package; std::shared_ptr package; diff --git a/brep/package-search.cxx b/brep/package-search.cxx index a840687..9b3fb2c 100644 --- a/brep/package-search.cxx +++ b/brep/package-search.cxx @@ -18,6 +18,7 @@ #include #include +#include #include #include #include @@ -72,11 +73,11 @@ namespace brep << TITLE << title << ~TITLE << CSS_STYLE << ident << A_STYLE () << ident - << PAGER_STYLE () << ident - << ".packages {font-size: x-large;}" << ident + << DIV_PAGER_STYLE () << ident + << "#packages {font-size: x-large;}" << ident << ".package {margin: 0.5em 0 0;}" << ident << ".name {font-size: x-large;}" << ident - << ".dependencies {margin: 0.3em 0 0;}" << ident + << ".tags {margin: 0.3em 0 0;}" << ~CSS_STYLE << ~HEAD << BODY; @@ -92,18 +93,14 @@ namespace brep // size_t pc (db_->query_value ().count); - s << DIV(CLASS="packages") - << "Packages (" << pc << ")" - << ~DIV; + s << DIV(ID="packages") << "Packages (" << pc << ")" << ~DIV; - // @@ Use appropriate view when clarify which package info to be displayed - // and search index structure get implemented. Query will also - // include search criteria if specified. + // @@ Query will also include search criteria if specified. // - using query = query; + using query = query; auto r ( - db_->query ( + db_->query ( "ORDER BY" + query::package::name + "OFFSET" + to_string (pr.page () * rop) + "LIMIT" + to_string (rop))); @@ -127,34 +124,20 @@ namespace brep << p.name << ~A << ~DIV - << DIV(CLASS="summary") - << p.summary - << ~DIV + << DIV(CLASS="summary") << p.summary << ~DIV + << DIV_TAGS (p.tags) + << DIV_LICENSES (v.license_alternatives) << DIV(CLASS="dependencies") << "Dependencies: " << v.dependencies.size () << ~DIV - << LICENSES (v.license_alternatives) - << TAGS (p.tags); - - s << ~DIV; + << ~DIV; } t.commit (); - auto u ( - [&q](size_t p) - { - string url ("/"); - if (p > 0) - url += "?p=" + to_string (p); - - if (!q.empty ()) - url += string (p > 0 ? "&" : "?") + q; - - return url; - }); + string u (q.empty () ? "/" : ("/?" + q)); - s << PAGER (pr.page (), pc, rop, options_->pages_in_pager (), u) + s << DIV_PAGER (pr.page (), pc, rop, options_->pages_in_pager (), u) << ~BODY << ~HTML; } diff --git a/brep/package-version-details.cxx b/brep/package-version-details.cxx index 0faecd2..162e783 100644 --- a/brep/package-version-details.cxx +++ b/brep/package-version-details.cxx @@ -5,7 +5,7 @@ #include #include -#include // make_shared() +#include // shared_ptr, make_shared() #include #include // invalid_argument @@ -18,6 +18,8 @@ #include #include +#include +#include #include #include #include @@ -48,12 +50,12 @@ namespace brep MODULE_DIAG; - path::reverse_iterator i (rq.path ().rbegin ()); - version ver; + auto i (rq.path ().rbegin ()); + version v; try { - ver = version (*i++); + v = version (*i++); } catch (const invalid_argument& ) { @@ -61,7 +63,7 @@ namespace brep } assert (i != rq.path ().rend ()); - const string& package (*i); + const string& p (*i); params::package_version_details pr; @@ -77,7 +79,8 @@ namespace brep } const char* ident ("\n "); - const string name (package + "-" + ver.string ()); + const string& vs (v.string ()); + const string name (p + " " + vs); const string title ("Package Version " + name); serializer s (rs.content (), title); @@ -85,17 +88,212 @@ namespace brep << HEAD << TITLE << title << ~TITLE << CSS_STYLE << ident - << "a {text-decoration: none;}" << ident - << "a:hover {text-decoration: underline;}" << ident - << ".name {font-size: xx-large; font-weight: bold;}" + << A_STYLE () << ident + << "#name {font-size: xx-large; font-weight: bold;}" << ident + << ".url {margin: 0.3em 0 0;}" << ident + << ".priority, #licenses, #dependencies, #requirements, " + "#locations, #changes {" << ident + << " font-size: x-large;" << ident + << " margin: 0.5em 0 0;" << ident + << "}" << ident + << ".comment {font-size: medium;}" << ident + << "ul {margin: 0; padding: 0 0 0 1em;}" << ident + << "li {font-size: large; margin: 0.1em 0 0;}" << ident + << ".conditional {font-weight: bold;}" << ident + << "pre {font-size: medium; margin: 0.1em 0 0 1em;}" << ~CSS_STYLE << ~HEAD - << BODY; + << BODY + << DIV(ID="name") + << A << HREF << "/go/" << mime_url_encode (p) << ~HREF << p << ~A + << " " << vs + << ~DIV; - s << DIV(CLASS="name") - << name + bool not_found (false); + shared_ptr pv; + + transaction t (db_->begin ()); //@@ Not committed, other places? + + try + { + package_version_id id { + p, v.epoch (), v.canonical_upstream (), v.revision ()}; + + pv = db_->load (id); + + // If the requested package version turned up to be an "external" one + // just respond that no "internal" package version is present. + // + not_found = pv->internal_repository == nullptr; + } + catch (const object_not_persistent& ) + { + not_found = true; + } + + if (not_found) + throw invalid_request (404, "Package '" + name + "' not found"); + + assert (pv->location); + const string url (pv->internal_repository.load ()->location.string () + + "/" + pv->location->string ()); + + const priority& pt (pv->priority); + + s << DIV(CLASS="url") << A << HREF << url << ~HREF << url << ~A << ~DIV + << DIV_PRIORITY (pt); + + if (!pt.comment.empty ()) + s << DIV(CLASS="comment") << pt.comment << ~DIV; + + const auto& ls (pv->license_alternatives); + + s << DIV(ID="licenses") + << "Licenses:" + << UL; + + for (const auto& la: ls) + { + s << LI; + + for (const auto& l: la) + { + if (&l != &la[0]) + s << " & "; + + s << l; + } + + if (!la.comment.empty ()) + s << DIV(CLASS="comment") << la.comment << ~DIV; + + s << ~LI; + } + + s << ~UL << ~DIV; + const auto& ds (pv->dependencies); + + if (!ds.empty ()) + { + s << DIV(ID="dependencies") + << "Dependencies:" + << UL; + + for (const auto& da: ds) + { + s << LI; + + if (da.conditional) + s << SPAN(CLASS="conditional") << "? " << ~SPAN; + + for (const auto& d: da) + { + if (&d != &da[0]) + s << " | "; + + // @@ Should it be a link to package version search page on the + // corresponding repository site ? + // + s << d.package; + + if (d.version) + { + static const strings operations ({"==", "<", ">", "<=", ">="}); + size_t op (static_cast (d.version->operation)); + assert (op < operations.size ()); + + // @@ Should it be a link to the best matching package version + // details page on the corresponding repository site ? + // + s << " " << operations[op] << " " << d.version->value.string (); + } + } + + if (!da.comment.empty ()) + s << DIV(CLASS="comment") << da.comment << ~DIV; + + s << ~LI; + } + + s << ~UL + << ~DIV; + } + + const auto& rm (pv->requirements); + + if (!rm.empty ()) + { + s << DIV(ID="requirements") + << "Requirements:" + << UL; + + for (const auto& ra: rm) + { + s << LI; + + if (ra.conditional) + s << SPAN(CLASS="conditional") << "? " << ~SPAN; + + if (ra.empty ()) + // If there is no requirement alternatives specified, then + // print the comment instead. + // + s << ra.comment; + else + { + for (const auto& r: ra) + { + if (&r != &ra[0]) + s << " | "; + + s << r; + } + + if (!ra.comment.empty ()) + s << DIV(CLASS="comment") << ra.comment << ~DIV; + } + + s << ~LI; + } + + s << ~UL + << ~DIV; + } + + const auto& er (pv->external_repositories); + + if (!er.empty ()) + { + s << DIV(ID="locations") + << "Alternative Locations:" + << UL; + + for (const auto& r: er) + { + repository_location l (move (r.load ()->location)); + assert (l.remote ()); + + string u ("http://" + l.host ()); + if (l.port () != 0) + u += ":" + to_string (l.port ()); + + u += "/go/" + mime_url_encode (p) + "/" + vs; + s << LI << A << HREF << u << ~HREF << u << ~A << ~LI; + } + + s << ~UL + << ~DIV; + } + + t.commit (); + + const string& ch (pv->changes); + + if (!ch.empty ()) + s << DIV(ID="changes") << "Changes:" << PRE << ch << ~PRE << ~DIV; + s << ~BODY << ~HTML; } diff --git a/brep/package-version-search.cxx b/brep/package-version-search.cxx index 336650e..166f116 100644 --- a/brep/package-version-search.cxx +++ b/brep/package-version-search.cxx @@ -18,6 +18,7 @@ #include #include +#include #include #include #include @@ -71,24 +72,25 @@ namespace brep << TITLE << title << ~TITLE << CSS_STYLE << ident << A_STYLE () << ident - << PAGER_STYLE () << ident - << ".name {font-size: xx-large; font-weight: bold;}" << ident - << ".summary {font-size: x-large; margin: 0.2em 0 0;}" << ident - << ".url {font-size: 90%;}" << ident - << ".email {font-size: 90%;}" << ident - << ".description {margin: 0.5em 0 0;}" << ident + << DIV_PAGER_STYLE () << ident + << "#name {font-size: xx-large; font-weight: bold;}" << ident + << "#summary {font-size: x-large; margin: 0.2em 0 0;}" << ident + << ".url {margin: 0.3em 0 0;}" << ident + << "#description {margin: 0.5em 0 0;}" << ident << ".tags {margin: 0.3em 0 0;}" << ident - << ".versions {font-size: x-large; margin: 0.5em 0 0;}" << ident + << "#versions {font-size: x-large; margin: 0.5em 0 0;}" << ident << ".package_version {margin: 0.5em 0 0;}" << ident << ".version {font-size: x-large;}" << ident << ".priority {margin: 0.3em 0 0;}" << ~CSS_STYLE << ~HEAD - << BODY; - - transaction t (db_->begin ()); + << BODY + << DIV(ID="name") << name << ~DIV; shared_ptr p; + size_t rop (options_->results_on_page ()); + + transaction t (db_->begin ()); try { @@ -99,12 +101,7 @@ namespace brep throw invalid_request (404, "Package '" + name + "' not found"); } - s << DIV(CLASS="name") - << name - << ~DIV - << DIV(CLASS="summary") - << p->summary - << ~DIV + s << DIV(ID="summary") << p->summary << ~DIV << DIV(CLASS="url") << A << HREF << p->url << ~HREF << p->url << ~A << ~DIV @@ -113,11 +110,9 @@ namespace brep << ~DIV; if (p->description) - s << DIV(CLASS="description") - << *p->description - << ~DIV; + s << DIV(ID="description") << *p->description << ~DIV; - s << TAGS (p->tags); + s << DIV_TAGS (p->tags); size_t pvc; { @@ -130,9 +125,7 @@ namespace brep query::internal_repository.is_not_null ()).count; } - s << DIV(CLASS="versions") - << "Versions (" << pvc << ")" - << ~DIV; + s << DIV(ID="versions") << "Versions (" << pvc << ")" << ~DIV; if (p->package_url) s << DIV(CLASS="url") @@ -147,8 +140,6 @@ namespace brep << ~A << ~DIV; - size_t rop (options_->results_on_page ()); - // @@ Use appropriate view when clarify which package version info to be // displayed and search index structure get implemented. Query will also // include search criteria if specified. @@ -171,37 +162,25 @@ namespace brep s << DIV(CLASS="package_version") << DIV(CLASS="version") << A - << HREF - << "/go/" << mime_url_encode (name) << "/" << vs - << ~HREF + << HREF << "/go/" << mime_url_encode (name) << "/" << vs << ~HREF << vs << ~A << ~DIV - << PRIORITY (v.priority) + << DIV_PRIORITY (v.priority) + << DIV_LICENSES (v.license_alternatives) << DIV(CLASS="dependencies") << "Dependencies: " << v.dependencies.size () << ~DIV - << LICENSES (v.license_alternatives) << ~DIV; } t.commit (); - auto u ( - [&name, &pr](size_t p) - { - string url (name); - if (p > 0) - url += "?p=" + to_string (p); - - if (!pr.query ().empty ()) - url += - string (p > 0 ? "&" : "?") + "q=" + mime_url_encode (pr.query ()); - - return url; - }); + string u (mime_url_encode (name)); + if (!pr.query ().empty ()) + u += "?q=" + mime_url_encode (pr.query ()); - s << PAGER (pr.page (), pvc, rop, options_->pages_in_pager (), u) + s << DIV_PAGER (pr.page (), pvc, rop, options_->pages_in_pager (), u) << ~BODY << ~HTML; } diff --git a/brep/package.cxx b/brep/package.cxx index 59efbfb..8b9a219 100644 --- a/brep/package.cxx +++ b/brep/package.cxx @@ -63,7 +63,7 @@ namespace brep dependencies_type dp, requirements_type rq, optional lc, - lazy_shared_ptr rp) + shared_ptr rp) : package (move (pk)), version (move (vr)), priority (move (pr)), @@ -73,7 +73,10 @@ namespace brep requirements (move (rq)), location (move (lc)) { - if (rp.load ()->internal) + //@@ Can't be sure we are in transaction. Instead, make caller + // pass shared_ptr. + // + if (rp->internal) internal_repository = move (rp); else external_repositories.emplace_back (move (rp)); diff --git a/brep/page b/brep/page index 06f3350..c7febd8 100644 --- a/brep/page +++ b/brep/page @@ -7,7 +7,6 @@ #include #include // size_t -#include #include @@ -28,16 +27,14 @@ namespace brep // Generates paging element. // - class PAGER + class DIV_PAGER { public: - using get_url_type = std::function; - - PAGER (std::size_t current_page, - std::size_t item_count, - std::size_t item_per_page, - std::size_t page_number_count, - get_url_type get_url); + DIV_PAGER (std::size_t current_page, + std::size_t item_count, + std::size_t item_per_page, + std::size_t page_number_count, + const std::string& url); void operator() (xml::serializer& s) const; @@ -47,12 +44,12 @@ namespace brep std::size_t item_count_; std::size_t item_per_page_; std::size_t page_number_count_; - get_url_type get_url_; + const std::string& url_; }; - // PAGER element default style. + // DIV_PAGER element default style. // - struct PAGER_STYLE + struct DIV_PAGER_STYLE { void operator() (xml::serializer& s) const; @@ -60,10 +57,10 @@ namespace brep // Generates package tags element. // - class TAGS + class DIV_TAGS { public: - TAGS (const strings& ts): tags_ (ts) {} + DIV_TAGS (const strings& ts): tags_ (ts) {} void operator() (xml::serializer& s) const; @@ -74,11 +71,10 @@ namespace brep // Generates package version license alternatives element. // - class LICENSES + class DIV_LICENSES { public: - LICENSES (const license_alternatives& la) - : license_alternatives_ (la) {} + DIV_LICENSES (const license_alternatives& l): license_alternatives_ (l) {} void operator() (xml::serializer& s) const; @@ -89,10 +85,10 @@ namespace brep // Generates package version priority element. // - class PRIORITY + class DIV_PRIORITY { public: - PRIORITY (const priority& pr): priority_ (pr) {} + DIV_PRIORITY (const priority& p): priority_ (p) {} void operator() (xml::serializer& s) const; diff --git a/brep/page.cxx b/brep/page.cxx index ad93e7c..552be3c 100644 --- a/brep/page.cxx +++ b/brep/page.cxx @@ -4,6 +4,7 @@ #include +#include #include #include // move() #include // min() @@ -30,23 +31,23 @@ namespace brep << "a:hover {text-decoration: underline;}"; } - // PAGER + // DIV_PAGER // - PAGER:: - PAGER (size_t current_page, - size_t item_count, - size_t item_per_page, - size_t page_number_count, - get_url_type get_url) + DIV_PAGER:: + DIV_PAGER (size_t current_page, + size_t item_count, + size_t item_per_page, + size_t page_number_count, + const string& url) : current_page_ (current_page), item_count_ (item_count), item_per_page_ (item_per_page), page_number_count_ (page_number_count), - get_url_ (move (get_url)) + url_ (url) { } - void PAGER:: + void DIV_PAGER:: operator() (serializer& s) const { if (item_count_ == 0 || item_per_page_ == 0) @@ -59,13 +60,22 @@ namespace brep if (pc > 1) { + auto u ( + [this](size_t page) -> string + { + return page == 0 + ? url_ + : url_ + (url_.find ('?') == string::npos ? "?p=" : "&p=") + + to_string (page); + }); + // Can consider customizing class names if use-case appear. // s << DIV(CLASS="pager"); if (current_page_ > 0) s << A(CLASS="pg-prev") - << HREF << get_url_ (current_page_ - 1) << ~HREF + << HREF << u (current_page_ - 1) << ~HREF << "<<" << ~A << " "; @@ -79,12 +89,10 @@ namespace brep for (size_t p (fp); p < tp; ++p) { if (p == current_page_) - s << SPAN(CLASS="pg-cpage") - << p + 1 - << ~SPAN; + s << SPAN(CLASS="pg-cpage") << p + 1 << ~SPAN; else s << A(CLASS="pg-page") - << HREF << get_url_ (p) << ~HREF + << HREF << u (p) << ~HREF << p + 1 << ~A; @@ -94,7 +102,7 @@ namespace brep if (current_page_ < pc - 1) s << A(CLASS="pg-next") - << HREF << get_url_ (current_page_ + 1) << ~HREF + << HREF << u (current_page_ + 1) << ~HREF << ">>" << ~A; @@ -102,9 +110,9 @@ namespace brep } } - // PAGER_STYLE + // DIV_PAGER_STYLE // - void PAGER_STYLE:: + void DIV_PAGER_STYLE:: operator() (xml::serializer& s) const { const char* ident ("\n "); @@ -114,9 +122,9 @@ namespace brep << ".pg-cpage {padding: 0 0.3em 0 0; font-weight: bold;}"; } - // LICENSES + // DIV_LICENSES // - void LICENSES:: + void DIV_LICENSES:: operator() (serializer& s) const { s << DIV(CLASS="licenses") @@ -139,9 +147,9 @@ namespace brep s << ~DIV; } - // TAGS + // DIV_TAGS // - void TAGS:: + void DIV_TAGS:: operator() (serializer& s) const { if (!tags_.empty ()) @@ -156,9 +164,9 @@ namespace brep } } - // PRIORITY + // DIV_PRIORITY // - void PRIORITY:: + void DIV_PRIORITY:: operator() (serializer& s) const { static const strings priority_names ( diff --git a/loader/loader.cxx b/loader/loader.cxx index 7d60da6..0739774 100644 --- a/loader/loader.cxx +++ b/loader/loader.cxx @@ -226,9 +226,9 @@ changed (const internal_repositories& repos, database& db) // configuration file. // auto rs ( - db.query (query::internal && - !query::id.canonical_name.in_range (names.begin (), - names.end ()))); + db.query ( + query::internal && + !query::id.canonical_name.in_range (names.begin (), names.end ()))); return !rs.empty (); } @@ -244,13 +244,15 @@ manifest_stream (const path& p, ifstream& f) return file_mtime (p); } -// Loads the repository packages from the 'packages' file and persists the +// Load the repository packages from the 'packages' file and persist the // repository. Should be called once per repository. // static void load_packages (const shared_ptr& rp, database& db) { - // packages_timestamp different from timestamp_nonexistent signals the + using brep::optional; // Ambiguity with butl::optional. + + // packages_timestamp other than timestamp_nonexistent signals the // repository packages are already loaded. // assert (rp->packages_timestamp == timestamp_nonexistent); @@ -282,12 +284,22 @@ load_packages (const shared_ptr& rp, database& db) // otherwise call it external. // + // @@ External packages and external package versions are not used by the + // current implementation in any way. The reason to keep them is to see + // if we decide to link dependency information displayed on package + // version details page to best matching package or package version + // details pages. But even if we decide to keep mentioned objects for + // that purpose the ammount of information we store about them can be + // reduces significantly. Seems all we need to keep is in which + // repository they are located. + // + for (auto& pm: pkm) { // The code below ensures that the package object get updated with a - // package manifest info of the highest version. It should also be assured - // that for the internal package only an internal package manifests are - // considered for an update purpose. + // package manifest info of the highest version. We should also make + // sure that for the internal package only internal package manifests + // are considered for this purpose. // max_package_version mv; @@ -319,13 +331,19 @@ load_packages (const shared_ptr& rp, database& db) query::id.data.package == pm.name, mv); if (rp->internal) - // Unconditionally update external package with internal package - // manifest info. Persist not yet persisted package. + { + // Since internal repositories get loaded first, the package + // can't be external. + // + assert (mv.version.empty ()); + + // Persist not yet persisted internal package. // update = true; + } else - // Update external package with external package manifest info - // of a higher version. Version of not persisted package is empty and + // Update the external package with the external package manifest info + // of a higher version. Version of non-persisted package is empty and // therefore less then any package manifest version, so the package // will be persisted. // @@ -337,7 +355,7 @@ load_packages (const shared_ptr& rp, database& db) // if (rp->internal) - // Update internal package with the internal package manifest info + // Update the internal package with the internal package manifest info // of a higher version. // update = mv.version < pm.version; @@ -353,7 +371,7 @@ load_packages (const shared_ptr& rp, database& db) { // Create the package object. // - brep::optional desc; // Ambiguity with butl::optional. + optional desc; // Don't add description for external repository packages. // @@ -399,7 +417,7 @@ load_packages (const shared_ptr& rp, database& db) // dependencies dep; requirements req; - brep::optional loc; // Ambiguity with butl::optional. + optional loc; string chn; // Don't add dependencies, requirements and changes for external @@ -449,13 +467,13 @@ load_packages (const shared_ptr& rp, database& db) if (rp->internal) { + // Just skip the duplicate. + // + // As soon as internal repositories get loaded first, the internal // package version can duplicate an internal package version only. // assert (pv->internal_repository != nullptr); - - // Just skip the duplicate. - // } else { @@ -468,19 +486,19 @@ load_packages (const shared_ptr& rp, database& db) db.persist (rp); // Save the repository state. } -// Loads the prerequsite repositories state from the 'repositories' file. -// Updates the repository persistent state to save repositories_timestamp +// Load the prerequsite repositories state from the 'repositories' file. +// Update the repository persistent state to save repositories_timestamp // member. Should be called once per internal repository. // static void -load_prerequsites (const shared_ptr& rp, database& db) +load_prerequisites (const shared_ptr& rp, database& db) { - // repositories_timestamp different from timestamp_nonexistent signals the - // repository prerequsites are already loaded. + // repositories_timestamp other than timestamp_nonexistent signals that + // repository prerequisites are already loaded. // assert (rp->repositories_timestamp == timestamp_nonexistent); - // Load prerequsites for internal repositories only. + // Load prerequisites for internal repositories only. // assert (rp->internal); @@ -655,9 +673,9 @@ main (int argc, char* argv[]) { // Rebuild repositories persistent state from scratch. // - db.erase_query (); - db.erase_query (); db.erase_query (); + db.erase_query (); + db.erase_query (); // On the first pass over the internal repositories we load their // packages. @@ -680,7 +698,7 @@ main (int argc, char* argv[]) shared_ptr r ( db.load (ir.location.canonical_name ())); - load_prerequsites (r, db); + load_prerequisites (r, db); } } diff --git a/tests/loader/driver.cxx b/tests/loader/driver.cxx index f8fb545..443da72 100644 --- a/tests/loader/driver.cxx +++ b/tests/loader/driver.cxx @@ -292,31 +292,14 @@ main (int argc, char* argv[]) brep::optional ( version_comparison{version ("1+1.2"), comparison::eq})})); - requirements& fpvr2 (fpv2->requirements); - assert (fpvr2.size () == 4); - - assert (fpvr2[0] == strings ({"linux", "windows", "macosx"})); - assert (!fpvr2[0].conditional); - assert (fpvr2[0].comment.empty ()); - - assert (fpvr2[1] == strings ({"c++11"})); - assert (!fpvr2[1].conditional); - assert (fpvr2[1].comment.empty ()); - - assert (fpvr2[2].empty ()); - assert (fpvr2[2].conditional); - assert (fpvr2[2].comment == "VC++ 12.0 or later if targeting Windows."); - - assert (fpvr2[3].empty ()); - assert (fpvr2[3].conditional); - assert (fpvr2[3].comment == - "libc++ standard library if using Clang on Mac OS X."); + assert (fpv2->requirements.empty ()); assert (fpv3->internal_repository.load () == sr); assert (fpv3->external_repositories.empty ()); assert (fpv3->package.load () == pf); assert (fpv3->version == version ("1.2.3-4")); assert (fpv3->priority == priority::low); + assert (fpv3->changes.empty ()); assert (fpv3->license_alternatives.size () == 1); @@ -339,6 +322,8 @@ main (int argc, char* argv[]) assert (fpv4->changes == "some changes 1\nsome changes 2"); assert (fpv4->license_alternatives.size () == 1); + assert (fpv4->license_alternatives[0].comment == + "Permissive free software license."); assert (fpv4->license_alternatives[0].size () == 1); assert (fpv4->license_alternatives[0][0] == "MIT"); @@ -390,11 +375,22 @@ main (int argc, char* argv[]) // Verify libfoo package versions. // assert (fpv5->internal_repository.load () == mr); - assert (fpv5->external_repositories.empty ()); + assert (fpv5->external_repositories.size () == 1); + assert (fpv5->external_repositories[0].load () == cr); + assert (fpv5->package.load () == pf); assert (fpv5->version == version ("1.2.4-1")); assert (fpv5->priority == priority::high); - assert (fpv5->changes.empty ()); + assert (fpv5->priority.comment == "Due to critical bug fix."); + + const char ch[] = R"DLM(1.2.4-1 + * applied patch for critical bug-219 + * regenerated documentation + +1.2.4 + * test suite extended significantly)DLM"; + + assert (fpv5->changes == ch); assert (fpv5->license_alternatives.size () == 2); assert (fpv5->license_alternatives[0].comment == @@ -407,16 +403,48 @@ main (int argc, char* argv[]) assert (fpv5->license_alternatives[1].size () == 1); assert (fpv5->license_alternatives[1][0] == "BSD"); - assert (fpv5->dependencies.size () == 1); - assert (fpv5->dependencies[0].size () == 1); + assert (fpv5->dependencies.size () == 2); + assert (fpv5->dependencies[0].size () == 2); + assert (fpv5->dependencies[0].comment == + "Crashes in range [1.1, 2.3.0]."); assert (fpv5->dependencies[0][0] == (dependency { "libmisc", brep::optional ( - version_comparison{version ("2.3.0"), comparison::ge})})); + version_comparison{version ("1.1"), comparison::lt})})); - assert (fpv5->requirements.empty ()); + assert (fpv5->dependencies[0][1] == + (dependency { + "libmisc", + brep::optional ( + version_comparison{version ("2.3.0"), comparison::gt})})); + + assert (fpv5->dependencies[1].size () == 1); + assert (fpv5->dependencies[1].comment == "Newer - better."); + + assert (fpv5->dependencies[1][0] == + (dependency {"libstudxml", nullopt})); + + requirements& fpvr5 (fpv5->requirements); + assert (fpvr5.size () == 4); + + assert (fpvr5[0] == strings ({"linux", "windows", "macosx"})); + assert (!fpvr5[0].conditional); + assert (fpvr5[0].comment == "Symbian is coming."); + + assert (fpvr5[1] == strings ({"c++11"})); + assert (!fpvr5[1].conditional); + assert (fpvr5[1].comment.empty ()); + + assert (fpvr5[2] == strings ({"VC++"})); + assert (fpvr5[2].conditional); + assert (fpvr5[2].comment == "12.0 or later if targeting Windows."); + + assert (fpvr5[3].empty ()); + assert (fpvr5[3].conditional); + assert (fpvr5[3].comment == + "libc++ standard library if using Clang on Mac OS X."); // Verify libexp package. // diff --git a/tests/loader/external/1/misc/packages b/tests/loader/external/1/misc/packages index 843408b..77e10de 100644 --- a/tests/loader/external/1/misc/packages +++ b/tests/loader/external/1/misc/packages @@ -29,3 +29,11 @@ license: MIT url: http://www.example.com/foo/ email: foo-users@example.com location: libfoo-0.1.tar.gz +: +name: libfoo +version: 1.2.4-1 +summary: Foo Library +license: MIT +url: http://www.example.com/foo/ +email: foo-users@example.com +location: libfoo-1.2.4-1.tar.gz diff --git a/tests/loader/internal/1/math/packages b/tests/loader/internal/1/math/packages index 9ce4063..ac6c675 100644 --- a/tests/loader/internal/1/math/packages +++ b/tests/loader/internal/1/math/packages @@ -17,14 +17,27 @@ optimization tools. There are over 100 functions in total with an extensive \ test suite. The API is similar to MATLAB. license: LGPLv2, MIT; If using with GNU TLS. license: BSD; If using with OpenSSL. -priority: high +priority: high; Due to critical bug fix. tags: c++, foo, math url: http://www.example.com/foo/ email: foo-users@example.com package-url: http://www.example.com/foo/pack package-email: pack@example.com -depends: libmisc >= 2.3.0 +depends: libmisc < 1.1 | libmisc > 2.3.0; Crashes in range [1.1, 2.3.0]. +depends: ? libstudxml; Newer - better. +requires: linux | windows | macosx; Symbian is coming. +requires: c++11 +requires: ? VC++; 12.0 or later if targeting Windows. +requires: ? ; libc++ standard library if using Clang on Mac OS X. location: libfoo-1.2.4-1.tar.gz +changes:\ +1.2.4-1 + * applied patch for critical bug-219 + * regenerated documentation + +1.2.4 + * test suite extended significantly +\ : name: libfoo version: 1.0 diff --git a/tests/loader/internal/1/stable/packages b/tests/loader/internal/1/stable/packages index d5f1551..8d1e2fd 100644 --- a/tests/loader/internal/1/stable/packages +++ b/tests/loader/internal/1/stable/packages @@ -33,17 +33,13 @@ url: http://www.example.com/foo/ email: foo-users@example.com depends: libbar <= 2.4.0 depends: libexp == 1+1.2 -requires: linux | windows | macosx -requires: c++11 -requires: ? ; VC++ 12.0 or later if targeting Windows. -requires: ? ; libc++ standard library if using Clang on Mac OS X. location: libfoo-1.2.2.tar.gz : name: libfoo version: 1.2.4 summary: The Foo Library description: Very good foo library. -license: MIT +license: MIT; Permissive free software license. tags: c++, foo url: http://www.example.com/foo/ email: foo-users@example.com diff --git a/web/xhtml b/web/xhtml index d683469..9c092bf 100644 --- a/web/xhtml +++ b/web/xhtml @@ -307,9 +307,12 @@ namespace web static const element H4 ("h4"); static const element H5 ("h5"); static const element H6 ("h6"); + static const element LI ("li"); static const element META ("meta"); static const element P ("p"); + static const element PRE ("pre"); static const element TITLE ("title"); + static const element UL ("ul"); static const inline_element A ("a"); static const inline_element B ("b"); -- cgit v1.1