Bidh sinn a’ ceangal a’ mheatair uisge ris an dachaigh spaideil

Uair dhe na h-uairean, bha siostaman fèin-ghluasaid dachaigh, no “dachaigh smart” mar a chanar riutha gu tric, gu math daor agus cha b’ urrainn ach na daoine beairteach am pàigheadh. An-diugh air a 'mhargaid gheibh thu innealan gu math saor le mothachaidhean, putanan / suidsichean agus actuators airson smachd a chumail air solais, socaidean, fionnarachadh, solar uisge agus luchd-cleachdaidh eile. Agus faodaidh eadhon an neach DIY as cam a dhol an sàs ann am bòidhchead agus innealan a chruinneachadh airson dachaigh spaideil aig prìs saor.

Bidh sinn a’ ceangal a’ mheatair uisge ris an dachaigh spaideil

Mar as trice, is e mothachairean no actuators a th’ anns na h-innealan a thathar a’ moladh. Bidh iad ga dhèanamh furasta suidheachaidhean a chuir an gnìomh mar “nuair a thèid mothachadh gluasad a phiobrachadh, tionndaidh air na solais” no “bidh an suidse faisg air an t-slighe a-mach a’ tionndadh na solais san àros gu lèir. ” Ach dòigh air choireigin cha do dh’obraich cùisean a-mach le telemetry. Aig a’ char as fheàrr, is e graf de theodhachd is taiseachd a th’ ann, no cumhachd sa bhad aig ionad sònraichte.

O chionn ghoirid chuir mi a-steach meatairean uisge le toradh pulse. Airson gach liotair a thèid tron ​​​​mheatair, tha an tionndadh cuilc air a chuir an gnìomh agus a’ dùnadh an neach-conaltraidh. Is e an aon rud a tha air fhàgail ri dhèanamh cumail ris na uèirichean agus feuchainn ri buannachd fhaighinn às. Mar eisimpleir, dèan sgrùdadh air caitheamh uisge a rèir uair agus latha den t-seachdain. Uill, ma tha grunn risers uisge anns an àros, tha e nas freagarraiche na taisbeanairean gnàthach uile fhaicinn air aon scrion na bhith a ’dìreadh a-steach do raointean duilich a ruighinn le flashlight.

Fon gearradh tha an dreach agam de inneal stèidhichte air ESP8266, a bhios a’ cunntadh buillean bho mheatairean uisge agus a’ cur leughaidhean tro MQTT chun t-seirbheisiche dachaigh smart. Nì sinn prògramadh ann am micropython a’ cleachdadh leabharlann uasyncio. Nuair a chruthaich mi am firmware, thàinig mi tarsainn air grunn dhuilgheadasan inntinneach, air am bi mi a’ bruidhinn san artaigil seo cuideachd. Rach!

An sgeama

Bidh sinn a’ ceangal a’ mheatair uisge ris an dachaigh spaideil

Tha cridhe a’ chuairt gu lèir na mhodal air microcontroller ESP8266. Bha ESP-12 air a phlanadh an toiseach, ach thionndaidh mi a-mach gu robh e uireasbhuidh. Dh'fheumadh sinn a bhith riaraichte leis a 'mhodal ESP-07, a bha ri fhaighinn. Gu fortanach, tha iad mar an ceudna an dà chuid a thaobh prìneachan agus gnìomhachd, tha an aon eadar-dhealachadh anns an antenna - tha fear a-staigh aig an ESP-12, agus tha fear a-muigh aig an ESP-07. Ach, eadhon às aonais antenna WiFi, gheibhear an comharra anns an t-seòmar-ionnlaid agam gu h-àbhaisteach.

sreangadh modal àbhaisteach:

  • putan ath-shuidheachadh le tarraing suas agus capacitor (ged a tha an dà chuid taobh a-staigh a ’mhodal mu thràth)
  • Tha an comharra comasachaidh (CH_PD) air a tharraing suas gu cumhachd
  • Tha GPIO15 air a shlaodadh chun na talmhainn. Chan eil feum air seo ach aig an toiseach, ach chan eil dad agam fhathast ri cheangal ris a’ chas seo; chan eil feum agam air tuilleadh

Gus am modal a chuir ann am modh firmware, feumaidh tu cuairt ghoirid GPIO2 gu làr, agus gus a dhèanamh nas goireasaiche, thug mi seachad putan Boot. Ann an suidheachadh àbhaisteach, tha am prìne seo air a tharraing gu cumhachd.

Chan eil staid loidhne GPIO2 air a sgrùdadh ach aig toiseach an obrachaidh - nuair a thèid cumhachd a chuir an sàs no dìreach às deidh ath-shuidheachadh. Mar sin bidh am modal an dàrna cuid a ’brògadh mar as àbhaist no a’ dol a-steach gu modh firmware. Aon uair ‘s gu bheil e air a luchdachadh, faodar am prìne seo a chleachdadh mar GPIO cunbhalach. Uill, leis gu bheil putan ann mu thràth, faodaidh tu gnìomh feumail a cheangal ris.

Airson prògramadh agus debugging cleachdaidh mi an UART, a tha na thoradh air cìr. Nuair a bhios feum air, bidh mi dìreach a’ ceangal inneal-atharrachaidh USB-UART an sin. Feumaidh tu cuimhneachadh gu bheil am modal air a stiùireadh le 3.3V. Ma dhìochuimhnicheas tu an inneal-atharrachaidh atharrachadh chun bholtadh seo agus 5V a thoirt seachad, is coltaiche gun loisg am modal a-mach.

Chan eil duilgheadas sam bith agam le dealan anns an t-seòmar-ionnlaid - tha an t-ionad suidhichte mu mheatair bho na meatairean, agus mar sin bidh mi air a stiùireadh le 220V. Mar thobar cumhachd bidh beag agam bacadh HLK-PM03 le Tenstar Robot. Gu pearsanta, tha ùine chruaidh agam le analog agus electronics cumhachd, ach an seo tha solar cumhachd deiseil ann an cùis bheag.

Gus comharran a dhèanamh air modhan obrachaidh, thug mi seachad LED ceangailte ri GPIO2. Ach, cha do chuir mi às dha, oir ... Tha LED aig modal ESP-07 mu thràth, agus tha e cuideachd ceangailte ri GPIO2. Ach leig leis a bhith air a’ bhòrd, air eagal ‘s gu bheil mi airson an LED seo a chuir a-mach chun chùis.

