• Система автоматизации с открытым исходным кодом на базе esp8266/esp32 микроконтроллеров и приложения IoT Manager. Наша группа в Telegram

esphttpd -> артефакты на страницах

Kitaro

New member
Добрый день, собирал ли кто вебсервер на основе esphttpd из UDK?
На страницах вылазят артефакты - хвосты кода, которых нет в усходном коде страницы, заливаемом в ESP, но которые появляются при компоновке страницы и отображении в браузере. Появляются в конце страницы, перед тегом </body>
Кто-нить сталкивался, победил?
 

Юрий Ботов

Moderator
Команда форума
То о чем вы говорите обычно бывает либо если вы забыли закрывающие тэги где то в html либо если браузер не распознал принятую информацию как html, вы с сервера не послали заголовок, либо весь либо его кусок с contenttype
 

Kitaro

New member
Врядли я что-то забыл, я беру страницу, что идет с примером, скажем wifi.tpl
вот код, что льется в ESP
Код:
<html><head><title>WiFi connection</title>
<link rel="stylesheet" type="text/css" href="style.css">
<script type="text/javascript" src="140medley.min.js"></script>
<script type="text/javascript">

var xhr=j();
var currAp="%currSsid%";

function createInputForAp(ap) {
    if (ap.essid=="" && ap.rssi==0) return;
    var div=document.createElement("div");
    div.id="apdiv";
    var rssi=document.createElement("div");
    var rssiVal=-Math.floor(ap.rssi/51)*32;
    rssi.className="icon";
    rssi.style.backgroundPosition="0px "+rssiVal+"px";
    var encrypt=document.createElement("div");
    var encVal="-64"; //assume wpa/wpa2
    if (ap.enc=="0") encVal="0"; //open
    if (ap.enc=="1") encVal="-32"; //wep
    encrypt.className="icon";
    encrypt.style.backgroundPosition="-32px "+encVal+"px";
    var input=document.createElement("input");
    input.type="radio";
    input.name="essid";
    input.value=ap.essid;
    if (currAp==ap.essid) input.checked="1";
    input.id="opt-"+ap.essid;
    var label=document.createElement("label");
    label.htmlFor="opt-"+ap.essid;
    label.textContent=ap.essid;
    div.appendChild(input);
    div.appendChild(rssi);
    div.appendChild(encrypt);
    div.appendChild(label);
    return div;
}

function getSelectedEssid() {
    var e=document.forms.wifiform.elements;
    for (var i=0; i<e.length; i++) {
        if (e[i].type=="radio" && e[i].checked) return e[i].value;
    }
    return currAp;
}


function scanAPs() {
    xhr.open("GET", "wifiscan.cgi");
    xhr.onreadystatechange=function() {
        if (xhr.readyState==4 && xhr.status>=200 && xhr.status<300) {
            var data=JSON.parse(xhr.responseText);
            currAp=getSelectedEssid();
            if (data.result.inProgress=="0" && data.result.APs.length>1) {
                $("#aps").innerHTML="";
                for (var i=0; i<data.result.APs.length; i++) {
                    if (data.result.APs[i].essid=="" && data.result.APs[i].rssi==0) continue;
                    $("#aps").appendChild(createInputForAp(data.result.APs[i]));
                }
                window.setTimeout(scanAPs, 20000);
            } else {
                window.setTimeout(scanAPs, 1000);
            }
        }
    }
    xhr.send();
}


window.onload=function(e) {
    scanAPs();
};
</script>
</head>
<body>
<div id="main">
<p>
Current WiFi mode: %WiFiMode%
</p>
<p>
Note: %WiFiapwarn%
</p>
<form name="wifiform" action="connect.cgi" method="post">
<p>
To connect to a WiFi network, please select one of the detected networks...<br>
<div id="aps">Scanning...</div>
<br>
WiFi password, if applicable: <br />
<input type="text" name="passwd" val="%WiFiPasswd%"> <br />
<input type="submit" name="connect" value="Connect!">
</p>
</div>
</body>
</html>
А вот что видно в браузере
Код:
<html><head>
<meta http-equiv="content-type" content="text/html; charset=windows-1251"><title>WiFi connection</title>
<link rel="stylesheet" type="text/css" href="WiFi%20connection_files/style.css">
<script type="text/javascript" src="WiFi%20connection_files/140medley.js"></script>
<script type="text/javascript">

var xhr=j();
var currAp="Power AP";

