Отправка POST-запросов через JavaScript
Уже достаточно давно многие сайты обладают динамическими страницами, то есть они обновляются без перезагрузки. Это достигается путём обращений к серверу через JavaScript, в большинстве случаев, это POST и GET запросы. И практически всегда такие сайты используют для этого Ajax. И далеко не все знают (к сожалению), что Ajax - это не отдельный язык, а всего лишь библиотека JavaScript. Вывод: Ajax - это лишь удобный способ отправить POST-запросы, но всё это можно сделать и без его помощи. Вот как отправить POST-запросы через JavaScript без Ajax, я расскажу в этой статье.
Мы с Вами сейчас решим классическую задачу - это суммирование двух чисел, заданных пользователем. То есть мы с Вами считаем из текстовых полей 2 числа, отправим их на сервер, получим ответ и выведем на страницу. И всё это без перезагрузки страницы.
Начнём с простого: написание PHP-кода:
<?php
$a = $_POST["a"];
$b = $_POST["b"];
echo $a + $b;
?>
Здесь всё элементарно, поэтому даже не буду комментировать. А вот теперь более сложная часть - клиентская:
<script type="text/javascript">
/* Данная функция создаёт кроссбраузерный объект XMLHTTP */
function getXmlHttp() {
var xmlhttp;
try {
xmlhttp = new ActiveXObject("Msxml2.XMLHTTP");
} catch (e) {
try {
xmlhttp = new ActiveXObject("Microsoft.XMLHTTP");
} catch (E) {
xmlhttp = false;
}
}
if (!xmlhttp && typeof XMLHttpRequest!='undefined') {
xmlhttp = new XMLHttpRequest();
}
return xmlhttp;
}
function summa() {
var a = document.getElementById("a").value; // Считываем значение a
var b = document.getElementById("b").value; // Считываем значение b
var xmlhttp = getXmlHttp(); // Создаём объект XMLHTTP
xmlhttp.open('POST', 'test.php', true); // Открываем асинхронное соединение
xmlhttp.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded'); // Отправляем кодировку
xmlhttp.send("a=" + encodeURIComponent(a) + "&b=" + encodeURIComponent(b)); // Отправляем POST-запрос
xmlhttp.onreadystatechange = function() { // Ждём ответа от сервера
if (xmlhttp.readyState == 4) { // Ответ пришёл
if(xmlhttp.status == 200) { // Сервер вернул код 200 (что хорошо)
document.getElementById("summa").innerHTML = xmlhttp.responseText; // Выводим ответ сервера
}
}
};
}
</script>
<div>
<input type="text" name="a" id="a" />
<br />
<input type="text" name="b" id="b" />
<br />
<input type="button" value="Сумма" onclick="summa()" />
<p>Сумма равна: <span id="summa"></span></p>
</div>
HTML-код я комментировать не буду, поскольку он совершенно прозрачный. А вот к JavaScript я немного добавлю, несмотря на подробные комментарии. Во-первых, функция getXmlHttp() является универсальной. Вы её можете смело копировать в свои скрипты. Её задача вернуть такой XMLHTTP, чтобы он работал в любом браузере. Потому что самый популярный вариант - это new XMLHttpRequest(), однако, он не работает, например, в IE6. Другие варианты также не являются универсальными, поэтому здесь мы просто подбираем под любой браузер рабочий вариант.
Я написал также в комментариях про "асинхронную работу". Есть ещё синхронный вариант. Отличие только в том, что в синхронном пока не будет получен ответ от сервера, браузер работать не будет, он просто повиснет. Мне трудно придумать такую задачу, где это необходимо, поэтому я сразу написал асинхронный вариант. Он работает следующим образом: мы отправляем запрос и ждём ответа, но при этом браузер не виснет. А когда ответ приходит (xmlhttp.readyState == 4), то мы сразу обрабатываем ответ. Вот это и есть асинхронный вариант работы, он чуть-чуть сложнее, но только его и нужно использовать (за исключением очень редких случаев).
Вот таким способом отправляются POST-запросы через JavaScript. Как видите, Ajax нам вовсе не потребовался. И я настоятельно рекомендую, если у Вас всего пару запросов на весь сайт, то даже не думайте использовать эту тяжеловесную библиотеку, а используйте материал данной статьи.
-
- Михаил Русаков
Комментарии (57):
Извиняюсь за невежество, но что значат эти try{}catch{}
Ответить
http://myrusakov.ru/exception-javascript.html
Ответить
Ахренеть... и в каких случаях это может понадобиться?
Ответить
Для создания динамики на страницах, без "левых" библиотек.
Ответить
Спасибо, то что нужно :)
Ответить
а на на стороне сервера в этом примере echo - передача ответа, а не вывод?
Ответить
Это вывод результата и ничего больше.
Ответить
responseText содержит все что бало echo?
Ответить
Да, в нём результат работы echo и будет.
Ответить
т.е на сервере должно выводиться толко то что является ответом яваскрипту?
Ответить
Разумеется, надо выводить только то, что нам нужно.
Ответить
Просто, быстро, легко и со вкусом !
Ответить
Михаил, скажите пожалуйста как можно после всего незаметно для пользователя обновить страницу? я просто пытаюсь сделать авторизацию без перезагрузки, но без неё не получается, всё работает но аватарка и всё остальное появляется только при обновлении страницы
Ответить
Тут уже нужно использовать DOM, либо JQuery. Добавлять одни элементы, удалять другие элементы.
Ответить
Ясно, значит я опять прогорел с юзабилити
Ответить
здравствуйте! при обновлении ajax страницы она возвращается к первоначальному виду. как сделать так чтобы после перезагрузки она не слетала ???
Ответить
Легко. _htmlbook.ru/html5/history
Ответить
Вот отправляю данные к php, через if (!defined("...")) die ("Hacking attempt!"); Не проходит, приходиться закрывать. Скажите как можно выполнить операцию без закрытия? И безопасен ли ваш ментод?
Ответить
Метод не представляет ни малейшей опасности, тут надо думать, что в PHP писать, а JavaScript и HTML - вообще клиентские языки.
Ответить
Я делаю проверку на содержание постов. Такой вопрос, может не по теме но охота узнать. Нужно закрыть доступ к каталогу, в котором находится php скрипт.Создаю htacess, с содержимым: [code]Order Deny,Allow Deny from all[/code] После я не могу обратиться к скрипту через post запрос.Какие выходы? Можно ли закрыть доступ к каталогу и сохранить весь процесс работы?
Ответить
Противоречие. Хотите, чтобы доступа к нему не было, но при этом пользователь туда отправляет данные. Если нужно скрыть какие-то библиотеки, то делайте это, а все скрипты-обработчики должны быть доступны.
Ответить
Нужно убрать из виду php скрипты, если вдруг пользователь догадается в каком каталоге они находятся.Скажите пожалуйста, что нужно прописать в htacess.Спасибо.
Ответить
Deny from all
Ответить
Прописал, положил. Не хочет присылать ответ php скрипт к js. На скок я понимаю.Нет выхода, или я что та не так сделал?
Ответить
Я писал, что НЕ надо засовывать обработчики в закрытые папки. Всё, что можно туда отправить - это библиотеки, а к ЛЮБЫМ обработчикам должен иметь доступ ЛЮБОЙ пользователь. Если не понимаете, почему так, а не по-другому, прочитайте про противоречие чуть выше, которое Вы требуете, и постарайтесь в него вникнуть.
Ответить
Спс, нашел выход.
Ответить
какой?
Ответить
Михаил, подскажите, пожалуйста, а как таким же образом передать значения выбранных чекбоксов?
Ответить
Взять checkbox через JS и проверить значение свойства checked: document.my_form.check.checked
Ответить
А возможно таким способом вывести не одну строку, а массив например. Например, встал на фамилию в списке, а серверный скрипт вернул все данные пользователя и вывести их в таблицу.
Ответить
Можно, да. Можно принять строку в формате JSON, полученную от PHP, далее в JS уже её превратить в обычный массив.
Ответить
Спасибо, буду разбираться.
Ответить
Михаил, попробовал поюзать ваш скрипт. Столкнулся с проблемой в IE9 на сайтах с кодировкой windows-1251. Возникает ошибка при обращении к xmlhttp.responseText. Есть какие-нибудь идеи?)
Ответить
Отправка через чистый JS или с использованием Ajax всегда требует кодировки UTF-8. Поэтому если данная функциональность необходима, то надо менять кодировку сайта.
Ответить
Вот только спросил, сразу получилось)) Проблема решилась, когда принудительно задал кодировку ответа сервера: header('Content-type: text/html; charset=windows-1251');
Ответить
Вы насчет "менять кодировку сайта" не шутите, Вконтакте на windows-1251!
Ответить
Да, Вы правы. Но постоянно слышу проблемы от людей, что с этой кодировкой у них при использовании того же Ajax проблемы. С UTF-8 таких проблем нет вообще. Поэтому всё равно лучше переходить на эту кодировку.
Ответить
Михаил, файл на сервере не грузится , а отладчик выдает . Origin null is not allowed by Access-Control-Allow-Origin. ..
Ответить
Попробуйте в другом браузере ещё.
Ответить
пробовал... Тут что-то связанное с крос-домеными запросами (с домена А на домен Б).
Ответить
Спасибо, надо добавить этот скрипт в арсенал.
Ответить
А как можно это прикрепить к добавлению комментариев(лучше пример)
Ответить
Пример привести не могу, тут не 10 строчек, а все 100, и это как минимум. Поэтому изучайте JS, изучайте PHP и MySQL, изучайте HTML. Без этих знаний, даже мой код не поможет. С этими знаниями Вы сами всё напишите.
Ответить
Михаил, сам код добавления комментариев у меня есть, с данными языками(HTML, CSS, PHP, MySQL) у меня все хорошо, я хочу увидеть пример кода js именно для комментариев
Ответить
Не вижу проблем получить на JS данные из формы, далее отправить эти данные, как в этой статье отправляются "a" и "b". Форма обычная, JS такой же, как и в статье.
Ответить
encodeURIComponent можно убрать
Ответить
xmlhttp.send("a=" + a +"&b=" + b); // Отправляем POST-запрос вот и так будет работать
Ответить
Михаил нужна ваша помощь! Как поступить - есть js селекторы которые должны передать значения на эту же страницу как POST данные пробовал обрабатывать форму на php . но затирает значения после отправки Пробовал на js(генерирую submit(); но после этого нельзя операторы добавлять - данные не передаются) пробовал асинхроным запросом к этому же документу , но что-то нет самого массива POST б а ответ js мне как бы и не нужен - надо дальше запускать функцию php выборки
Ответить
Михаил, а как отправить <span id="summa"></span> в обратную связь? У меня есть калькулятор, так вот все значения отправляются кроме итоговой. Здесь есть name благодаря ему значение отправляется в POST <input type="text" name="a" id="a" /> А здесь нет возможности поставить name <span id="summa"></span> Скрипт на чистом яве без библиотек
Ответить
Добрый день Михаил, огромная Вам благодарность за статью! Возник один вопрос, хочу что бы функция возвращала результат, т.е. пытаюсь сделать return xmlhttp.responseText; но приходит только undefined, хотя alert(xmlhttp.responseText) все прекрасно отображает. Подскажите в чем может быть проблема?
Ответить
Как правильно возвращать в JS: http://javascript.ru/return
Ответить
Спасибо громадное! Я из этого примера сделала простой и элегантный скрипт для заказа обратного звонка. Долго искала в интернете что-то, чтобы просто вставить на сайт - но там все либо очень сложно и подробности платно, либо просто РНР форма обсуждается. А тут - конфетка!
Ответить
Помогло - наконец то нашёл то, что мне было нужно. Спасибо за статью.
Ответить
Здравствуйте, Михаил! Прошу Вас подсказать как решать такую задачу - есть открытый http сайт от транслирует котировки примерно 1 раз в сек которые обновляются на сайте, мне надо с сайта эту котировку получить для дальнейшей обработки. Подходит ли тема данного урока для решения этой задачи или надо искать что-то другое?
Ответить
в on submit return false надо было сделать, иначе в браузерах страницы рефрешнет
Ответить
прошло 7 лет, вы все так же рекомендуете избегать Ajax ? А если не избегать, можете такой же пример с использования Ajax для этого же примера?
Ответить
А можно ли этот скрипт оформить как "функцию", на вход которой подается произвольный набор переменных и она возвращает произвольный набор результатов?
Ответить
Для добавления комментариев надо войти в систему.
Если Вы ещё не зарегистрированы на сайте, то сначала зарегистрируйтесь.