Fabrication industrielle
Internet des objets industriel | Matériaux industriels | Entretien et réparation d'équipement | Programmation industrielle |
home  MfgRobots >> Fabrication industrielle >  >> Manufacturing Technology >> Processus de fabrication

Moniteur de tension du thermocouple du chauffe-eau

Composants et fournitures

Adafruit Raspberry Pi Zero WH
× 1
Arduino Nano R3
× 1

À propos de ce projet

Système de surveillance de la veilleuse du chauffe-eau

Les chauffe-eau à gaz traditionnels maintiennent une veilleuse 24x7. Cette veilleuse chauffe un thermocouple qui génère une faible tension (jusqu'à 30 millivolts). Cette tension est utilisée par le thermostat du chauffe-eau pour maintenir ouverte une vanne de gaz. Si la veilleuse s'éteint, la tension s'arrête et le robinet de gaz se ferme automatiquement.

Dans mon chauffe-eau, la veilleuse s'éteint de temps en temps. Comme cela ne se produit que 3 fois par an environ, je ne veux pas remplacer le chauffe-eau coûteux. J'ai essayé de remplacer le thermocouple, mais cela n'a pas résolu le problème.

Ma solution :surveiller la tension générée par le thermocouple. S'il tombe à zéro, envoyez des SMS et des e-mails pour que je puisse rallumer la veilleuse. N'oubliez pas qu'il n'y a aucun risque de fuite de gaz ici, car la vanne de gaz se fermera chaque fois que la tension du thermocouple tombe à zéro.

Présentation

Un Raspberry Pi Zero WH sera utilisé pour envoyer des e-mails et des SMS lorsque la veilleuse s'éteindra. Parce que le Raspberry Pi n'a pas de moyen de mesurer la tension, un Arduino Nano est utilisé pour surveiller la tension du thermocouple.

Les Arduinos ont des convertisseurs analogique-numérique (ADC) qui peuvent lire une tension et la convertir en un nombre compris entre 0 et 1023. Dans ce projet, l'Arduino lit la tension du thermocouple et communique cette valeur au Raspberry Pi. Le Raspberry Pi reçoit la lecture de tension et l'interprète. Si la valeur est trop faible, nous supposons que la veilleuse s'est éteinte et envoyons des notifications.

Étape 1 :Préparez votre Raspberry Pi

Installez et exécutez le Raspberry Pi sur votre réseau (vous pouvez consulter mon autre projet pour obtenir des instructions pour le faire).

Créez un programme Python qui recevra les lectures de tension de l'Arduino. Le programme bouclera et enverra des notifications lorsque la lecture de tension est trop basse. Le code source est joint.

Étape 2 :préparez votre Arduino

J'ai acheté des Arduino Nano chinois bon marché, il a donc fallu quelques essais et erreurs pour les faire fonctionner avec mon ordinateur Windows 10.

Chargez l'Arduino avec un croquis pour mesurer la tension sur sa broche d'entrée toutes les 30 secondes. L'Arduino peut mesurer une tension comprise entre 0 et une tension de référence. On peut sélectionner 1.1V ou 5V comme tension de référence. Étant donné que le thermocouple ne produit que 30 millivolts au maximum, nous utiliserons la tension de référence de 1,1 V pour une meilleure résolution. L'Arduino ADC sort 0 pour 0V et 1023 pour 1.1V. Comme mentionné, le thermocouple produit au plus 30 millivolts, donc la lecture sera de 28 ou moins.

Étape 3 :connectez l'Arduino à la source de tension

Le thermocouple envoie la tension au thermostat du chauffe-eau via un fil coaxial. L'extérieur du fil est positif.

Coupez le fil à environ 5 pouces du thermostat du chauffe-eau. Coupez un peu l'extérieur du fil coaxial pour que le fil du milieu soit accessible. Ne détruisez pas l'isolant peint sur le fil du milieu. Nous ne voulons pas que le fil du milieu court-circuite à l'extérieur du fil coaxial.

Connectez le fil de manière à ce qu'il fournisse la tension positive au thermostat du chauffe-eau et à la broche d'entrée Arduino. J'ai utilisé la broche d'entrée A0. Le côté négatif de la source de tension doit être connecté à la terre de l'Arduino, ainsi que le côté négatif du thermostat du chauffe-eau.

J'ai utilisé des fils de 1 pied de long avec des pinces crocodiles aux extrémités pour faire les connexions.

Étape 4 :connectez l'Arduino au Raspberry Pi

Notre croquis exécuté sur l'Arduino transmettra le numéro de tension de l'ADC au Raspberry Pi. L'Arduino enverra le signal en sortie de sa broche numérique 9.

Les Arduinos envoient des signaux à +5V. Le Raspberry Pi ne peut recevoir qu'une entrée 3V. Par conséquent, entre l'Arduino et le Raspberry Pi, il doit y avoir un diviseur de tension. Cela réduit la tension de 5 V à environ 2,8 V.

Un diviseur de tension est un système de résistances qui réduisent la tension d'entrée.

La tension de sortie est déterminée par la relation du diviseur de tension.

On ne peut pas utiliser une seule résistance pour réduire la tension car lorsqu'aucun courant ne circule, la tension des deux côtés de la résistance sera Vin (5V). L'utilisation d'un diviseur de tension réduira la tension même en l'absence de courant.

Les fils de terre de tout doivent être connectés. Voir le schéma de connexion.

Étape 5 :Arduino transmet la mesure de tension

Toutes les 30 secondes, l'esquisse Arduino obtient la mesure de tension de l'ADC et transmet le nombre au Raspberry Pi. J'ai décidé d'utiliser un système de signalisation primitif à un fil de la broche Arduino 9 à la broche 16 Raspberry Pi.

Étape 6 :Raspberry Pi reçoit la mesure de tension

Le Raspberry Pi utilise un programme Python avec une boucle infinie pour écouter les fronts montants sur la broche 16. Lorsqu'un front montant est détecté, on suppose que l'Arduino a commencé à transmettre un nombre.

Système de signalisation
Transmettez un numéro à deux chiffres (ex :"12"). Chaque chiffre est précédé d'une impulsion positive reçue sur la broche 16. Les impulsions positives suivantes séparées de moins de 20 millisecondes (ms) incrémentent la valeur de ce chiffre. Une pause de plus de 40 ms indique que ce chiffre est terminé et que le chiffre suivant commence. Une autre pause de plus de 40 ms indique que le deuxième chiffre est terminé. Le nombre entier à deux chiffres est maintenant complet.

Dans le code Python exécuté sur le Raspberry Pi, le nombre reçu de l'Arduino est renvoyé par la méthode qui interprète les signaux de l'Arduino. Un autre code Python décide si une notification doit être envoyée ou non. Ensuite, le code retourne à l'attente du prochain front montant sur la broche 16.

Étape 7 :envoyer la notification

Si la tension est trop faible, incrémentez le compteur faible. Un faible nombre est maintenu pour éviter les fausses alarmes. Si le nombre bas atteint 5, alors la tension a été basse pendant 5 mesures. Chaque mesure est espacée de 30 secondes. Envoyez la notification et réinitialisez le nombre bas. Les notifications sont envoyées à l'aide de smtplib et d'un compte Gmail. Un horodatage est stocké dans le code Python lorsque la notification est envoyée. La prochaine notification ne sera pas envoyée avant 6 heures.

Pour envoyer des alertes SMS, j'ai utilisé une fonctionnalité fournie par la plupart des fournisseurs de téléphonie mobile :la possibilité d'envoyer un SMS par e-mail à leurs utilisateurs. Ex :pour Verizon :[email protected] envoie un SMS à ce numéro.

Gmail
J'ai créé un nouveau compte Gmail à utiliser pour envoyer les notifications. Au début, j'ai configuré les paramètres de sécurité de ce compte Gmail pour autoriser un accès « moins sécurisé », afin que le code Python puisse envoyer des e-mails. Cependant, après quelques mois, Gmail peut désactiver cet accès moins sécurisé. J'ai découvert que Gmail préfère que les utilisateurs utilisent des mots de passe d'application.

Configuration d'un mot de passe d'application
https://support.google.com/accounts/answer/185833

Étape 8 :Tout connecter

Connectez l'Arduino au fil du thermocouple du chauffe-eau et au Raspberry Pi via le diviseur de tension. (La partie supérieure de mon diviseur de tension utilise deux résistances qui totalisent 550 ohms, car ce sont les résistances que j'avais sous la main.) Allumez l'Arduino et il commencera à mesurer la tension et à envoyer des signaux au Raspberry Pi toutes les 30 secondes.