function createInputForAp(ap) {
    if (ap.essid=="" && ap.rssi==0) return;
    var div=document.createElement("div");
    div.id="apdiv";
    var rssi=document.createElement("div");
    var rssiVal=-Math.floor(ap.rssi/51)*32;
    rssi.className="icon";
    rssi.style.backgroundPosition="0px "+rssiVal+"px";
    var encrypt=document.createElement("div");
    var encVal="-64"; //assume wpa/wpa2
    if (ap.enc=="0") encVal="0"; //open
    if (ap.enc=="1") encVal="-32"; //wep
    encrypt.className="icon";
    encrypt.style.backgroundPosition="-32px "+encVal+"px";
    var input=document.createElement("input");
    input.type="radio";
    input.name="essid";
    input.value=ap.essid;
    if (currAp==ap.essid) input.checked="1";
    input.id="opt-"+ap.essid;
    var label=document.createElement("label");
    label.htmlFor="opt-"+ap.essid;
    label.textContent=ap.essid;
    div.appendChild(input);
    div.appendChild(rssi);
    div.appendChild(encrypt);
    div.appendChild(label);
    return div;
}

function getSelectedEssid() {
    var e=document.forms.wifiform.elements;
    for (var i=0; i<e.length; i++) {
        if (e[i].type=="radio" && e[i].checked) return e[i].value;
    }
    return currAp;
}


function scanAPs() {
    xhr.open("GET", "wifiscan.cgi");
    xhr.onreadystatechange=function() {
        if (xhr.readyState==4 && xhr.status>=200 && xhr.status<300) {
            var data=JSON.parse(xhr.responseText);
            currAp=getSelectedEssid();
            if (data.result.inProgress=="0" && data.result.APs.length>1) {
                $("#aps").innerHTML="";
                for (var i=0; i<data.result.APs.length; i++) {
                    if (data.result.APs[i].essid=="" && data.result.APs[i].rssi==0) continue;
                    $("#aps").appendChild(createInputForAp(data.result.APs[i]));
                }
                window.setTimeout(scanAPs, 20000);
            } else {
                window.setTimeout(scanAPs, 1000);
            }
        }
    }
    xhr.send();
}


window.onload=function(e) {
    scanAPs();
};
</script>
</head>
<body>
<div id="main">
<p>
Current WiFi mode: Client
</p>
<p>
Note: Click <a href="http://192.168.137.238/wifi/setmode.cgi?mode=2">here</a> to go to standalone AP mode.
</p>
<form name="wifiform" action="connect.cgi" method="post">
<p>
To connect to a WiFi network, please select one of the detected networks...<br>
</p><div id="aps"><div id="apdiv"><input name="essid" value="Guests" id="opt-Guests" type="radio"><div class="icon" style="background-position: 0px -96px;"></div><div class="icon" style="background-position: -32px 0px;"></div><label for="opt-Guests">Guests</label></div><div id="apdiv"><input name="essid" value="TEST-NPS" id="opt-TEST-NPS" type="radio"><div class="icon" style="background-position: 0px -96px;"></div><div class="icon" style="background-position: -32px -64px;"></div><label for="opt-TEST-NPS">TEST-NPS</label></div><div id="apdiv"><input name="essid" value="Guests" id="opt-Guests" type="radio"><div class="icon" style="background-position: 0px -96px;"></div><div class="icon" style="background-position: -32px 0px;"></div><label for="opt-Guests">Guests</label></div><div id="apdiv"><input name="essid" value="Power AP" id="opt-Power AP" checked="checked" type="radio"><div class="icon" style="background-position: 0px -128px;"></div><div class="icon" style="background-position: -32px -64px;"></div><label for="opt-Power AP">Power AP</label></div><div id="apdiv"><input name="essid" value="Guests" id="opt-Guests" type="radio"><div class="icon" style="background-position: 0px -96px;"></div><div class="icon" style="background-position: -32px 0px;"></div><label for="opt-Guests">Guests</label></div></div>
<br>
WiFi password, if applicable: <br>
<input name="passwd" val="shall we dance" type="text"> <br>
<input name="connect" value="Connect!" type="submit">
<p></p>
</form></div>


br /&gt;
<input name="connect" value="Connect!" type="submit">
<p></p>



</body></html>

артефакт появляется между </form></div> и </body></html> и имеет вид куска кода, а точнее его последних строк:


br /&gt;
<input name="connect" value="Connect!" type="submit">
<p></p>
 

Юрий Ботов

