SensorAgeConditionTests.swift 3.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384
  1. // LoopFollow
  2. // SensorAgeConditionTests.swift
  3. import Foundation
  4. @testable import LoopFollow
  5. import Testing
  6. struct SensorAgeConditionTests {
  7. let cond = SensorAgeCondition()
  8. // MARK: - 10-day lifetime (default)
  9. @Test("fires when within threshold hours of 10-day expiry")
  10. func firesNear10DayExpiry() {
  11. let alarm = Alarm.sensorChange(threshold: 12, lifetimeDays: 10)
  12. // Sensor inserted 9 days and 13 hours ago → 11 hours until 10-day mark → within 12-hour window
  13. let insertTime = Date().addingTimeInterval(-9 * 86400 - 13 * 3600).timeIntervalSince1970
  14. let data = AlarmData.withSensorInsertTime(insertTime)
  15. #expect(cond.evaluate(alarm: alarm, data: data, now: .init()))
  16. }
  17. @Test("does NOT fire when far from 10-day expiry")
  18. func doesNotFireEarly() {
  19. let alarm = Alarm.sensorChange(threshold: 12, lifetimeDays: 10)
  20. // Sensor inserted 8 days ago → 2 days until 10-day mark → outside 12-hour window
  21. let insertTime = Date().addingTimeInterval(-8 * 86400).timeIntervalSince1970
  22. let data = AlarmData.withSensorInsertTime(insertTime)
  23. #expect(!cond.evaluate(alarm: alarm, data: data, now: .init()))
  24. }
  25. // MARK: - 15-day lifetime
  26. @Test("fires when within threshold hours of 15-day expiry")
  27. func firesNear15DayExpiry() {
  28. let alarm = Alarm.sensorChange(threshold: 12, lifetimeDays: 15)
  29. // Sensor inserted 14 days and 13 hours ago → 11 hours until 15-day mark
  30. let insertTime = Date().addingTimeInterval(-14 * 86400 - 13 * 3600).timeIntervalSince1970
  31. let data = AlarmData.withSensorInsertTime(insertTime)
  32. #expect(cond.evaluate(alarm: alarm, data: data, now: .init()))
  33. }
  34. @Test("does NOT fire at day 10 when lifetime is 15 days")
  35. func doesNotFireAtDay10With15DayLifetime() {
  36. let alarm = Alarm.sensorChange(threshold: 12, lifetimeDays: 15)
  37. // Sensor inserted 10 days ago → 5 days until 15-day mark → should NOT fire
  38. let insertTime = Date().addingTimeInterval(-10 * 86400).timeIntervalSince1970
  39. let data = AlarmData.withSensorInsertTime(insertTime)
  40. #expect(!cond.evaluate(alarm: alarm, data: data, now: .init()))
  41. }
  42. // MARK: - Edge cases
  43. @Test("does NOT fire when sageInsertTime is nil")
  44. func ignoresMissingSensor() {
  45. let alarm = Alarm.sensorChange(threshold: 12)
  46. let data = AlarmData.withSensorInsertTime(nil)
  47. #expect(!cond.evaluate(alarm: alarm, data: data, now: .init()))
  48. }
  49. @Test("does NOT fire when sageInsertTime is zero (no sensor data)")
  50. func ignoresZeroInsertTime() {
  51. let alarm = Alarm.sensorChange(threshold: 12)
  52. let data = AlarmData.withSensorInsertTime(0)
  53. #expect(!cond.evaluate(alarm: alarm, data: data, now: .init()))
  54. }
  55. @Test("does NOT fire when threshold is nil")
  56. func ignoresNilThreshold() {
  57. let alarm = Alarm.sensorChange(threshold: nil)
  58. let insertTime = Date().addingTimeInterval(-11 * 86400).timeIntervalSince1970
  59. let data = AlarmData.withSensorInsertTime(insertTime)
  60. #expect(!cond.evaluate(alarm: alarm, data: data, now: .init()))
  61. }
  62. @Test("defaults to 10-day lifetime when sensorLifetimeDays is nil")
  63. func defaultsTo10Days() {
  64. let alarm = Alarm.sensorChange(threshold: 12, lifetimeDays: nil)
  65. // Sensor inserted 9 days and 13 hours ago → within 12-hour window of 10-day mark
  66. let insertTime = Date().addingTimeInterval(-9 * 86400 - 13 * 3600).timeIntervalSince1970
  67. let data = AlarmData.withSensorInsertTime(insertTime)
  68. #expect(cond.evaluate(alarm: alarm, data: data, now: .init()))
  69. }
  70. }