From 5fcd8a3c9677ac676445f91d64432dd07b27678e Mon Sep 17 00:00:00 2001
From: Tobias Triffterer <tobias@ep1.ruhr-uni-bochum.de>
Date: Sun, 25 Apr 2021 23:32:51 +0200
Subject: [PATCH] Add Parser for setTargetState Command
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

This new method does the usual input validation. As only three values
are allowed for the only parameter “newstate”, they are explicitly
checked, because “never trust your clients”...
---
 src/command.cpp | 23 ++++++++++++++++++++++-
 src/command.h   |  1 +
 2 files changed, 23 insertions(+), 1 deletion(-)

diff --git a/src/command.cpp b/src/command.cpp
index 6d85713..e400e0e 100644
--- a/src/command.cpp
+++ b/src/command.cpp
@@ -77,6 +77,8 @@ Command Command::fromString(const QString& source)
             return parseStoreToken(rootobj);
         case Action::updateExperimentState:
             return parseUpdateExperimentState(rootobj);
+        case Action::setTargetState:
+            return parseSetTargetState(rootobj);
         case Action::sendHistogramUpdate:
         case Action::moveTargetCloser:
         case Action::moveTargetFarther:
@@ -91,7 +93,6 @@ Command Command::fromString(const QString& source)
         // Not yet implemented:
         case Action::queryServerInformation:
         case Action::updateHistogram:
-        case Action::setTargetState:
         case Action::fillHistogram:
             return Command();
         default:
@@ -207,6 +208,26 @@ Protocol::Command Protocol::Command::parseUpdateExperimentState(const QJsonObjec
            );
 }
 
+Protocol::Command Protocol::Command::parseSetTargetState(const QJsonObject& input)
+{
+    if (!input.keys().contains(QStringLiteral("newstate")) || !input.value(QStringLiteral("newstate")).isString()) {
+        logError(QStringLiteral("setTargetState command does not contain newstate."));
+        return Command();
+    }
+    if (input.value(QStringLiteral("newstate")).toString() != QStringLiteral("open")
+            && input.value(QStringLiteral("newstate")).toString() != QStringLiteral("closed")
+            && input.value(QStringLiteral("newstate")).toString() != QStringLiteral("goldfoil")) {
+        logError(QStringLiteral("newstate parameter of setTargetState command is invalid."));
+        return Command();
+    }
+
+    return Command(
+               Action::setTargetState,
+               Arguments{std::make_pair(QStringLiteral("newstate"), input.value(QStringLiteral("newstate")).toString())},
+               input.value(QStringLiteral("token")).toString()
+           );
+}
+
 QString Command::toString() const
 {
     if (action == Action::invalid)
diff --git a/src/command.h b/src/command.h
index d87819c..d6e9586 100644
--- a/src/command.h
+++ b/src/command.h
@@ -73,6 +73,7 @@ private:
     static Command parseStoreToken(const QJsonObject& input);
     static Command parseError(const QJsonObject& input);
     static Command parseUpdateExperimentState(const QJsonObject& input);
+    static Command parseSetTargetState(const QJsonObject& input);
 
     static QString getActionString(const Action action);
 };
-- 
GitLab