Moderator
Команда форума
Так где HTTP заголовки то???

В минимале они выглядят подобным образом:
Код:
HTTP/1.1 200 OK\r\nContent-Type: text/html\r\n\r\n
а чтобы не тормозило надо еще и длину передаваемого файла указывать.

Вот это почитайте: Что такое Http заголовки (Http headers). Общая теория.
 

Kitaro

New member
Я понял, Вы пытаетесь мне сказать, что esphttpd неправильно обрабатывает запросы
Код:
HTTP/1.1 200 OK
Server: esp8266-httpd/0.4
Transfer-Encoding: chunked
Content-Type: text/html
Так я собственно о том же и спрашиваю, я могу переписать и вникнуть в библиотеку перефирии, но в стек HTTP я не влезу, в силу отсутствия нужных знаний, и переписать его я не смогу.
Вот и спрашиваю, сталкивался ли кто с чем-то подобным и как лечил...
версия esphttpd из UDK Текущая стабильная версия: 2.2.1 от 30.10.2016

upd:
а
Код:
<html><head><title>Test</title>
<!--<link rel="stylesheet" type="text/css" href="style.css">-->
<!--<meta http-equiv="refresh" content="60" > 13.57-->
<meta charset=UTF-8>
<script type="text/javascript">
    String.format = function() {
    var s = arguments[0];
    for (var i = 0; i < arguments.length - 1; i++) {
    var reg = new RegExp("\\{" + i + "\\}", "gm");
    s = s.replace(reg, arguments[i + 1]);
    }
    return s;
    }
function myFunction() {

    var t = document.getElementById("myRange").value;
    var x = (t%60);
    if ( x < 10 )
        { x = "0" + x; }
    var y = (t-x)/60;
    if ( y < 10 )
        { y = "0" + y; }
    document.getElementById("demo").innerHTML = "" + y + ":" + x;
}
window.onload=function(e) {
    myFunction()
    };
</script>
</head>
<body>
<p> </p>
<p> </p>
<p> </p>
<div id="main">
<form method="post" action="led.cgi">
<input type="submit" name="led" value="255">
<input type="submit" name="led" value="0">
</form>
<input type="range" id="myRange" min="0" max="1440" step="5" value="540" onchange="myFunction()">
<p id="demo"></p>
</div>
</body>
</html>

вообще загружает
Код:
<html><head><title>Test</title>
<!--<link rel="stylesheet" type="text/css" href="style.css">-->
<!--<meta http-equiv="refresh" content="60" > 13.57-->
<meta charset=UTF-8>
<script type="text/javascript">
    String.format = function() {
    var s = arguments[0];
    for (var i = 0; i < arguments.length - 1; i++) {
    var reg = new RegExp("\\{" + i + "\\}", "gm");
    s = s.replace(reg, arguments[i + 1]);
    }
    return s;
    }
function myFunction() {

    var t = document.getElementById("myRange").value;
    var x = (t
 
Последнее редактирование:

Kitaro

New member
Мдя... лучшее враг хорошего.
Если после отладки страницы ее всю свернуть в одну строку, артефакты уходят... Но все таки хотелось бы знать, это все результат моих издевательств над кодом или это фича?
 

Kitaro

New member
ну, сами библиотеки esphttpd я не модифицировал.
скомпили только что пример из UDK, там точно также есть артефакты на странице, скажем, мигания светодиодом, если взять эту страницу, что идет в примере и свернуть в строку - артефакты уходят.
Я-то для себя нашел как исправить, просто интересно, никто с таким не сталкиваля что-ли, или просто не заморачивался?
 
Взял библиотеку из примеров как и ты. и тот же косяк появился. странички у меня все появляются полностью. но последний закрывающий тэг есть всегда и везде.
Причём эти артефакты появляются только на страницах файлов. А вот на страничке 404 этого безобразия нет.
 
Последнее редактирование:
Решилось!
в начале каждого файла html надо добавить строку
[inline]<!DOCTYPE html>[/inline]
и никаких артефактов!
 

Kirill_ow

New member
Ошибка в программе которая собирает файлы для файловой системы . Она вместо 2 символов переноса каретки ставит 1, реальный размер файла уменьшается на количество строк, а в заголовке программа ставит исходный размер. Можете открыть прошивку и html например far-ом и сравнить.
Я написал свою простенькую программу на C# которая, делает бинарник.
Может есть текстовый редактор, который делает 1 символ в конце строки...
 
Сверху Снизу