Repository: bpicode/fritzctl (go)

Issue:
Error: fritzctl temperature
When using the command "fritzctl temperature x x" with an temperature above 28 degrees the script is giving out an error instead of showing a message with the allowed temperature range.

Pull request description:
Issue #57: check for valid temperature values before apply
Closes #57 

Patch:
diff --git a/fritz/aha.go b/fritz/aha.go
index db9bc4e..641a370 100644
--- a/fritz/aha.go
+++ b/fritz/aha.go
@@ -67,12 +67,14 @@ func (aha *ahaHTTP) Toggle(ain string) (string, error) {
 
 // ApplyTemperature sets the desired temperature on a "HKR" device. The device is identified by its AIN.
 func (aha *ahaHTTP) ApplyTemperature(value float64, ain string) (string, error) {
-	doubledValue := 2 * value
-	rounded := round(doubledValue)
+	param, err := temperatureParam(value)
+	if err != nil {
+		return "", err
+	}
 	url := aha.homeAutoSwitch().
 		query("ain", ain).
 		query("switchcmd", "sethkrtsoll").
-		query("param", fmt.Sprintf("%d", rounded)).
+		query("param", fmt.Sprintf("%d", param)).
 		build()
 	return httpread.ReadFullyString(aha.getf(url))
 }
@@ -103,6 +105,16 @@ func (aha *ahaHTTP) homeAutoSwitch() fritzURLBuilder {
 	return newURLBuilder(aha.client.Config).path(homeAutomationURI).query("sid", aha.client.SessionInfo.SID)
 }
 
+func temperatureParam(t float64) (int64, error) {
+	doubled := round(2 * t)
+	regular := doubled >= 16 && doubled <= 56
+	special := doubled == 253 || doubled == 254
+	if ! (regular || special) {
+		return 0, fmt.Errorf("invalid temperature value: %.1f°C is not contained in the set of acceptable values: 8-28°C, 126.5, 127", t)
+	}
+	return doubled, nil
+}
+
 // round rounds a float64 value to an integer.
 func round(v float64) int64 {
 	return int64(v + 0.5)


Test patch:
diff --git a/fritz/aha_test.go b/fritz/aha_test.go
index de9a70f..1f9fe05 100644
--- a/fritz/aha_test.go
+++ b/fritz/aha_test.go
@@ -109,3 +109,15 @@ func TestRounding(t *testing.T) {
 		})
 	}
 }
+
+// TestUnacceptableTempValues asserts that temperatures outside the range of the spec are perceived as invalid.
+func TestUnacceptableTempValues(t *testing.T) {
+	assertions := assert.New(t)
+	h := HomeAutomation(nil)
+
+	_, err := h.ApplyTemperature(7.5, "1235")
+	assertions.Error(err)
+
+	_, err = h.ApplyTemperature(55, "1235")
+	assertions.Error(err)
+}