Opened 6 years ago

Closed 5 years ago

Last modified 11 months ago

#14587 closed defect (fixed)

require.ready is no longer supported

Reported by: thecheatah Owned by: rcgill
Priority: high Milestone: 1.8
Component: Loader Version: 1.7.1
Keywords: Cc:
Blocked by: Blocking:

Description

requirejs no longer implements require.ready method, instead asks to use domReady. Please use this in the dojo.ready module.

Change History (15)

comment:1 Changed 6 years ago by bill

  • Component changed from General to Loader
  • Owner set to rcgill

@thecheatah - As I mentioned on the mailing list, this should be filed against the Loader component. Switching the component.

@rcgill - the code in question is apparently:

	// define requireCompleteSignal; impl depends on loader
	if(has("dojo-loader")){
		require.on("idle", onLoad);
		requestCompleteSignal = function(){
			if(require.idle()){
				onLoad();
			} // else do nothing, onLoad will be called with the next idle signal
		};
	}else{
		// RequireJS or similar
		requestCompleteSignal = function(){
			// the next function call will fail if you don't have a loader with require.ready
			// in that case, either fix your loader, use dojo's loader, or don't call dojo.ready;
			require.ready(onLoad);
		};
	}

comment:2 Changed 6 years ago by rcgill

  • Resolution set to fixed
  • Status changed from new to closed

In [27540]:

removed requirejs compat for require.ready since requirejs doesn't support that API anymore; fixes #14587

comment:3 Changed 6 years ago by kgf

  • Milestone changed from tbd to 1.8

comment:4 Changed 5 years ago by rbackhouse

With the removal of the "if" block the code will always call require.on and require.idle. As these are not AMD spec'd how are other AMD loaders supposed to support this module ?

Last edited 5 years ago by rbackhouse (previous) (diff)

comment:5 Changed 5 years ago by peller

  • Resolution fixed deleted
  • Status changed from closed to reopened

reopening in consideration of feedback from @rbackhouse. Are on() and idle() likely to be common API? If not, can they be replaced also?

comment:6 Changed 5 years ago by rcgill

  • Resolution set to fixed
  • Status changed from reopened to closed

The dojo/ready module executes callbacks under two conditions:

  1. DOM content loaded is achieved.
  2. All requested modules have arrived and been evaluated.

It is possible to add callbacks for only the DOM content loaded condition with the dojo/domReady plugin, and this plugin uses no special dojo loader functions. Other loaders have implemented this functionality.

The two condition variant is exclusive to dojo. It was originally called dojo.addOnLoad and renamed to dojo.ready. Other loaders do not implement this function and it takes special loader knowledge to know when all requested module have arrived. There has been debate about defining a public interface to determine this kind of loader state. But, to date, there is no agreement to go forward.

In short, if you want to use dojo.ready() or the dojo/ready plugin, then you must use the dojo loader.

comment:7 Changed 5 years ago by rbackhouse

In short, if you want to use dojo.ready() or the dojo/ready plugin, then you must use the dojo loader.

The dojo/ready reference is originating from dojo/dijit code. That means that dojo is unusable with other loaders.

comment:8 Changed 5 years ago by rbackhouse

The reference is in dijit/_WidgetBase.

comment:9 follow-up: Changed 5 years ago by bill

Well, that reference in dijit is only used when the async flag is set to false, or more specifically, when "dijit-legacy-requires" is true. There might be other cases though when dojo/ready does get used.

But anyway, dojo/ready will go away for 2.0 so this is not a long term issue.

comment:10 Changed 5 years ago by rbackhouse

While the call to ready is conditional the fact that the dojo/ready module is listed as a depedency in the define call ensures it get loaded regardless. It's when dojo/ready is loaded that the proprietary API calls are made.

comment:11 Changed 5 years ago by bill

Ah I see. OK, and that's due to [26754]. Could workaround it by something like below, but it's probably not worth it at this point.

if(has("dijit-legacy-requires")){
	require(["dojo/ready", function(ready){
 		ready(0, function(){
			var requires = ["dijit/_base"];
			require(requires);	// use indirection so modules not rolled into a build
		});
	});
}

comment:12 Changed 5 years ago by peller

Perhaps it's worth an experiment or branch to see how close this gets us to requirejs compatibility. *If* this is all that's preventing requirejs compatibility, waiting until 2.0 could be a problem for users stuck on the 1.x line. Should we open a new ticket to consider this?

comment:13 Changed 5 years ago by bill

You can experiment if you like. I don't think that's the only issue though.

Dojo's hash.js, hccss.js, parser.js, touch.js, and uacss.js, and dijit's Focus.js, hccss.js, _CssStateMixin.js, RichText.js, and Viewport.css all use dojo/ready rather than dojo/domReady! because dojo/domReady! has issues when the app is running in sync mode (even though those modules are written in AMD). Plus dojo/ready is used by robot to tell when the document in the iframe has finished loading.

The other reason those modules use dojo/ready is for the priority queue, i.e. to make sure that hccss etc. runs before the parser does.

comment:14 in reply to: ↑ 9 Changed 11 months ago by afinnell

Replying to bill:

Well, that reference in dijit is only used when the async flag is set to false, or more specifically, when "dijit-legacy-requires" is true. There might be other cases though when dojo/ready does get used.

But anyway, dojo/ready will go away for 2.0 so this is not a long term issue.

Four years later...

Unfortunately using the philosophy that everything will be better in 2.x means that everyone suffers in the meantime. It's been four years since this post and we still don't have a working 2.0 version with the alleged fix. Why can't this be fixed? It seems incredibly easy. I'll even submit the code if needed.

Last edited 11 months ago by afinnell (previous) (diff)

comment:15 Changed 11 months ago by dylan

@afinnell: Hindsight is definitely 20:20. If we could go back in time, we'd probably have made Dojo 2 just be a cleaned-up, AMD-only version of Dojo 1.x, and the great work we're doing now for Dojo 2 ( http://github.com/dojo/meta ) would be Dojo 3. On the plus side, we're closing in on Dojo 2 beta in the next few months. For what it's worth, Dojo has been reasonably compatible with RequireJS since Dojo 1.9 a few years ago.

If you want to submit a PR, I'll review and land it. We're planning a 1.12 release in November.

Note: See TracTickets for help on using tickets.