Четете резултати от PHP масив в реално време с Javascript

Със сигурност не мога да разреша този проблем сам, след като се опитвам няколко дни. Това е проблема:

Трябва да покажем информация на екрана (HTML), която се генерира в реално време в PHP файл.

PHP извършва много активно обхождане, връща огромни масиви от URL адреси, всеки URL трябва да се показва в реално време в HTML, веднага щом PHP го улови, затова използваме Ob_flush() и flush методи за ехо и отпечатване на масивите веднага щом ги получим.

Междувременно трябва да покажем тази информация по някакъв начин, така че потребителите да могат да я видят, докато работи (тъй като може да отнеме повече от един час, докато приключи).

Не е възможно да се направи, доколкото разбирам, с AJAX, тъй като трябва да направим само 1 заявка и да прочетем информацията в масива. Също така не съм напълно сигурен дали comet може да направи нещо подобно, тъй като ще прекъсне връзката веднага щом получи нова информация, а масивът наистина бързо увеличава размера си.

Освен това и само за да направим нещата по-сложни, няма реална нужда да отпечатвате или повтаряте информацията (URL адреси) вътре в масива, тъй като HTML файлът е включен като потребителски интерфейс на същия файл, който обработва и генерира масива, който трябва да покажем.

Дълга история накратко; трябва да поставим тук:

<ul>
    <li></li>
    <li></li>
    <li></li>
    <li></li>
    <li></li>
    ...
</ul>

Безкраен и актуализиран в реално време списък с URL адреси, които се генерират и изпращат в масив, 1000 реда по-долу, в PHP цикъл.

Всяка помощ ще бъде наистина повече от оценена. Благодаря предварително!


person Chris Russo    schedule 14.09.2012    source източник
comment
Ще работи ли да запишете PHP масива във файл и да го анализирате с Javascript? Можете да ajax файла по всяко време и той ще има всички резултати, докато PHP непрекъснато го добавя.   -  person Jon Egeland    schedule 15.09.2012
comment
Здравей, Джон, много ти благодаря за бързия отговор. Това е добър подход и вече обмисляхме това, но не е възможно, тъй като натоварването вече е наистина огромно.   -  person Chris Russo    schedule 15.09.2012
comment
Беше любопитно дали сокетите са ти свършили работа....   -  person Stephen    schedule 18.09.2012


Отговори (5)


Опитайте уеб-сокети.

Те предлагат комуникация в реално време между клиент и сървър и използването на socket.io осигурява съвместимост между различни браузъри. По принцип ви дава същите резултати като long-polling/comet, но има по-малко излишни разходи между заявките, така че е по-бързо.

В този случай бихте използвали уеб сокети, за да изпращате актуализации на клиента относно текущото състояние на обработката (или каквото и да е правил).

Вижте това Използване на PHP със Socket.io

person Jamund Ferguson    schedule 14.09.2012
comment
Тук бях принуден от много неща, не просто да публикувам връзка като отговор, предлагам ви да направите същото, като обясните защо WebSockets биха били по-идеални от вече публикуваните отговори и сте прав, това е най-доброто решение от всичките.. ;) - person dbf; 15.09.2012
comment
Запознат съм с тях и звучи като добра възможност, ще разгледам това, има ли някакво решение, което бихте предложили да направите тези реализации? Благодаря много! - person Chris Russo; 15.09.2012
comment
Благодаря, продължаваме с този подход!! - person Chris Russo; 15.09.2012

Да предположим, че сте използвали схема, при която PHP пише на Memcached сървър.

всеки ключ, който записвате като rec1, rec2, rec3

Също така съхранявате current_min и current_max

Потребителят постоянно анкетира с ajax. За всяка заявка те включват последния ключ, който са видели, наречете това k. След това сървърът връща всички записи от k до max.

Ако няма незабавно налични записи, сървърът преминава в цикъл на изчакване за максимум, например 3 секунди, като проверява дали има нови записи на всеки 100 ms