Gluaisidh sinn air adhart chun phàirt as inntinniche. Chan eil loidsig sam bith aig meatairean uisge; chan urrainn dhut leughaidhean gnàthach iarraidh orra. Is e an aon rud a tha ri fhaighinn dhuinn sparradh - a’ dùnadh fiosan an t-suidse cuilc gach liotair. Tha na toraidhean suidse cuilc agam ceangailte ri GPIO12/GPIO13. Leigidh mi an resistor tarraing-suas gu prògramach taobh a-staigh a’ mhodal.

An toiseach, dhìochuimhnich mi resistors R8 agus R9 a thoirt seachad agus chan eil an dreach agam den bhòrd aca. Ach leis gu bheil mi mu thràth a’ postadh an diagram airson gum faic a h-uile duine, is fhiach an ro-shealladh seo a cheartachadh. Tha feum air innealan-aghaidh gus nach loisg iad am port ma bhios am firmware a’ glitching agus a’ suidheachadh a’ phrìne gu aon, agus an t-atharrachadh cuilc a’ giorrachadh na loidhne seo gu làr (leis an resistor 3.3V / 1000Ohm = 3.3mA aig a’ char as àirde).

Tha an t-àm ann smaoineachadh air dè nì thu ma thèid an dealan a-mach. Is e a’ chiad roghainn luachan tùsail iarraidh bhon t-seirbheisiche aig an toiseach. Ach dh'fheumadh seo iom-fhillteachd mòr den phròtacal iomlaid. A bharrachd air an sin, tha coileanadh an inneal sa chùis seo an urra ri staid an fhrithealaiche. Mura tòisich am frithealaiche às deidh an cumhachd a chuir dheth (no tòiseachadh nas fhaide air adhart), cha b’ urrainn don mheatair uisge luachan tùsail iarraidh agus cha obraich e gu ceart.

Mar sin, chuir mi romhpa luachan sàbhalaidh sàbhalaidh a chuir an gnìomh ann an chip cuimhne ceangailte tro I2C. Chan eil riatanasan sònraichte agam airson meud a’ chuimhne flash - chan fheum thu ach 2 àireamh a shàbhaladh (an àireamh de liotairean a rèir meatairean uisge teth is fuar). Nì eadhon am modal as lugha. Ach feumaidh tu aire a thoirt don àireamh de chuairtean clàraidh. Airson a 'mhòr-chuid de mhodalan is e seo 100 mìle cearcall, airson cuid suas ri millean.

Bhiodh e coltach gu bheil millean gu mòr. Ach rè na 4 bliadhna de bhith a’ fuireach san àros agam, dh’ ith mi beagan a bharrachd air 500 meatair ciùbach de dh’ uisge, sin 500 mìle liotair! Agus 500 mìle clàr ann am flash. Agus is e sin dìreach uisge fuar. Faodaidh tu, gu dearbh, a’ chip ath-reic a h-uile dà bhliadhna, ach tha e coltach gu bheil chips FRAM ann. Bho shealladh prògramadh, is e seo an aon I2C EEPROM, dìreach le àireamh mhòr de chuairtean ath-sgrìobhaidh (ceudan de mhilleanan). Is e dìreach nach urrainn dhomh fhathast faighinn chun bhùth le leithid de mhicro-chuairtean, agus mar sin airson a-nis seasaidh an 24LC512 àbhaisteach.

Bòrd cuairte clò-bhuailte

An toiseach, bha mi an dùil am bòrd a dhèanamh aig an taigh. Mar sin, chaidh am bòrd a dhealbhadh mar aon-thaobhach. Ach às deidh dhomh uair a thìde a chuir seachad le iarann ​​​​lasair agus masg solder (chan eil e ann an dòigh air choreigin comme il faut às aonais), chuir mi romham fhathast na bùird òrdachadh bho na Sìonaich.

Bidh sinn a’ ceangal a’ mheatair uisge ris an dachaigh spaideil

Cha mhòr mus òrdaich mi am bòrd, thuig mi, a bharrachd air a’ chip cuimhne flash, gum b’ urrainn dhomh rudeigin eile a bha feumail a cheangal ris a’ bhus I2C, leithid taisbeanadh. Tha e fhathast na cheist dè dìreach a thèid a thoirt dha, ach feumar a chuir air a’ bhòrd. Uill, leis gu robh mi a’ dol a dh’ òrdachadh bùird bhon fhactaraidh, cha robh adhbhar ann mi fhìn a chuingealachadh gu bòrd aon-thaobhach, agus mar sin is e na loidhnichean I2C an aon fheadhainn air taobh cùil a’ bhùird.

Bha duilgheadas mòr ann cuideachd leis an uèirleadh aon-shligheach. Air sgàth Chaidh am bòrd a tharraing mar aon-thaobhach, agus mar sin bhathas an dùil na slighean agus na pàirtean SMD a chuir air aon taobh, agus na pàirtean toraidh, na ceanglaichean agus an solar cumhachd air an taobh eile. Nuair a fhuair mi na bùird mìos an dèidh sin, dhìochuimhnich mi mun phlana tùsail agus shàbhail mi na pàirtean gu lèir air an taobh aghaidh. Agus dìreach nuair a thàinig e gu bhith a 'solar an t-solar cumhachd thàinig e a-mach gun robh na buannachdan agus na h-eas-bhuannachdan air an ceangal air ais. Bha agam ri tuathanachas le geansaidhean. Anns an dealbh gu h-àrd, tha mi air an uèirleadh atharrachadh mar-thà, ach tha an talamh air a ghluasad bho aon phàirt den bhòrd gu fear eile tro phrìneachan a 'phutan Boot (ged a bhiodh e comasach slighe a tharraing air an dàrna sreath).

Thionndaidh e a-mach mar seo

Bidh sinn a’ ceangal a’ mheatair uisge ris an dachaigh spaideil

Taigheadas

Is e an ath cheum an corp. Ma tha clò-bhualadair 3D agad, chan e duilgheadas a tha seo. Cha do chuir mi cus dragh orm - dìreach tharraing mi bogsa den mheud cheart agus rinn mi gearraidhean anns na h-àiteachan ceart. Tha an còmhdach ceangailte ris a 'bhodhaig le sgriothan beaga fèin-tapadh.

Bidh sinn a’ ceangal a’ mheatair uisge ris an dachaigh spaideil

