Skip to content
This repository has been archived by the owner on May 30, 2023. It is now read-only.

IndexedDB support #10992

Closed
ariya opened this issue Jan 17, 2013 · 13 comments
Closed

IndexedDB support #10992

ariya opened this issue Jan 17, 2013 · 13 comments

Comments

@ariya
Copy link
Owner

ariya commented Jan 17, 2013

[email protected] commented:

Greetings. IndexedDB support would be stellar. Thanks much, keep up the great work.

Historical note, there was a forum post from June 2012 on this, and the reply was to create a ticket. I have not found that ticket, and am creating it thusly. Thanks again.

Disclaimer:
This issue was migrated on 2013-03-15 from the project's former issue tracker on Google Code, Issue #992.
🌟   3 people had starred this issue at the time of migration.

@JamesMGreene
Copy link
Collaborator

Will be covered by PR #404, see discussion there.

@tanx
Copy link

tanx commented Jun 2, 2013

+1 on this one.

I saw that phantomjs supports web sql. Perhaps it would be possible to use the IDB shim for initial support:
https://github.com/axemclion/IndexedDBShim

Unfortunatley I could not get this to work. Do I have to pass special parameters to phantomjs to enable web sql?

thanks

@evil-shrike
Copy link

After reading all comments in #404 and here I don't fully understand IndexedDB support status.
Can I enable IndexedDB for my app in 1.9 in any way?
It's very important for us that our application supports offline mode via two technologies: localStorage and IndexedDB. But our unit-tests tests only localStorage code branch as PhantomJS doesn't support IndexedDB by default.

@vitallium
Copy link
Collaborator

@evil-shrike no, you can't. IndexedDB is not supported by PhantomJS. It will be in 2.x version.

@evil-shrike
Copy link

@vitallium thanks for the answer. Is there any plans for releasing 2.x?

@vitallium
Copy link
Collaborator

@evil-shrike you can read about next version here: https://groups.google.com/forum/#!topic/phantomjs/z_147Zj1l58

@eloff
Copy link

eloff commented Nov 2, 2013

I don't see this under the 2.0 milestone, is it still planned for inclusion?

@JamesMGreene
Copy link
Collaborator

We aren't planning specifically to include it but we do expect that the newer version of WebKit will come with it built-in, yes.

At this point, there are too many issues and feature requests that we are speculating will be automatically resolved with the WebKit upgrade to bother even marking them as such until we can actually prove it.

@coolaj86
Copy link

coolaj86 commented Dec 2, 2013

I successfully loaded PouchDB and used it (which requires the IndexedDB API) by including IndexedDBShim.min.js and specifying --local-storage-path=./html5-storage/.

I'm actually using node-phantom-simple and the call I used to inject was

page.injectJs('./IndexedDBShim.min.js', function () { /* ... */ });

Gist at https://gist.github.com/coolaj86/8190827

Example

wget http://nparashuram.com/IndexedDBShim/dist/IndexedDBShim.min.js
wget http://download.pouchdb.com/pouchdb-nightly.min.js
mkdir ./html5-storage/
touch ./html5-storage/.gitkeep
node test-phantom.js

test-phantom.js:

'use strict';

var phantom = require('node-phantom-simple')
  ;

phantom.create(function (err, ph) {
  console.log('created phantom instance');

  ph.createPage(function(err, page) {
    console.log('created page instance');

    function loadPouchDb() {
      page.injectJs('./IndexedDBShim.min.js', function (/*err*/) {
        page.injectJs('./pouchdb-nightly.min.js', function (/*err*/) {
          page.evaluate(function () {
            window.callPhantom('Pouch should be loaded...');
            new window.Pouch('test-db', function (err, db) {
              window.callPhantom('Pouch initialized successfully!');
              setTimeout(function () {
                db.get('BOGOID', function (err, data) {
                  if (err) {
                    window.callPhantom("item doesn't exist" + JSON.stringify(err));
                  } else if (data) {
                    window.callPhantom('item exists' + JSON.stringify(data));
                  }
                  window.callPhantom('saving an item...');
                  db.put({ _id: 'BOGOID', foo: 'bar', _rev: (data && (data.rev || data._rev)) }, function (err, data) {
                    window.callPhantom({ msg: 'saved a data item', error: err, data: data });
                    db.get('BOGOID', function (err, data) {
                      window.callPhantom({ code: 'exit', msg: 'got a data item', error: err, data: data });
                    });
                  });
                });
              }, 100);
            });

          }.toString(), function () {
          });
        });
      });
    }

    // Basically this is window.onerror
    page.onError = function (err) {
      console.error(err);
      ph.exit();
    };

    // fired on window.callPhantom except the first call from evaluateAsync
    page.onCallback = function (data) {
      if (data && 'exit' === data.code) {
        console.log('Kill Code Received');
        ph.exit();
      }
      console.log('CALLBACK: ' + JSON.stringify(data));
    };

    page.open('https://gist.github.com/', function (err, status) {
      console.log('opening page...');

      if (err || 'success' !== status) {
        console.log('err, status', err, status);
        ph.exit();
        return;
      }
    });

    page.onLoadFinished = function () {
      // often never happens
      console.log('load finished');
      testMessagePassing();
      loadPouchDb();
    };

    page.onUrlChanged = function(targetUrl) {
      console.log('New URL: ' + targetUrl);
    };

    function testMessagePassing() {
      // IMPORTANT: you must call `.toString()` on the first function
      // IMPORTANT: closure won't work, you must pass variables with `replace(/'TPL'/g, JSON.stringify(data))`
      // The first call to window.callPhantom will fire the evaluateAsync callback, all others fire page.onCallback
      page.evaluateAsync(function () {
        window.callPhantom("this is ignored" + 'MESSAGE'); // this will end the evaluateAsync, but will not pass parameters
        window.callPhantom("this is goes to 'onCallback'" + 'MESSAGE');
        window.callPhantom("this also goes to 'onCallback'" + 'MESSAGE');
      }.toString().replace(/'MESSAGE'/g, JSON.stringify("hello world")), function (err, data) {
        // this doesn't receive err on script error and doesn't receive data on data
        console.log('window.callPhantom called the first time:', data);
      });
    }

  });
}, { parameters: { 'local-storage-path': './html5-storage' } });

Note: I'm not sure if it's a problem with the shim or phantomjs, but the put works, but the get doesn't.

@schmod
Copy link

schmod commented Jan 13, 2015

Any progress on this?

@kristofdegrave
Copy link

I'm currently writting my own indexeddbmock because I wanted to use PhantomJS for automating my tests. Currently I'm only able to mock the structure, but I'm working on the data now. If you are interested have a look at https://github.com/kristofdegrave/indexedDBmock

@cherrydev
Copy link

@JamesMGreene, I'm a little confused about the mention of waiting on WebKit, since as far as I can see, WebKit supports indexeddb.

@cherrydev
Copy link

Looks like indexeddb works now in phantomjs 2.0 and this can be closed. I haven't tested it extensively, but it looks like as long as you set local-storage-path and local-storage-quota you can create, insert and query data properly.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

10 participants