Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > JavaScript: Применение библиотек > AJAX запрос. Почему срабатывает функция ошибки?


Автор: SanychBY 4.6.2013, 18:55
Здравствуйте. Есть код
Код

$('#button_save').click(function()
    {
        
        var text = $('#text').val();
        $.ajax({type:"POST", dataType:"json", url:"articlejs.php", data:{text:text,a:a}, success: function (data)
        {
        
         $('#text').val('');
        alert(data);
        }, error: function(XMLHttpRequest, textStatus, errorThrown)
        {
            $('#text').val('ERROR'+ XMLHttpRequest +" "+ errorThrown)
            alert(textStatus);},
        });
        
    });

Но по странным причинам срабатывает функция ошибки хотя сам запрос успешно передается(я уверен в это, потому что происходит запись в базу данных)

Автор: Arantir 4.6.2013, 19:35
Цитата(SanychBY @  4.6.2013,  17:55 Найти цитируемый пост)
я уверен в это, потому что происходит запись в базу данных

Запись в базу может происходить раньше той строки, на которой, например, скрипт вылетает с ошибкой 500.
Попробуйте запустить его без ajax (создайте тестовую форму) и посмотрите, что выводится в ответ.

Автор: SanychBY 4.6.2013, 21:43
Цитата(Arantir @  4.6.2013,  19:35 Найти цитируемый пост)
Запись в базу может происходить раньше той строки, на которой, например, скрипт вылетает с ошибкой 500.
Попробуйте запустить его без ajax (создайте тестовую форму) и посмотрите, что выводится в ответ. 

Я раньше использовал этот северный код изменился код AJAX так что PHP точно рабочий

Автор: Arantir 4.6.2013, 23:14
Скажите тогда уж хотя бы что именно за ошибка возникает.

Автор: SanychBY 5.6.2013, 13:07
Цитата(Arantir @  4.6.2013,  23:14 Найти цитируемый пост)
Скажите тогда уж хотя бы что именно за ошибка возникает. 

Я писал уже ребятам на другом форуме http://www.cyberforum.ru/javascript-jquery/thread891072.html буду благодарен если Вы посмотрите

Автор: Arantir 5.6.2013, 15:03
Там все верно говорят. 
Это не json:
Код
echo "{\"rez\": \"Успешно\"}";

потому что корректный json с кириллицей должен выглядеть вот так:
Код
{"rez":"\u0443\u0441\u043f\u0435\u0448\u043d\u043e"}
Без пробелов и без кириллицы.
Соответственно, ваш код падает уже на пробеле.

И обработчика JSON.parse() не нужно, ибо вы же сами указали 
Код
dataType:"json"

JQuery автоматически парсит полученный объект и передает его в первый аргумент колбэка success.


Автор: SanychBY 5.6.2013, 15:49
Цитата(Arantir @  5.6.2013,  15:03 Найти цитируемый пост)
Это не json:

Если это не json то как будет json?

Автор: ksnk 5.6.2013, 16:15
Цитата(SanychBY @  5.6.2013,  15:49 Найти цитируемый пост)
Если это не json то как будет json? 


Цитата(Arantir @  5.6.2013,  15:03 Найти цитируемый пост)
{"rez":"\u0443\u0441\u043f\u0435\u0448\u043d\u043e"}

Вот так  smile 

json генерируется на стороне сервера специальной функцией json_encode.

Код

echo json_encode(array('rez'=>'Успешно'));

Автор: SanychBY 5.6.2013, 16:16
Цитата(ksnk @  5.6.2013,  16:15 Найти цитируемый пост)
json генерируется на стороне сервера специальной функцией json_encode.

А просто echo нельзя? 

Автор: ksnk 5.6.2013, 16:45
Можно.  smile Но при этом не работает функция декодирования.

Вообще, с моей точки зрения json слишком жесткий формат. Задумывалось это все явно в виде куска javascript, выдающего некую конструкцию. Со всеми языковыми тонкостями и вкусностями. А получилось как всегда. Вот так у меня обычно используется.
Код