Thug mi iomradh mu thràth gum faodar am putan Boot a chleachdadh mar phutan coitcheann - mar sin seallaidh sinn e air a’ phannal aghaidh. Gus seo a dhèanamh, tharraing mi “tobar” sònraichte far a bheil am putan a’ fuireach.

Bidh sinn a’ ceangal a’ mheatair uisge ris an dachaigh spaideil

Taobh a-staigh a ’chùis tha studs cuideachd air a bheil am bòrd air a chuir a-steach agus air a cheangal le aon sgriubha M3 (cha robh barrachd àite air a’ bhòrd)

Thagh mi an taisbeanadh mu thràth nuair a chlò-bhuail mi a’ chiad dreach sampall den chùis. Cha do ghabh leughadair dà-loidhne àbhaisteach a-steach don chùis seo, ach aig a’ bhonn bha taisbeanadh OLED SSD1306 128 × 32. Tha e rud beag beag, ach chan fheum mi a bhith a’ coimhead air a h-uile latha - tha e cus dhòmhsa.

Le bhith a’ faighinn a-mach mar seo agus mar a bhiodh na uèirichean air an gluasad bhuaithe, chuir mi romham an taisbeanadh a steigeadh ann am meadhan na cùise. Tha ergonomics, gu dearbh, fo par - tha am putan air a mhullach, tha an taisbeanadh aig a ’bhonn. Ach thuirt mi mu thràth gun tàinig am beachd an taisbeanadh a cheangal ro fhadalach agus bha mi ro leisg am bòrd ath-shreangadh gus am putan a ghluasad.

Tha an inneal air a chruinneachadh. Tha am modal taisbeanaidh air a cheangal ris an t-snot le glaodh teth

Bidh sinn a’ ceangal a’ mheatair uisge ris an dachaigh spaideil

Bidh sinn a’ ceangal a’ mheatair uisge ris an dachaigh spaideil

Tha an toradh deireannach ri fhaicinn air KDPV

Firmware

Gluaisidh sinn air adhart gu pàirt bathar-bog. Airson ciùird bheaga mar seo, is toil leam a bhith a’ cleachdadh Python (micropython) - tha an còd a’ tionndadh a-mach gu bhith gu math toinnte agus so-thuigsinn. Gu fortanach, chan fheumar a dhol sìos gu ìre a’ chlàir gus microseconds a bhrùthadh a-mach - faodar a h-uile càil a dhèanamh bho Python.

Tha e coltach gu bheil a h-uile dad sìmplidh, ach chan eil e gu math sìmplidh - tha grunn ghnìomhan neo-eisimeileach aig an inneal:

  • Bidh an neach-cleachdaidh a 'putadh a' phutan agus a 'coimhead air an taisbeanadh
  • Litrichean diog agus ùraich luachan ann an cuimhne flash
  • Bidh am modal a’ cumail sùil air a’ chomharra WiFi agus ag ath-cheangal ma tha sin riatanach
  • Uill, às aonais bulb solais frasach tha e do-dhèanta

Chan urrainn dhut gabhail ris nach do dh’obraich aon ghnìomh ma tha fear eile steigte airson adhbhar air choireigin. Tha mi air mo lìonadh de chacti mu thràth ann am pròiseactan eile agus a-nis tha mi fhathast a’ faicinn glitches ann an stoidhle “Chaill mi liotair eile oir bha an taisbeanadh ag ùrachadh aig an àm sin” no “chan urrainn don neach-cleachdaidh dad a dhèanamh fhad‘ s a tha am modal a ’ceangal ris. WiFi.” Gu dearbh, faodar cuid de rudan a dhèanamh tro bhriseadh, ach faodaidh tu a dhol a-steach do chuingealachaidhean a thaobh fad, neadachadh gairmean, no atharrachaidhean neo-atamach air caochladairean. Uill, bidh an còd a nì a h-uile càil gu sgiobalta a ’tionndadh gu bhith na mhush.

В pròiseact nas miosa Chleachd mi multitasking clasaigeach preemptive agus FreeRTOS, ach sa chùis seo thionndaidh am modail a-mach gu bhith tòrr nas freagarraiche leabharlannan coroutines agus uasync . A bharrachd air an sin, tha buileachadh Python de coroutines dìreach iongantach - tha a h-uile dad air a dhèanamh gu sìmplidh agus gu goireasach don phrògramadair. Dìreach sgrìobh do loidsig fhèin, dìreach innis dhomh dè na h-àiteachan as urrainn dhut gluasad eadar sruthan.

Tha mi a’ moladh a bhith a’ sgrùdadh nan eadar-dhealachaidhean eadar ioma-obair ro-sheasmhach agus farpaiseach mar chuspair roghainneil. A-nis gluaisidh sinn air adhart chun chòd mu dheireadh.

#####################################
# Counter class - implements a single water counter on specified pin
#####################################
class Counter():
    debounce_ms = const(25)
    
    def __init__(self, pin_num, value_storage):
        self._value_storage = value_storage
        
        self._value = self._value_storage.read()
        self._value_changed = False

        self._pin = Pin(pin_num, Pin.IN, Pin.PULL_UP)

        loop = asyncio.get_event_loop()
        loop.create_task(self._switchcheck())  # Thread runs forever

Tha gach cuntair air a làimhseachadh le eisimpleir den chlas Counter. An toiseach, tha a 'chiad luach cunntais air a thoirt air falbh bhon EEPROM (value_storage) - seo mar a thèid ath-bheothachadh an dèidh fàilligeadh cumhachd a thoirt gu buil.

Tha am prìne air a thòiseachadh le tarraing a-steach don t-solar cumhachd: ma tha an tionndadh cuilc dùinte, tha an loidhne neoni, ma tha an loidhne fosgailte, thèid a tharraing suas chun t-solar cumhachd agus leugh an rianadair fear.

Tha gnìomh air leth ga chuir air bhog an seo cuideachd, a nì sgrùdadh air a’ phrìne. Bidh gach cuntair a 'ruith a ghnìomh fhèin. Seo an còd aice

    """ Poll pin and advance value when another litre passed """
    async def _switchcheck(self):
        last_checked_pin_state = self._pin.value()  # Get initial state

        # Poll for a pin change
        while True:
            state = self._pin.value()
            if state != last_checked_pin_state:
                # State has changed: act on it now.
                last_checked_pin_state = state
                if state == 0:
                    self._another_litre_passed()

            # Ignore further state changes until switch has settled
            await asyncio.sleep_ms(Counter.debounce_ms)

