diff options
author | Karen Arutyunov <karen@codesynthesis.com> | 2021-04-16 22:04:22 +0300 |
---|---|---|
committer | Karen Arutyunov <karen@codesynthesis.com> | 2021-04-19 18:35:30 +0300 |
commit | f0c4ddcc96ae4eea5e158359bc21f51c3261bdd2 (patch) | |
tree | f2d12cb67395a4be2053379958b94d8ec6d333d9 | |
parent | e4c22fd4b9ba9782acd0c0a10866cbeaf8be694d (diff) |
Match package spec local repository locations in pkg-build case-insensitively on Windows
-rw-r--r-- | bpkg/database.cxx | 10 | ||||
-rw-r--r-- | bpkg/package.hxx | 10 | ||||
-rw-r--r-- | bpkg/package.xml | 6 | ||||
-rw-r--r-- | bpkg/pkg-build.cxx | 29 | ||||
-rw-r--r-- | tests/pkg-build.testscript | 33 |
5 files changed, 80 insertions, 8 deletions
diff --git a/bpkg/database.cxx b/bpkg/database.cxx index 7ba19f0..e355860 100644 --- a/bpkg/database.cxx +++ b/bpkg/database.cxx @@ -41,15 +41,21 @@ namespace bpkg // Register the data migration functions. // -#if 0 template <odb::schema_version v> using migration_entry = odb::data_migration_entry<v, DB_SCHEMA_VERSION_BASE>; static const migration_entry<8> migrate_v8 ([] (odb::database& db) { + for (shared_ptr<repository> r: pointer_result (db.query<repository> ())) + { + if (!r->name.empty ()) // Non-root repository? + { + r->local = r->location.local (); + db.update (r); + } + } }); -#endif database open (const dir_path& d, tracer& tr, bool create) diff --git a/bpkg/package.hxx b/bpkg/package.hxx index e7379b3..ad45fa8 100644 --- a/bpkg/package.hxx +++ b/bpkg/package.hxx @@ -27,7 +27,7 @@ // #define DB_SCHEMA_VERSION_BASE 6 -#pragma db model version(DB_SCHEMA_VERSION_BASE, 7, closed) +#pragma db model version(DB_SCHEMA_VERSION_BASE, 8, closed) namespace bpkg { @@ -390,11 +390,19 @@ namespace bpkg optional<string> certificate; // PEM representation. fragments_type fragments; + // While we could potentially calculate this flag on the fly, that would + // complicate the database queries significantly. + // + optional<bool> local; // nullopt for root repository. + public: explicit repository (repository_location l): location (move (l)) { name = location.canonical_name (); + + if (!name.empty ()) // Non-root? + local = location.local (); } // Database mapping. diff --git a/bpkg/package.xml b/bpkg/package.xml index 2b94c71..55e3a9a 100644 --- a/bpkg/package.xml +++ b/bpkg/package.xml @@ -1,4 +1,10 @@ <changelog xmlns="http://www.codesynthesis.com/xmlns/odb/changelog" database="sqlite" version="1"> + <changeset version="8"> + <alter-table name="repository"> + <add-column name="local" type="INTEGER" null="true"/> + </alter-table> + </changeset> + <changeset version="7"> <alter-table name="available_package_dependencies"> <add-column name="type" type="TEXT" null="true"/> diff --git a/bpkg/pkg-build.cxx b/bpkg/pkg-build.cxx index 9d9b384..082696e 100644 --- a/bpkg/pkg-build.cxx +++ b/bpkg/pkg-build.cxx @@ -2620,17 +2620,38 @@ namespace bpkg { using query = query<repository>; - auto q (db.query<repository> (query::location.url == l)); - auto i (q.begin ()); + // For case-insensitive filesystems (Windows) we need to match the + // location case-insensitively against the local repository URLs + // and case-sensitively against the remote ones. + // + // Note that the root repository will never be matched, since its + // location is empty. + // + const auto& url (query::location.url); + +#ifndef _WIN32 + query q (url == l); +#else + string u (url.table ()); + u += '.'; + u += url.column (); + + query q ( + (!query::local && url == l) || + ( query::local && u + " COLLATE nocase = " + query::_val (l))); +#endif + + auto rs (db.query<repository> (q)); + auto i (rs.begin ()); - if (i != q.end ()) + if (i != rs.end ()) { r = i.load (); // Fallback to parsing the location if several repositories // match. // - if (++i != q.end ()) + if (++i != rs.end ()) r = nullptr; } } diff --git a/tests/pkg-build.testscript b/tests/pkg-build.testscript index 6fe5eb9..50db679 100644 --- a/tests/pkg-build.testscript +++ b/tests/pkg-build.testscript @@ -159,6 +159,7 @@ pkg_unpack += -d cfg 2>! rep_add += -d cfg 2>! rep_remove += -d cfg 2>! rep_fetch += -d cfg --auth all --trust-yes 2>! +rep_list += -d cfg # Let's disable the progress indication that complicates stderr output # validation. @@ -3757,7 +3758,7 @@ test.options += --no-progress } } -: ignore-case +: ignore-case-pkg : { test.arguments += --yes --auth all --trust-yes @@ -3792,6 +3793,36 @@ test.options += --no-progress $pkg_drop libbar } +: ignore-case-rep +: +: Test that package spec local repository location is matched +: case-insensitively on Windows. +: +if (!$remote && !$posix) +{ + $clone_cfg; + + $* "libbar@$rep/t5" 2>>~%EOE%; + added pkg:build2.org/pkg-build/t5 + fetching pkg:build2.org/pkg-build/t5 + fetched libbar/1.2.0 + unpacked libbar/1.2.0 + configured libbar/1.2.0 + %info: .+ is up to date% + updated libbar/1.2.0 + EOE + + $* "libbar@$rep/T5" 2>>~%EOE%; + fetching pkg:build2.org/pkg-build/t5 + %info: .+ is up to date% + updated libbar/1.2.0 + EOE + + $rep_list >~'%pkg:build2\.org/pkg-build/t5 .+t5%'; + + $pkg_drop libbar +} + : git-rep : if! $git_supported |