Ако записите станат достъпни, те се изпращат незабавно.

Всеки път, когато клиентът получи актуализации или връзката е прекъсната, те незабавно стартират нова заявка...

Писането на нов запис е само въпрос на вмъкване на max+1 и увеличаване на min и max, където max-min е броят записи, които искате да запазите налични...

person Stephen    schedule 14.09.2012
comment
Благодаря, Стивън, това е интересен подход. Мислите ли, че трябва да работи по-бързо от базата данни или опциите на сокета? - person Chris Russo; 15.09.2012
comment
Със сигурност по-бързо от db опция, тъй като memcached вмъкване/изтриване ще бъде O(1) и ще се съхранява напълно в паметта.. Уеб сокетите вероятно са оптимални за изпращане на данни, но в момента се поддържат донякъде непоследователно за браузъри. FF ги премахна за кратко от FF4 и ги постави обратно за FF5, защото откри проблем със сигурността, който присъстваше на ниво стандарти. - person Stephen; 15.09.2012
comment
Благодаря много Стивън, също страхотно решение. - person Chris Russo; 15.09.2012

Алтернатива на уеб сокетите е COMET

Написах статия за това, заедно с последване, описващо моя опит.

Според моя опит COMET е бърз. Уеб сокетите определено са бъдещето, но ако сте в ситуация, в която просто трябва да го свършите, можете да стартирате COMET за по-малко от час.

Определено тук е необходима някаква структура на споделена памет - може би временна таблица в паметта във вашата база данни или Memcached, както Стивън вече предложи.

person Tim G    schedule 14.09.2012

Мисля, че най-добрият начин да направите това би бил първият PHP скрипт да записва всеки запис в база данни (MySQL или SQLite може би), а след това да имате втори PHP скрипт, който чете от базата данни и извежда най-новите записи. След това използвайте AJAX, за да извиквате този скрипт от време на време и да добавяте записите, които изпраща към вашата таблица. Ще трябва да намерите начин да задействате първия скрипт.

Javascript трябва да запише идентификатора на последния URL адрес, който вече има, и да го изпрати в AJAX заявката, след което PHP може да избере всички редове с идентификатори, по-големи от това.

Ако броят на URL адресите е толкова голям, че не можете да съхранявате толкова голяма база данни на вашия сървър (някой може да попита как един браузър ще се справи с толкова голяма таблица!), тогава винаги можете да имате PHP скрипта, който извежда най-новите записи, изтрива ги и от базата данни.

Редактиране: Когато правите много MySQL вмъквания, има няколко неща, които можете да направите, за да го ускорите. Има отличен отговор тук, който ги описва подробно. Накратко, използвайте MyISAM и въведете възможно най-много редове в една заявка (имайте буферен масив в PHP, към който добавяте URL адреси и когато е пълен, вмъкнете целия буфер в една заявка).

person gandaliter    schedule 14.09.2012
comment
Здравей Gandaliter, много ти благодаря за коментара! това е най-бързото внедряване, което сме правили в системата, вече изпробвахме този подход, но все още оказва силно влияние върху производителността, тъй като има огромно количество заявки за вмъкване. Освен това предполага създаване на втори файл само за четене на информацията, която се обработва в същия произход. Нещо друго идва ли ви наум? - person Chris Russo; 15.09.2012

If I were you , I try to solve this with two way .
First of all I encode the output part array  with json and with the setTimeout function with javascript I'll decode it and append with <ul id="appendHere"></ul> so 

когато списъкът се актуализира, той автоматично ще се актуализира. Като cronjob с js.

Вторият начин, ако кажете, че не мога да взема изход по време на обработка, така че използването на вмъкване на данни в mysql е безсмислено, мисля, използвайте MongoDb или т.н., за да увеличите скоростта. Между другото, ще достигнете това, от което се нуждаете, с вашия ключ и никога няма да дублирате въведената стойност.

person Emre Karataşoğlu    schedule 14.09.2012