Tha feum air dàil de 25ms gus breab-conaltraidh a shìoladh, agus aig an aon àm bidh e a’ riaghladh cho tric sa dhùisgeas a’ ghnìomh (fhad ‘s a tha an obair seo a’ cadal, tha gnìomhan eile a’ ruith). Gach 25ms bidh an gnìomh a’ dùsgadh, a’ sgrùdadh a’ phrìne agus ma tha na ceanglaichean suidse cuilc dùinte, tha liotair eile air a dhol tron ​​mheatair agus feumar seo a phròiseasadh.

    def _another_litre_passed(self):
        self._value += 1
        self._value_changed = True

        self._value_storage.write(self._value)

Tha a bhith a 'giollachd an ath litr gu math beag - tha an cuntair dìreach ag àrdachadh. Uill, bhiodh e math an luach ùr a sgrìobhadh air draibh flash.

Airson a bhith furasta a chleachdadh, tha “accessors” air an toirt seachad

    def value(self):
        self._value_changed = False
        return self._value

    def set_value(self, value):
        self._value = value
        self._value_changed = False

Uill, a-nis leig dhuinn brath a ghabhail air toileachas Python agus an leabharlann uasync agus nì sinn inneal-aghaidh feitheamh (ciamar as urrainn dhuinn seo eadar-theangachadh gu Ruisis? Am fear ris am faod dùil a bhith agad?)

    def __await__(self):
        while not self._value_changed:
            yield from asyncio.sleep(0)

        return self.value()

    __iter__ = __await__  

Is e gnìomh cho goireasach a tha seo a dh’ fheitheamh gus an tèid an luach cunntais ùrachadh - bidh an gnìomh a’ dùsgadh bho àm gu àm agus a’ sgrùdadh a’ bhratach _value_changed. Is e an rud fionnar mun ghnìomh seo gum faod an còd gairm tuiteam na chadal fhad ‘s a tha thu a’ gairm a ’ghnìomh seo agus a’ cadal gus am faighear luach ùr.

Dè mu dheidhinn brisidhean?Faodaidh, aig an ìre seo faodaidh tu mo tholladh, ag ràdh gun tuirt thu fhèin mu bhriseadh-dùil, ach gu fìrinneach rinn thu sgrùdadh prìne gòrach. Gu fìrinneach is e brisidhean a’ chiad rud a dh’ fheuch mi. Anns an ESP8266, faodaidh tu briseadh iomall a chuir air dòigh, agus eadhon inneal-làimhseachaidh a sgrìobhadh airson a ’bhriseadh seo ann am Python. Anns a 'bhriseadh seo, faodar luach caochladair ùrachadh. Is dòcha gum biodh seo gu leòr nam biodh an cuntair na inneal tràillean - fear a dh'fhuiricheas gus an tèid an luach seo iarraidh.

Gu mì-fhortanach (no gu fortanach?) tha an inneal agam gnìomhach, feumaidh e fhèin teachdaireachdan a chuir tro phròtacal MQTT agus dàta a sgrìobhadh gu EEPROM. Agus an seo thig cuingealachaidhean a-steach - chan urrainn dhut cuimhne a riarachadh ann am brisidhean agus stac mhòr a chleachdadh, a tha a ’ciallachadh gun urrainn dhut dìochuimhneachadh mu bhith a’ cur teachdaireachdan thairis air an lìonra. Tha bunan ann mar micropython.schedule () a leigeas leat gnìomh air choireigin a ruith “cho luath‘ s a ghabhas, ”ach tha a’ cheist ag èirigh, “dè a’ phuing? ” Dè ma tha sinn a 'cur teachdaireachd de sheòrsa air choreigin an-dràsta, agus an uairsin thig briseadh a-steach agus a' milleadh luachan nan caochladairean. No, mar eisimpleir, thàinig cuntair ùr bhon t-seirbheisiche fhad ‘s nach robh sinn air an t-seann fhear a sgrìobhadh sìos fhathast. San fharsaingeachd, feumaidh tu casg a chuir air sioncronadh no faighinn a-mach às ann an dòigh eadar-dhealaichte.

Agus bho àm gu àm RuntimeError: clàr stac làn thubaistean agus cò aig a tha fios carson?

Le cunntas-bheachd soilleir agus uasync, sa chùis seo bidh e dòigh air choireigin nas bòidhche agus nas earbsaiche

Thug mi obair le EEPROM gu clas beag

class EEPROM():
    i2c_addr = const(80)

    def __init__(self, i2c):
        self.i2c = i2c
        self.i2c_buf = bytearray(4) # Avoid creation/destruction of the buffer on each call


    def read(self, eeprom_addr):
        self.i2c.readfrom_mem_into(self.i2c_addr, eeprom_addr, self.i2c_buf, addrsize=16)
        return ustruct.unpack_from("<I", self.i2c_buf)[0]    
        
    
    def write(self, eeprom_addr, value):
        ustruct.pack_into("<I", self.i2c_buf, 0, value)
        self.i2c.writeto_mem(self.i2c_addr, eeprom_addr, self.i2c_buf, addrsize=16)

Ann am Python, tha e doirbh obrachadh gu dìreach le bytes, ach is e na bytes a tha sgrìobhte gu cuimhne. B’ fheudar dhomh an tionndadh eadar integer agus bytes a fheansa a’ cleachdadh an leabharlann ustruct.

Gus nach tèid an nì I2C agus seòladh na cealla cuimhne a ghluasad a h-uile uair, phaisg mi suas e ann an clasaig beag agus goireasach

class EEPROMValue():
    def __init__(self, i2c, eeprom_addr):
        self._eeprom = EEPROM(i2c)
        self._eeprom_addr = eeprom_addr
        

    def read(self):
        return self._eeprom.read(self._eeprom_addr)


    def write(self, value):
        self._eeprom.write(self._eeprom_addr, value)

Tha an nì I2C fhèin air a chruthachadh leis na crìochan sin

i2c = I2C(freq=400000, scl=Pin(5), sda=Pin(4))

Tha sinn a 'tighinn chun a' phàirt as inntinniche - buileachadh conaltradh leis an fhrithealaiche tro MQTT. Uill, chan eil feum air a 'phròtacal fhèin a chur an gnìomh - lorg mi e air an eadar-lìon buileachadh asyncronach deiseil. Is e seo a bhios sinn a’ cleachdadh.

