mirror of
https://github.com/torlando-tech/pyxis.git
synced 2026-08-22 18:49:54 +00:00
238 lines
9.8 KiB
C++
238 lines
9.8 KiB
C++
#include "UI/LXMF/MapStyleSelector.h"
|
|
|
|
#include <cstdlib>
|
|
#include <cstring>
|
|
#include <iostream>
|
|
|
|
namespace {
|
|
int passed = 0;
|
|
int failed = 0;
|
|
#define CHECK(expr) do { if (expr) { ++passed; } else { ++failed; std::cerr << "FAIL line " << __LINE__ << ": " #expr << '\n'; } } while (false)
|
|
|
|
Pyxis::MapStyleSummary style(const char* id, const char* label) {
|
|
Pyxis::MapStyleSummary result{};
|
|
std::strncpy(result.id, id, sizeof(result.id) - 1U);
|
|
std::strncpy(result.label, label, sizeof(result.label) - 1U);
|
|
return result;
|
|
}
|
|
|
|
void emptyAndSingleStyleDisableCycling() {
|
|
Pyxis::MapStyleSelector selector;
|
|
Pyxis::MapStyleRequest request{};
|
|
CHECK(selector.state() == Pyxis::MapStyleSelector::State::DISCOVERING);
|
|
CHECK(selector.setCatalog(4U, nullptr, 0U, nullptr));
|
|
CHECK(selector.count() == 0U);
|
|
CHECK(!selector.canCycle());
|
|
CHECK(!selector.requestNext(request));
|
|
|
|
const Pyxis::MapStyleSummary only[] = {style("osm-bright", "Bright")};
|
|
CHECK(selector.setCatalog(5U, only, 1U, "osm-bright"));
|
|
CHECK(std::strcmp(selector.activeId(), "osm-bright") == 0);
|
|
CHECK(std::strcmp(selector.activeLabel(), "Bright") == 0);
|
|
CHECK(!selector.canCycle());
|
|
CHECK(!selector.requestNext(request));
|
|
}
|
|
|
|
void cyclesDeterministicallyAndBoundsPendingIntent() {
|
|
Pyxis::MapStyleSelector selector;
|
|
const Pyxis::MapStyleSummary styles[] = {
|
|
style("osm-bright", "Bright"), style("dark-matter", "Dark"),
|
|
style("positron", "Positron"), style("toner", "Toner")};
|
|
CHECK(selector.setCatalog(9U, styles, 4U, "dark-matter"));
|
|
CHECK(selector.canCycle());
|
|
|
|
Pyxis::MapStyleRequest request{};
|
|
CHECK(selector.requestNext(request));
|
|
CHECK(request.catalog_generation == 9U);
|
|
CHECK(std::strcmp(request.style_id, "positron") == 0);
|
|
CHECK(request.token != 0U);
|
|
CHECK(selector.state() == Pyxis::MapStyleSelector::State::APPLYING);
|
|
CHECK(selector.activationInFlight());
|
|
Pyxis::MapStyleRequest duplicate{};
|
|
CHECK(!selector.requestNext(duplicate));
|
|
|
|
Pyxis::MapStyleCompletion stale{};
|
|
stale.token = request.token + 1U;
|
|
stale.catalog_generation = request.catalog_generation;
|
|
stale.success = true;
|
|
std::strcpy(stale.style_id, request.style_id);
|
|
CHECK(!selector.complete(stale));
|
|
CHECK(std::strcmp(selector.activeId(), "dark-matter") == 0);
|
|
|
|
Pyxis::MapStyleCompletion failure{};
|
|
failure.token = request.token;
|
|
failure.catalog_generation = request.catalog_generation;
|
|
failure.success = false;
|
|
std::strcpy(failure.style_id, request.style_id);
|
|
CHECK(selector.complete(failure));
|
|
CHECK(selector.state() == Pyxis::MapStyleSelector::State::ERROR);
|
|
CHECK(std::strcmp(selector.activeId(), "dark-matter") == 0);
|
|
|
|
CHECK(!selector.requestNext(request));
|
|
CHECK(selector.releaseActivation(failure.token));
|
|
CHECK(selector.requestNext(request));
|
|
Pyxis::MapStyleCompletion success{};
|
|
success.token = request.token;
|
|
success.catalog_generation = request.catalog_generation;
|
|
success.success = true;
|
|
std::strcpy(success.style_id, request.style_id);
|
|
CHECK(selector.complete(success));
|
|
CHECK(selector.releaseActivation(success.token));
|
|
CHECK(selector.state() == Pyxis::MapStyleSelector::State::READY);
|
|
CHECK(std::strcmp(selector.activeId(), "positron") == 0);
|
|
CHECK(std::strcmp(selector.activeLabel(), "Positron") == 0);
|
|
}
|
|
|
|
void rejectsMalformedCatalogsAndStaleCompletions() {
|
|
Pyxis::MapStyleSelector selector;
|
|
Pyxis::MapStyleSummary duplicate[] = {
|
|
style("osm-bright", "Bright"), style("osm-bright", "Again")};
|
|
CHECK(!selector.setCatalog(1U, duplicate, 2U, "osm-bright"));
|
|
const Pyxis::MapStyleSummary styles[] = {
|
|
style("osm-bright", "Bright"), style("toner", "Toner")};
|
|
CHECK(!selector.setCatalog(0U, styles, 2U, "osm-bright"));
|
|
CHECK(!selector.setCatalog(2U, styles, 2U, "unknown"));
|
|
CHECK(selector.setCatalog(3U, styles, 2U, "osm-bright"));
|
|
Pyxis::MapStyleRequest request{};
|
|
CHECK(selector.requestNext(request));
|
|
CHECK(!selector.setCatalog(4U, styles, 2U, "osm-bright"));
|
|
Pyxis::MapStyleCompletion old{};
|
|
old.token = request.token;
|
|
old.catalog_generation = request.catalog_generation + 1U;
|
|
old.success = false;
|
|
std::strcpy(old.style_id, request.style_id);
|
|
CHECK(!selector.complete(old));
|
|
old.catalog_generation = request.catalog_generation;
|
|
CHECK(selector.complete(old));
|
|
CHECK(selector.releaseActivation(old.token));
|
|
CHECK(std::strcmp(selector.activeId(), "osm-bright") == 0);
|
|
}
|
|
|
|
void permitsSoleInstalledStyleWhenNoRecognizedStyleIsActive() {
|
|
Pyxis::MapStyleSelector selector;
|
|
const Pyxis::MapStyleSummary only[] = {style("positron", "Positron")};
|
|
CHECK(selector.setCatalog(9U, only, 1U, nullptr));
|
|
CHECK(selector.canCycle());
|
|
CHECK(std::strcmp(selector.activeId(), "") == 0);
|
|
CHECK(std::strcmp(selector.activeLabel(), "Style") == 0);
|
|
Pyxis::MapStyleRequest request{};
|
|
CHECK(selector.requestNext(request));
|
|
CHECK(std::strcmp(request.style_id, "positron") == 0);
|
|
}
|
|
|
|
void activationLeaseSpansCatalogReconciliation() {
|
|
Pyxis::MapStyleSelector selector;
|
|
const Pyxis::MapStyleSummary styles[] = {
|
|
style("osm-bright", "Bright"), style("toner", "Toner")};
|
|
CHECK(selector.setCatalog(7U, styles, 2U, "osm-bright"));
|
|
|
|
Pyxis::MapStyleRequest first{};
|
|
CHECK(selector.requestNext(first));
|
|
CHECK(selector.activationOwnedBy(first.token));
|
|
CHECK(!selector.activationOwnedBy(first.token + 1U));
|
|
CHECK(!selector.releaseActivation(first.token + 1U));
|
|
|
|
Pyxis::MapStyleCompletion success{};
|
|
success.token = first.token;
|
|
success.catalog_generation = first.catalog_generation;
|
|
success.success = true;
|
|
std::strcpy(success.style_id, first.style_id);
|
|
CHECK(selector.complete(success));
|
|
|
|
CHECK(!selector.setCatalog(8U, styles, 2U, "toner"));
|
|
CHECK(selector.reconcileActivation(first.token, 8U, styles, 2U, "toner", false));
|
|
Pyxis::MapStyleRequest second{};
|
|
CHECK(!selector.requestNext(second));
|
|
CHECK(selector.releaseActivation(first.token));
|
|
CHECK(!selector.activationInFlight());
|
|
CHECK(selector.requestNext(second));
|
|
CHECK(second.catalog_generation == 8U);
|
|
CHECK(std::strcmp(second.style_id, "osm-bright") == 0);
|
|
}
|
|
|
|
void cancellationIsScopedToUnborrowedOwner() {
|
|
Pyxis::MapStyleSelector selector;
|
|
const Pyxis::MapStyleSummary styles[] = {
|
|
style("osm-bright", "Bright"), style("toner", "Toner")};
|
|
CHECK(selector.setCatalog(12U, styles, 2U, "osm-bright"));
|
|
Pyxis::MapStyleRequest request{};
|
|
CHECK(selector.requestNext(request));
|
|
CHECK(!selector.cancelPending(request.token + 1U));
|
|
CHECK(selector.cancelPending(request.token));
|
|
CHECK(selector.state() == Pyxis::MapStyleSelector::State::READY);
|
|
|
|
CHECK(selector.requestNext(request));
|
|
CHECK(selector.cancelPending(request.token));
|
|
CHECK(selector.requestNext(request));
|
|
Pyxis::MapStyleCompletion failure{};
|
|
failure.token = request.token;
|
|
failure.catalog_generation = request.catalog_generation;
|
|
failure.success = false;
|
|
std::strcpy(failure.style_id, request.style_id);
|
|
CHECK(selector.complete(failure));
|
|
CHECK(selector.clearError());
|
|
CHECK(selector.state() == Pyxis::MapStyleSelector::State::READY);
|
|
CHECK(selector.releaseActivation(request.token));
|
|
}
|
|
|
|
void committedActivationFailureStillReconcilesGeneration() {
|
|
Pyxis::MapStyleSelector selector;
|
|
const Pyxis::MapStyleSummary styles[] = {
|
|
style("osm-bright", "Bright"), style("toner", "Toner")};
|
|
CHECK(selector.setCatalog(21U, styles, 2U, "osm-bright"));
|
|
Pyxis::MapStyleRequest request{};
|
|
CHECK(selector.requestNext(request));
|
|
|
|
Pyxis::MapStyleCompletion reload_failure{};
|
|
reload_failure.token = request.token;
|
|
reload_failure.catalog_generation = request.catalog_generation;
|
|
reload_failure.success = false;
|
|
std::strcpy(reload_failure.style_id, request.style_id);
|
|
CHECK(selector.complete(reload_failure));
|
|
CHECK(selector.reconcileActivation(request.token, 22U, styles, 2U,
|
|
"toner", true));
|
|
CHECK(selector.state() == Pyxis::MapStyleSelector::State::ERROR);
|
|
CHECK(selector.generation() == 22U);
|
|
CHECK(std::strcmp(selector.activeId(), "toner") == 0);
|
|
CHECK(selector.releaseActivation(request.token));
|
|
|
|
Pyxis::MapStyleRequest retry{};
|
|
CHECK(selector.requestNext(retry));
|
|
CHECK(retry.catalog_generation == 22U);
|
|
CHECK(std::strcmp(retry.style_id, "osm-bright") == 0);
|
|
}
|
|
|
|
void hiddenLifecycleCannotReintroduceFailureDuringReconciliation() {
|
|
Pyxis::MapStyleSelector selector;
|
|
const Pyxis::MapStyleSummary styles[] = {
|
|
style("osm-bright", "Bright"), style("toner", "Toner")};
|
|
CHECK(selector.setCatalog(30U, styles, 2U, "osm-bright"));
|
|
Pyxis::MapStyleRequest request{};
|
|
CHECK(selector.requestNext(request));
|
|
Pyxis::MapStyleCompletion failure{};
|
|
failure.token = request.token;
|
|
failure.catalog_generation = request.catalog_generation;
|
|
failure.success = false;
|
|
std::strcpy(failure.style_id, request.style_id);
|
|
CHECK(selector.complete(failure));
|
|
CHECK(selector.clearError());
|
|
CHECK(selector.reconcileActivation(request.token, 31U, styles, 2U,
|
|
"toner", false));
|
|
CHECK(selector.state() == Pyxis::MapStyleSelector::State::READY);
|
|
CHECK(selector.releaseActivation(request.token));
|
|
}
|
|
}
|
|
|
|
int main() {
|
|
emptyAndSingleStyleDisableCycling();
|
|
cyclesDeterministicallyAndBoundsPendingIntent();
|
|
rejectsMalformedCatalogsAndStaleCompletions();
|
|
permitsSoleInstalledStyleWhenNoRecognizedStyleIsActive();
|
|
activationLeaseSpansCatalogReconciliation();
|
|
cancellationIsScopedToUnborrowedOwner();
|
|
committedActivationFailureStillReconcilesGeneration();
|
|
hiddenLifecycleCannotReintroduceFailureDuringReconciliation();
|
|
std::cout << "map style selector: " << passed << " passed, " << failed << " failed\n";
|
|
return failed == 0 ? EXIT_SUCCESS : EXIT_FAILURE;
|
|
}
|