$.ajax({
        url:'/personal/filter/filter.php',
        complete: function(xml,code){
            var data=xml.responseText;
            //console.log(data);
            try{
                eval('data='+data);
                if(data...
                }
            catch(e) { /* trigger error handler */;}
...

так можно вставлять внутрь html комментарии(я так от бедности вставляю отладочную информацию), не заботится об именах в двойных кавычках, и не в коем случае не иначе.

Автор: SanychBY 5.6.2013, 16:51
Цитата(ksnk @  5.6.2013,  16:45 Найти цитируемый пост)
Можно.   Но при этом не работает функция декодирования.

Вообще, с моей точки зрения json слишком жесткий формат. Задумывалось это все явно в виде куска javascript, выдающего некую конструкцию. Со всеми языковыми тонкостями и вкусностями. А получилось как всегда. Вот так у меня обычно используется.

Это я понял smile 


Цитата(ksnk @  5.6.2013,  16:45 Найти цитируемый пост)
код Javascript
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
$.ajax({
        url:'/personal/filter/filter.php',
        complete: function(xml,code){
            var data=xml.responseText;
            //console.log(data);
            try{
                eval('data='+data);
                if(data...
                }
            catch(e) { /* trigger error handler */;}
...

так можно вставлять внутрь html комментарии(я так от бедности вставляю отладочную информацию), не заботится об именах в двойных кавычках, и не в коем случае не иначе. 

Это нет  smile 

Автор: ksnk 5.6.2013, 17:00
У сервера результат запрашивается не в виде json, а в виде обычного plain-html. 
Сервер выдает json. Во всяком случае - пытается. Или грохается странным образом с текстовым сообщением об ошибке. 
Получаемый от сервера результат пытаемся "привести к json" простым eval'ом. Если он не приводится - выводим в лог сообщение об ошибке и выписываем само сообщение, чтобы не искать потом его в панели отладки Хрома. 

Обработка ведется в методе complete, так как этот метод обязательно сработает при таймауте, аборте и ошибке. Хотя код староват и у меня зреет ощущение, что сейчас все ошибки с jQuery, которые им обходились, вроде уже исправлены.

Автор: Arantir 5.6.2013, 18:07
Цитата(SanychBY @  5.6.2013,  15:16 Найти цитируемый пост)
А просто echo нельзя?  

Можно, но Вы же не соблюдаете формат json в своем echo. Как минимум кириллица должна быть в виде "\u<код_символа>". Проблелы, возможно, убираются декодировщиком, но их тоже быть не должно. А у вас пробел после двоеточия.

Строка вроде "{rez: "Успешно"}" может быть разве что объектом в коде самого JS-скрипта. Так что, в принципе, ее можно превратить в объект с помощью eval (выполняет текст, как код), как это показал ksnk.

Однако eval надо использовать максимально осознанно. Если в data могут попасть данные, вводимые где-нибудь юзером (например, коммент к статье), то кто-то может сделать всем посетителям полный кавардак и грохнуть браузер бесконечным циклом, который просто вписал в коммент и который потом выполнился у всех, кто посмотрел страницу с комментом.


Цитата(ksnk @  5.6.2013,  15:15 Найти цитируемый пост)
echo json_encode(array('rez'=>'Успешно'));

Это вполне хорошее решение. И не намного сложнее чего-то типа "echo "{\"rez\": \"Успешно\"}";"

Автор: SanychBY 5.6.2013, 22:01
Цитата(ksnk @  5.6.2013,  17:00 Найти цитируемый пост)
У сервера результат запрашивается не в виде json, а в виде обычного plain-html. 
Сервер выдает json. Во всяком случае - пытается. Или грохается странным образом с текстовым сообщением об ошибке. 
Получаемый от сервера результат пытаемся "привести к json" простым eval'ом. Если он не приводится - выводим в лог сообщение об ошибке и выписываем само сообщение, чтобы не искать потом его в панели отладки Хрома. 

Обработка ведется в методе complete, так как этот метод обязательно сработает при таймауте, аборте и ошибке. Хотя код староват и у меня зреет ощущение, что сейчас все ошибки с jQuery, которые им обходились, вроде уже исправлены. 


Цитата(Arantir @  5.6.2013,  18:07 Найти цитируемый пост)
Можно, но Вы же не соблюдаете формат json в своем echo. Как минимум кириллица должна быть в виде "\u<код_символа>". Проблелы, возможно, убираются декодировщиком, но их тоже быть не должно. А у вас пробел после двоеточия.

Строка вроде "{rez: "Успешно"}" может быть разве что объектом в коде самого JS-скрипта. Так что, в принципе, ее можно превратить в объект с помощью eval (выполняет текст, как код), как это показал ksnk.

Однако eval надо использовать максимально осознанно. Если в data могут попасть данные, вводимые где-нибудь юзером (например, коммент к статье), то кто-то может сделать всем посетителям полный кавардак и грохнуть браузер бесконечным циклом, который просто вписал в коммент и который потом выполнился у всех, кто посмотрел страницу с комментом.

Ребята вот конечный код
Код

var a = location.search;
    
    $('#button_save').click(function()
    {
        
        var text = $('#text').val();
        $.ajax({type:"POST", dataType:"json", url:"articlejs.php", data:{text:text,a:a}, success: function (data)
        {
        
         $('#text').val('');
        alert(data.rez);
        }, error: function(XMLHttpRequest, textStatus, errorThrown)
        {
            $('#text').val('ERROR'+ XMLHttpRequest +" "+ errorThrown)
            alert(textStatus);},
        });
        
    });

И все равно срабатывает функция ошибки
PHP
Код

header('content-type: application/x-javascript; charset=utf-8');
echo json_encode(array('rez'=>'done'));
    
    exit();

Автор: Arantir 5.6.2013, 23:00
Цитата(SanychBY @  5.6.2013,  21:01 Найти цитируемый пост)
header('content-type: application/x-javascript; charset=utf-8');

Правило №1: Не знаешь — не делай.

С чего это вдруг json стал javascript-приложением? о_О
Вообще-то json — это текст. Он может иметь MIME-тип text/plain. Или на худой конец text/html, так как это тоже, в принципе, текст.
Грубо говоря, json-ом его делает только то, что функция JSON.parse с ним не вызовет ошибки. То есть суть лишь в формате, но текст есть текст.

Отвлекитесь слегка от jQuery и поинтересуйтесь, как работает HTTP, JavaScript и AJAX. Чтобы меньше всякой алхимии было =)


У json, конечно, есть MIME-тип application/json, но суть в том, что JS парсит его из текста, который получает с запроса. 

Автор: SanychBY 5.6.2013, 23:06
Цитата(Arantir @  5.6.2013,  23:00 Найти цитируемый пост)
Правило №1: Не знаешь — не делай.

Вы не правы

Цитата(Arantir @  5.6.2013,  23:00 Найти цитируемый пост)
С чего это вдруг json стал javascript-приложением? о_О
Вообще-то json — это текст. Он может иметь MIME-тип text/plain. Или на худой конец text/html, так как это тоже, в принципе, текст.
Грубо говоря, json-ом его делает только то, что функция JSON.parse с ним не вызовет ошибки. То есть суть лишь в формате, но текст есть текст.

Да мне все равно что использовать просто я хочу обработать data и мне показалось json само нормально для этого подходит. 
Цитата(Arantir @  5.6.2013,  23:00 Найти цитируемый пост)
Отвлекитесь слегка от jQuery и поинтересуйтесь, как работает HTTP, JavaScript и AJAX. Чтобы меньше всякой алхимии было =)

все читал все изучал

Добавлено через 5 минут и 2 секунды
Тем более если вы такой умный и мудрый так подскажите где ошибка

Автор: Arantir 5.6.2013, 23:13
Кроме json сервер случайно больше ничего не выдает? 

Цитата(SanychBY @  5.6.2013,  22:06 Найти цитируемый пост)
Вы не правы

Может быть. Я этому правилу не следую  smile 


Автор: SanychBY 5.6.2013, 23:17
Цитата(Arantir @  5.6.2013,  23:13 Найти цитируемый пост)
Кроме json сервер случайно больше ничего не выдает? 

http://www.cyberforum.ru/javascript-jquery/thread891072.html
http://forum.sources.ru/index.php?showtopic=377821
Я писал на других форумах об этой проблеме, но никто не знает где болезнь. Там много скринов и информации. Буду благодарен если вы ознакомитесь.

Автор: Arantir 5.6.2013, 23:17
Попробуйте запустить это:
Код

$.ajax({type:"POST", dataType:"text", url:"articlejs.php",
    success: function (data)
    {
        alert(data);
    }, 
    error: function(XMLHttpRequest, textStatus, errorThrown)
    {
        alert(errorThrown);
    }
});
И скажите, что выводит.

Добавлено через 3 минуты и 40 секунд
js-файл и php-файл точно оба сохранены в utf-8?

Добавлено через 5 минут и 4 секунды
Цитата(SanychBY @  5.6.2013,  22:06 Найти цитируемый пост)
Тем более если вы такой умный и мудрый так подскажите где ошибка 

Простите, просто выпендриваюсь =)

Автор: ksnk 6.6.2013, 06:47
SanychBY, дай лучше адрес странички, на которой тестируешь. 

Если информация секретна/локальна/"нипакажу", то нужно смотреть ответ сервера на запрос.
Смотреть нужно в окне отладки Хрома Ctrl-Shift-j, во вкладке Network. Там нужно найти и выбрать запрос "с ошибкой", найти в нем вкладку Response, отметить все и бросить сюда.  


Автор: SanychBY 6.6.2013, 20:51
Цитата(Arantir @  5.6.2013,  23:17 Найти цитируемый пост)
Попробуйте запустить это:

Все замечательно работает.

Цитата(Arantir @  5.6.2013,  23:17 Найти цитируемый пост)
js-файл и php-файл точно оба сохранены в utf-8?

проверил -точно
Цитата(ksnk @  6.6.2013,  06:47 Найти цитируемый пост)
 дай лучше адрес странички, на которой тестируешь. 

http://smartapk.vv.si/article.php?a=4
мне это нужно что бы сделать систему комментариев. Вам придется пройти регистрацию что бы иметь возможность их оставлять(подтверждать мыло не обязательно - само письмо Вам придет, но проверки активировано оно или нет пока нет)  
извиняюсь за убогую регистрацию - работаю=)

Автор: Arantir 6.6.2013, 21:23
Создайте файл *.php с двумя строчками:
Код

<?php
echo json_encode(array('rez'=>'done'));
и впишите вместо articlejs.php.

Если все станет ОК, то разбирайтесь с articlejs.php.
Чтобы не было лишнего вывода, то сделайте так:
Код

<?php
ob_start(); // запись в буффер

// ... Ваш код articlejs.php

ob_end_clean(); // очищаем буффер
echo json_encode(array('rez'=>'done'));
exit();

Автор: SanychBY 6.6.2013, 21:46
Все работает при мини-коде! А при полном нет(((
Вот полный
Код

<?php
header('content-type: application/json; charset=utf8');
if (((isset($_COOKIE['email']) and isset($_COOKIE['password'])) or (isset($_SESSION['password']) and isset($_SESSION['email']))) and isset($_POST['a']))
{
    include("baza/baza1.php");
    $q=$_POST['a'];
    $a = strlen($q);
    $b = $a -3;
    $qsu = substr($q, -$b, $b);
    $emailc = $_COOKIE['email'];
    $passwordc=$_COOKIE['password'];
    $emails = $_SESSION['email'];
    $passwords = $_SESSION['password'];
    $rezult = mysql_query("SELECT id FROM noteusers WHERE email='$emailc' AND password='$passwordc' OR email='$emails' AND password='$passwords'",$db);
$myrow = mysql_fetch_array($rezult);
$id = $myrow['id'];
   //добавить коментрий  
    if (isset($_POST['text']) and isset($_POST['a']))
{
    $text=$_POST['text'];
    $rezultatv = mysql_query("INSERT INTO commentsartcles (autor,articleid,text) VALUES ('$id',$qsu,'$text')");
    echo json_encode(array('response' => 'Yes!'));
    
    exit;

}
//голосовать за стаью
if (isset($_POST['param']))
{
    $param=$_POST['param'];
    $rezultat = mysql_query("INSERT INTO votearticles (articlesid,user,vote) VALUES ($qsu,'$id','$param')");
}
}
?>

Автор: Arantir 6.6.2013, 21:59
Значит он выдает лишние байты в ответ. Сделайте так, как в моем предыдущем посте описано, чтобы не выводилось лишнего в браузер.

Автор: SanychBY 6.6.2013, 22:10
Цитата(Arantir @  6.6.2013,  21:59 Найти цитируемый пост)
Значит он выдает лишние байты в ответ. Сделайте так, как в моем предыдущем посте описано, чтобы не выводилось лишнего в браузер. 

египетские боги! Он работает! Спасибо Вам огромное!

Автор: SanychBY 7.6.2013, 12:16
Arantir, но сказали что это не исправление а костыль

Автор: Arantir 7.6.2013, 12:39
SanychBY, вообще-то, сказали правильно =)

Но это не означает, что существует какие-то две строчки, которые есть "настоящим исправлением". Коли бы так было, то не было бы костылей. На то они и костыли, что подпирают что-то большее.

Ну это еще не самое плохое решение, ведь ошибки все равно видно в логах, они всего-лишь в браузер не выводятся.

Проблема в Вашей структуре скрипта. Та, которую Вы привели, честно говоря, она немного удручает =) Она не ошибочна сама по себе, просто в ней очень трудно эти ошибки находить, если они там появляются.

Добавить ООП и паттернов бы не помешало =) А вообще, попробуйте попользоваться каким-то фреймворком, хотя бы поначалу, чтобы почерпнуть существующих идей и приемов.

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)