Toaster with web server

Arduino files download: Sonoff_toaster_timer

This is really not a toaster with a web server, but a toaster that is controlled by a Sonoff Wifi switch, that is running a web server. There were two objectives with this project:

  • To be able to continue using my toaster that had a mechanical problem: It didn’t release the bread when time was up – Instead it continued toasting for ever. This is my second toaster of the same type that breaks. It’s obviously not reliable, but it does take long slices of bread
  • To be able to sequence the toasting like this: Toast-Pause-Toast-Stop. I had previously noticed that the toast quality was increased significantly when I did this manually – The slices didn’t get dry on the outside and wet on the inside. The pause is 30s long, to allow water to steam off of the bread before the last half minute of heat is applied

There are several reasons that I couldn’t use the Sonoff power switch and its control app EWeLink as it is:

  • It doesn’t work without Internet
  • Cloud server issues: Sonoff connects to an online web server to store settings and keep track of time etc. When I bought my 4 Sonoffs they couldn’t connect to the server because it was overloaded (?) and if they finally connected, their behavior was generally unreliable. It went on like that for a week, then I uninstalled the EWeLink app and threw the switches in a drawer for half a year
  • The timing was too inexact. If I recall correctly, the finest resolution is 1 minute
  • Way too limited scheduling: It was not possible to make an On-Off sequence. I wanted something like: On (2min), Off (30s), On (30s), Off. The only option in EWeLink was to turn On or Off at a certain time of the day
  • What happens if the Internet connection breaks while some appliance is on

 The project, Sonoff controlled by a local web page

The Sonoff contains an ESP8266 processor that does most of the work. Most importantly it has Wifi capabilities, which is why it’s used in many “Internet of Things”-applications. It’s possible to run a web server on the ESP8266, and have the user interface on a web page control the ESP8266 program. So in my case it serves a HTML / Javascript page with five buttons and a simple progress bar. The buttons select one of three “Toast Sequence Programs”, a “One-Shot 30s Toast Program” or the “Immediate Stop”. The shortest toast program is for white bread that is a bit dry, the longest is for dark bread that is frozen.

The Stop button doesn’t fit on my medieval iPhone 5 screen

New firmware, Arduino,

To upload firmware to the ESP8266. I used Arduino IDE 1.8.1 and a USB-Serial TTL converter. I followed these instructions for wiring:

Sorry, the power cord just popped off

There was also info on what libraries needed to be installed, how to set up an ESP web server, connect to Wifi and more. A good place to get started.

Maybe not randomnerdtutorials, after all

I soon realized that the code on randomnerdtutorials would be dangerous for this project. It works something like this: When you click a button on the web page, a new page is loaded. Appended to the URL is the name of the button that you clicked. This is a common way to pass data between html pages. The problem is that when the toast program is finished, it’s quite possible that you still have this page (with the button name) loaded in your web browser. Which means that if you reload the page (which can happen automatically in many situations, ie on a computer restart) the toaster will start again.


Then I found this page: that demonstrates using AJAX XMLHttpRequest techniques to do calls without reloading the page. It was a better fit for my needs in many ways:

  • URL doesn’t change when you click a button
  • During development, the HTML code is kept in a well-formatted separate header file. When uploaded to ESP, the HTML is stored in Flash memory using the Arduino Flash memory routines. When the program runs, the HTML is read in to RAM when needed. Many examples online that do this use the SPIFF file system instead of Arduino Flash memory routines. SPIFF requires separate manual uploads from the computer to the ESP. I didn’t want to learn that in this project, I already had too many things that could go wrong
  • CSS styles in the header – I knew I didn’t want to download online (Bootstrap or similar) CSS definitions to my ESP at runtime. Because then it will fail if there’s no Internet connection. One of the reasons to do this project to begin with, was to make it suffice with a local network

The circuits4you code is a bit hard to understand, partly because there are about 10 different variables and handlers with similar names, partly because of the involved parallel code structures in HTML, Javascript and C. That’s why people hate web development. Also there were some small errors in the code :) Anyone who has done some HTML can probably spot this one:

server.send(200,”text/plane”, ledState); //Send web page

It’s not like we’re going to send an airplane to the web server. Also, data stored in Flash memory can’t be read into a C String variable like this:

String s = MAIN_page; //Read HTML contents

I changed it to:

String s = FPSTR(MAIN_page);   //Read HTML contents

Here’s the finished ESP8266 code, which is actually an Arduino sketch. It could be optimized a bit, and the States and Steps could be better clarified but still

And here’s the code for the HTML page. It needs to sit in a file called index_html.h next to the main sketch file


Upper Left is the Sonoff. The Green Led shows the state: On for Toast, Flashing green for Pause

Helpful links

Reprogram Sonoff Smart Switch with Web Server

ESP8266 ajax – update part of web page without refreshing

ESP8266 Timer / ticker examples