¿Cómo devolver un objeto JSON con una API REST personalizada en Magento 2?

14

Estoy escribiendo una demostración personalizada de REST API; ahora puede devolver números y cadenas en mi demo, pero quiero que devuelva un objeto JSON como otras API REST.

En mi demo, llamo a la API de Magento 2 (es decir, obtengo información del cliente: http: //localhost/index.php/rest/V1/customers/1 ) con curl, y devuelve una cadena JSON:

"{\" id \ ": 1, \" group_id \ ": 1, \" default_billing \ ": \" 1 \ ", \" created_at \ ": \" 2016-12-13 14: 57: 30 \ " , \ "updated_at \": \ "2016-12-13 15:20:19 \", \ "created_in \": \ "Default Store View \", \ "email \": \ "[email protected] \ ", \" nombre \ ": \" azol \ ", \" apellido \ ": \" young \ ", \" store_id \ ": 1, \" website_id \ ": 1, \" direcciones \ ": [{ \ "id \": 1, \ "customer_id \": 1, \ "region \": {\ "region_code \": \ "AR \", \ "region \": \ "Arad \", \ "region_id \ ": 279}, \" region_id \ ": 279, \" country_id \ ": \" RO \ ", \" street \ ": [\" abc \ "], \" phone \ ": \" 111 \ ",\"código postal\":\"1111 \ ", \" city \ ": \" def \ ", \" firstname \ ": \" azol \ ", \" lastname \ ": \" young \ ", \" default_billing \ ": true}], \ "disable_auto_group_change \": 0} "

La respuesta es una cadena JSON, pero todas las claves tienen una barra diagonal. Sé que puedo eliminar la barra diagonal str_replace, pero es una forma estúpida. ¿Hay alguna otra forma de devolver un objeto JSON sin barras dentro de las claves?

************ ACTUALIZACIÓN 2016.12.27 ************

Pegué mi código de prueba aquí:

   $method = 'GET';
    $url = 'http://localhost/index.php/rest/V1/customers/1';

    $data = [
        'oauth_consumer_key' => $this::consumerKey,
        'oauth_nonce' => md5(uniqid(rand(), true)),
        'oauth_signature_method' => 'HMAC-SHA1',
        'oauth_timestamp' => time(),
        'oauth_token' => $this::accessToken,
        'oauth_version' => '1.0',
    ];

    $data['oauth_signature'] = $this->sign($method, $url, $data, $this::consumerSecret, $this::accessTokenSecret);

    $curl = curl_init();

    curl_setopt_array($curl, [
        CURLOPT_RETURNTRANSFER => 1,
        CURLOPT_URL => $url,
        CURLOPT_HTTPHEADER => [
            'Authorization: OAuth ' . http_build_query($data, '', ','),
            'Content-Type: application/json'
        ], 
    ]);

    $result = curl_exec($curl);
    curl_close($curl);

    // this code has slash still
    //return stripslashes("hi i\" azol"); 

    // has slashes still
    //return stripcslashes("{\"id\":1,\"group_id\":1,\"default_billing\":\"1\",\"created_at\":\"2016-12-13 14:57:30\",\"updated_at\":\"2016-12-13 15:20:19\",\"created_in\":\"Default Store View\",\"email\":\"[email protected]\",\"firstname\":\"azol\",\"lastname\":\"young\",\"store_id\":1,\"website_id\":1,\"addresses\":[{\"id\":1,\"customer_id\":1,\"region\":{\"region_code\":\"AR\",\"region\":\"Arad\",\"region_id\":279},\"region_id\":279,\"country_id\":\"RO\",\"street\":[\"abc\"],\"telephone\":\"111\",\"postcode\":\"1111\",\"city\":\"def\",\"firstname\":\"azol\",\"lastname\":\"young\",\"default_billing\":true}],\"disable_auto_group_change\":0}");

    // has slashes still
    //return json_encode(json_decode($result), JSON_UNESCAPED_SLASHES);

    // this code will throw and expcetion:
    // Undefined property: *****\*****\Model\Mycustom::$_response
    //return  $this->_response->representJson(json_encode($data));

    return $result;
azol.young
fuente
¿Intentas con return json_encode($result, JSON_UNESCAPED_SLASHES);?
Khoa TruongDinh
sí, lo he intentado, arrojará una excepción, porque $ result es una cadena
azol.young
Pruebe de otra manera: $json_string = stripslashes($result)yreturn json_decode($json_string, true);
Khoa TruongDinh

Respuestas:

1

Podemos usar json_encodecon JSON_UNESCAPED_SLASHES:

json_encode($response, JSON_UNESCAPED_SLASHES);
Khoa TruongDinh
fuente
hola, sí, lo hice en mi código, pero todavía tiene una barra diagonal
azol.young
¿Intentaste con la stripslashes()función o json_encode($str, JSON_UNESCAPED_SLASHES);?
Khoa TruongDinh
Lee mi respuesta actualizada.
Khoa TruongDinh
1
Pruebe $ this -> _ response-> representJson (json_encode ($ data));
Pratik
Hola khoa gracias He intentado codificar "json_encode ($ respuesta, JSON_UNESCAPED_SLASHES);" y stripslashes ("hola i \" azol ") ;, todavía tiene barra .......
azol.young
1

Cree ws.php en el directorio raíz de magento 2 y pegue el siguiente código en el archivo:

<?php
    use Magento\Framework\App\Bootstrap;
    require __DIR__ . '/app/bootstrap.php';
    $params = $_SERVER;
    $bootstrap = Bootstrap::create(BP, $params);


    function sign($method, $url, $data, $consumerSecret, $tokenSecret)
    {
        $url = urlEncodeAsZend($url);
        $data = urlEncodeAsZend(http_build_query($data, '', '&'));
        $data = implode('&', [$method, $url, $data]);
        $secret = implode('&', [$consumerSecret, $tokenSecret]);
        return base64_encode(hash_hmac('sha1', $data, $secret, true));
    }

    function urlEncodeAsZend($value)
    {
        $encoded = rawurlencode($value);
        $encoded = str_replace('%7E', '~', $encoded);
        return $encoded;
    }

    // REPLACE WITH YOUR ACTUAL DATA OBTAINED WHILE CREATING NEW INTEGRATION
    $consumerKey = 'YOUR_CONSUMER_KEY';
    $consumerSecret = 'YOUR_CONSUMER_SECRET';
    $accessToken = 'YOUR_ACCESS_TOKEN';
    $accessTokenSecret = 'YOUR_ACCESS_TOKEN_SECRET';

    $method = 'GET';
    $url = 'http://localhost/magento2/rest/V1/customers/1';

//
$data = [
    'oauth_consumer_key' => $consumerKey,
    'oauth_nonce' => md5(uniqid(rand(), true)),
    'oauth_signature_method' => 'HMAC-SHA1',
    'oauth_timestamp' => time(),
    'oauth_token' => $accessToken,
    'oauth_version' => '1.0',
];

$data['oauth_signature'] = sign($method, $url, $data, $consumerSecret, $accessTokenSecret);

$curl = curl_init();

curl_setopt_array($curl, [
    CURLOPT_RETURNTRANSFER => 1,
    CURLOPT_URL => $url,
    CURLOPT_HTTPHEADER => [
        'Authorization: OAuth ' . http_build_query($data, '', ',')
    ]
]);

$result = curl_exec($curl);
curl_close($curl);

echo $result;

$response = \Zend_Json::decode($result);
echo "<pre>";
print_r($response);
echo "</pre>";

Después de esto, ejecute este archivo usando un enlace como http: //localhost/magento2/ws.php en el navegador y verifique la salida.

Nilesh Gosai
fuente
1

Intenté usar el siguiente script para probar si obtengo barras en la misma respuesta API:

<?php
// create a new cURL resource
$ch = curl_init();

// set URL and other appropriate options
curl_setopt($ch, CURLOPT_URL, "http://www.example.test/rest/all/V1/customers/12408");
curl_setopt($ch, CURLOPT_HEADER, false);
curl_setopt($ch, CURLOPT_HTTPHEADER, ['Authorization: Bearer oc34ouc8lvyvxcbn16llx7dfrjygdoh2', 'Accept: application/json']);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);

// grab URL and pass it to the browser
$result = curl_exec($ch);

var_dump($result);

// close cURL resource, and free up system resources
curl_close($ch);

Lo que produce esta respuesta (truncada por la función var_dump de PHP):

$ php -f apitest2.php 
/var/www/html/dfl/htdocs/apitest2.php:14:
string(1120) "{"id":12408,"group_id":13,"default_billing":"544","default_shipping":"544","created_at":"2018-05-24 08:32:59","updated_at":"2018-05-24 08:32:59","created_in":"Default Store View","email":"...

Como puede ver, no hay cortes en mi respuesta.

Así que te sugiero que tengas dos opciones:

  • Investigue por qué su configuración de cURL está devolviendo una respuesta con barras inclinadas. ¿Quizás tenga algo que ver con el uso de oauth? Parece que algo está tomando la respuesta cruda de cURL y luego está tratando de hacer algo (como generarlo) y en el proceso agregar barras inclinadas
  • Persevera con encontrar una manera de eliminar las barras usando str_replaceo similar.

Una vez que tenga su respuesta sin barras, puede usar la siguiente línea para forzar a PHP a convertir la cadena en un objeto JSON:

$object = json_decode( $output, false, 512, JSON_FORCE_OBJECT);
ProcessEight
fuente