Turbo.visit(location, { frame: frame }) not loading in frame

Given below page and Stimulus controller where everything is wired up properly:

# page.html.erb
<turbo-frame id="tags"...>

# tag-controller.js
Turbo.visit(url, { frame: "tags" } );

When the Turbo.visit is executed, it renders the URL on the whole page instead within the tags Turbo frame. Am I missing how this is supposed to work?

According to the docs, I believe that adding the frame option to Turbo.visit is supposed to render the location within the specified frame:

If frame is specified, find a <turbo-frame> element with an [id] attribute that matches the provided value, and navigate it to the provided location. If the <turbo-frame> cannot be found, perform a page-level Application Visit.

Have you made sure you have a turbo-frame “tags” on the returned HTML ? Turbo Reference states that otherwise it will do an “Application visit”

Also, always worth checking which version of Turbo you’re using. The framework has been evolving rapidly over the last year-or-so. If you are on an older version, it might be that the frame-based .visit() was added in a more recent version.

Ahhh I’m such a dummy - I had duplicate HTML elements with the id tags :(.

The code just does a getElementById so of course it grabs any element with the matching id. It would be better if it was restricted to <turbo-frame> elements only, but I know ids are supposed to be unique to the page.

I learned this lesson the hard way years and years ago, and one of the best things you can do when JS is acting up like this is run your page through the W3 validator. You will not believe how pedantic JS can get!


1 Like

@walterdavis that is a great idea!