Tha a h-uile rud as inntinniche air a chruinneachadh anns a 'chlas CounterMQTTClient, a tha stèidhichte air an leabharlann MQTTClient. Feuch an tòisich sinn bhon iomall

#####################################
# Class handles both counters and sends their status to MQTT
#####################################
class CounterMQTTClient(MQTTClient):

    blue_led = Pin(2, Pin.OUT, value = 1)
    button = Pin(0, Pin.IN)

    hot_counter = Counter(12, EEPROMValue(i2c, EEPROM_ADDR_HOT_VALUE))
    cold_counter = Counter(13, EEPROMValue(i2c, EEPROM_ADDR_COLD_VALUE))

An seo faodaidh tu prìneachan agus putanan bulb solais a chruthachadh agus a rèiteachadh, a bharrachd air nithean meatair uisge fuar is teth.

Le toiseach tòiseachaidh, chan eil a h-uile dad cho beag

    def __init__(self):
        self.internet_outage = True
        self.internet_outages = 0
        self.internet_outage_start = ticks_ms()

        with open("config.txt") as config_file:
            config['ssid'] = config_file.readline().rstrip()
            config['wifi_pw'] = config_file.readline().rstrip()
            config['server'] = config_file.readline().rstrip()
            config['client_id'] = config_file.readline().rstrip()
            self._mqtt_cold_water_theme = config_file.readline().rstrip()
            self._mqtt_hot_water_theme = config_file.readline().rstrip()
            self._mqtt_debug_water_theme = config_file.readline().rstrip()

        config['subs_cb'] = self.mqtt_msg_handler
        config['wifi_coro'] = self.wifi_connection_handler
        config['connect_coro'] = self.mqtt_connection_handler
        config['clean'] = False
        config['clean_init'] = False
        super().__init__(config)

        loop = asyncio.get_event_loop()
        loop.create_task(self._heartbeat())
        loop.create_task(self._counter_coro(self.cold_counter, self._mqtt_cold_water_theme))
        loop.create_task(self._counter_coro(self.hot_counter, self._mqtt_hot_water_theme))
        loop.create_task(self._display_coro())

Gus crìochan obrachaidh leabharlann mqtt_as a shuidheachadh, thèid faclair mòr de dhiofar shuidheachaidhean a chleachdadh - config. Tha a’ mhòr-chuid de na roghainnean bunaiteach ceart gu leòr dhuinn, ach feumar mòran shuidheachaidhean a shuidheachadh gu soilleir. Gus nach sgrìobh thu na roghainnean gu dìreach sa chòd, bidh mi gan stòradh anns an fhaidhle teacsa config.txt. Leigidh seo leat an còd atharrachadh ge bith dè na roghainnean a th ’ann, a bharrachd air grunn innealan co-ionann le diofar pharaimearan.

Bidh am bloc mu dheireadh de chòd a’ tòiseachadh grunn coroutines gus diofar dhleastanasan an t-siostaim a fhrithealadh. Mar eisimpleir, seo coroutine a bhios a’ frithealadh cunntais

    async def _counter_coro(self, counter, topic):
        # Publish initial value
        value = counter.value()
        await self.publish(topic, str(value))

        # Publish each new value
        while True:
            value = await counter
            await self.publish_msg(topic, str(value))

Bidh an coroutine a’ feitheamh ann an lùb airson cunntais luach ùr agus, cho luath ‘s a nochdas e, cuiridh e teachdaireachd tro phròtacal MQTT. Bidh a 'chiad phìos còd a' cur a 'chiad luach eadhon ged nach eil uisge a' sruthadh tron ​​​​chunntair.

Bidh an clas bunaiteach MQTTClient a 'frithealadh fhèin, a' tòiseachadh ceangal WiFi agus ag ath-cheangal nuair a thèid an ceangal a chall. Nuair a tha atharrachaidhean ann an staid a’ cheangail WiFi, bidh an leabharlann ag innse dhuinn le bhith a’ fònadh wifi_connection_handler

    async def wifi_connection_handler(self, state):
        self.internet_outage = not state
        if state:
            self.dprint('WiFi is up.')
            duration = ticks_diff(ticks_ms(), self.internet_outage_start) // 1000
            await self.publish_debug_msg('ReconnectedAfter', duration)
        else:
            self.internet_outages += 1
            self.internet_outage_start = ticks_ms()
            self.dprint('WiFi is down.')
            
        await asyncio.sleep(0)

Tha an gnìomh air a chopaigeadh gu h-onarach bho eisimpleirean. Anns a 'chùis seo, bidh e a' cunntadh an àireamh de bhriseadh a-mach (internet_outages) agus an ùine. Nuair a thèid an ceangal ath-nuadhachadh, thèid ùine leisg a chuir chun t-seirbheisiche.

Air an t-slighe, chan eil feum air a 'chadal mu dheireadh ach gus a' ghnìomh a dhèanamh asyncronach - anns an leabharlann tha e air a ghairm tro feitheamh, agus chan urrainnear ach gnìomhan aig a bheil bodhaig a 'feitheamh ri fear eile a ghairm.

A bharrachd air ceangal ri WiFi, feumaidh tu cuideachd ceangal a stèidheachadh ris a’ bhròcair MQTT (frithealaiche). Bidh an leabharlann a’ dèanamh seo cuideachd, agus gheibh sinn an cothrom rudeigin feumail a dhèanamh nuair a thèid an ceangal a stèidheachadh

    async def mqtt_connection_handler(self, client):
        await client.subscribe(self._mqtt_cold_water_theme)
        await client.subscribe(self._mqtt_hot_water_theme)

An seo bidh sinn a’ fo-sgrìobhadh do ghrunn theachdaireachdan - tha comas aig an fhrithealaiche a-nis na luachan cunntais gnàthach a shuidheachadh le bhith a’ cur an teachdaireachd co-fhreagarrach.

    def mqtt_msg_handler(self, topic, msg):
        topicstr = str(topic, 'utf8')
        self.dprint("Received MQTT message topic={}, msg={}".format(topicstr, msg))

        if topicstr == self._mqtt_cold_water_theme:
            self.cold_counter.set_value(int(msg))

        if topicstr == self._mqtt_hot_water_theme:
            self.hot_counter.set_value(int(msg))

