Запись и воспроизведение javascript

Я знаю, что можно записывать движения мыши, прокрутку и нажатия клавиш. А как же изменения в документе? Как записать изменения в документ?

вот моя попытка. Должен быть лучший, более простой способ хранения всех событий?

Я благодарен за все советы что я могу сделать!

<!DOCTYPE html>
<html>
<head>
<title>Record And replay javascript</title>
</head>
<body id="if_no_other_id_exist">

<div style="height:100px;background:#0F0" id="test1">click me</div>
<div style="height:100px;background:#9F9" class="test2">click me</div>
<div style="height:100px;background:#3F9" id="test3">click me</div>
<div style="height:100px;background:#F96" id="test4">click me</div>



<script src="http://code.jquery.com/jquery-latest.min.js"></script>
<script>

$(document).ready(function() {
var the_time_document_is_redy = new Date().getTime();
var the_replay = '';


$('div').live("click", function (){
var the_length_of_visit = new Date().getTime() - the_time_document_is_redy;


// check if the element that is clicked has an id
if (this.id)
{

the_replay =
the_replay
+
"setTimeout("$('#"
+
this.id
+
"').trigger('click')","
+
the_length_of_visit
+
");"
;


alert (
"The following javascript will be included in the file in the replay version:nn"
+ 
the_replay
) // end alert

} // end if



// if it does not have an id, check if the element that is clicked has an class
else if (this.className)
{

// find the closest id to better target the element (needed in my application)
var closest_div_with_id = $(this).closest('[id]').attr('id');

the_replay =
the_replay
+
"setTimeout("$('#"
+
closest_div_with_id
+
" ."
+
this.className
+
"').trigger('click')","
+
the_length_of_visit
+
");"
;


alert (
"The following javascript will be included in the file in the replay version:nn"
+ 
the_replay
) // end alert

} // end if

});






// fall back if there are no other id's
$('body').attr('id','if_no_other_id_exist');


// example of how it will work in the replay version
setTimeout("$('#test1').trigger('click')",10000);

});
</script>
</body>
</html>

5 ответов


воспроизведение действий пользователя с помощью Javascript-это сложные проблемы.

во-первых, вы не можете перемещать курсор мыши, вы также не можете эмулировать наведение мыши/зависания. Таким образом, исчезает большая часть пользовательских взаимодействий со страницей.

во-вторых, действия, однажды записанные, большую часть времени они должны воспроизводиться в другой среде, чем они были записаны в первую очередь. Я имею в виду, что вы можете воспроизводить действия на экране с меньшим разрешением, другой клиентский браузер, другой контент, обслуживаемый на основе воспроизведения файлов cookie браузера и т. д.

Если вы потратите время на изучение доступных сервисов, которые позволяют записывать действия посетителей сайта (http://clicktale.com, http://userfly.com/ чтобы назвать несколько), вы увидите, что ни один из них не способен полностью воспроизводить действия пользователей, особенно когда дело доходит до mouseovers, ajax, сложных виджетов JS.

Что касается вашего вопроса для обнаружение изменений, внесенных в DOM - как заявил Крис Бискарди в своем ответе, есть событий мутации, которые предназначены для этого. Однако имейте в виду, что они реализованы не в каждом браузере. А именно, IE не поддерживает их (они будут поддерживаться с IE 9, согласно этой записи в блоге на msdn http://blogs.msdn.com/b/ie/archive/2010/03/26/dom-level-3-events-support-in-ie9.aspx).

полагаться на тех событиях может быть соответствующ для вы, в зависимости от варианта использования.

Как " лучше более простой способ хранения всех событий". Есть и другие способы (синтаксис мудрый), прослушивания событий по вашему выбору, однако обработка (=хранение) их не может быть обработана простым способом, если вы не хотите сериализовать целые объекты событий, которые не были бы хорошей идеей, если бы вы должны были отправить информацию об этих событиях на какой-то сервер для их хранения. Вы должны знать о том, что есть огромное количество событий появляются вокруг при использовании веб-сайта, следовательно, огромное количество потенциальных данных для хранения/отправки на сервер.

Я надеюсь я ясно выразился и вы найдете некоторые из этих сведений полезно. Я сам участвовал в проекте, который был нацелен на то, чего вы пытаетесь достичь, поэтому я знаю, насколько сложно это может стать, как только вы начнете копаться в предмете.


мне стало любопытно этот вопрос и реализовал доказательство концепции здесь

https://jsbin.com/nemake/edit?js, выход

используя демо

  • попробуйте нажать запись, щелкнув вокруг, нажмите запись еще раз, а затем нажмите кнопку Воспроизвести.
  • Play создает <iframe>, вводит исходный HTML и воспроизводит пользовательские события.
  • чтобы изменить масштаб изменить REPLAY_SCALE переменной в исходном коде.
  • для изменения скорости воспроизведения изменить SPEED переменной в исходном коде.
  • NB я тестировал jsbin только на chrome 56.

детали реализации:

  • он поддерживает mousemove, нажмите и введите. Я опустил другие (прокрутка, изменение размера окна, наведение, фокус и т. д.), Но должен быть легко расширяемым.
  • прослушиватели событий обходят любые event.stopPropagation() используя захват при прослушивании событий в документе.
  • отображение воспроизведения в другом разрешении выполняется с помощью zoom С помощью CSS3.
  • прозрачный холст может быть наложен, чтобы нарисовать линии трассировки мыши. Я использую простой div, поэтому никаких линий трассировки.

вопросы:

  • воображая, что мы захватываем пользовательские события на реальном веб-сайте. Поскольку страница могла измениться между сейчас и воспроизведения, мы не можем полагаться на сервер клиента при проигрывании записи в iframe. Вместо этого мы должны сделать снимок html, все запросы ajax и запросы ресурсов, сделанные во время записи. В демо я только снимок HTML для простоты. Однако на практике все дополнительные запросы должны храниться на сервере в режиме реального времени по мере их загрузки на странице клиента. Кроме того, во время воспроизведения важно, чтобы запросы воспроизводились с той же временной шкалой, что они были восприняты пользователем. Для моделирования сроков запросу смещение и продолжительность каждого запроса также должны быть сохранены. Загрузка всех запросов страниц по мере их загрузки на клиент замедлит работу клиентской страницы. Одним из способов оптимизации этой загрузки может быть хэширование md5 содержимого запроса до их загрузки, если хэш md5 уже присутствует на сервере, данные запроса не нужно повторно загружать. Кроме того, сеанс одного пользователя может использовать данные запроса, загруженные другим пользователем с помощью этого хэширования метод.

  • тщательное рассмотрение будет необходимо при загрузке всех событий. Поскольку будет создано много событий, это означает много данных. Возможно, некоторое сжатие событий может быть сделано, например, потеря некоторых менее важных событий mousemove. Запрос на загрузку не должен быть сделан на событие, чтобы свести к минимуму количество запросов. События должны буферизоваться до тех пор, пока не будет достигнут размер буфера или время ожидания перед каждой партией событий. Тайм-аут должен быть используется, поскольку пользователь может закрыть страницу в любой момент, потеряв некоторые события.

  • во время воспроизведения исходящие почтовые запросы должны быть высмеяны, чтобы предотвратить дублирование событий в другом месте.

  • во время воспроизведения агент пользователя должен быть подделан, но это может быть ненадежным при рендеринге исходного дисплея.

  • пользовательский код записи может конфликтовать с кодом клиента. например, jquery. Пространства имен будут обязаны избежать этот.

  • могут быть некоторые крайние случаи, когда ввод и нажатие не могут воспроизводить тот же результирующий HTML, что и в оригинале, например, случайные числа, время даты. Наблюдатели мутаций могут потребоваться для наблюдения за изменениями HTML, хотя и не поддерживаются во всех браузерах. Скриншоты могут пригодиться здесь, но могут оказаться OTT.


Я считаю, что вы ищете события мутации.

http://www.w3.org/TR/2000/REC-DOM-Level-2-Events-20001113/events.html#Events-eventgroupings-mutationevents

вот некоторые ресурсы для ты:

http://tobiasz123.wordpress.com/2009/01/19/utilizing-mutation-events-for-automatic-and-persistent-event-attaching/

http://forum.jquery.com/topic/mutation-events-12-1-2010

https://github.com/jollytoad/jquery.mutation-events

обновление:

в ответ на комментарий, очень, очень простая реализация:

//callback function
function onNodeInserted(){alert('inserted')}
//add listener to dom(in this case the body tag)
document.body.addEventListener ('DOMNodeInserted', onNodeInserted, false); 
//Add element to dom 
$('<div>test</div>').appendTo('body')

Как сказал WTK, вы получаете себя на территории комплекса.


запись

сохраните начальный DOM страницы, удалите из него скрипты, а также вам нужно изменить все относительные URL-адреса на абсолютные.

затем запишите мутации DOM и событие клавиатуры/мыши.

Replay

начать с первоначальной сохраненной дом, применять мутаций и событий того времени.

на самом деле, клики ничего не сделают, потому что мы удалили любые скрипты. но потому что мы спасли изменения DOM мы можем воспроизвести эффект после щелчка.


в последнее время мы можем использовать mutationobserver'а

mutationobserver'а предоставляет разработчикам возможность оперативно реагировать на изменения в дом. Он разработан как замена событий мутации, определенных в спецификация событий DOM3.

медленная демонстрация, потому что консоль.сообщение журнала огромно.

var mutationObserver = new MutationObserver(function(mutations) {
  mutations.forEach(function(mutation) {
    console.log(mutation)
  })
})
mutationObserver.observe(watchme, {
  attributes: true,
  characterData: true,
  childList: true,
  subtree: true,
  attributeOldValue: true,
  characterDataOldValue: true
})
<div id="watchme" contenteditable>
  Hello world!
</div>