James,
I believe I have a working sketch that is sort of the best of both worlds. The NodeMCU ESP32 will handle all timing of the ‘button press sequences’ so no reliance on the ST cloud for that. However, you will see 4 devices created in SmartThings which will allow you to ‘monitor’ the brewing cycle if you desire. (Note, the toggling of the power button, lid switch, and brew button are only 1 second each, so visibly watching this in the ST Classic app may not be very useful.)
OK, here are a few useful tidbits of information:
- In your ST_Anything library, you will find a file named ‘constants.h’ which you will need to edit. Please UNCOMMENT the following line as shown below and save the file. This will prevent automatic refresh updates from the ESP32 to SmartThings, which would screw up the sequencing of the various digital outputs during the brewing cycle.
#define DISABLE_REFRESH //If uncommented, will disable periodic refresh of the sensors and executors states to the ST Cloud - improves performance, but may reduce data integrity
-
This ST_Anything_Keurig sketch creates 4 Timed Relay devices.
- The first one (relaySwitch1) is the one that is used to start the brewing cycle. It will appear as ON in SmartThings for the entire 900,000ms (15min). Turning this off manually via the ST app is not recommended. This device should Turned ON to start the sequence as part of your Alexa Good Morning Routine.
- The second one (relaySwitch2) is used to toggle the power button. It is used at the start of the brewing cycle to turn on the unit, and again at the end to turn off the unit. It’s output pin is held for 1000ms to accomplish this. Do NOT manually change this device from within the ST App.
- The third one (relaySwitch3) is used to toggle the lid. It is used at the start of the brewing cycle after the unit is powered on. It’s output pin is held for 1000ms to accomplish this. Do NOT manually change this device from within the ST App.
- The fourth one (relaySwitch4) is used to start the brewing. It is used at the start of the brewing cycle after the lid has been cycled. It’s output pin is held for 1000ms to accomplish this. Do NOT manually change this device from within the ST App.
-
The GPIO pins are defined in the sketch for the Power (GPIO19), Lid (GPIO18), and Brewing (GPIO5). These should be wired into your Keurig machine. Do NOT wire pin 23 to anything! I just needed a spare pin for the overall brewing CYCLE timer.
-
Based on your old sketch, it appears that the digital output pins were being pulled LOW to simulate the button presses. I have reproduced this behavior in the definition of the S_TimeRelay devices.
-
All of the sequencing of the brewing cycle is being handled within the callbackSend() routine. It should be fairly straightforward to understand and tweak as you see fit.
-
As always, you’ll need to edit the sketch to add your WiFi credentials
Hope this helps get you going!
//******************************************************************************************
// File: ST_Anything_Keurig_ESP32WiFi.ino
// Author: Dan G Ogorchock
//
// Summary: This Arduino Sketch, along with the ST_Anything library and the revised SmartThings
// library, demonstrates the ability of one ESP32 to implement
// a multi input/output custom device for integration into SmartThings.
// The ST_Anything library takes care of all of the work to schedule device updates
// as well as all communications with the ESP32's WiFi.
//
// ST_Anything_Keurig implements the following ST Capabilities as a demo of what is possible with a single ESP32
// - 1 x Switch devices (used to turn on a digital output (e.g. LED, relay, etc...)
//
// Change History:
//
// Date Who What
// ---- --- ----
// 2020-01-26 Dan Ogorchock Original Creation
//
//
//******************************************************************************************
//******************************************************************************************
// SmartThings Library for ESP32WiFi
//******************************************************************************************
#include <SmartThingsESP32WiFi.h>
//******************************************************************************************
// ST_Anything Library
//******************************************************************************************
#include <Constants.h> //Constants.h is designed to be modified by the end user to adjust behavior of the ST_Anything library
#include <Device.h> //Generic Device Class, inherited by Sensor and Executor classes
#include <Sensor.h> //Generic Sensor Class, typically provides data to ST Cloud (e.g. Temperature, Motion, etc...)
#include <Executor.h> //Generic Executor Class, typically receives data from ST Cloud (e.g. Switch)
#include <InterruptSensor.h> //Generic Interrupt "Sensor" Class, waits for change of state on digital input
#include <PollingSensor.h> //Generic Polling "Sensor" Class, polls Arduino pins periodically
#include <Everything.h> //Master Brain of ST_Anything library that ties everything together and performs ST Shield communications
#include <EX_Switch.h> //Implements an Executor (EX) via a digital output to a relay
#include <S_TimedRelay.h> //Implements a Sensor to control a digital output pin with timing/cycle repeat capabilities
//******************************************************************************************
//Define which Arduino Pins will be used for each device
//******************************************************************************************
//"RESERVED" pins for ESP32 - best to avoid
#define PIN_0_RESERVED 0 //reserved ESP32 boot/program upload
#define PIN_1_RESERVED 1 //reserved ESP32 for TX0
#define PIN_3_RESERVED 3 //reserved ESP32 for RX0
#define PIN_6_RESERVED 6 //reserved ESP32 for flash
#define PIN_7_RESERVED 7 //reserved ESP32 for flash
#define PIN_8_RESERVED 8 //reserved ESP32 for flash
#define PIN_9_RESERVED 9 //reserved ESP32 for flash
#define PIN_10_RESERVED 10 //reserved ESP32 for flash
#define PIN_11_RESERVED 11 //reserved ESP32 for flash
//Digital Pins
//KEURIG Special Logic
#define PIN_CYCLE 23 //Active during complete automated brewing cycle (nothing wired to this pin!!!)
#define PIN_POWER 19 //Power Switch
#define PIN_LID 18 //Lid Switch
#define PIN_BREW 5 //Brew Switch
bool brewingCycleActive;
//******************************************************************************************
//ESP832 WiFi Information
//******************************************************************************************
String str_ssid = "yourSSIDhere"; // <---You must edit this line!
String str_password = "yourWiFiPasswordHere"; // <---You must edit this line!
IPAddress ip(192, 168, 1, 233); //Device IP Address // <---You must edit this line!
IPAddress gateway(192, 168, 1, 1); //Router gateway // <---You must edit this line!
IPAddress subnet(255, 255, 255, 0); //LAN subnet mask // <---You must edit this line!
IPAddress dnsserver(192, 168, 1, 1); //DNS server // <---You must edit this line!
const unsigned int serverPort = 8090; // port to run the http server on
// Smartthings Hub Information
IPAddress hubIp(192, 168, 1, 149); // smartthings hub ip // <---You must edit this line!
const unsigned int hubPort = 39500; // smartthings hub port
//const unsigned int hubPort = 39501; // hubitat elevation hub port
//******************************************************************************************
//st::Everything::callOnMsgSend() optional callback routine. This is a sniffer to monitor
// data being sent to ST. This allows a user to act on data changes locally within the
// Arduino sktech.
//******************************************************************************************
void callbackSend(const String &msg)
{
String strTemp = msg;
// Serial.print(F("ST_Anything CallbackSend: Sniffed data = "));
// Serial.println(msg);
//TODO: Add local logic here to take action when a device's value/state is changed
//Masquerade as the ThingShield to send data to the Arduino, as if from the ST Cloud (uncomment and edit following line)
//st::receiveSmartString("Put your command here!"); //use same strings that the Device Handler would send
if (brewingCycleActive == false) {
if (strTemp == "relaySwitch1 on") {
Serial.println("");
Serial.println("Brewing Cycle Started");
Serial.println("");
brewingCycleActive = true;
Serial.println("");
Serial.println("Toggling Power Switch to turn on Keurig");
Serial.println("");
st::receiveSmartString("relaySwitch2 on"); //Cycle Power
}
}
else {
if (strTemp == "relaySwitch2 off") {
delay(5000);
Serial.println("");
Serial.println("Toggling Lid Switch");
Serial.println("");
st::receiveSmartString("relaySwitch3 on"); //Toggle Lid Switch
}
if (strTemp == "relaySwitch3 off") {
delay(5000);
Serial.println("");
Serial.println("Toggling Brew Switch");
Serial.println("");
st::receiveSmartString("relaySwitch4 on"); //Toggle Brew Switch
}
if (strTemp == "relaySwitch1 off") { //Cycle is complete
brewingCycleActive = false;
Serial.println("");
Serial.println("Brewing Cycle Complete");
Serial.println("");
Serial.println("Toggling Power Switch to turn off Keurig");
Serial.println("");
st::receiveSmartString("relaySwitch2 on"); //Cycle Power
}
}
}
//******************************************************************************************
//Arduino Setup() routine
//******************************************************************************************
void setup()
{
brewingCycleActive = false;
//******************************************************************************************
//Declare each Device that is attached to the Arduino
// Notes:
// - For details on each device's constructor arguments below, please refer to the
// corresponding header (.h) and program (.cpp) files.
// - The new Composite Device Handler is comprised of a Parent DH and various Child
// DH's. The names used below MUST not be changed for the Automatic Creation of
// child devices to work properly. Simply increment the number by +1 for each duplicate
// device (e.g. contact1, contact2, contact3, etc...) You can rename the Child Devices
// to match your specific use case in the ST Phone Application.
//******************************************************************************************
//Polling Sensors
//Interrupt Sensors
//Special sensors/executors (uses portions of both polling and executor classes)
static st::S_TimedRelay sensor1(F("relaySwitch1"), PIN_CYCLE, LOW, true, 900000, 0, 1); //Complete brewing cycle - 15 minutes
static st::S_TimedRelay sensor2(F("relaySwitch2"), PIN_POWER, LOW, true, 1000, 0, 1); //Power Switch
static st::S_TimedRelay sensor3(F("relaySwitch3"), PIN_LID, LOW, true, 1000, 0, 1); //Lid Switch
static st::S_TimedRelay sensor4(F("relaySwitch4"), PIN_BREW, LOW, true, 1000, 0, 1); //Brew Switch
//Executors
//static st::EX_Switch executor1(F("switch1"), PIN_SWITCH_1, LOW, true);
//*****************************************************************************
// Configure debug print output from each main class
// -Note: Set these to "false" if using Hardware Serial on pins 0 & 1
// to prevent communication conflicts with the ST Shield communications
//*****************************************************************************
st::Everything::debug=true;
st::Executor::debug=true;
st::Device::debug=true;
st::PollingSensor::debug=true;
st::InterruptSensor::debug=true;
//*****************************************************************************
//Initialize the "Everything" Class
//*****************************************************************************
//Initialize the optional local callback routine (safe to comment out if not desired)
st::Everything::callOnMsgSend = callbackSend;
//Create the SmartThings ESP32WiFi Communications Object
//STATIC IP Assignment - Recommended
st::Everything::SmartThing = new st::SmartThingsESP32WiFi(str_ssid, str_password, ip, gateway, subnet, dnsserver, serverPort, hubIp, hubPort, st::receiveSmartString);
//DHCP IP Assigment - Must set your router's DHCP server to provice a static IP address for this device's MAC address
//st::Everything::SmartThing = new st::SmartThingsESP32WiFi(str_ssid, str_password, serverPort, hubIp, hubPort, st::receiveSmartString);
//Run the Everything class' init() routine which establishes WiFi communications with SmartThings Hub
st::Everything::init();
//*****************************************************************************
//Add each sensor to the "Everything" Class
//*****************************************************************************
st::Everything::addSensor(&sensor1);
st::Everything::addSensor(&sensor2);
st::Everything::addSensor(&sensor3);
st::Everything::addSensor(&sensor4);
//*****************************************************************************
//Add each executor to the "Everything" Class
//*****************************************************************************
//st::Everything::addExecutor(&executor1);
//*****************************************************************************
//Initialize each of the devices which were added to the Everything Class
//*****************************************************************************
st::Everything::initDevices();
}
//******************************************************************************************
//Arduino Loop() routine
//******************************************************************************************
void loop()
{
//*****************************************************************************
//Execute the Everything run method which takes care of "Everything"
//*****************************************************************************
st::Everything::run();
}