Bidh an gnìomh seo a’ pròiseas teachdaireachdan a tha a’ tighinn a-steach, agus a rèir a’ chuspair (tiotal teachdaireachd), tha luachan aon de na cunntairean air an ùrachadh

Dà ghnìomh cuideachaidh

    # Publish a message if WiFi and broker is up, else discard
    async def publish_msg(self, topic, msg):
        self.dprint("Publishing message on topic {}: {}".format(topic, msg))
        if not self.internet_outage:
            await self.publish(topic, msg)
        else:
            self.dprint("Message was not published - no internet connection")

Cuiridh an gnìomh seo teachdaireachd ma thèid an ceangal a stèidheachadh. Mura h-eil ceangal ann, thèid an teachdaireachd a leigeil seachad.

Agus is e dìreach gnìomh goireasach a tha seo a bhios a’ gineadh agus a ’cur teachdaireachdan deasbaid.

    async def publish_debug_msg(self, subtopic, msg):
        await self.publish_msg("{}/{}".format(self._mqtt_debug_water_theme, subtopic), str(msg))

Na h-uimhir de theacsa, agus chan eil sinn air LED a bhrùthadh fhathast. Seo

    # Blink flash LED if WiFi down
    async def _heartbeat(self):
        while True:
            if self.internet_outage:
                self.blue_led(not self.blue_led()) # Fast blinking if no connection
                await asyncio.sleep_ms(200) 
            else:
                self.blue_led(0) # Rare blinking when connected
                await asyncio.sleep_ms(50)
                self.blue_led(1)
                await asyncio.sleep_ms(5000)

Tha mi air 2 mhodh blinking a thoirt seachad. Ma thèid an ceangal a chall (no ma tha e dìreach ga stèidheachadh), bidh an inneal a’ priobadh gu sgiobalta. Ma thèid an ceangal a stèidheachadh, bidh an inneal a’ frasadh aon uair gach 5 diog. Ma tha feum air, faodar modhan frasaidh eile a chuir an gnìomh an seo.

Ach tha an LED dìreach a’ magadh. Bha sinn cuideachd ag amas air an taisbeanadh.

    async def _display_coro(self):
        display = SSD1306_I2C(128,32, i2c)
    
        while True:
            display.poweron()
            display.fill(0)
            display.text("COLD: {:.3f}".format(self.cold_counter.value() / 1000), 16, 4)
            display.text("HOT:  {:.3f}".format(self.hot_counter.value() / 1000), 16, 20)
            display.show()
            await asyncio.sleep(3)
            display.poweroff()

            while self.button():
                await asyncio.sleep_ms(20)

Seo na bha mi a’ bruidhinn - cho sìmplidh agus cho goireasach ‘s a tha e le coroutines. Tha an gnìomh beag seo a’ toirt cunntas air eòlas cleachdaiche ENTIRE. Bidh an coroutine dìreach a’ feitheamh ris a’ phutan a bhrùthadh agus a’ tionndadh air an taisbeanadh airson 3 diogan. Tha an taisbeanadh a’ sealltainn na leughaidhean meatair gnàthach.

Tha rud no dhà air fhàgail fhathast. Seo an gnìomh a tha (ath) a’ tòiseachadh an iomairt slàn seo. Bidh am prìomh lùb dìreach a’ cur diofar fhiosrachadh deasbaid uair sa mhionaid. San fharsaingeachd, bidh mi ga aithris mar a tha e - chan eil mi a’ smaoineachadh gu bheil feum air cus beachd a thoirt seachad

   async def main(self):
        while True:
            try:
                await self._connect_to_WiFi()
                await self._run_main_loop()
                    
            except Exception as e:
                self.dprint('Global communication failure: ', e)
                await asyncio.sleep(20)

    async def _connect_to_WiFi(self):
        self.dprint('Connecting to WiFi and MQTT')
        sta_if = network.WLAN(network.STA_IF)
        sta_if.connect(config['ssid'], config['wifi_pw'])
        
        conn = False
        while not conn:
            await self.connect()
            conn = True

        self.dprint('Connected!')
        self.internet_outage = False

    async def _run_main_loop(self):
        # Loop forever
        mins = 0
        while True:
            gc.collect()  # For RAM stats.
            mem_free = gc.mem_free()
            mem_alloc = gc.mem_alloc()

            try:
                await self.publish_debug_msg("Uptime", mins)
                await self.publish_debug_msg("Repubs", self.REPUB_COUNT)
                await self.publish_debug_msg("Outages", self.internet_outages)
                await self.publish_debug_msg("MemFree", mem_free)
                await self.publish_debug_msg("MemAlloc", mem_alloc)
            except Exception as e:
                self.dprint("Exception occurred: ", e)
            mins += 1

            await asyncio.sleep(60)

Uill, dhà no dhà a bharrachd shuidheachaidhean agus rèiteachaidhean gus an tuairisgeul a chrìochnachadh

#####################################
# Constants and configuration
#####################################


config['keepalive'] = 60
config['clean'] = False
config['will'] = ('/ESP/Wemos/Water/LastWill', 'Goodbye cruel world!', False, 0)

MQTTClient.DEBUG = True

EEPROM_ADDR_HOT_VALUE = const(0)
EEPROM_ADDR_COLD_VALUE = const(4)

Bidh e uile a’ tòiseachadh mar seo

client = CounterMQTTClient()
loop = asyncio.get_event_loop()
loop.run_until_complete(client.main())

Thachair rudeigin nam chuimhne

Mar sin, tha an còd gu lèir ann. Luchdaich mi suas na faidhlichean a’ cleachdadh ampy utility - leigidh e leat an luchdachadh suas chun draibhear flash a-staigh (am fear san ESP-07 fhèin) agus an uairsin faighinn thuige bhon phrògram mar fhaidhlichean àbhaisteach. An sin cuideachd luchdaich mi suas na leabharlannan mqtt_as, uasyncio, ssd1306 agus cruinneachaidhean a chleachd mi (air an cleachdadh am broinn mqtt_as).

Bidh sinn a’ cur air bhog agus... Bidh sinn a’ faighinn MemoryError. A bharrachd air an sin, mar as motha a dh’ fheuch mi ri tuigsinn càite dìreach an robh an cuimhne ag aoidion, mar as motha de chlò-bhualaidhean deasbaid a chuir mi, is ann as tràithe a nochd a’ mhearachd seo. Thug sgrùdadh goirid Google mi gu tuigse nach eil aig a’ mhicro-riaghladair, ann am prionnsapal, ach 30 kB de chuimhne, anns nach urrainn 65 kB de chòd (a’ toirt a-steach leabharlannan) freagairt.

