def save_value_to_fermentrack(self, verbose=False): if self.obj is None: # If we don't have a TiltConfiguration object loaded, we can't save the data point if verbose: print("{} Tilt: No object loaded for this color".format( self.color)) return False if self._cache_expired(): if verbose: print("{} Tilt: Cache is expired/No data available to save". format(self.color)) return False if self.smoothed_gravity() is None or self.smoothed_temp() is None: if verbose: print("{} Tilt: No data available to save".format(self.color)) return False # TODO - Test that temp_format actually works as intended here new_point = GravityLogPoint( gravity=self.smoothed_gravity(), gravity_latest=self.gravity, temp=self.smoothed_temp(), temp_latest=self.temp, temp_format=self.obj.sensor.temp_format, temp_is_estimate=False, associated_device=self.obj.sensor, ) if self.obj.sensor.active_log is not None: new_point.associated_log = self.obj.sensor.active_log new_point.save() # Also, set/save the RSSI/Raw Temp/Raw Gravity so we can load it for debugging self.obj.rssi = self.rssi self.obj.raw_gravity = self.raw_gravity self.obj.raw_temp = self.raw_temp self.obj.tilt_pro = self.tilt_pro self.obj.sends_battery = self.sends_battery self.obj.weeks_on_battery = self.weeks_on_battery self.obj.firmware_version = self.firmware_version self.obj.save_extras_to_redis() self.last_saved_value = datetime.datetime.now() if verbose: print("{} Tilt: Logging {}".format(self.color, self.smoothed_gravity())) else: if verbose: print("No data received.")
def ispindel_handler(request): if request.body is None: logger.error("No data in iSpindel request body") return JsonResponse( { 'status': 'failed', 'message': "No data in request body" }, safe=False, json_dumps_params={'indent': 4}) import pprint with open( os.path.join(settings.BASE_DIR, "log", 'ispindel_raw_output.log'), 'w') as logFile: pprint.pprint(request.body.decode('utf-8'), logFile) # As of the iSpindel firmware version 5.6.1, the json posted contains the following fields: # {u'ID': 3003098, # u'angle': 77.4576, # u'battery': 4.171011, # u'gravity': 27.22998, # u'name': u'iSpindel123', # u'temperature': 24.75, # u'token': u'tokengoeshere'} ispindel_data = json.loads(request.body.decode('utf-8')) with open( os.path.join(settings.BASE_DIR, "log", 'ispindel_json_output.log'), 'w') as logFile: pprint.pprint(ispindel_data, logFile) try: ispindel_obj = IspindelConfiguration.objects.get( name_on_device=ispindel_data['name']) except: logger.error(u"Unable to load sensor with name {}".format( ispindel_data['name'])) return JsonResponse( { 'status': 'failed', 'message': "Unable to load sensor with that name" }, safe=False, json_dumps_params={'indent': 4}) # Let's calculate the gravity using the coefficients stored in the ispindel configuration. This will allow us to # reconfigure on the fly. angle = float(ispindel_data['angle']) calculated_gravity = ispindel_obj.third_degree_coefficient * angle**3 calculated_gravity += ispindel_obj.second_degree_coefficient * angle**2 calculated_gravity += ispindel_obj.first_degree_coefficient * angle calculated_gravity += ispindel_obj.constant_term converted_temp, temp_format = ispindel_obj.sensor.convert_temp_to_sensor_format( float(ispindel_data['temperature']), getattr(ispindel_data, 'temp_units', 'C')) new_point = GravityLogPoint( gravity= calculated_gravity, # We're using the gravity we calc within Fermentrack temp=converted_temp, temp_format=temp_format, temp_is_estimate=False, associated_device=ispindel_obj.sensor, gravity_latest=calculated_gravity, temp_latest=converted_temp, extra_data=angle, ) if ispindel_obj.sensor.active_log is not None: new_point.associated_log = ispindel_obj.sensor.active_log new_point.save() # Set & save the 'extra' data points to redis (so we can load & use later) ispindel_obj.angle = angle if 'ID' in ispindel_data: ispindel_obj.ispindel_id = ispindel_data['ID'] if 'battery' in ispindel_data: ispindel_obj.battery = ispindel_data['battery'] if 'gravity' in ispindel_data: ispindel_obj.ispindel_gravity = ispindel_data['gravity'] if 'token' in ispindel_data: ispindel_obj.token = ispindel_data['token'] ispindel_obj.save_extras_to_redis() return JsonResponse({ 'status': 'ok', 'gravity': calculated_gravity }, safe=False, json_dumps_params={'indent': 4})
def tiltbridge_handler(request): if request.body is None: logger.error("No data in TiltBridge request body") return JsonResponse( { 'status': 'failed', 'message': "No data in request body" }, safe=False, json_dumps_params={'indent': 4}) # This should look like this: # { # 'mdns_id': 'mDNS ID goes here', # 'tilts': {'color': 'Purple', 'temp': 74, 'gravity': 1.043}, # {'color': 'Orange', 'temp': 66, 'gravity': 1.001} # } try: tiltbridge_data = json.loads(request.body.decode('utf-8')) except json.JSONDecodeError: return JsonResponse( { 'status': 'failed', 'message': "Malformed JSON - Unable to parse!" }, safe=False, json_dumps_params={'indent': 4}) try: if 'mdns_id' in tiltbridge_data: tiltbridge_obj = TiltBridge.objects.get( mdns_id=tiltbridge_data['mdns_id']) else: logger.error(u"Malformed TiltBridge JSON - No mdns ID provided!") return JsonResponse( { 'status': 'failed', 'message': "Malformed JSON - No mDNS ID provided!" }, safe=False, json_dumps_params={'indent': 4}) except ObjectDoesNotExist: logger.error(u"Unable to load TiltBridge with mDNS ID {}".format( tiltbridge_data['mdns_id'])) return JsonResponse( { 'status': 'failed', 'message': "Unable to load TiltBridge with that mdns_id" }, safe=False, json_dumps_params={'indent': 4}) if tiltbridge_data['tilts'] is None: # The TiltBridge has no connected Tilts. Return success (but note as such) return JsonResponse( { 'status': 'success', 'message': "No Tilts in TiltBridge data to process" }, safe=False, json_dumps_params={'indent': 4}) for this_tilt in tiltbridge_data['tilts']: try: tilt_obj = TiltConfiguration.objects.get( connection_type=TiltConfiguration.CONNECTION_BRIDGE, tiltbridge=tiltbridge_obj, color__iexact=this_tilt) except ObjectDoesNotExist: # We received data for an invalid tilt from TiltBridge continue raw_temp = float(tiltbridge_data['tilts'][this_tilt]['temp']) converted_temp, temp_format = tilt_obj.sensor.convert_temp_to_sensor_format( float(raw_temp), tiltbridge_data['tilts'][this_tilt]['tempUnit']) raw_gravity = float(tiltbridge_data['tilts'][this_tilt]['gravity']) normalized_gravity = tilt_obj.apply_gravity_calibration(raw_gravity) new_point = GravityLogPoint( gravity=normalized_gravity, temp=converted_temp, temp_format=temp_format, temp_is_estimate=False, associated_device=tilt_obj.sensor, gravity_latest=normalized_gravity, temp_latest=converted_temp, ) if tilt_obj.sensor.active_log is not None: new_point.associated_log = tilt_obj.sensor.active_log new_point.save() # Now that the point is saved, save out the 'extra' data so we can use it later for calibration tilt_obj.raw_gravity = raw_gravity tilt_obj.raw_temp = raw_temp # TODO - Determine if we want to record this in F or sensor_format tilt_obj.save_extras_to_redis() return JsonResponse( { 'status': 'success', 'message': "TiltBridge data processed successfully" }, safe=False, json_dumps_params={'indent': 4})
def ispindel_handler(request): if request.body is None: logger.error("No data in iSpindel request body") return JsonResponse( { 'status': 'failed', 'message': "No data in request body" }, safe=False, json_dumps_params={'indent': 4}) import pprint with open( os.path.join(settings.BASE_DIR, "log", 'ispindel_raw_output.log'), 'w') as logFile: pprint.pprint(request.body.decode('utf-8'), logFile) # As of the iSpindel firmware version 5.6.1, the json posted contains the following fields: # {u'ID': 3003098, # u'angle': 77.4576, # u'battery': 4.171011, # u'gravity': 27.22998, # u'name': u'iSpindel123', # u'temperature': 24.75, # u'token': u'tokengoeshere'} # As of iSpindel 6.2.0 it looks like this: # {"name":"iSpindel001","ID":9390968,"token":"fermentrack","angle":68.81093,"temperature":73.175,"temp_units":"F","battery":4.103232,"gravity":22.80585,"interval":20,"RSSI":-41} try: ispindel_data = json.loads(request.body.decode('utf-8')) except json.JSONDecodeError: return JsonResponse( { 'status': 'failed', 'message': "No JSON data was posted (are you accessing this manually?)" }, safe=False, json_dumps_params={'indent': 4}) with open( os.path.join(settings.BASE_DIR, "log", 'ispindel_json_output.log'), 'w') as logFile: pprint.pprint(ispindel_data, logFile) try: ispindel_obj = IspindelConfiguration.objects.get( name_on_device=ispindel_data['name']) except: logger.error(u"Unable to load sensor with name {}".format( ispindel_data['name'])) return JsonResponse( { 'status': 'failed', 'message': "Unable to load sensor with that name" }, safe=False, json_dumps_params={'indent': 4}) # Let's calculate the gravity using the coefficients stored in the ispindel configuration. This will allow us to # reconfigure on the fly. angle = float(ispindel_data['angle']) calculated_gravity = ispindel_obj.third_degree_coefficient * angle**3 calculated_gravity += ispindel_obj.second_degree_coefficient * angle**2 calculated_gravity += ispindel_obj.first_degree_coefficient * angle calculated_gravity += ispindel_obj.constant_term if 'temp_units' in ispindel_data: # If we were provided temp units, use them ispindel_temp_units = ispindel_data['temp_units'] else: # Default to celsius ispindel_temp_units = 'C' converted_temp, temp_format = ispindel_obj.sensor.convert_temp_to_sensor_format( float(ispindel_data['temperature']), ispindel_temp_units) new_point = GravityLogPoint( gravity= calculated_gravity, # We're using the gravity we calc within Fermentrack temp=converted_temp, temp_format=temp_format, temp_is_estimate=False, associated_device=ispindel_obj.sensor, gravity_latest=calculated_gravity, temp_latest=converted_temp, extra_data=angle, ) if ispindel_obj.sensor.active_log is not None: new_point.associated_log = ispindel_obj.sensor.active_log new_point.save() # Set & save the 'extra' data points to redis (so we can load & use later) ispindel_obj.angle = angle if 'ID' in ispindel_data: ispindel_obj.ispindel_id = ispindel_data['ID'] if 'battery' in ispindel_data: ispindel_obj.battery = ispindel_data['battery'] if 'gravity' in ispindel_data: ispindel_obj.ispindel_gravity = ispindel_data['gravity'] if 'token' in ispindel_data: ispindel_obj.token = ispindel_data['token'] ispindel_obj.save_extras_to_redis() return JsonResponse({ 'status': 'ok', 'gravity': calculated_gravity }, safe=False, json_dumps_params={'indent': 4})
def ispindel_handler(request): if request.body is None: # TODO - Log this return JsonResponse( { 'status': 'failed', 'message': "No data in request body" }, safe=False, json_dumps_params={'indent': 4}) # import pprint # with open('ispindel_json_output.txt', 'w') as logFile: # pprint.pprint(ispindel_data, logFile) # As of the iSpindel firmware version 5.6.1, the json posted contains the following fields: # {u'ID': 3003098, # u'angle': 77.4576, # u'battery': 4.171011, # u'gravity': 27.22998, # u'name': u'iSpindel123', # u'temperature': 24.75, # u'token': u'tokengoeshere'} ispindel_data = json.loads(request.body.decode('utf-8')) try: ispindel_obj = IspindelConfiguration.objects.get( name_on_device=ispindel_data['name']) except: # TODO - Log This messages.error( request, u'Unable to load sensor with name {}'.format( ispindel_data['name'])) return JsonResponse( { 'status': 'failed', 'message': "Unable to load sensor with that name" }, safe=False, json_dumps_params={'indent': 4}) # Let's calculate the gravity using the coefficients stored in the ispindel configuration. This will allow us to # reconfigure on the fly. calculated_gravity = ispindel_obj.third_degree_coefficient * ispindel_data[ 'angle']**3 calculated_gravity += ispindel_obj.second_degree_coefficient * ispindel_data[ 'angle']**2 calculated_gravity += ispindel_obj.first_degree_coefficient * ispindel_data[ 'angle'] calculated_gravity += ispindel_obj.constant_term # iSpindel devices always report temp in celsius. Convert to the user's preferred temp format converted_temp, temp_format = ispindel_obj.sensor.convert_temp_to_sensor_format( ispindel_data['temperature'], 'C') new_point = GravityLogPoint( gravity= calculated_gravity, # We're using the gravity we calc within Fermentrack temp=converted_temp, temp_format=temp_format, temp_is_estimate=False, associated_device=ispindel_obj.sensor, gravity_latest=calculated_gravity, temp_latest=ispindel_data['temperature'], extra_data=ispindel_data['angle'], ) if ispindel_obj.sensor.active_log is not None: new_point.associated_log = ispindel_obj.sensor.active_log new_point.save() # Set & save the 'extra' data points to redis (so we can load & use later) if 'angle' in ispindel_data: ispindel_obj.angle = ispindel_data['angle'] if 'ID' in ispindel_data: ispindel_obj.ispindel_id = ispindel_data['ID'] if 'battery' in ispindel_data: ispindel_obj.battery = ispindel_data['battery'] if 'gravity' in ispindel_data: ispindel_obj.ispindel_gravity = ispindel_data['gravity'] if 'token' in ispindel_data: ispindel_obj.token = ispindel_data['token'] ispindel_obj.save_extras_to_redis() return JsonResponse({ 'status': 'ok', 'gravity': calculated_gravity }, safe=False, json_dumps_params={'indent': 4})
def tiltbridge_handler(request): if request.body is None: logger.error("No data in TiltBridge request body") return JsonResponse({'status': 'failed', 'message': "No data in request body"}, safe=False, json_dumps_params={'indent': 4}) import pprint with open(os.path.join(settings.BASE_DIR, "log", 'tiltbridge_raw_output.log'), 'w') as logFile: pprint.pprint(request.body.decode('utf-8'), logFile) # This should look like this (while testing only): # { # 'api_key': 'Key Goes Here', # 'tilts': {'color': 'Purple', 'temp': 74, 'gravity': 1.043}, # {'color': 'Orange', 'temp': 66, 'gravity': 1.001} # } tiltbridge_data = json.loads(request.body.decode('utf-8')) with open(os.path.join(settings.BASE_DIR, "log", 'tiltbridge_json_output.log'), 'w') as logFile: pprint.pprint(tiltbridge_data, logFile) try: if 'api_key' in tiltbridge_data: tiltbridge_obj = TiltBridge.objects.get(api_key=tiltbridge_data['api_key']) else: logger.error(u"Malformed TiltBridge JSON - No key provided!") return JsonResponse({'status': 'failed', 'message': "Malformed JSON - No api_key provided!"}, safe=False, json_dumps_params={'indent': 4}) except ObjectDoesNotExist: logger.error(u"Unable to load TiltBridge with key {}".format(tiltbridge_data['api_key'])) return JsonResponse({'status': 'failed', 'message': "Unable to load TiltBridge with that name"}, safe=False, json_dumps_params={'indent': 4}) for this_tilt in tiltbridge_data['tilts']: try: tilt_obj = TiltConfiguration.objects.get(connection_type=TiltConfiguration.CONNECTION_BRIDGE, tiltbridge=tiltbridge_obj, color__iexact=this_tilt) raw_temp = tiltbridge_data['tilts'][this_tilt]['temp'] converted_temp, temp_format = tilt_obj.sensor.convert_temp_to_sensor_format(float(raw_temp), 'F') raw_gravity = 0 normalized_gravity = tilt_obj.apply_gravity_calibration(raw_gravity) # TODO - Use the calibration function to recalculate gravity new_point = GravityLogPoint( gravity=normalized_gravity, temp=converted_temp, temp_format=temp_format, temp_is_estimate=False, associated_device=tilt_obj.sensor, gravity_latest=normalized_gravity, temp_latest=converted_temp, ) if tilt_obj.sensor.active_log is not None: new_point.associated_log = tilt_obj.sensor.active_log new_point.save() # Now that the point is saved, save out the 'extra' data so we can use it later for calibration tilt_obj.raw_gravity = raw_gravity tilt_obj.raw_temp = raw_temp # TODO - Determine if we want to record this in F or sensor_format tilt_obj.save_extras_to_redis() except ObjectDoesNotExist: # We received data for an invalid tilt from TiltBridge pass return JsonResponse({'status': 'success', 'message': "TiltBridge data processed successfully"}, safe=False, json_dumps_params={'indent': 4})