Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to use the tool in online environments where context needs to be specified? #24

Closed
specialorange opened this issue Jul 18, 2014 · 12 comments

Comments

@specialorange
Copy link

http://stackoverflow.com/questions/24788968/use-backbone-debugger-in-online-js-environment

Trying to get the functionality to validate tested collaborative code on JSFiddle or Plnkr or the like...

@Maluen
Copy link
Owner

Maluen commented Jul 18, 2014

Currently backbone running into iframes isn't supported.

The extension still needs a way to detect the contexts of the page and to let you choose the one to use, plus changing the panel so to interact with the right context.

I've looked up at this time ago, since can be useful also for using it with Ripple, etc. but seemed to require quite a lot of work.

If you can help, I'm on this ;)

@ghost
Copy link

ghost commented Sep 2, 2014

What would you need for help with this?

@Maluen
Copy link
Owner

Maluen commented Sep 2, 2014

A simple solution could be to detect the page iframes in the panel activation page (that with the link "Restart the application in debug mode") and let the user choose the context to use, e.g. with a select.

An instance of the backbone agent is injected in every frame (via inspectedWindow.reload, unfortunately doesn't seem to exist a way to choose a specific frame), hence, we need a way for each instance to detect in which frame it is running (probably by getting its url, could be that this must be done in the content script) in order to send that information to the panel.

The panel will then execute functions only in the choosen iframe (see inspectedWindow.eval "frameURL" and inspectedPageClient.js#L26) and ignore messages from other instances.

@ghost
Copy link

ghost commented Sep 2, 2014

Do you have any branches you've already been working on this in?

@Maluen
Copy link
Owner

Maluen commented Sep 2, 2014

No branches unfortunately, I just did some problem analysis.

Anyway, the ember inspector is doing something similar, the codebase is huge, but you can take a look at:

I get that this can be quite confusing without knowing the codebase, I will try to look at that myself as soon as possible.

@Maluen
Copy link
Owner

Maluen commented Sep 3, 2014

Some screenshots ;)

image

image

Works, but before pushing I've to do some cleanups and adjustments.

@ghost
Copy link

ghost commented Sep 3, 2014

Haha, guess I won't be of any help, I didn't have time last night to dig into it. Thanks for getting it done so quickly!

@Maluen
Copy link
Owner

Maluen commented Sep 7, 2014

Changes pushed, took a bit of time since I had to rethink various aspects of the communication model to integrate this new "multi frame" scenario in the seamless way possible.

No iframe selection dialogs or anything else to set on startup, no additional actions are required.
The frame used is the first where Backbone is detected, maybe in the future we could add the possibility to override the one to use, if needed.

However, to the best of my knowledge, it seems that Chrome allows you to execute code in the context of a frame only by specifying its url, which is not necessarily unique!
Follows a list of limitations of the current solution (that I'm aware of):

  • Partial support for pages with multiple frames with the same url, if Backbone is defined in one of them. Since they result as indistinguishable, Chrome execute code only on the first, while the messages sent will sum up in the panel, very buggy.
  • Don't work for Backbone define into sandboxed iframes, since content script cannoted be injected here <-- like jsbin! This requires more testing
  • Didn't tested on iframes without src (e.g. with content injected directly via js), in those the url defaults to "about:blank", there could be content script injection problems or code execution issues. <-- like jsbin! This requires more testing
  • The tool will break on older versions of Chrome where inspectedWindow.eval "frameURL" isn't supported, the documentation is not of great help here, it states that the feature is on beta channel and will come on stable from v38, but that's obviously false since I'm on stable (v37) and works (and worked also on v36) without a glance! This requires more testing

As an additional note, there is (very) limited support for Ripple since it dynamically completely change the page content after the page has loaded, moving all the content into an iframe with the same src of the page!
This leaves the tool with an old, already detected, useless context, with additional messages coming from the new iframe, which has the same url and are thus considered as the same, but with Chrome which continues to execute code in the old context (since they have the same urls).

@jasonLaster
Copy link

Hmm. I wonder if the injected script could find the frames.

Then search each for backbone. Extreme? Maybe...

@Maluen
Copy link
Owner

Maluen commented Dec 24, 2014

@jasonLaster yeh you could, right now that's pretty much what the debugger does, except it runs multiple injected script instances, one per frame.

You could also run one single instance on the top frame and search the frames here manually, but note that there are the same origin security policies that could prevent you from accessing the frame contents, this applies even to the associated content scripts.

@jasonLaster
Copy link

Hmm. Interesting. Maybe something here: emberjs/ember-inspector#29

@Maluen
Copy link
Owner

Maluen commented Dec 25, 2014

I looked a bit at their code, not too deeply, but it seems that they get the iframes on the page + monitor new added frames and inject the ember_debug (their corresponding agent) on them as soon as they are detected.

This is in a way what we are doing right now, except we use the chrome.devtools.inspectedWindow.reload function that does this automatically, since we need to run the agent since from the beginning, while they probably don't have this requirement.

Problem is in the communication from panel to agent, since we are using https://developer.chrome.com/extensions/devtools_inspectedWindow#method-eval but this allows only to specify the frameurl, not the frameid.

A solution is to use a messaging-only interaction, where the panel sends a message with a request, e.g. send me the view 12 info, and the agent sends back a message with the requested data.

The ember inspector seems to do something like this, which probably is also more general since they also support other browsers: each ember_debug instance creates an unique id based on the url, the date, the application itself, etc.

This unique id is then used in the communication, the panel sends a message with the unique id, every agent (ember_debug) receives it and skips the message if the id is not the same; you could also send a null id and the message seems to be interpreted like a broadcast.

This is a doable solution, but for sure could make the communication a bit trickier, since you have to keep track of what response is associated to what request, don't know if there is some simple method to track responses.

References:

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

No branches or pull requests

3 participants