Ach tha slighe a-mach. Tha e a 'tionndadh a-mach nach eil micropython a' cur an gnìomh còd gu dìreach bho fhaidhle .py - tha am faidhle seo air a chur ri chèile an toiseach. A bharrachd air an sin, tha e air a chur ri chèile gu dìreach air an microcontroller, air a thionndadh gu bytecode, a tha an uairsin air a stòradh mar chuimhneachan. Uill, airson an neach-cruinneachaidh a bhith ag obair, feumaidh tu cuideachd tomhas sònraichte de RAM.

Is e an cleas am microcontroller a shàbhaladh bho chruinneachadh dian-ghoireasan. Faodaidh tu na faidhlichean a chuir ri chèile air coimpiutair mòr agus am bytecode deiseil a luchdachadh suas a-steach don microcontroller. Gus seo a dhèanamh, feumaidh tu an firmware micropython a luchdachadh sìos agus a thogail goireas mpy-cross.

Cha do sgrìobh mi Makefile, ach chaidh mi troimhe le làimh agus chuir mi ri chèile na faidhlichean riatanach gu lèir (leabharlannan nam measg) rudeigin mar seo

mpy-cross water_counter.py

Chan eil air fhàgail ach faidhlichean a luchdachadh suas leis an leudachadh .mpy, gun a bhith a’ dìochuimhneachadh an .py co-fhreagarrach a dhubhadh às bho shiostam faidhle an inneil.

Rinn mi a h-uile leasachadh anns a’ phrògram (IDE?) ESPlorer. Leigidh e leat sgriobtaichean a luchdachadh suas chun microcontroller agus an cur an gnìomh sa bhad. Anns a 'chùis agam, tha loidsig agus cruthachadh a h-uile nì suidhichte anns an fhaidhle water_counter.py (.mpy). Ach gus an tòisich seo gu fèin-ghluasadach, feumaidh faidhle a bhith ann cuideachd ris an canar main.py aig an toiseach. A bharrachd air an sin, bu chòir dha a bhith dìreach .py, agus chan ann ro-làimh .mpy. Seo an t-susbaint bheag aige

import water_counter

Bidh sinn ga chuir air bhog - bidh a h-uile dad ag obair. Ach tha cuimhne an-asgaidh uamhasach beag - timcheall air 1kb. Tha planaichean agam fhathast gus gnìomhachd an inneil a leudachadh, agus tha e soilleir nach eil an kilobyte seo gu leòr dhomh. Ach thionndaidh e a-mach gu bheil slighe a-mach airson a’ chùis seo cuideachd.

Seo an rud. Eadhon ged a tha na faidhlichean air an cur ri chèile ann am bytecode agus a ’fuireach air an t-siostam faidhle a-staigh, gu fìrinneach tha iad fhathast air an luchdachadh a-steach do RAM agus air an cur gu bàs às an sin. Ach tha e a ’tionndadh a-mach gum faod micropython bytecode a chuir an gnìomh gu dìreach bho chuimhne flash, ach airson seo feumaidh tu a thogail gu dìreach a-steach don firmware. Chan eil e duilich, ged a thug e beagan ùine air an leabhar-lìn agam (dìreach an sin thachair Linux agam).

Tha an algorithm mar a leanas:

  • Luchdaich sìos agus stàlaich ESP Fosgail SDK. Bidh an rud seo a’ cruinneachadh inneal-cruinneachaidh agus leabharlannan airson prògraman airson an ESP8266. Air a chruinneachadh a rèir an stiùiridh air prìomh dhuilleag a’ phròiseict (thagh mi an suidheachadh STANDALONE = tha)
  • Luchdaich sìos seòrsaichean micropython
  • Cuir na leabharlannan riatanach ann am puirt / esp8266 / modalan taobh a-staigh craobh micropython
  • Bidh sinn a 'cruinneachadh a' firmware a rèir an stiùiridh san fhaidhle puirt/esp8266/README.md
  • Bidh sinn a’ luchdachadh suas am firmware chun microcontroller (bidh mi a’ dèanamh seo air Windows a’ cleachdadh prògraman ESP8266Flasher no Python esptool)

Sin agad e, a-nis togaidh 'import ssd1306' an còd gu dìreach bhon firmware agus cha tèid RAM a chaitheamh airson seo. Leis an cleas seo, cha do luchdaich mi suas ach còd an leabharlainn a-steach don firmware, fhad ‘s a tha còd a’ phrìomh phrògram air a chuir gu bàs bhon t-siostam faidhle. Leigidh seo leat am prògram atharrachadh gu furasta gun a bhith ag ath-chruinneachadh am firmware. Aig an àm seo tha timcheall air 8.5kb de RAM an-asgaidh agam. Leigidh seo leinn tòrr diofar fheartan feumail a chuir an gnìomh san àm ri teachd. Uill, mura h-eil cuimhne gu leòr ann, faodaidh tu am prìomh phrògram a phutadh a-steach don firmware.

Mar sin dè a bu chòir dhuinn a dhèanamh mu dheidhinn a-nis?

Gu ceart, tha am bathar-cruaidh air a shàrachadh, tha am firmware sgrìobhte, tha am bogsa air a chlò-bhualadh, tha an inneal steigte air a’ bhalla agus gu toilichte a’ priobadh bulb solais. Ach airson a-nis is e bogsa dubh a th’ ann (gu litearra agus gu fìrinneach) agus chan eil mòran feum ann fhathast. Tha an t-àm ann rudeigin a dhèanamh leis na teachdaireachdan MQTT a thèid a chuir chun fhrithealaiche.

Tha an “dachaigh spaideil” agam a’ snìomh air adhart Majordomo siostam. Tha am modal MQTT an dàrna cuid a’ tighinn a-mach às a’ bhogsa, no tha e furasta a chuir a-steach bhon mhargaidh tuilleadain - chan eil cuimhne agam cò às a fhuair mi e. Chan e rud fèin-sheasmhach a th’ ann am MQTT - feumaidh tu rud ris an canar. broker - frithealaiche a gheibh, a sheòrsachadh agus a chuir air adhart teachdaireachdan MQTT gu teachdaichean. Bidh mi a’ cleachdadh mosgìoto, a tha (mar majordomo) a’ ruith air an aon lìon.

