Skip to content
This repository has been archived by the owner on May 21, 2024. It is now read-only.

Store target's custom meta data when installing #1370

Merged
merged 2 commits into from
Sep 23, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions config/sql/migration/migrate.21.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
-- Don't modify this! Create a new migration instead--see docs/schema-migrations.adoc
SAVEPOINT MIGRATION;

ALTER TABLE installed_versions ADD COLUMN custom_meta TEXT NOT NULL DEFAULT "";

DELETE FROM version;
INSERT INTO version VALUES(21);

RELEASE MIGRATION;
13 changes: 13 additions & 0 deletions config/sql/rollback/rollback.21.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
-- Don't modify this! Create a new migration instead--see docs/schema-migrations.adoc
SAVEPOINT ROLLBACK_MIGRATION;

CREATE TABLE installed_versions_migrate(id INTEGER PRIMARY KEY, ecu_serial TEXT NOT NULL, sha256 TEXT NOT NULL, name TEXT NOT NULL, hashes TEXT NOT NULL, length INTEGER NOT NULL DEFAULT 0, correlation_id TEXT NOT NULL DEFAULT '', is_current INTEGER NOT NULL CHECK (is_current IN (0,1)) DEFAULT 0, is_pending INTEGER NOT NULL CHECK (is_pending IN (0,1)) DEFAULT 0, was_installed INTEGER NOT NULL CHECK (was_installed IN (0,1)) DEFAULT 0);
INSERT INTO installed_versions_migrate(ecu_serial, sha256, name, hashes, length, correlation_id, is_current, is_pending, was_installed) SELECT installed_versions.ecu_serial, installed_versions.sha256, installed_versions.name, installed_versions.hashes, installed_versions.length, installed_versions.correlation_id, installed_versions.is_current, installed_versions.is_pending, installed_versions.was_installed FROM installed_versions;

DROP TABLE installed_versions;
ALTER TABLE installed_versions_migrate RENAME TO installed_versions;

DELETE FROM version;
INSERT INTO version VALUES(20);