Étape 9 :Exécutez le programme Python

  • Créez un script qui lance votre programme Python.
  • Modifiez la crontab racine pour exécuter automatiquement votre script au démarrage. Modifiez les chemins de répertoire en fonction de votre Raspberry Pi et de l'emplacement où vous avez enregistré le programme Python.
  • Pour modifier la crontab :
    sudo crontab -e
  • Ajoutez une ligne pour exécuter votre script 'kick-off' lorsque le Raspberry Pi est redémarré :
    @reboot sh /home/pi/hotwater/run_HotWaterNotifier.sh>> /home/pi/hotwater /logs/HotWaterNotifier.log 2>&1
  • Pour exécuter manuellement (avant d'avoir la configuration de crontab)
    Exécutez d'abord le processus (exécutez votre script run_HotWaterNotifier.sh)
    Ensuite, tapez ctrl-Z pour suspendre votre processus
    Ensuite, tapez bg une ou deux fois pour envoyer le processus en arrière-plan
    Tapez disown , cela permet au processus de continuer à s'exécuter après votre déconnexion
  • Pour voir si le processus est toujours en cours d'exécution
    ps aux | grep -i Eau Chaude


Code

  • Code Arduino
  • Code Phython
  • Script pour démarrer le code Python
Code ArduinoArduino
Celui-ci lit la tension toutes les 30 secondes et envoie des signaux au Raspberry Pi
/************************************ ************************************************* HotWaterHeater Mesure la tension provenant du thermocouple du chauffe-eau. Utilise la signalisation pour envoyer cette mesure de capteur de tension au Raspberry Pi. ******************************************************** ************************** ///double ReferenceVoltage =5.0 ; //tension de référence inutiliséedouble ReferenceVoltage =1.1;int OUTPUT_PIN =9;int INTRA_DIGIT_WAIT=20;int BETWEEN_DIGIT_WAIT=50;///////////////////////// ////////////////////////////////////////////////////////////// ///// la fonction de configuration s'exécute une fois lorsque vous appuyez sur reset ou mettez la carte sous tension///////////////////////////// ///////////////////////////////////////////////void setup( ) { // initialise la broche numérique LED_BUILTIN en tant que sortie. pinMode(LED_BUILTIN, SORTIE); pinMode(OUTPUT_PIN, SORTIE); // définit la broche numérique 9 comme sortie analogReference(INTERNAL); Serial.begin(9600); // ouvre le port série, définit le débit de données à 9600 bps}//////////////////////////////////// ///////////////////////////////////////// La fonction de boucle passe encore une fois pour toujours.// Mesurez la tension sur la broche d'entrée.// Envoyez ensuite cette lecture au Raspberry Pi//////////////////////// ////////////////////////////////////////////////////////////// ///boucle vide() { int pinInput; double tension; pinInput =analogRead (A0) ; // Sonde d'entrée Serial.print("PinInputA0="); Serial.print(pinInput); // L'Arduino ADC est un convertisseur dix bits, ce qui signifie que la valeur de sortie sera comprise entre 0 et 1023 voltage =(pinInput * ReferenceVoltage ) / 1023; Serial.print(", voltageA0="); Serial.println(tension); //Remarque :une lecture de 5 =5,38 mV sendNumberSignal(pinInput, OUTPUT_PIN, INTRA_DIGIT_WAIT, BETWEEN_DIGIT_WAIT); //Exécuter le contrôle une fois toutes les 30 secondes de délai (30000);}/************************************ ******************************************** * Signalez un numéro sur un fil unique. * * Pour chaque chiffre, envoyez une série d'impulsions. * Il y a aussi une impulsion de lancement initiale. * Chaque impulsion ressemble à :__/ 20ms \__20ms__ * 20+20ms entre les fronts montants au sein d'un même chiffre * * Entre les chiffres :__/ 20ms \__20ms__ 50ms___ * 20+20+50ms entre les chiffres ********* ******************************************************** ******************/void sendNumberSignal(int number, int pin, int intraDigitWait, int betweenDigitWait) { int dizaines =nombre/10 ; uns entiers =nombre % 10 ; Serial.print("Signalisation :"); Serial.println(numéro); // débogage //////// //Serial.print("tens:"); //Série.println(dizaines); //Serial.print("uns:"); //Série.println(uns); //Serial.print("millis:"); //Série.println(millis()); // débogage //////// //Serial.println("envoyer des dizaines"); //Serial.print("millis:"); //Série.println(millis()); //envoyer le nombre des dizaines sendPulse(pin, intraDigitWait); for (int i=0; i 
Code PhythonPython
Ce code reçoit des signaux de l'Arduino. Il interprète les signaux en une lecture de tension. Il décide alors si la tension est trop basse. Si la tension est trop basse, il envoie des e-mails et des SMS.
################################## ############################################### HotWaterNotifier.py# Surveillez la broche d'entrée et recevez les signaux d'un Arduino. # Décodez les signaux en mesures de capteurs de tension numériques. # Lorsque la lecture de la tension reçue est trop faible, cela indique que le voyant # est éteint. Lorsque cela se produit pour 5 mesures consécutives, supposez que# la veilleuse est vraiment éteinte. Envoyez des e-mails/textos et enregistrez l'heure.# N'envoyez un e-mail/texte que toutes les six heures.## Ceci a été écrit pour Python 2.7. Des modifications mineures peuvent être nécessaires pour Python 3.########################################## ########################################importer smtplibimport RPi.GPIO as GPIOimport osimport os.pathimport timeimport datetimeimport stringimport loggingimport sys#Input GPIO pour recevoir les signaux de l'ArduinoGPIO_Alert=16# Combien d'heures d'attente entre les e-mailsemailWaitHours=6# Lecture du capteur basse tension.# Inférieur ou égal à ceci est une basse tension.lowSensorReading=1# Une fois ce nombre bas les lectures du capteur sont atteintes, envoyez l'alertemaxLowVoltageCount=5# pour la numérotation GPIO, choisissez BCMGPIO.setmode(GPIO.BCM)GPIO.setup(GPIO_Alert, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)lastEmailSentTime =datetime.datetime(2000,1, 1,0,0,0,0) #déclarer la variable globale#################################### ############################################# Configurer l'enregistreur.## ##################################################### ##########################def setup_custom_logger(name):formatter =logging.Formatter(fmt='%(asctime)s %(levelname )-8s %( message)s', datefmt='%Y-%m-%d %H:%M:%S') handler =logging.FileHandler('HotWaterLog.txt', mode='a') handler.setFormatter(formatter) screen_handler =logging.StreamHandler(stream=sys.stdout) screen_handler.setFormatter(formatter) logger =logging.getLogger(name) logger.setLevel(logging.DEBUG) logger.addHandler(handler) logger.addHandler(screen_handler) return logger## ##################################################### ############################# Fonction d'envoi d'emails/sms################ ##################################################### ############def send_email_alert() :# autorise l'écriture dans la variable globale global lastEmailSentTime # vérifie si suffisamment de temps s'est écoulé depuis le dernier e-mail nowTime =datetime.datetime.now() emailWaitDelta =datetime .timedelta(hours=emailWaitHours) limitTime =nowTime - emailWaitDelta #si suffisamment de temps s'est écoulé, envoyez l'e-mail. si lastEmailSentTime est None ou limitTime> lastEmailSentTime:logger.info('Envoi d'une alerte par e-mail...') HOST ="smtp.gmail.com" PORT =587 SUBJECT ="Alerte chauffe-eau" #Ceci devrait être un objet de liste pour plusieurs adresses TO =["[email protected]", "[email protected]"] #TO =["[email protected]"] FROM ="[email protected]" PWD ="XXXXXXXXXXXXXX" text =" Basse tension mesurée sur le chauffe-eau" #Le champ à est joint en 1 chaîne ici. #C'est ce qui est affiché au destinataire sur son email. BODY =string.join(("de :%s" %FROM, "to :%s" %", ".join(TO), "Sujet :%s" %SUBJECT, " ", texte), "\r \n") essayez :s =smtplib.SMTP(HOST,PORT) s.set_debuglevel(1) s.ehlo() s.starttls() s.login(FROM, PWD) s.sendmail(FROM,TO,BODY) s.quit except Exception as e:logger.exception('Exception intercepté fichier envoyant un e-mail. Essayer à nouveau dans 6 heures') #définir l'heure pour qu'un e-mail ne soit pas envoyé pendant 6 heures lastEmailSentTime =nowTime else:logger.info(' Pas d'envoi d'e-mail. Dernier e-mail envoyé à :' + lastEmailSentTime.strftime("%Y-%m-%d %H:%M:%S"))################ ##################################################### ############### Recevoir des signaux de l'Arduino.# Un nombre est composé de deux chiffres. (un chiffre des dizaines et un chiffre des unités)# L'Arduino transmet toujours un nombre, composé de 2 chiffres.# Les signaux reçus sont une série d'impulsions hautes sur la broche d'entrée.# La méthode waitReceiveNumber() compte les impulsions hautes et le [compte -1] est# la valeur du chiffre.# Chaque chiffre est précédé d'1 impulsion.## 70 ms max entre les fronts du signal dans le même chiffre# les fronts montants séparés par moins de 70 ms sont le même chiffre# s'ils sont supérieurs plus de 70 ms, puis passez au chiffre suivant # 200 ms signifie que le nombre est complet################################## ###############################################def waitReceiveNumber(GPIO_Alert ):lastSignalTime =datetime.datetime(2000,1,1,0,0,0,0) isTens=True isFirstIteration=True tensValue=0 onesValue=0 receiveEdge=None #Moins de 70ms entre les impulsions :c'est toujours le même chiffre en cours de transmission # Incrémenter la valeur du chiffre actuel #Plus de 70ms :passer au chiffre suivant singleDigitMilliseconds =datetime.timedelta(milliseconds=70) #If this timeout est atteint, c'est la fin du nombre wholeNumberWaitTime =200 # attendez ici qu'un front montant soit détecté #logger.info('Waiting on GPIO pin:' + str(GPIO_Alert)) tandis que True:#Arduino envoie une impulsion lorsque vous flashez cela, démarrez le Raspberry Pi en second. #L'Arduino devrait démarrer plus rapidement en cas de panne de courant. if isFirstIteration :receiveEdge =GPIO.wait_for_edge(GPIO_Alert, GPIO.RISING, timeout=-1) # attend indéfiniment jusqu'à ce qu'une impulsion de lancement else :receiveEdge =GPIO.wait_for_edge(GPIO_Alert, GPIO.RISING, timeout=wholeNumberWaitTime) #wait for jusqu'à waitTime ms #calculer les métriques de synchronisation pour ce signal signalTime =datetime.datetime.now() signalInterval =signalTime - lastSignalTime lastSignalTime =signalTime #debugging:logger.info('signalInterval:' + str(signalInterval.total_seconds() * 1000 )) #déterminer quel chiffre incrémenter si (signalInterval =singleNumberMilliseconds :if isTens :#shift to ones isTens =False onesValue+=1 else:#isOnes #ne peut pas passer au chiffre suivant, donc le nombre est complet. #Cela ne devrait pas arriver. Une fois le nombre terminé, #l'attente devrait expirer et receiveEdge devrait être Aucun. return ((tensValue -1)*10) + (onesValue -1) else:#timeout, donc le nombre est complet. return ((tensValue -1)*10) + (onesValue -1)################################## ############################################### La méthode principale# ##################################################### ############################def main() :logger.info('Starting HotWaterNotifier') referenceVoltage =1.1 lowVoltageCount=0 essayez :while True:#Cela bloquera jusqu'à ce qu'il reçoive des signaux de l'Arduino. #Il ne reviendra qu'une fois qu'un numéro complété sera reçu. sensorReading =waitReceiveNumber(GPIO_Alert) #calculer la tension à partir de la tension de lecture du capteur Arduino =(sensorReading * referenceVoltage ) / 1023; logger.info('sensorReading:' + str(sensorReading) + ', voltage:' + str(voltage)) if sensorReading <=lowSensorReading:lowVoltageCount+=1 #increment if lowVoltageCount>=maxLowVoltageCount:logger.info('Alerte basse tension ') send_email_alert() lowVoltageCount=0 #réinitialiser le compteur car nous avons envoyé une alerte else :lowVoltageCount=0 #réinitialiser le compteur car une bonne tension a été reçue sauf KeyboardInterrupt :logger.info('Keyboard interrupt receive') GPIO.cleanup() # nettoie GPIO sur CTRL+C exit GPIO.cleanup() # nettoie GPIO################################ ################################################ Le test méthode email################################################## ##############################def testEmail() :logger.info('Starting HotWaterNotifier') referenceVoltage =1.1 lowVoltageCount=0 essayez :send_email_alert() sauf KeyboardInterrupt :logger.info('Interruption clavier reçue') GPIO.cleanup() # nettoie GPIO sur CTRL+C exit GPIO.cleanup() # nettoie GPIO######## ############ ##################################################### ########### Une variable globale###################################### ############################################ Configurer un fichier journal logger =setup_custom_logger ('HotWaterNotifier')############################################## #################################### Appelez la méthode principale.## Appelez testEmail() ici à la place si vous voulez tester la capacité de messagerie.############################################ #####################################if __name__=="__main__":main()
Script pour démarrer le code PythonSH
C'est le script que crontab appelle pour démarrer le code Python
#!/bin/bash# run_HotWaterNotifier.sh# Lancer le notifiercd /home/pi/hotwatersudo python HotWaterNotifier.py

Processus de fabrication

  1. Surveillance de la température ambiante avec Moteino's et Raspberry Pi
  2. Créer un moniteur Ambilight à l'aide d'Arduino
  3. Acquisition de données en temps réel d'un panneau solaire à l'aide d'Arduino
  4. Capturer les gouttes d'eau avec Arduino
  5. Comment créer un moniteur d'énergie et un enregistreur de données Arduino
  6. Moniteur de fréquence cardiaque utilisant l'IoT
  7. L'eau chaude parfaite de la pompe à chaleur
  8. Comment choisir la meilleure pompe à eau chaude sanitaire ?
  9. Une introduction à la pompe à eau chaude