GithubHelp home page GithubHelp logo

cimice's Introduction

Build Status

Cimice is an experimental user session recorder. The goal is to recreate, at least in part, the core function of already popular cloud services available online (see below).

Cimice

Features

  • Built-in support for click, mousemove, scroll and resize events
  • No dependencies
  • Easily extendible

Installation

All you need is cimice.min.js file inside /dist folder that you can get from the cloned repo via git clone https://github.com/artf/grapesjs.git / npm install cimice or download it directly from here

Development

Clone the repository and enter inside the folder

$ npm install cimice
$ cd cimice

Install all necessary dependencies

$ npm install

Start dev server

$ npm run dev

Usage

Below you can see some of the real live examples on how to use Cimice for better fit your needs.

Recording

Example 1 (quick but not recommended)

Record the entire site and send data to some endpoint every 5 seconds

let rec = new cimice.Recorder({
  target: document.documentElement
});

rec.startRecording();

setInterval(() => {
  let json = JSON.stringify(rec.getMovie());
  let xhr = new XMLHttpRequest();
  xhr.open('POST', 'https://your/endpoint');
  xhr.send(json);
}, 5000);

Example 2

The first example is simple but there is a big overhead as you send always all recorded frames and keep them in memory. Furthermore, you could potentially send data even without user interaction and that is pretty annoying. In the example I use XMLHttpRequest, to send data over the net, only for the simplicity but you can replace it with your favorite alternative (JQuery, socket.io, etc)

let rec = new cimice.Recorder({
  target: document.documentElement
});

// At first, when the recording starts I want to be sure to send initial
// data about the movie/target/screen
rec.on('startRecording', () => {
  let movieJson = JSON.stringify(rec.getMovie());
  let xhr = new XMLHttpRequest();
  xhr.open('POST', 'https://save/movie');
  xhr.send(movieJson);
});

// Next listener sends last new recorded frames every 50 interactions (with default mousemove
// event it's already pretty much high frequency) and remove them from the collection.
// Anyway this logic is pretty much simple but ok as example, I suggest to build your own.
rec.on('recording', () => {
  let movie = rec.getMovie();
  let frames = movie.getFrames();
  let framesJson = JSON.stringify(frames);
  if(!(frames.length % 50)){
    let xhr = new XMLHttpRequest();
    xhr.open('POST', 'https://save/frames');
    xhr.send(framesJson);
    movie.setFrames([]);
  }
});

rec.startRecording();

Playing

// Here I supposed to have all recorded data inside fetched movie, but following the
// second recording example you could probably have to fetch also frames data. So
// you could have to do something like this:
// let movieJSON = fetchMovie();
// let framesJSON = fetchFrames(); // Should be an array of objects
// movieJSON.frames = framesJSON;
// let movie = new cimice.Movie(movieJSON);

let movieJSON = fetchMovie();
let movie = new cimice.Movie(movieJSON);
let player = new cimice.Player({
  target: document.getElementById('some-div')
});
player.setMovie(movie);
player.play();

Extend

Cimice comes out of the box with few recordable events (click, mousemove, scroll and resize), but you can extend this behavior. In the example below you will see how to track right mouse click (of course only the click itself, no context menu will pop up)

Track right mouse click

// RECORDER
// At first, init your recorder to be able to listen right click events (contextmenu)
let rec = new cimice.Recorder({
  target: document.documentElement,
  events: ['mousemove', 'click', 'scroll', 'resize', 'contextmenu']
});
rec.startRecording();
// ... your logic to store data

// PLAYER
// ... fetch your movie and frames data
let movie = new cimice.Movie(movieJSON);
let player = new cimice.Player({
  target: document.getElementById('some-div')
});
player.setMovie(movie);
player.on('contextmenu', function(frame){
  let dot = document.createElement("div");
  dot.style.backgroundColor = 'blue';
  dot.style.width = '10px';
  dot.style.height = '10px';
  dot.style.borderRadius = '100%';
  dot.style.marginLeft = '-5px';
  dot.style.marginTop = '-5px';
  dot.style.position = 'absolute';
  dot.style.left = player.getCursorX() + 'px';
  dot.style.top = player.getCursorY() + 'px';
  player.getTarget().appendChild(dot);
});

player.play();

API

You can find API Reference here. The documentation is generated via documentationjs so if there is something to fix/add do it inside the code not API file itself

Testing

Simple test run

$ npm test

Run and watch test

$ npm run test:dev

Cool cloud services

If you're looking for something serious I suggest to checkout this list. If you know others feel free to pull request

Known issues & limitations

  • In Firefox, when you click 'play' button, for some reason, it will add the necessary iframe but immediately after will reload it, so you'll see nothing. One other click on 'play' should display iframe correctly
  • In Safari, 'play' won't work. Seems like there is an issue with writing inside iframe (working on this)
  • Dynamic contents (eg. via AJAX) are not supported.

Why cimice?

Cimice /ˈtʃimitʃe/, in italian, means literally a bug, but in this context supposed to be a wiretap

License

MIT

cimice's People

Contributors

artf avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

cimice's Issues

Some questions regarding setup

Can you give more details on how to use it? Questions that come to mind:

  1. What does an endpoint look like, can "https://save/frames" be any url that can receive POST, like a "rec.php"? If so, why do I not receive anything there?
  2. Is that script on a website within script tags or is it somewhere out of reach and somehow referenced from the main index.html/index.php?
  3. How is movie data being stored and read?

Internal scroll

This project works wonders! I just have a question. Inside the screen I want to record, I have a div which is receiving elements inside it. This causes a vertical scroll on this div. I would like to make Cimice record this automatic scroll. How can I achieve that?

Text input recreation

Created a html which has form with username and password.Used cimice to record the events but when i am playing back cimice is able to mimic the actions of mouse events only.

Playing long videos

Your play function obviously reads in the frames all at once in the movieJSON.

Do you always load your full movieJSON to the page, or is there a way to stream it? As in just get the pieces you need, as you need it?

can not observe textarea text change but work well with input

my own keyup event calback:

keyupEventCallback(recorder, movie, e) {
    let focusedElement = document.activeElement;
    focusedElement.setAttribute('value', focusedElement.value);

    const t = e.target;
    const b = t.body;
    const scrollTop = b ? (b.parentNode.scrollTop || b.scrollTop) : t.scrollTop;
    const scrollLeft = b ? (b.parentNode.scrollLeft || b.scrollLeft) : t.scrollLeft;
    movie.addFrame({
      scrollY: scrollTop,
      scrollX: scrollLeft,
      cursorX: e.pageX,
      cursorY: e.pageY,
      width: recorder.target.clientWidth,
      height: recorder.target.clientHeight,
      eventType: e.type,
    });
  }

works fun with input, but not work with textarea.

something wrong?

Source for cimice.min.js

I was looking through the cimice.min.js file and was wondering if there is an un-minified and more readable version somewhere that I can look at?

Did you write this file from scratch or did you base it on something else?

Thanks!

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.