it-swarm-eu.dev

Come costruire un oggetto json valido per la risposta ajax di un componente?

Ho impostato una chiamata Ajax nel mio componente.

Mi sembra di aver ricevuto la chiamata iniziale, il controller, il modello di dati funziona perché quando eseguo la chiamata JavaScript lo sto mostrando nella finestra di ispezione del codice come risposta:

({"userblock":"none","fileName":"","fileLocat":"","username":null,"type":"current"});

Ma non riesco ad accedere ai dati tramite il mio JavaScript:

function initialise() {

    console.log(" start Ajax Call ");
    jQuery.ajax({
        type: "POST",
        url: 'index.php?option=com_daily&task=ajax.initialisePerson&format=json',

        data: registration,
        success: function(response){
            console.log("back from ajax");// this shows nothing
            console.log("response is "+response[0].userblock);// this shows nothing
            if(response.message !=""){....

Immagino che sto facendo qualcosa di stupido, ma qualsiasi aiuto sarebbe fantastico.

Il codice controller è:

public function ajax()
{
    $user       = JFactory::getUser();
    $jinput     = JFactory::getApplication()->input;
    // Check Token!
    $token      = JSession::getFormToken();
    $call_token = $jinput->get('token', 0, 'ALNUM');
    if($token == $call_token)
    {
        $task = $this->getTask();
        switch($task)
        {
            case 'initialisePerson':
                try
                {
                    $returnRaw = $jinput->get('raw', false, 'BOOLEAN');
                    $viewValue = $jinput->get('view', NULL, 'INT');

                    if($viewValue)
                    {
                        $result = $this->getModel('ajax')->displayDetails($viewValue);
                    }
                    else
                    {
                        $result = false;
                    }
                    if($callback = $jinput->get('callback', null, 'CMD'))
                    {
                        echo $callback . "(".json_encode($result).");";
                    }
                    elseif($returnRaw)
                    {
                        echo json_encode($result);
                    }
                    else
                    {
                        echo "(".json_encode($result).");";
                    }
                }
                catch(Exception $e)
                {
                    if($callback = $jinput->get('callback', null, 'CMD'))
                    {
                        echo $callback."(".json_encode($e).");";
                    }
                    else
                    {
                        echo "(".json_encode($e).");";
                    }
                }
                break;
        }
    }

Quindi, questo mi ha portato al problema:

echo "(".json_encode($e).");";

Ho usato questo codice e dovrebbe essere

echo json_encode($result);

Ora funziona tutto.

1
user1616338

Come hai avuto le parentesi tonde? Anche il punto e virgola è sbagliato.

Gli oggetti hanno parentesi graffe e matrici con parentesi quadre. La tua stringa funzionerà con i 2 problemi corretti. È possibile accedere ai valori con response.userblock, response.fileName ... Non vi è alcun "messaggio" nella risposta, quindi non otterrai nulla.

Dovresti usare la funzione json_encode in PHP. Potrebbe anche essere una buona idea catturare gli errori.

1
Javatasse

Per quanto riguarda la tua chiamata ajax al controllore che genera json, method è il termine più moderno anziché typeda JQuery 1.9

jQuery.ajax({
    method: 'POST',  // method is more modern than type
    url: 'index.php?option=com_daily&task=ajax.initialisePerson&format=json',
    data: registration,
    success: (function (response) { ...

Non ho ancora creato personalmente un componente basato su Ajax, ma esiste un tutorial dedicato per questo che mostra una sintassi più leggibile per passare i parametri della chiamata Ajax.

https://docs.joomla.org/J3.x:Developing_an_MVC_Component/Adding_AJAX



Per quanto riguarda il tuo controller, fai molta attenzione a trasmettere json valido solo su ogni possibile risposta.

Hai ragione nell'identificare che l'avvolgimento della tua stringa json in ( E ); Interromperà la sintassi della stringa, ma devi controllare anche le altre stringhe di risposta. Con echo $callback . "(".json_encode($result).");";, $callback Romperà anche la tua stringa json.

La mia raccomandazione è di eseguire tutta la tua gestione condizionale e salvare tutti i tuoi dati in una variabile $response. (Inserisco sempre i dati nel mio array $response Come elementi associati come:

if ($condition === true) {
    $response['message'] = "pass";                   // whatever
    $response['data'] = [1,2,3];                     // whatever
} else {
    $response['message'] = "fail";                   // whatever
    $response['error'] = "Syntax Error in X Query";  // whatever
}

Poi lo passo indietro attraverso una piccola e ordinata funzionalità di Joomla per la fine degli script:

echo new JResponseJson($response);

In questo modo, i tuoi dati php sono sempre perfettamente codificati e la chiamata di codifica viene eseguita solo una volta alla fine.

Ora, quando i dati vengono restituiti a jQuery come stringa di risposta, utilizzare response = JSON.parse(response); per convertire la stringa in qualcosa che javascript può masticare. Se i miei dati di risposta possono includere elementi opzionali, controllo se esistono prima di provare ad accedervi scrivendo una condizione in (per impedire la generazione di avvisi).

Ecco un assaggio di ciò:

success(function (response) {
    //console.log(JSON.stringify(response));  // see what Joomla generates for you
    response = JSON.parse(response);

    if ("message" in response.data) {
        if (response.data.message == "pass") {
            if ("data" in response.data) {
                console.log(response.data.data);
            } else {
                console.log("uhoh, 'data' element not found in response.data");
            }
        } elseif (response.data.message == "fail") {
            if ("error" in response.data) {
                console.log(response.data.error);
            } else {
                console.log("uhoh, 'error' element not found in response.data");
            }
        } else {
            console.log("Unknown response.data.message value");
        }
    } else {
        console.log("uhoh, 'message' element not found in response.data");
    }
}

A volte uso message come chiave per un valore che voglio visualizzare in un bootstrap. A volte uso alert come chiave per un valore che Voglio essere visualizzato come popup/avviso javascript. Non offrire mai codici di errore o messaggi mysql non elaborati nella risposta, se hai intenzione di restituire un elemento error, rendilo sufficientemente specifico da guidare te e i tuoi utenti, ma abbastanza genericamente che le parti malintenzionate non possono ricavarne dettagli utili. Se si isolano valori separati in questo modo, può rendere la manipolazione dei dati nel javascript più pulita e più intuitiva per gli altri programmatori.

1
mickmackusa