Releases: HomeSpan/HomeSpan
HomeSpan 2.1.2
Updates and Corrections
-
Added UUID validation for Custom Services (#1020)
- reports an error in CLI at startup if invalid Service UUID is found
- similar to existing UUID validation for Custom Characteristics
-
Renamed example sketch RemoteDevice8286.ino to RemoteDevice8266.ino (#1028)
- corrects a long-standing typo in the filename
-
Modified OTA updating so that the HomeSpan check for its Magic Cookie is only made if uploading a new sketch (#1023)
- avoids OTA aborting when OTA is used to upload SPIFFS data
-
Refactored the JSON parsing logic that handles PUT Characteristic requests from HomeKit
- now properly supports any JSON-allowed Unicode character used in a JSON string value, from U+0020 to U+10FFFF
- allows string-based Characteristics to include escaped quotes, escaped solidus and reverse solidus, and any of the JSON token characters ,:[]{} that would have previously caused a parsing error
- also now allows for empty string-based Characteristics (previously would have led to a parsing error)
- now properly supports any JSON-allowed Unicode character used in a JSON string value, from U+0020 to U+10FFFF
-
Added new
setMaxStringLength(uint8_t n)
method to Characteristics- allows user to change maximum length of string-based Characteristics from HAP default of 64 to n (less than 256)
- though specified by HAP, this value does not seem to be used by HomeKit, and this method does not appear necessary
-
Added new homeSpan method
void assumeTimeAcquired()
(#1033)- calling this method tells HomeSpan to assume that you have acquired the time using your own code
- useful if you don't want to specify a timeServerURL when enabling the Web Log, but would rather acquire it manually
-
Added new homeSpan method
setGetCharacteristicsCallback(void (*func)(const char *getCharList))
- sets an optional user-defined callback function, func, to be called by HomeSpan whenever it receives a GET /characteristics request from HomeKit
- HomeKit generally sends this request to every paired device each time the Home App is opened on an iPhone or Mac
- this callback is useful in circumstances where the current state of a sensor-style Characteristic must be read by HomeSpan using a separate "expensive" process that should be called only when needed as opposed to being continuously updated in a Services
loop()
method - the function func must be of type void and accept one argument of type const char * into which HomeSpan passes the list of Characteristic AID/IID pairs that HomeKit provided in its HTTP GET request
- getCharList can be used to determine if the HTTP GET request includes the AID/IID pair for any specific Characteristic
- this allows the user to act on the callback based on which specific Characteristics were requested by HomeKit
- see new helper SpanCharacteristic method
foundIn(const char *getCharList)
that returns true or false depending on whether the AID/IID for a specific Characteristic is found in getCharList - for completeness, also added
uint32_t getAID()
methods to each of the SpanAccessory, SpanService, and SpanCharacteristic classes
-
Explicitly added added
#include <mutex>
to HomeSpan.cpp to address compatibility issue with Arduino-ESP32 v3.2.0 (#1048) -
Fixed bug in
Pixel::getPin()
that would report channel number instead of pin number
HomeSpan 2.1.1
Integrated Support for OTA Partition Rollbacks
-
Users can now configure HomeSpan to automatically rollback new sketches uploaded via OTA to a previous version if the new sketch crashes the device before 8000 being validated
- adds new header file
SpanRollback.h
- when included at the top of a user's sketch this disables the auto-validation of any newly-updated OTA partition that the ESP32-Arduino library otherwise would perform at startup
- users can instead manually validate their sketch in software, which allows the device to automatically rollback to a prior sketch if the new sketch is not marked as valid
- adds new homeSpan method
markSketchOK()
allowing users to mark the currently running partition as valid after uploading a new sketch via OTA - adds new homeSpan method
setPollingCallback(void (*f)())
allowing users to add a callback function, f, that HomeSpan calls one time after the very first call topoll()
has completed- provides a good check-point for users to mark new sketches uploaded via OTA as valid
- adds new CLI 'p' command that prints partition full table to the Serial Monitor
- includes details on whether OTA partitions are marked valid, invalid, undefined, etc.
- adds new homeSpan method
setCompileTime(char *compTime)
allowing users to set the compile date/time of the sketch to any arbitrary string, compTime- the compile date/time string provided is indicated in Serial Monitor during start-up as well as in the top table of the Web Log output
- if this method is called without a parameter HomeSpan uses the macros
__DATE__
and__TIME__
as provided by the compiler during compilation to create a date/time string - setting the compile date/time with this method allows users to easily determine which version of their sketch is running after an OTA update by simply looking at the Web Log output, which is very helpful when OTA Rollbacks are enabled
- see OTA.md for details on how to use OTA Rollbacks
- adds new header file
HomeSpan Watchdog Timer
-
Users can now configure HomeSpan to add a watchdog task that reboots the device if it has frozen or gone into an infinite loop preventing normal HomeSpan operations
- works especially well when used in conjunction with the OTA rollback functionality above by allowing the operating system itself to automatically rollback a newly-uploaded sketch via OTA that freezes or hangs the device completely before the sketch is validated
- adds new homeSpan method
enableWatchdog(uint16_t nSeconds)
- creates a separate HomeSpan task watchdog timer designed to trigger a reboot of the device if not periodically reset at least every nSeconds
- calling this method after the HomeSpan watchdog timer has already been enabled changes the timeout to a new value of nSeconds
- adds new homeSpan method
resetWatchdog()
used to periodically reset the HomeSpan watchdog timer- this method is already embedded in all HomeSpan library functions as needed
- users DO NOT need to call
resetWatchdog()
themselves in their own sketch unless they have created a process that delays the normal operation ofhomeSpan.poll()
- adds new homeSpan method
disableWatchdog()
to disable the HomeSpan watchdog timer after it has been enabled- has no effect if the HomeSpan watchdog timer is not currently enabled
- see WDT.md for a complete discussion of the HomeSpan and other system watchdog timer
Other Updates
- Added homeSpan method
Span& useEthernet()
to force HomeSpan to use Ethernet instead of WiFi, even if ETH has not yet been called or an Ethernet card has not been found prior tohomeSpan.begin()
being called (#997)
Bug Fixes
HomeSpan 2.1.0
Integrated Support for Ethernet Connectivity!
-
Users can now readily connect HomeSpan to their home networks via Ethernet as an alternative to WiFi (#738)
- no new homeSpan methods are required - during start-up HomeSpan checks if you've instructed the ESP32 to establish an Ethernet connection, and if so it will switch into "Ethernet mode" and not attempt to connect to your network via WiFi
- once in Ethernet mode, HomeSpan customizes some of the output to the Serial Monitor and Web Log so it is clear Ethernet and not WiFi connectivity is being used
- HomeSpan handles all reporting of connects/disconnects/reconnects just as it normally does for WiFi connections
- to establish Ethernet connectivity, simply use the Arduino-ESP32's ETH library by calling
ETH.begin()
in your sketch with the appropriate parameters for your Ethernet board- you must call
ETH.begin()
before callinghomeSpan.begin()
- you do not need to include
ETH.h
in your sketch - note that the Arduino-ESP32
ETH
library supports both direct-connect PHY as well as standalone SPI-based Ethernet boards
- you must call
- adds new homeSpan method
setConnectionCallback()
, which is a renamed version of the (now deprecated)setWifiCallbackAll
to reflect the fact that this method can be used with both Ethernet and WiFi connections
WiFi Enhancements
-
When connecting to a WiFi mesh network with multiple access points, HomeSpan now automatically connects to the access point with the strongest WiFi signal (i.e. the greatest RSSI)
- previously HomeSpan would simply connect to the first access point it found that matched the SSID specified by the user, even if other access points with the same SSID had stronger signals
- the BSSID (6-byte MAC address) of the access point to which HomeSpan is currently connected is provided in the Web Log as well as in the Serial Monitor in response to the 's' CLI command
-
New WiFi-management methods
- adds new homeSpan method
setConnectionTimes(uint32_t minTime, uint32_t maxTime, uint8_t nSteps)
that allows fine-tuning of how long HomeSpan wait for each connection attempt when trying to connect to a WiFi network (#896) - adds new homeSpan method
enableWiFiRescan(uint32_t iTime=1, uint32_t pTime=0, int thresh=3)
that causes HomeSpan to periodically re-scan for all access points matching the configured SSID and automatically switches to the access point with the strongest signal (#955)- useful after a mesh network is rebooted and HomeSpan initially reconnects to a more distance access point because a closer one with a stronger signal has not yet fully rebooted
- adds new homeSpan method
addBssidName(String bssid, string name)
that allows users to create optional display names for each access point in a WiFi mesh network according to their 6-byte BSSID addresses- when defined, HomeSpan will display both this name and the BSSID of an access point whenever presenting info on the Serial Monitor or writing to the Web Log
- adds new homeSpan method
setWifiBegin(void (*f)(const char *, const char *))
that allows users to create an alternative function that HomeSpan uses instead of simply callingWiFi.begin()
when attempting to connect to a WiFi network (#780)- provides ability to create customizations, such as using a different type of call to establish WiFi connectivity (e.g. connectivity to an enterprise network), or adding extra set-up functionality to be called while connectivity is being established (e.g. changing the WiFi power)
- adds new 'D' CLI command that forces HomeSpan to disconnect and then automatically re-connect to the configured WiFi network
- adds new 'Z' CLI command that scans a user's WiFi network environment and displays information about each SSID (including each BSSID for mesh networks with multiple access points broadcasting the same SSID) on the Serial Monitor
- if defined, the HomeSpan Status LED will turn on and double-blink whenever a WiFi scan is being performed
- adds new homeSpan method
-
DEPRECATIONS
setWifiCallbackAll
has been renamed tosetConnectionCallback()
to reflect the fact this callback can be used for both WiFi and Ethernet connectionssetWifiCallback
has been deprecated --- the more genericsetConnectionCallback()
should be used instead- requires any existing callbacks to be upgraded to add a single integer argument representing the number of connection attempts, similar to how
setWifiCallbackAll()
, and nowsetConnectionCallback()
, works
- requires any existing callbacks to be upgraded to add a single integer argument representing the number of connection attempts, similar to how
Multi-Threading
-
Made Web Log writing/reading thread-safe (#899)
- adds
shared_mutex
locks to web log writing and reading functions- while web log is being displayed, writing new log records is temporarily suspended
- while a new log record is being written, displaying or accessing the web log is temporarily suspended
- this fixes a latent bug related to a race condition between displaying the web log and writing a log record when the separate thread HomeSpan creates at start-up to handle initial contact with an NTP server records the time found
- adds
-
Made HomeSpan autopolling thread-safe
- add
shared_mutex
lock to polling task - adds new macro
homeSpanPAUSE
that temporarily suspends the polling task once it completes its current run- allows users to make modifications to HomeSpan Characteristics and perform any other HomeSpan functions from a separate thread without worrying about inconsistencies if HomeSpan polling was being run at the same time
- pauses only for the duration of the scope under which it was called --- polling resumes automatically after end of scope is reached
- adds new macro
homeSpanRESUME
that resumes running of the polling task- use is optional --- only needed if user wants to resume polling that was paused using
homeSpanPAUSE
prior to the end of scope is reached
- use is optional --- only needed if user wants to resume polling that was paused using
- adds new homeSpan method
std::shared_mutex& getMutex()
that returns theshared_mutex
used to lock the polling task- only needed if you want to create your own thread-locking lock management instead of using the above macros
- adds new MultiThreading Tutorial Example
- add
Web Log
-
Web Log can now auto-refresh from browser
- if a Web Log request from a browser includes the query string, refresh=N, HomeSpan will add an HTTP Refresh response header to the HTML it serves back to the browser to cause it to auto-refresh the Web Log request every N seconds
- N must be greater or equal to 1
- example: http://homespan-4e8eb8504e59.local/status?refresh=10
-
Web Log requests are now case-insensitive
- example: http://homespan-4e8eb8504e59.local/STATUS?REFRESH=10 is equivalent to above
Bug Fixes
- Fixes a latent bug that prevented compilation when the homeSpan methods
controllerListBegin()
andcontrollerListEnd()
were used in a sketch (# 8000 950)
Compatibility with Arduino-ESP32 v3.1.0 (IDF v5.3.2)
- Set new LEDC "deconfigure" parameter to false in LedPin
- Added logic to handle name change in macros SOC_TOUCH_VERSION_1 /2 to macro SOC_TOUCH_SENSOR_VERSION
Other
- Updated the documentation in the CustomNVSPartition Example to note that even with the addition of a custom partitions.csv file, you still need to set the Partition Scheme in the IDE to a scheme that provides APP partitions that are large enough to hold your sketch. This is because the Arduino IDE uses the scheme selected to determine the size of the APP partitions, and checks the size of the sketch against the size of these App partitions even though the IDE ultimately uses the partitions.csv file for the scheme once loading the sketch to the device
HomeSpan 2.0.0
Re-factored for compatibility with Arduino-ESP32 Board Manager version 3
- requires Arduino-ESP32 Board Manager 3.0.2 or later
- Espressif did not include the Sodium cryptography library in versions 3.0.0 and 3.0.1, which is required by HomeSpan
- all user-sketches written under HomeSpan 1.9.1 should work without modification under HomeSpan 2.0.0, with the exception of sketches in which the user directly accessed IDF-4 functionality, which may or may not be compatible with IDF-5
- supports use of the ESP32-C6 chip
- though the Arduino-ESP32 Board Manager also supports the ESP-H2, HomeSpan does not since the H2 does not have WiFi capabilities, as currently required
New API Functions
-
Complete re-write of the HomeSpan Pixel and RFControl libraries
- you can now instantiate both Pixel and RFControl objects in the same sketch (previously these classes were incompatible with each other and could not be used in the same sketch)
-
Expanded Pixel class functionality
- adds support for 5-color RGBWC (red, green, blue, warm-white, and cool-white) LEDs
- adds new method
Pixel::Color::WC()
to support setting warm-white / cool-white color values - adds new methods
Pixel::Color::CCT()
andPixel::setTemperatures()
to automatically set the warm-white / cool-white colors of a Pixel device based on whatever correlated color temperature (CCT) the user specifies (e.g. 3000K) - adds new constructor
Pixel(int pin, const char *pixelType)
that provides the ability to both select the colors and specify their transmission order (pixelType) to match a very wide variety of Pixel devices (ranging from pure-white LEDs to 5-color RGBWC LEDs)- deprecates constructor
Pixel(int pin, pixelType_t pixelType)
that limited pixelType to a pre-defined set of values. This constructor will be removed in future versions of HomeSpan
- deprecates constructor
- adds new method
boolean Pixel::hasColor(char c)
to determine whether an existing Pixel object supports any particular color- deprecates
boolean Pixel::isRGBW()
which only distinguished RGB from RGBW devices. This method will be removed in future versions of HomeSpan
- deprecates
- upgraded the PixelTester sketch to interactively step users through selecting and testing the correct pixelType for their device
- added new Pixel-RGBWC example demonstrating how to implement an RGBWC Pixel light-strip with separate Home App controls for the RGB and WC LED
- see the Pixels.md page for full details
❗ IMPORTANT SIZE CONSIDERATIONS ❗
- version 3 of the Arduino-ESP32 Board Manager has a much larger footprint than version 2
- the same HomeSpan sketch compiled under 1.9.1 will be approximately 200K larger when compiled under HomeSpan 2.0.0-rc.1
- as a result, HomeSpan sketches will no longer fit into the Default partition scheme which only allocates 1.3MB to an App partition
- HomeSpan sketches must instead be compiled under a larger partition scheme (such as Minimal SPIFFS, which provides for 1.9MB partitions)
- HOWEVER - Espressif does not support changing partition tables via OTA!
- changes to the partition table are ignored if a sketch is updated via OTA
- you can only update the partition table on a device if you load the sketch via the Serial port when connected to a computer
- this means that if you have remote device running a HomeSpan sketch using the Default partition scheme, you will not be able to migrate to HomeSpan 2.0.0 using OTA
- you must first connect the device directly to your computer, change the partition scheme to Minimal SPIFFS, and then update the sketch via the Serial port
- once HomeSpan has been successfully updated via the Serial Port using the new partition scheme, OTA can be used for any further updates (provided you don't need to subsequently change the partition scheme again for some other reason).
HomeSpan 2.0.0-rc.1
Re-factored for compatibility with Arduino-ESP32 Board Manager version 3
- requires Arduino-ESP32 Board Manager 3.0.2 or later
- Espressif did not include the Sodium cryptography library in versions 3.0.0 and 3.0.1, which is required by HomeSpan
- all user-sketches written under HomeSpan 1.9.1 should work without modification under HomeSpan 2.0.0, with the exception of sketches in which the user directly accessed IDF-4 functionality, which may or may not be compatible with IDF-5
- supports use of the ESP32-C6 chip
- though the Arduino-ESP32 Board Manager also supports the ESP-H2, HomeSpan does not since the H2 does not have WiFi capabilities, as currently required
New API Functions
-
Complete re-write of the HomeSpan Pixel and RFControl libraries
- you can now instantiate both Pixel and RFControl objects in the same sketch (previously these classes were incompatible with eachother and could not be used in the same sketch)
-
Expanded Pixel class functionality
- adds support for 5-color RGBWC (red, green, blue, warm-white, and cool-white) LEDs
- adds new method
Pixel::Color::WC()
to support setting warm-white / cool-white color values - adds new methods
Pixel::Color::CCT()
andPixel::setTemperatures()
to automatically set the warm-white / cool-white colors of a Pixel device based on whatever correlated color temperature (CCT) the user specifies (e.g. 3000K) - adds new constructor
Pixel(int pin, const char *pixelType)
that provides the ability to both select the colors and specify their transmission order (pixelType) to match a very wide variety of Pixel devices (ranging from pure-white LEDs to 5-color RGBWC LEDs)- deprecates constructor
Pixel(int pin, pixelType_t pixelType)
that limited pixelType to a pre-defined set of values. This constructor will be removed in future versions of HomeSpan
- deprecates constructor
- adds new method
boolean Pixel::hasColor(char c)
to determine whether an existing Pixel object supports any particular color- deprecates
boolean Pixel::isRGBW()
which only distinguished RGB from RGBW devices. This method will be removed in future versions of HomeSpan
- deprecates
- upgraded the PixelTester sketch to interactively step users through selecting and testing the correct pixelType for their device
- added new Pixel-RGBWC example demonstrating how to implement an RGBWC Pixel light-strip with separate Home App controls for the RGB and WC LED
- see the Pixels.md page for full details
❗ IMPORTANT SIZE CONSIDERATIONS ❗
- version 3 of the Arduino-ESP32 Board Manager has a much larger footprint than version 2
- the same HomeSpan sketch compiled under 1.9.1 will be approximately 200K larger when compiled under HomeSpan 2.0.0-rc.1
- as a result, HomeSpan sketches will no longer fit into the Default partition scheme which only allocates 1.3MB to an App partition
- HomeSpan sketches must instead be compiled under a larger partition scheme (such as Minimal SPIFFS, which provides for 1.9MB partitions)
- HOWEVER - Espressif does not support changing partition tables via OTA!
- changes to the partition table are ignored if a sketch is updated via OTA
- you can only update the partition table on a device if you load the sketch via the Serial port when connected to a computer
- this means that if you have remote device running a HomeSpan sketch using the Default partition scheme, you will not be able to migrate to HomeSpan 2.0.0 using OTA
- you must first connect the device directly to your computer, change the partition scheme to Minimal SPIFFS, and then update the sketch via the Serial port
- once HomeSpan has been successfully updated via the Serial Port using the new partition scheme, OTA can be used for any further updates (provided you don't need to subsequently change the partition scheme again for some other reason).
HomeSpan v1.9.1
New API Functions
-
New integrated support for TLV8 Characteristics
-
new
TLV8()
class library for the creation and management of TLV8 objects. Methods include:add()
- adds a TLV8 record containing a byte stream, string, numerical value, zero-length tag, or even another complete TLV8 objectfind()
- finds the TLV8 record matching a specified tag over an optionally-specified rangelen()
- returns the length of the specified TLV8 record
8000
print()
- prints each TLV8 record (or a range of records) to the Serial MonitorprintAll()
- recursively prints all sub-TLV8 objects to the Serial Monitorwipe()
- erases all records from a TLV8 object
-
new
TLV8_it()
iterators used to extract and read data from TLV8 records. Methods include:getTag()
- returns the numeric TAG for a TLV8 recordgetLen()
- returns the LENGTH of a TLV8 recordget()
- returns a pointer to the VALUE byte-stream of a TLV8 recordget()[]
- returns a particular byte in the VALUE byte-stream of a TLV8 recordgetVal()
- a template function to convert the VALUE byte-stream of a TLV8 record to a numeric value
-
new
homeSpan
methods to read and write TLV8 objects to and from a TLV CharacteristicgetTLV()
andgetNewTLV()
reads from a TLV8-based Characteristic into a TLV8 objectsetTLV()
writes TLV8 object into a TLV8-based Characteristic
-
added new
CUSTOM_CHAR_TLV8()
that allows for easy creation of custom TLV8 Characteristics -
added integrated support for new TLV8 Characteristic DisplayOrder
- sets the order in which the Input Sources for a Television Service are displayed for selection in the Home App
- credit to @zwaldowski (homebridge/HAP-NodeJS#644 (comment)) for reverse-engineering this undocumented Apple Characteristic, and to HomeBridge for documenting its UUID
-
added new Tutorial Example 22 - TLV8 Characteristics demonstrating use of the
TLV8()
class and TLV8 Characteristics -
see the new TLV8.md page for complete details and documentation
-
-
New methods to read Controller data (for advanced use-cases only) (#801)
- adds new
homeSpan
methodsetControllerCallback()
to set optional callback function that HomeSpan calls whenever a controller is added, removed, or updated - adds new
homeSpan
methodscontrollerListBegin()
andcontrollerListEnd()
- returns constant iterators to the beginning and end of the linked-list HomeSpan uses to store all controller data
- methods to read the controller data pointed to by such iterators include:
getID()
- returns a pointer to the 36-byte Device ID of the controllergetLTPK()
- a pointer to the 32-byte Long-Term Public Key of the controllerisAdmin()
- returns true if the controller has admin permission, else returns false
- see the API Reference for details
- adds new
-
New methods to read and set the IIDs of Services and Characteristics
- adds new
SpanService
methodgetIID()
that returns the IID of a Service - adds new
SpanCharacteristic
methodgetIID()
that returns the IID of a Characteristic - adds new
homeSpan
methodresetIID(int newIID)
that resets the IID count for the current Accessory - see the API Reference for details
- adds new
-
Added support for more Pixel chips (#781 / #784)
- new constructor
Pixel(uint8_t pin, [pixelType_t pixelType])
allows your to set the order in which colors are transmitted to the pixel chip, where pixelType is one of the following:- PixelType::RGB, PixelType::RBG, PixelType::BRG, PixelType::BGR, PixelType::GBR, PixelType::GRB
- PixelType::RGBW, PixelType::RBGW, PixelType::BRGW, PixelType::BGRW, PixelType::GBRW, PixelType::GRBW*
- deprecated previous constructor
Pixel(uint8_t pin, boolean isRGBW)
- this constructor will continue to work, but you will receive a warning during compilation that it has been deprecated
- users should switch to the new constructor to avoid potential compatibility issues with future versions of HomeSpan
- added new method
boolean isRGBW()
- returns true if Pixel was constructed as RGBW, else false if constructed as RGB only (i.e. no white LED)
- created new PixelTester sketch (found under Other-> Examples) to aid in determining the pixelType for any LED Strip
- new constructor
-
New Tutorial Example 21 - AccessoryIdentifier
- demonstrates how to trigger an Accessory's Identifier Characteristic, optionally used to help identify a device during initial pairing to the Home App
-
Converted the
getLinks()
SpanService method to a template function- new form is now:
vector<T> getLinks<T=SpanService *>(const char *serviceName=NULL)
- if template parameter, T, is specified, the elements of the returned vector will be cast into type T
- if serviceName is specified, only those services matching serviceName will be included in the return vector
- fully backwards-compatible with original
getLinks()
method
- new form is now:
-
New ability to halt the pulse generation for a ServoPin (#874)
- calling
set(NAN)
for a ServoPin halts the pulse generation, which (for most analog servos) allows the motor to be freely rotated - calling
set(position)
, where position equal the desired number of degrees, restarts the pulse generation and sets the servo position accordingly
- calling
Internal Updates
-
Added support for Characteristics that require the write-response protocol to process write requests (#801)
- not needed for any Characteristics that are currently supported by HomeSpan
- but available for use with any Custom Characteristics that may require the write-response protocol
- this feature is automatically enabled as needed - no user coding, setup, or configuration required
- write-response requests will be processed regardless of whether the Characteristic has the WR permission set
-
Added extra checks when using
setVal()
- a warning message is output on the Serial Monitor if
setVal()
is called to change the value of a Characteristic from within theupdate()
method at the same time the Home App is sending an update request for that value - does not apply if
setVal()
is called from withinupdate()
to change the value of a Characteristic in response to a write-response request from the Home App
- a warning message is output on the Serial Monitor if
-
Refactored client/slot management to save memory and prepare for future integration of Ethernet support
- fixed-array of Client/Socket connections replaced by dynamic linked-list
- serial interface now only shows active client connections (rather than a fixed list of client slots)
- deprecated
homeSpan.reserveSocketConnections()
- no longer needed since new HomeKit Architecture requires only one or two connections from a central Home Hub
- function throws compiler deprecation warning, but otherwise function does nothing
-
Allow dynamic variables to be used for the string arguments in
homeSpan.begin()
andhomeSpan.setHostNameSuffix()
(#837)- string variables are now fully copied into their own memory rather than simply copying the pointers
- allows local dynamic variables that go out of scope to be used as parameters
Bug Fixes
-
Fixed bug introduced in 1.9.0 that prevented
homeSpan.setPairingCode()
from saving (and subsequently using) the request Setup Pairing Code (#786)- this method now operates silently, unless an invalid pairing code is provided, in which case an error is reported to the Serial Monitor and the sketch is halted
- the process for setting the Pairing Code using the CLI 'S' command or via the Access Point are unchanged - confirmation messages are still output to the Serial Monitor and errors do not cause the sketch to halt
-
Fixed memory leak introduced in 1.9.0 that would fail to free a small temporary memory block created when verifying a new connection (#844)
- had no practical impact when using a Home Hub since Home Kit only creates a few permanent connections
- had significant impact when not using a Home Hub in cases where the Home App repeatedly drops and re-establishes connections, resulting in slow erosion of heap memory and then out-of-memory failure of the device after a few days (note use of HomeSpan without a Home Hub is not formally supported)
-
Fixed latent bug in SpanPoint
- HomeSpan would crash when printing SpanPoint configuration information to the Serial Monitor (the 'i' CLI command) if any of the instances of SpanPoint had receiveSize=0
- this bug never surfaced before since all the SpanPoint examples were based on receiving data and therefore had a non-zero receiveSize
Deleted Functions
-
Deleted
homeSpan.setMaxConnections()
, which had been deprecated many versions ago -
Deleted stand-alone
SpanRange
structure, which had been deprecated many versions ago- this has no impact on standard use of the Characteristic method
setRange()
- this has no impact on standard use of the Characteristic method
HomeSpan v1.9.0
New API Functions
-
New ability to "chain" homeSpan methods
- converted the following homeSpan methods that previously returned void to now return Span &:
- setControlPin, setStatusPin, setStatusPixel, setStatusDevice, setStatusAutoOff
- setApSSID, setApPassword, setApTimeout, setCommandTimeout, setLogLevel
- reserveSocketConnections, setPortNum, setHostNameSuffix, setQRID
- enableAutoStartAP, setApFunction, setWifiCredentials, setWifiCallback, setPairCallback, setStatusCallback
- setPairingCode, setSketchVersion, enableWebLog, setTimeServerTimeout, setWebLogCSS, setSerialInputDisable
- allows for chaining multiple homeSpan methods
- example:
homeSpan.setControlPin(21).setStatusPin(13);
- converted the following homeSpan methods that previously returned void to now return Span &:
-
New ability to add custom content to the Web Log through a user-defined callback function (#657)
- adds new homeSpan method
Span& setWebLogCallback(void (*func)(String &))
- provides a hook into the HTML that HomeSpan uses to generate the Web Log output
- a reference to a String is passed as the first argument to func after the HTML for the initial table is produced, but before the table is ended and the second table is started
- creating a function func to extend this String allows the user to add arbitrary data to additional rows of the initial table, as well as to optionally end the table and add a completely new block of custom HTML
- see Logging.md for details
- adds new homeSpan method
-
New ability to suppress WiFi "Trying to connect to..." messages (#670)
- adds new homeSpan method
Span& setVerboseWifiReconnect(bool verbose=true)
- set verbose to false to suppress WiFi "Trying to connect to..." messages from being logged to the Serial Monitor and Web Log
- see Reference.md for details
- adds new homeSpan method
-
Updated WiFi Callback functionality (#655)
- adds new homeSpan method
Span& setWifiCallbackAll(void (*func)(int count))
- similar to existing homeSpan method
setWiFiCallback(void (*func)())
except that func is called every time a WiFi connection is established or re-established after a disconnect - func must be of type void and accept a single int argument, count, that HomeSpan uses to pass the number of times a WiFi connection has been established or re-established
- see Reference.md for details
- adds new homeSpan method
-
New ability to trigger HomeSpan actions by power-cycling (or resetting) the device one or more times (#629)
- adds new homeSpan method
Span& setRebootCallback(void (*func)(uint8_t count), uint32_t upTime=5000)
- func must be of type void and accept one argument of type uint8_t
- func is called by HomeSpan after booting once upTime milliseconds have elapsed (default upTime=5000 ms if not specified)
- the parameter count, which is passed by HomeSpan to func, indicates the number of "short" reboots that have occurred prior to the current reboot, where a "short" reboot is any that occurs before upTime milliseconds have elapsed
- see Reference.md for details
- adds new homeSpan method
-
New ability to disable SpanPoint encryption (#712)
- adds new class-level method
SpanPoint::setEncryption(boolean encrypt)
- if encrypt set to true, encryption is enabled; if encrypt set to false, encryption is disabled
- by default, SpanPoint encryption is enabled unless this method is called to disable it
- if SpanPoint encryption is disabled on the main device, it must be disabled on all remote SpanPoint devices as well
- enabling/disabling SpanPoint encryption changes the maximum number of connections that can be supported by a single device:
- with encryption, max=7 remote devices
- without encryption, max=20 remote devices
- these limitations are a result of the underlying ESP-NOW protocol
- if exceeded, HomeSpan will provide warning messages on the Serial Monitor during start-up
- see NOW.md for details
- adds new class-level method
-
New ability to get handle of HomeSpan Auto Poll task (#725)
- adds homeSpan method
TaskHandle_t getAutoPollTask()
- returns the Task Handle for the HomeSpan Auto Poll Task (when invoked by
homeSpan.autoPoll()
), or NULL if Auto Polling is not used - see Reference.md for details
- adds homeSpan method
-
New ability to use Inverted or Touch Buttons as a Control Button (#701)
- adds triggerType as a second, optional argument to
Span& setControlPin(uint8_t pin, PushButton::triggerType_t triggerType=PushButton::TRIGGER_ON_LOW)
, where triggerType has the same meaning as in SpanButton:PushButton::TRIGGER_ON_LOW
- triggers when pin is driven LOW
- suitable for buttons that connect pin to GROUND (this is the default when triggerType is not specified)
PushButton::TRIGGER_ON_HIGH
- triggers when pin is driven HIGH
- suitable for buttons that connect pin to VCC (typically 3.3V)
PushButton::TRIGGER_ON_TOUCH
- uses the device's touch-sensor peripheral to trigger when a sensor attached to pin has been touched
- not available on ESP32-C3
- as an alternative, you can set triggerType to any user-defined function of the form
boolean(int arg)
to utilize any device as a Control Button
- see Reference.md for details
- adds triggerType as a second, optional argument to
-
New HomeSpan constants to reflect allowable states for each Characteristic (#679)
- can use named constants instead of integers when reading and writing values of applicable Characteristics
- very helpful since Apple is no longer publishing its non-commercial HAP document that provided a list and description of the states for each Characteristic
- example:
if(target.getNewVal()==target.ARM_STAY) {...}
- see ServiceList.md for an update list of Services, Characteristics, and their constants
-
New ability to name individual Services (#485)
- deprecated Characteristic::Name() and replaced with Characteristic::ConfiguredName() for all Services except the AccessoryInformation Service, which till requires Characteristic::Name()
- completely re-wrote Example 11 (ServiceNames) to reflect the new use of the ConfiguredName Characteristic
-
Updated the Services and Characteristics web page to provide functional descriptions and detailed specifications for every Service and Characteristic supported by HomeSpan
- page is autogenerated as needed from the structure and comments presented in certain HomeSpan library files
- includes a complete list of all allowed constants for each Characteristic (and their default values)
-
New Stepper Motor Drivers
- Stepper_UNIPOLAR: a generic driver for any 4-wire center-tapped unipolar motor
- Stepper_UNL2003: support for the UNL2003 driver board
- see Stepper.md for details
-
Removed dependencies on various "extra" #include files
- the following #include files are now embedded in HomeSpan.h and do not need to be specified in any sketch:
- extras/Pixel.h
- extras/RFControl.h
- extras/PwmPin.h
- extras/StepperControl.h
- automatic inclusion of these files does not yield a larger binary since the classes within each module are not linked into the final binary unless a class is explicitly used in your sketch (or by HomeSpan itself)
- including these files in sketch has no impact but is allowed (providing backwards compatibility for sketches that previously included these files)
- the following #include files are now embedded in HomeSpan.h and do not need to be specified in any sketch:
-
Additional Web Log functionality (#770)
- adds new homeSpan method
getWebLog(void (*f)(const char *, void *), void *args)
- when called, HomeSpan streams the current Web Log HTML text, and any optionally-specified user-data, args, directly to the user-defined function, f(), for user-defined processing
- setting the optional fourth argument of
homeSpan.enableWebLog()
to NULL sets the URL for the Web Log to NULL- this causes HomeSpan to ignore any HTTP requests for the Web Log page
- allows use of
enableWebLog()
to set the time from an NTP server without also serving Web Log pages
- see Logging.md for details
- adds new homeSpan method
Significant Refactoring to Optimize Memory Use
- HomeSpan can now support approximately TWICE the number of Accessories using the same amount of memory
- Minimized memory use also means much more room for users to add non-HomeSpan features to their sketch without running out of memory, especially if the non-HomeSpan code consumes a lot of stack space
- HomeSpan now automatically detects the presence of PSRAM (SPIRAM) and will utilize that extra memory to the largest extent possible to keep internal RAM free for certain HomeSpan functions and ESP32 functions (e.g. WiFi) that require internal RAM. Also keeps internal RAM free for use by any non-HomeSpan code that does not (or cannot) use PSRAM
- Changed HomeSpan's 41-Accessory limit to a 150-Accessory Limit (as specified by HAP) since it is now possible to create a device with many more than 41 Accessories without running out of memory, especially if PSRAM is used (#619)
- HomeSpan will print a warning to the Serial Monitor at boot-up if free internal RAM seems to be getting too low based on memory use before WiFi is started
- Refactoring included:
- converted all large fixed-size stack-based buffers to dynamically-sized heap-based buffers
- ensure applicable heap-based buffers use PSRAM when available
- added custom allocators to containers, and custom constructors to objects, to ensure they use PSRAM when available
- converted the static array that stored all pairing info for 16 Controllers to a linked-list only storing data for Controllers as needed
- HomeKit typically only assigns a few Controllers, so no need always reserve space for 16
- also frees up a lot of NVS space (since Controller pairing info is stored there)
- converted the containers holding the lists of required and optional Characteristics for each Service to a much more efficient storage class
...
HomeSpan v1.8.0
Updates
-
New Stepper Motor Control
- adds new StepperControl class that allows for smooth, uninterrupted operation of one or more stepper motors running in the background while HomeSpan continues to run simultaneously in the foreground
- includes drivers for the Toshiba TB6612 and Allegro A3967 stepper motor chips
- supports creation of user-defined drivers
- provides the following methods:
StepperControl *setStepType(int mode)
- sets the stepping mode (including microstepping)StepperControl *setAccel(float accelSize, float accelSteps)
- automatic acceleration and deceleration for smooth starts and stopsvoid move(int nSteps, uint32_t msDelay, endAction_t endAction)
- turns the motor a specified number of steps, with a specified delay between stepsvoid moveTo(int nPosition, uint32_t msDelay, endAction_t endAction)
- turns the motor to an absolute position, with a specified delay between stepsStepperControl *enable()
- enables the motor driverStepperControl *disable()
- disables the motor driverStepperControl *brake()
- puts the motor into a short brake stateint position()
- returns the absolute position of the motorvoid setPosition(int pos)
- resets the absolute position of the motorint stepsRemaining()
- returns the number steps remaining to turn the motor
- includes a fully worked example of a motorized window shade
- see Stepper.md for details
-
Upgrades to HomeSpan Web Log output (#563 and #566 - thanks @frankonski)
- adds new method
void homeSpan.setWebLogCSS(const char *css)
that allows you to define custom style sheets (CSS) for the Web Log text, tables, and background - adds charset=utf-8 to HTML responses to ensure proper handling of UTF-8 characters
- adds version numbers for the Sodium and MbedTLS libraries
- adds HomeKit pairing status
- adds text description of Reset Reason code
- see Logging.md for details
- adds new method
-
Upgrades to Web Log Time Server initialization (#553)
- the process for retrieving the time and date from an NTP server upon booting now runs in the background as a separate task
- HomeSpan is no longer blocked from running during the NTP query
- the default time-out for the NTP server query has been extended from 10 seconds to 120 seconds
-
Added methods to disable HomeSpan's use of the USB Serial port (#576)
- new Log Level, -1, causes HomeSpan to suppress all OUTPUT messages
- new homeSpan method
setSerialInputDisable(boolean val)
disables/re-enables HomeSpan's reading of CLI commands INPUT into the Arduino Serial Monitor - useful when the USB Serial port is needed to communicate with a separate Serial device instead of with the Serial Monitor
- new homeSpan method
boolean getSerialInputDisable()
returns true if HomeSpan's reading of CLI commands from the Serial Monitor is disabled, else returns false
-
Added ability to use a non-standard LED as the HomeSpan Status LED (#590)
- new homeSpan method
setStatusDevice(Blinkable *sDev)
sets the Status LED to the Blinkable object sDev - allows an LED connected to a pin expander, or any other non-standard LED controller (such as an inverted LED that lights when a pin is LOW instead of HIGH) to be used as the HomeSpan Status LED
- see Blinkable.md for details (including an example) on how to create Blinkable objects
- new homeSpan method
Bug Fix
-
Addressed a compilation error caused by a conflict between the name of an internal enum, "BUTTON", which is used by SpanButton, but also happens to be a macro definition used in the pins_arduino.h configuration files for the adafruit_feather_esp32_v2, adafruit_qtpy_esp32c3, and cytron_maker_feather_aiot_s3 boards (#564)
- Solution was to change the name of the enum from "BUTTON" to "HS_BUTTON" in SpanButton. This is a private enum and has no end-user impact
HomeSpan v1.7.2
Updates
-
New ability to set OTA password from within sketch (#503)
- adds
homeSpan.enableOTA(const char *pwd, boolean safeLoad=true)
method - see OTA.md for details
- adds
-
Added logic to allow duplicates of the same Custom Characteristic to be "defined" in more than one file in a sketch (#499)
- include
#define CUSTOM_CHAR_HEADER
before#include "HomeSpan.h"
in any file using a Custom Characteristic macro to create a duplicate of a Custom Characteristic that was already defined in another file - the allows the use of the same Custom Characteristic across multiple files in the same sketch without the compiler throwing a "redefinition error"
- see Reference.md for details
- include
-
Extended functionality of
setValidValues()
to work with more than just UINT8 Characteristics (#487)- now works with INT, UINT16, and UINT32 Characteristics, as well as UINT8 Characteristics
- will be ignored and throw a Warning message on the Serial Monitor if used with any other Characteristic format
-
Added two more parameters to
homeSpan.autoPoll()
that allow the user to set priority and CPU (#536)- new signature is
autoPoll(uint32_t stackSize=8192, uint32_t priority=1, uint32_t cpu=0)
- cpu parameter is ignored on single-processor boards
- see Reference.md for details
- new signature is
-
Added new methods to LedPin class that enable use of ESP32's built-in fade controls (#529)
int fade(float level, uint32_t fadeTime, int fadeType=ABSOLUTE)
automatically fades an LedPin to the level specified over the fadeTime (in milliseconds) specifiedint fadeStatus()
returns the current fading status (e.g. fading, not fading) of an LedPin- see PWM.md for details
-
Added ability to Clone the Pairing Data from one device to another (#543)
- adds new 'P' and 'C' commands to the CLI
- enables a broken device to be swapped for a new device (running the same sketch) without the need to unpair the old device or pair the new device
- avoids loss of automations, scenes, and any other Home App customizations associated with device
- new and old device can be different chips (e.g. ESP32-S2 versus ESP32-C3)
- see Cloning.MD for details
Bug Fix
-
Deleted initialization of WiFiClient (was being set to zero), which caused "Bad file number" errors when HomeSpan first boots (#508)
- this error message was only output to the Serial Monitor if the sketch was compiled with "Core Debug Level" set to "error" or above
HomeSpan 1.7.1
Updates
-
Improved SpanPoint scanning
- the last channel used for transmission is now automatically retained in NVS so that upon reboot this channel, rather than the lowest channel allowed by your channel mask, will become the first channel tried when transmissions resume
- helps improve battery life by likely reducing the number of channels SpanPoint may need to try upon reboot (because it starts scanning with a channel that was previously known to work)
- exception: the channel stored will not be used upon reboot if it is not allowed by your channel mask
- this feature requires no user configuration and is automatically implemented on any "remote" HomeSpan device
- this feature is not used for "main" HomeSpan devices connecting to HomeKit (the channel is set according to your WiFi network)
-
Connect an ESP8266 to HomeSpan using ESP-NOW
- added an option to the SpanPoint constructor indicating that SpanPoint should use the ESP32 device's AP MAC Address instead of its STA MAC Address when transmitting and receiving data via ESP-NOW
- this enables SpanPoint to receive ESP-NOW data from ESP8266 devices
- without this option, data transmission from a "Remote" ESP8266 device to the "Main" ESP32 device running HomeSpan fail as soon as HomeSpan connects to a central WiFi network (this is not an issue when the Remote device is also an ESP32)
- added a list of all SpanPoint objects instantiated in a sketch showing their parameters and associated MAC Addresses, along with current WiFi channel being used by the device, to the HomeSpan Info displayed in the Serial Monitor when typing 'i' into the CLI
- added a detailed example, RemoteDevice8266, illustrating how to configure ESP-NOW on an ESP8266 so it can transmit data to an ESP32 running HomeSpan
- see the SpanPoint page for full details
- added an option to the SpanPoint constructor indicating that SpanPoint should use the ESP32 device's AP MAC Address instead of its STA MAC Address when transmitting and receiving data via ESP-NOW
-
New SpanToggle class
- similar to SpanButton, but provides functionality to read the state of a toggle-switch
- calls the
button()
method within a Service whenever the switch is toggled from one position to another - automatically debounces the switch to prevent false triggers
- include a
posiiton()
method that returns the state of the toggle switch (CLOSED or OPEN) - useful for implementing Contact Sensors
- see the API Reference for full details
-
Added TelevisionSpeaker Service
- allows user to control the volume of a Television from Apple's Remote App (found in the Control Panel on an iPhone)
- updated Television example to include this new Service
-
Added HAP-R2 DATA format to store and transmit byte-array Characteristics
- includes new methods
setData()
,getData()
, andgetNewData()
, which are analogous tosetVal()
,getVal()
, andgetNewVal()
- includes new macro
CUSTOM_CHAR_DATA()
for creating custom byte-array Characteristics - note that HAP-R2 does not currently include any Characteristics that use the DATA format, but other applications, such as Eve for HomeKit, do make use of this format
- see the API Reference for full details
- includes new methods
-
Added optional flag to LedPin that inverts the PWM output signal
- useful for generating two, separate out-of-phase PWM signals (one inverted, one not) to drive certain two-pin devices in a push/pull manner, such as a piezo-electric buzzer
-
Relocated the Other Examples folder so that it is now a subfolder of "examples"
- required for proper displaying and access to the examples when using version 2 of the Arduino IDE
-
Added logic to prevent the extraneous broadcasting of an Access Point SSID when SpanPoint is being used
- since SpanPoint starts WiFi in AP+STA mode when data is to be received, this caused the device to broadcast its AP SSID, even though the device was not running an access point server