Às deidh don inneal teachdaireachd a chuir co-dhiù aon uair, nochdaidh an luach sa bhad air an liosta.

Bidh sinn a’ ceangal a’ mheatair uisge ris an dachaigh spaideil

Faodaidh na luachan sin a-nis a bhith co-cheangailte ri nithean siostam, faodar an cleachdadh ann an sgriobtaichean fèin-ghluasaid agus a bhith fo ùmhlachd grunn mhion-sgrùdaidhean - tha iad uile taobh a-muigh raon an artaigil seo. Is urrainn dhomh an siostam majordomo a mholadh do dhuine sam bith le ùidh sianal Electronics Ann an Lens - tha caraid cuideachd a’ togail dachaigh spaideil agus gu soilleir a’ bruidhinn mu bhith a’ stèidheachadh an t-siostam.

Seallaidh mi graf no dhà dhut. Is e seo graf sìmplidh de luachan làitheil

Bidh sinn a’ ceangal a’ mheatair uisge ris an dachaigh spaideil
Chithear nach robh cha mhòr duine a’ cleachdadh an uisge air an oidhche. Uair no dhà chaidh cuideigin dhan taigh beag, agus tha e coltach gu bheil an sìoltachan osmosis cùil a’ deoghal dà liotair gach oidhche. Anns a 'mhadainn, bidh caitheamh a' meudachadh gu mòr. Mar as trice bidh mi a 'cleachdadh uisge bho ghoileadair, ach an uairsin bha mi airson bath a ghabhail agus thionndaidh mi gu uisge teth a' bhaile airson ùine ghoirid - tha seo cuideachd ri fhaicinn gu soilleir anns a 'ghraf gu h-ìosal.

Bhon ghraf seo dh’ ionnsaich mi gu bheil feum air 6-7 l de uisge airson a dhol dhan taigh beag, feumaidh tu 20-30 liotairean de dh’ fhras a ghabhail, feumaidh mu 20 liotair a bhith a’ nighe shoithichean, agus feumar 160 liotair a ghabhail ann an amar. Bidh mo theaghlach ag ithe timcheall air 500-600 liotair gach latha.

Dhaibhsan a tha gu sònraichte fiosrach, faodaidh tu coimhead air na clàran airson gach luach fa leth

Bidh sinn a’ ceangal a’ mheatair uisge ris an dachaigh spaideil

Às an seo dh’ ionnsaich mi, nuair a bhios an tap fosgailte, gu bheil uisge a’ sruthadh aig astar timcheall air 1 liotair gach 5 s.

Ach anns an fhoirm seo is dòcha nach eil na staitistig gu math goireasach airson coimhead air. Tha comas aig Majordomo cuideachd clàran caitheamh fhaicinn a rèir latha, seachdain agus mìos. An seo, mar eisimpleir, tha graf caitheamh ann am bàraichean

Bidh sinn a’ ceangal a’ mheatair uisge ris an dachaigh spaideil

Gu ruige seo chan eil agam ach dàta airson seachdain. Ann am mìos, bidh an graf seo nas taisbeanaiche - bidh colbh air leth aig gach latha. Tha an dealbh air a mhilleadh beagan leis na h-atharrachaidhean air na luachan a chuireas mi a-steach le làimh (an colbh as motha). Agus chan eil e soilleir fhathast an do shuidhich mi na ciad luachan gu ceàrr, cha mhòr ciùb nas lugha, no an e bug a tha seo anns a’ firmware agus nach deach a h-uile liotair a chunntadh. Feum air barrachd ùine.

Tha feum fhathast aig na grafaichean fhèin air beagan draoidheachd, gealachadh, peantadh. Is dòcha gun tog mi cuideachd graf de chaitheamh cuimhne airson adhbharan deasbaid - air eagal ’s gu bheil rudeigin ag aoidion ann. Is dòcha gun seall mi dòigh air choireigin amannan nuair nach robh eadar-lìn ann. Airson a-nis, tha seo uile aig ìre bheachdan.

co-dhùnadh

An-diugh tha an àros agam air fàs beagan nas buige. Le inneal cho beag, bidh e nas fhasa dhomh sùil a chumail air caitheamh uisge san taigh. Nam biodh mi diombach na bu thràithe air “a-rithist, dh’ ith sinn tòrr uisge ann am mìos, ”a-nis is urrainn dhomh stòr a’ chaitheamh seo a lorg.

Is dòcha gum bi e neònach do chuid a bhith a’ coimhead air na leughaidhean air an sgrion ma tha e meatair air falbh bhon mheatair fhèin. Ach anns an àm ri teachd nach eil fada, tha mi an dùil gluasad gu àros eile, far am bi grunn risers uisge ann, agus is coltaiche gum bi na meatairean fhèin suidhichte air an t-slighe a-steach. Mar sin bidh inneal leughaidh iomallach glè fheumail.

Tha mi cuideachd an dùil gnìomhachd an inneil a leudachadh. Tha mi mu thràth a’ coimhead air bhalbhaichean motair. A-nis, gus an goileadair a thionndadh gu uisge a 'bhaile, feumaidh mi 3 tapan a thionndadh ann an àite a tha doirbh a ruigsinn. Bhiodh e fada na b’ fhasa seo a dhèanamh le aon phutan leis a’ chomharra iomchaidh. Uill, gu dearbh, is fhiach e dìon an aghaidh aoidion a chuir an gnìomh.

Anns an artaigil thug mi cunntas air an dreach agam de inneal stèidhichte air ESP8266. Nam bheachd-sa, thàinig mi suas le dreach glè inntinneach de firmware micropython a ’cleachdadh coroutines - sìmplidh agus snog. Dh'fheuch mi ri cunntas a thoirt air mòran de na nuances agus easbhaidhean a choinnich mi tron ​​​​iomairt. Is dòcha gun tug mi cunntas mionaideach air a h-uile càil; gu pearsanta, mar leughadair, tha e nas fhasa dhomh a dhol thairis air an stuth neo-riatanach na bhith a’ smaoineachadh nas fhaide air adhart dè nach deach a ràdh.

Mar as àbhaist, tha mi fosgailte do chàineadh cuideachail.

Còd tùs
Circuit agus bòrd
Modail cùise

Source: www.habr.com

Cuir beachd ann