web-dev-qa-db-ja.com

Drupal 8)を使用してコントローラーでJSONデータを受信する方法

モジュールの設定ページの1つであるAngularJSを使用しているため、モデルとしてクライアント側にjavascriptオブジェクトがあります。誰かが私を助けてくれますか?ajaxでJSONとして送信した場合、どのようにこのデータをコントローラでキャッチするのですか?

これは私が組み立てたモデルです。

var model = {
  title: 'This is a title',
  url: '/random-custom-url',
  description: 'little descrp',
  blocks: [
    {id: 1, name: 'block1', description: 'blockdecrtiption1', terms: [{"tid":"1","name":"term1","vid":"tags"}]},
    {id: null, name: 'block2', description: 'blockdecrtiption2', terms: []},
    {id: 3, name: 'block3', description: 'blockdecrtiption3', terms: []}
  ]
};

(php連想配列として)コントローラーの関数で「キャッチ」したいので、それを処理してデータベースに保存できます(データベースに独自のテーブルがあり、モジュールのhook_schema()で作成されています)。このための正しいルート設定は何ですか?コントローラの関数で、ajaxで投稿されたデータを取得する方法と、それを連想配列に変換する方法を教えてください。

どうもありがとう!

5
Peter Hurtony

簡単に言うと、これを行わないでください。独自のテーブルを作成しないでください。 Drupal 8.の方法ではありません。むしろ、独自のエンティティタイプを使用してください。 https://drupal.stackexchange.com/a/95208/49 を参照してください- https://www.drupal.org/developing/api/entityhttps://api.drupal.org/api/drupal/core%21modules%21system%21core.api.php/group/entity_api/8 for more。ストレージコントローラーがSQLスキーマを生成し、すべてのストレージ作業を行います。RESTモジュールが必要なものを処理します。以下同様に。

編集:JSONで受信して返信する一般的なケース。最初に、Drupal APIがないことを確認してください。ありそうです。RESTはエンティティを提供し、Viewsはエンティティのリスト(およびその他のリスト)を提供します) 。

そうでない場合は、リクエストを引数として使用してカスタムコントローラーを作成する必要があります。 (引数としてRequest $requestを追加するだけで ルートのパラメータ を参照).

JSONで応答するには、Responseオブジェクト、その中のJsonResponseTimezoneController :: getTimeZone および core/modules/system/system.routing.yml の関連するルーティングエントリを確認します。

そう:

class MyController {
  public function myJson(Request $request) {
    $params = array();
    $content = $request->getContent();
    if (!empty($content)) {
      // 2nd param to get as array
      $params = json_decode($content, TRUE);
    }
    // Process $params...
    return new JsonResponse($params);
  }
}
6
user49

もっとD8を実行したい場合は、ここでD8を実行する方法の概要を説明します。これにより、自分ですべてを実行する必要なしに柔軟に対応できます。適切な休憩の統合では、すべての異なるHTTPステータスコード、ヘッダーフィールドなどを操作する必要があります。休憩は、部分的にそれを処理します

RESTモジュールはRESTの一般的な抽象化を提供しますが、そもそもエンティティーにタイトではありません。エンティティは一例にすぎません。

最初に、他のすべてのプラグインと同様に、残りのプラグインを登録する必要があります。

namespace Drupal\pinguin\Plugin\rest\resource;

use Drupal\rest\Plugin\ResourceBase;

/**
 * Provides a resource for database watchdog log entries.
 *
 * @RestResource(
 *   id = "pinguin",
 *   label = @Translation("Example rest plugin for pinguins"),
 *   uri_paths = {
 *     "canonical" = "/pinguin/{id}"
 *   },
 *   serialization_class = "Drupal\pinguin\PingInterface"
 * )
 */
class Pinguin extends ResourceBase {
}

PushやUPDATEのような更新リクエストを行う場合、それは serializer component を使用してデータを何らかのphp配列/オブジェクトに変換します。それを行うには、2つのステップを使用します。最初に、着信データが、たとえばJSONからPHP配列にデコードされます。次のステップは非正規化です。このステップは、非正規化データ(PHP配列)をドメインオブジェクトに変換します。 Ping(単一のペンギン)。

最初のステップは、結果のクラスをアノテーションで指定することです(上記を参照)。新しい非正規化を登録するには、次のエントリを.services.ymlに追加します。

services:
  pinguin.denormalizer.pinguin:
    class: Drupal\pinguin\normalizer\PinguinDenormalizer
    tags:
      - { name: normalizer }

このノーマライザは、変換できるインターフェースを指定します。

<?php

namespace Drupal\pinguin\normalizer;

use \Drupal\serialization\Normalizer\NormalizerBase;

class PinguinDenormalizer extends NormalizerBase {

   // IMPORTANT
   /**
    * The interface or class that this Normalizer supports.
    *
    * @var array
    */
    protected $supportedInterfaceOrClass = array('Drupal\pinguin\PingInterface');

    /**
    * {@inheritdoc}
    */
    public function denormalize($data, $class, $format = NULL, array $context  = array()) {     
      // Validate the data.
      if (empty($data['location']) || $data['location'] == 'northpole') {
        throw new \UnexpectedValueException("this can't be real pinguins");
      }

      // create the domain object.
      return new Ping($data['name'], $data['location'], $data['family']);
    }
 }

このシリアル化が完了すると、プラグインクラスのHTTPメソッドにちなんで名前が付けられたメソッド(たとえば「post」)が呼び出されます。そこではあなたがやりたいことが何でもできます。

<?php
class Pinguin extends ResourceBase {
  public function post(PingInterface $ping) {
    // deal with the data, save it for example.
    $ping_storage->save($ping):
  }
}

これらの抽象化の利点は、着信フォーマットを処理する必要がないことですが、その一方で、開始するには一連のコードが必要です。

10
Daniel Wehner

コントローラの関数で、ajaxで投稿されたデータを取得する方法と、それを連想配列に変換する方法を教えてください。

use Drupal\Component\Serialization\Json;
//...
class MyController {
  public function myPostAction(Request $request) {
    $params = Json::decode($request->getContent());
    //...
  }
}
4
Trupal

これらの例が$request->getContent()メソッドを提案するのはなぜですか?これにより、未加工のリクエスト本文(クエリ文字列のキーと値のペア)が返されます。

私は$request->request->all()がすでに配列を提供しているので、より適切だと思います。 AJAXリクエストが適切な形式であることを確認する必要があるだけです。

0
bpile