RELEASE ROLLBACK_MIGRATION;
4 changes: 2 additions & 2 deletions config/sql/schema.sql
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
CREATE TABLE version(version INTEGER);
INSERT INTO version(rowid,version) VALUES(1,20);
INSERT INTO version(rowid,version) VALUES(1,21);
CREATE TABLE device_info(unique_mark INTEGER PRIMARY KEY CHECK (unique_mark = 0), device_id TEXT, is_registered INTEGER NOT NULL DEFAULT 0 CHECK (is_registered IN (0,1)));
CREATE TABLE ecu_serials(id INTEGER PRIMARY KEY, serial TEXT UNIQUE, hardware_id TEXT NOT NULL, is_primary INTEGER NOT NULL DEFAULT 0 CHECK (is_primary IN (0,1)));
CREATE TABLE misconfigured_ecus(serial TEXT UNIQUE, hardware_id TEXT NOT NULL, state INTEGER NOT NULL CHECK (state IN (0,1)));
CREATE TABLE installed_versions(id INTEGER PRIMARY KEY, ecu_serial TEXT NOT NULL, sha256 TEXT NOT NULL, name TEXT NOT NULL, hashes TEXT NOT NULL, length INTEGER NOT NULL DEFAULT 0, correlation_id TEXT NOT NULL DEFAULT '', is_current INTEGER NOT NULL CHECK (is_current IN (0,1)) DEFAULT 0, is_pending INTEGER NOT NULL CHECK (is_pending IN (0,1)) DEFAULT 0, was_installed INTEGER NOT NULL CHECK (was_installed IN (0,1)) DEFAULT 0);
CREATE TABLE installed_versions(id INTEGER PRIMARY KEY, ecu_serial TEXT NOT NULL, sha256 TEXT NOT NULL, name TEXT NOT NULL, hashes TEXT NOT NULL, length INTEGER NOT NULL DEFAULT 0, correlation_id TEXT NOT NULL DEFAULT '', is_current INTEGER NOT NULL CHECK (is_current IN (0,1)) DEFAULT 0, is_pending INTEGER NOT NULL CHECK (is_pending IN (0,1)) DEFAULT 0, was_installed INTEGER NOT NULL CHECK (was_installed IN (0,1)) DEFAULT 0, custom_meta TEXT NOT NULL DEFAULT "");
CREATE TABLE primary_keys(unique_mark INTEGER PRIMARY KEY CHECK (unique_mark = 0), private TEXT, public TEXT);
CREATE TABLE tls_creds(ca_cert BLOB, ca_cert_format TEXT,
client_cert BLOB, client_cert_format TEXT,
Expand Down
52 changes: 37 additions & 15 deletions src/libaktualizr/storage/sqlstorage.cc
Original file line number Diff line number Diff line change
Expand Up @@ -986,15 +986,15 @@ void SQLStorage::saveInstalledVersion(const std::string& ecu_serial, const Uptan
return;
}
} else {
auto statement =
db.prepareStatement<std::string, std::string, std::string, std::string, int64_t, std::string, int, int>(
"INSERT INTO installed_versions(ecu_serial, sha256, name, hashes, length, correlation_id, "
"is_current, is_pending, was_installed) VALUES (?,?,?,?,?,?,?,?,?);",
ecu_serial_real, target.sha256Hash(), target.filename(), hashes_encoded,
static_cast<int64_t>(target.length()), target.correlation_id(),
static_cast<int>(update_mode == InstalledVersionUpdateMode::kCurrent),
static_cast<int>(update_mode == InstalledVersionUpdateMode::kPending),
static_cast<int>(update_mode == InstalledVersionUpdateMode::kCurrent));
std::string custom = Json::FastWriter().write(target.custom_data());
auto statement = db.prepareStatement<std::string, std::string, std::string, std::string, int64_t, std::string,
std::string, int, int>(
"INSERT INTO installed_versions(ecu_serial, sha256, name, hashes, length, custom_meta, correlation_id, "
"is_current, is_pending, was_installed) VALUES (?,?,?,?,?,?,?,?,?,?);",
ecu_serial_real, target.sha256Hash(), target.filename(), hashes_encoded, static_cast<int64_t>(target.length()),
custom, target.correlation_id(), static_cast<int>(update_mode == InstalledVersionUpdateMode::kCurrent),
static_cast<int>(update_mode == InstalledVersionUpdateMode::kPending),
static_cast<int>(update_mode == InstalledVersionUpdateMode::kCurrent));

if (statement.step() != SQLITE_DONE) {
LOG_ERROR << "Can't set installed_versions: " << db.errmsg();
Expand Down Expand Up @@ -1036,11 +1036,11 @@ bool SQLStorage::loadInstallationLog(const std::string& ecu_serial, std::vector<
loadEcuMap(db, ecu_serial_real, ecu_map);

std::string query =
"SELECT id, sha256, name, hashes, length, correlation_id FROM installed_versions WHERE "
"SELECT id, sha256, name, hashes, length, correlation_id, custom_meta FROM installed_versions WHERE "
"ecu_serial = ? ORDER BY id;";
if (only_installed) {
query =
"SELECT id, sha256, name, hashes, length, correlation_id FROM installed_versions WHERE "
"SELECT id, sha256, name, hashes, length, correlation_id, custom_meta FROM installed_versions WHERE "
"ecu_serial = ? AND was_installed = 1 ORDER BY id;";
}

Expand All @@ -1058,6 +1058,7 @@ bool SQLStorage::loadInstallationLog(const std::string& ecu_serial, std::vector<
auto hashes_str = statement.get_result_col_str(3).value();
auto length = statement.get_result_col_int(4);
auto correlation_id = statement.get_result_col_str(5).value();
auto custom_str = statement.get_result_col_str(6).value();

// note: sha256 should always be present and is used to uniquely identify
// a version. It should normally be part of the hash list as well.
Expand All @@ -1070,7 +1071,17 @@ bool SQLStorage::loadInstallationLog(const std::string& ecu_serial, std::vector<
hashes.emplace_back(Uptane::Hash::Type::kSha256, sha256);
}

new_log.emplace_back(filename, ecu_map, hashes, static_cast<uint64_t>(length), correlation_id);
Uptane::Target t(filename, ecu_map, hashes, static_cast<uint64_t>(length), correlation_id);
if (!custom_str.empty()) {
Json::Reader reader;
Json::Value custom;
if (reader.parse(custom_str, custom)) {
t.updateCustom(custom);
} else {
LOG_ERROR << "Unable to parse custom data: " << reader.getFormatedErrorMessages();
}
}
new_log.emplace_back(t);

ids_map[id] = k;
k++;
Expand Down Expand Up @@ -1108,6 +1119,7 @@ bool SQLStorage::loadInstalledVersions(const std::string& ecu_serial, boost::opt
auto hashes_str = statement.get_result_col_str(2).value();
auto length = statement.get_result_col_int(3);
auto correlation_id = statement.get_result_col_str(4).value();
auto custom_str = statement.get_result_col_str(5).value();

// note: sha256 should always be present and is used to uniquely identify
// a version. It should normally be part of the hash list as well.
Expand All @@ -1119,13 +1131,23 @@ bool SQLStorage::loadInstalledVersions(const std::string& ecu_serial, boost::opt
LOG_WARNING << "No sha256 in hashes list";
hashes.emplace_back(Uptane::Hash::Type::kSha256, sha256);
}
Uptane::Target t(filename, ecu_map, hashes, static_cast<uint64_t>(length), correlation_id);
if (!custom_str.empty()) {
Json::Reader reader;
Json::Value custom;
if (reader.parse(custom_str, custom)) {
t.updateCustom(custom);
} else {
LOG_ERROR << "Unable to parse custom data: " << reader.getFormatedErrorMessages();
}
}

return Uptane::Target(filename, ecu_map, hashes, static_cast<uint64_t>(length), correlation_id);
return t;
};

if (current_version != nullptr) {
auto statement = db.prepareStatement<std::string>(
"SELECT sha256, name, hashes, length, correlation_id FROM installed_versions WHERE "
"SELECT sha256, name, hashes, length, correlation_id, custom_meta FROM installed_versions WHERE "
"ecu_serial = ? AND is_current = 1 LIMIT 1;",
ecu_serial_real);

Expand All @@ -1144,7 +1166,7 @@ bool SQLStorage::loadInstalledVersions(const std::string& ecu_serial, boost::opt

if (pending_version != nullptr) {
auto statement = db.prepareStatement<std::string>(
"SELECT sha256, name, hashes, length, correlation_id FROM installed_versions WHERE "
"SELECT sha256, name, hashes, length, correlation_id, custom_meta FROM installed_versions WHERE "
"ecu_serial = ? AND is_pending = 1 LIMIT 1;",
ecu_serial_real);

Expand Down
7 changes: 7 additions & 0 deletions src/libaktualizr/storage/storage_common_test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -301,6 +301,10 @@ TEST(storage, load_store_installed_versions) {
};
Uptane::EcuMap primary_ecu{{Uptane::EcuSerial("primary"), Uptane::HardwareIdentifier("primary_hw")}};
Uptane::Target t1{"update.bin", primary_ecu, hashes, 1, "corrid"};
Json::Value custom;
custom["version"] = 42;
custom["foo"] = "bar";
t1.updateCustom(custom);
storage->savePrimaryInstalledVersion(t1, InstalledVersionUpdateMode::kCurrent);
{
std::vector<Uptane::Target> log;
Expand All @@ -324,6 +328,8 @@ TEST(storage, load_store_installed_versions) {
EXPECT_EQ(current->ecus(), primary_ecu);
EXPECT_EQ(current->correlation_id(), "corrid");
EXPECT_EQ(current->length(), 1);
EXPECT_EQ(current->custom_data()["foo"], "bar");
EXPECT_EQ(current->custom_data()["version"], 42);
}

// Set t2 as a pending version
Expand Down Expand Up @@ -391,6 +397,7 @@ TEST(storage, load_store_installed_versions) {
storage->loadInstallationLog("primary", &log, true);
EXPECT_EQ(log.size(), 4);
EXPECT_EQ(log.back().filename(), "update3.bin");
EXPECT_EQ(log[0].custom_data()["foo"], "bar");
}

// Add a secondary installed version
Expand Down
1 change: 1 addition & 0 deletions src/libaktualizr/uptane/tuf.h
Original file line number Diff line number Diff line change
Expand Up @@ -240,6 +240,7 @@ class Target {
std::vector<HardwareIdentifier> hardwareIds() const { return hwids_; };
std::string custom_version() const { return custom_["version"].asString(); }
Json::Value custom_data() const { return custom_; }
void updateCustom(Json::Value &custom) { custom_ = custom; };
std::string correlation_id() const { return correlation_id_; };
void setCorrelationId(std::string correlation_id) { correlation_id_ = std::move(correlation_id); };
uint64_t length() const { return length_; }
Expand Down