2016-10-10 5 views
3

Ich versuche, StreamedResponse zu verwenden, um Fortschritt auf meiner Indexseite in Symfony2 auszugeben.Wie verwende ich StreamedResponse, um Vorlagenansicht in Symfony2 zu rendern

Dieser Code unten zeigt meine Fortschritte bei den API-Aufrufen, wie es auftritt, aber ich habe Probleme beim Rendern der gestreamten Informationen in einer tatsächlichen Ansicht. Im Moment gibt es nur Klartext oben auf der Seite aus, dann wird die Ansicht gerendert, wenn alles fertig ist.

Ich möchte nicht das endgültige Array zurückgeben und schließen Sie die Funktion, bis alles geladen ist, aber ich kann nicht scheinen, eine regelmäßige Zweigvorlage anzuzeigen, während ich den Fortschritt ausgeben.

Ich habe versucht, Render, aber nichts scheint diese Ansicht Datei auf dem Bildschirm wirklich auszugeben, wenn ich zurückkomme. Ein weiteres wichtiges Detail ist, dass ich versuche, alles zum Zweig zu machen und es scheint einige interessante Probleme damit zu geben.

+0

Sind diese 15 Anfragen sequenziellen? – Rhono

+0

@Rhono, ja, sie sind sequentiell. Im Moment wird die Seite nicht gerendert, bis sie alle vollständig sind. Daher versuche ich den Fortschritt zu zeigen, wenn jeder Anruf beendet ist. – absentx

Antwort

0

Wie ich es verstehe, haben Sie nur eine Chance, etwas vom Server (PHP/Zweig) an den Browser auszugeben, dann ist es an JavaScript, um weitere Änderungen vorzunehmen (zB eine Fortschrittsanzeige aktualisieren).

Ich würde die Verwendung von Multi-CURL empfehlen, um alle 15 Anfragen asynchron durchzuführen. Dadurch entspricht die Gesamtanforderungszeit der langsamsten Anforderung, sodass Sie Ihre Seite viel schneller bereitstellen und möglicherweise die Fortschrittsleiste nicht mehr benötigen.

// Create the multiple cURL handle 
$mh = curl_multi_init(); 
$handles = array(); 
$responses = array(); 

// Create and add the cURL handles to the $mh 
foreach($widgets as $widget) { 
    $ch = $curler->getHandle($widget->getURL()); // Code that returns a cURL handle 
    $handles[] = $ch; 
    curl_multi_add_handle($mh, $ch); 
} 

// Execute the requests 
do { 
    curl_multi_exec($mh, $running); 
    curl_multi_select($mh); 
} while ($running > 0); 

// Get the request content 
foreach($handles as $handle) { 
    $responses[] = curl_multi_getcontent($handle); 

    // Close the handles 
    curl_close($handle); 
} 
curl_multi_close(); 

// Do something with the responses 
// ... 

Idealerweise wäre dies eine Methode Ihrer Curler Dienst sein.

public function processHandles(array $widgets) 
{ 
    // most of the above 

    return $responses; 
} 
0

Sie können die gesamte Logik implementiert in der setCallback Methode, so betrachten Sie diesen Code:

public function indexAction($countryCode) 
{ 

    $Widgets = []; 

    $response = new StreamedResponse(); 

    $curlerService = $this->get('curler'); 

    $response->setCallback(function() use ($Widgets, $curlerService, $countryCode) { 

     foreach ($Widgets as $Widget) { 

      $curlerUrl = $Widget->getApiUrl() 
       . '?action=returnWidgets' 
       . '&data=' . urlencode(serialize(array(
        'countryCode' => $countryCode 
       ))); 

      $requestStartTime = microtime(true); 
      $curler = $curlerService->curlAUrl($curlerUrl); 
      $curlResult = json_decode($curler['body'], true); 


      if(isset($curlResult['data'])){ 
       //do some processing on the data 
      } 
      flush(); 
      sleep(1); 
      var_dump($Widget->getName()); 
      var_dump((microtime(true) - $requestStartTime)); 
      flush(); 

     } 

    }); 

    // Directly return the streamed response object 
    return $response; 

} 

Weiterführende Literatur this und this Artikel.

Hope this Hilfe

+0

hi @absentx hast du dir diese Antwort angesehen? Was denkst du über? – Matteo

Verwandte Themen