Short version:
I'm updating some old libs to try to get them in AMD/requirejs format for management, but some of them have dependencies on old code.
Main Question:
I'm primarily confused as to what to list in the:
define(['what','goes','here'],function('what','needs','to','be','here'){})
and what goes in the shim dependencies list when dealing with combinations of AMD and non-AMD tools, and things like jquery-ui and jquery plugins.
ADDITIONAL INFO
The problem:
One of the older libraries depends on .draggable() from (and older version of) jquery-ui, some old version of a jquery plugin called 'onScreen', a spinner modal called spin.js -- all of which are not AMD friendly. (I also implemented an update to an AMD friendly new version of dropzone)
Two of the older libraries also use a modal library called vex which requires a dependency of vex.dialog. The existing site has an old version that is uglified.
I'm trying not to completely revamp this code as the longer term goal would be to remove those dependencies entirely, but I may not have to the time now to figure out what they are doing.
I've tried every combination of define(['list','of','stuff']) I can think of, but some of the libraries like spin (class Spinner), vex/vex.dialog and onScreen still don't always load properly. (sometimes I get one, but then lose another)
Can I define a shim AND include a list of AMD modules in the define? And if so, do I include the AMD list of dependencies in the shim in require.config? What goes where and why?
My libraries:
ImageSelector (requires AwsHelper, Utilities and ImageLayout below)
-- uses jquery (AMD), dropzone (AMD) and an old jquery plugin called jquery.onscreen.js (non-AMD)
-- depends on vex and vex.dialog (non-AMD)
-- uses .draggable() from old jquery-ui (non-AMD)
-- calls a global function 'loadSpinner' which uses spin.js (non-AMD -- see Utilities below)
ImageLayout (requires AwsHelper and Utilities - has attached instance of ImageSelector as a property .selector for methods that work in conjunction with the selector)
-- uses jquery (AMD)
-- also utilizes vex/vex.dialog (non-AMD)
Utilities
-- I'm trying to move the loadSpinner() function that requires spin.js (class Spinner, non-AMD) into this
-- I've managed thus far to avoid dependencies on things like jquery in this by refactoring code
Long version:
I'm trying to update some website code to use require.js for dependency management and to make the code more portable. But I'm running into a number of dependencies on old code that don't appear to be AMD-ready. Where possible, I'm trying to replace these with updated code and/or replace their functionality entirely, but in a number of cases, the code is minified and it's difficult to get a quick handle on what it's doing.
Rather than getting mired in minutia of trying to figure out and either replace or update these things, I read about how 'shim' can be used in some cases to handle these types of non-AMD code, but I'm still unclear on how to configure them.
Here's what I have... I have three libraries I have updated and one new one I created. One called 'ImageSelector' builds a web-gui to allow uploading files with dropzone. (My reason for updating it is that I converted it from using a local filesystem to using Amazon AWS S3 storage.) A second one called 'ImageLayout' handles the business logic of creating a product layout of photos selected by the user. (ImageSelector is split into two frames, a left one for uploading and sorting user files into folders, a right one for building the layout. Thus ImageSelector is dependent on ImageLayout)
The third library is one I created just with a number of repeatedly use 'utility' functions used across the website. There is an existing structured-code version of this in global scope with just a list of functions like roundPrecision(), sanitizeFilename(), escapeRegex(), baseName(), etc. I was going to build this with static methods, but then realized I can customize it if I spawn instances of it instead (e.g. I can change the characters 'sanitized' for different applications with global instance parameters)
The new one is the AwsHelper which is not a problem as it's entirely new code and handles all the interaction with Amazon AWS and S3. It was created in a define() AMD format while the others I have converted to define()/export format.
Anyway, some functions of the ImageLayout can be used independently by the order system, but for the most part, it's used as a dependency of the ImageSelector. AwsHelper is used mostly by ImageSelector but there are two functions in ImageLayout that utilize it. All of the above use the Utilities library.
My guess is something like this in the config (using ImageSelector as an example, but I'm wondering if "jquery" an "dropzone" need to be in there or the function define or both?)
shim: {
"ImageSelector": {
deps: ["jquery","dropzone","vex","vex.dialog","jquery-ui","jquery.onscreen"]
}
}
Additional require.js semantic questions:
(I'll post these separately if needed, but they may be short-answer and related)
Is there anything anywhere that shows how require.js searches for files? e.g. I understand about r.js for uglifying, but in some cases I can't track down the original code for these things. Can filenames include .min.js on the end or version numbers and will require.js still find them or should I rename and/or symlink files? e.g. jquery.js vs jquery-1.7.min.js for example.
The spin.js referenced above actually includes a class definition called 'Spinner'. How do I represent that in the config/shim?
Well, I posted that based on my experimenting the last 3 days riddled with failures, expecting more trouble. But apparently, shim was straightforward and having the required libs in more than one place (shim definitions and define([])) wasn't a problem.
I took a blind guess going through the examples on the require.js and came up with this configuration and amazingly it worked first try! (which makes me nervous as this is the first time I've gotten this code to work with no errors since trying to import it to require.js)
Here's what I came up with:
requirejs.config({
"baseUrl": "/js/lib",
"paths": {
"ImageSelector" : "../awsS3/ImageSelector",
"ImageLayout" : "../awsS3/ImageLayout",
"AwsHelper" : "../awsS3/AwsHelper",
"Utilities" : "../awsS3/Utilities"
},
"shim": {
"jquery.onscreen": {
"deps": ['jquery'],
"exports": 'jQuery.fn.onScreen'
},
"jquery-ui" : ['jquery'],
"vex.dialog" : ['jquery','vex'],
"vex" : ['jquery'],
"spin" : {
"exports": "Spinner"
},
"aws-sdk" : {
"exports" : "AWS"
},
"Utilities": ["spin"],
"AwsHelper": ["jquery","aws-sdk"],
"ImageSelector": {
"deps" : ["jquery","dropzone","vex","vex.dialog","jquery-ui","jquery.onscreen","ImageLayout","AwsHelper","Utilities"]
},
"ImageLayout": {
"deps" : ["jquery","vex","vex.dialog","Utilities"]
}
}
});
I also noted that some of the version naming was handled in the paths, thus I just named my libs in the paths and got rid of my "app/" directory reference altogether.
I saw the following code snippet
val settings = configuration.underlying.as[CookieSecretSettings]("silhouette.oauth1TokenSecretProvider")
I believe configuration is of type play.api.Configuration and underlying is of typeConfig` (https://www.playframework.com/documentation/2.6.x/api/scala/index.html#play.api.Configuration)
I copied the code in my Apploader (as I am using Compile Time Injection). The BuiltInComponentsFromContext has a configuration variable. I thought to use that as follows val config = configuration.underlying.as[CookieAuthenticatorSettings]("silhouette.authenticator") but the compiler cannot resolve as. What am I doing wrong?
The Config library seem to have asInstanceOf instead of as but I get other errors if I use that. I notice that the code for which as works uses play version 2.4.2 while I am using 2.6.12.
I realize this is an old question, but I stumbled upon this exact problem today and couldn't find anything helpful.
The as method is provided by a third-party library (Ficus) to read case classes and Scala types from Typesafe config. You need to include it in your build dependencies, then add to imports:
import net.ceedubs.ficus.Ficus._
import net.ceedubs.ficus.readers.ArbitraryTypeReader._
Here I am, again. With another question concerning cakephp-2.5 and the plugin 'highcharts'.
I've been looking at the demo's an all the different things I could find were the extendings from the controllers. But... that isn't required because it's a plug, am I right?
So, I have included th plugin to my loadings inside the bootstrap file, and when I'm trying to render my HighChart I'm receiving the following error;
Error: Chart: "1" could not be found. Ensure that Chart Name is the same string that is passed to $this->HighCharts->render() in your view.
But the demos are working fine! Any idea what I f*cked up? The names are the same, I even renamed them to 'asd' ( both! ) and it still doesn't work. ^^"
I know this is an incredibly late response but for the benefit of those still experiencing problems with this, the CakePHP 2.* Highcharts plugin has been updated and is compatible up to CakePHP version 2.5.7.
Do note however that in order to maintain product name consistency throughout the repo, all previous references to "HighCharts" have been changed to "Highcharts" and "high_charts" is now simply "highcharts" . So for eg. you now have to call $this->Highcharts->render() where before you would have used $this->HighCharts->render().
The plugin was not yet compatible with CakePHP 2.5. Right now as we speak the developer is working on a new release for 2.5. :)
In CakePHP 2.5, you can avoid the error above and render your chart by calling it.
For example from within index() within your controller, use:
$this->bar();
In this example, bar() is the name of the function containing your chart.
Is there any way to to some kind of code splitting in Dart? I'd like to defer the loading of some rarely used code to accelerate the initial code download. In Javascript, I'd inject a new <script> tag, in GWT i'd just call GWT.runAsync(). Is there something similar in Dart?
According to this link, <script> injection won't work ("Each HTML page can have at most one Dart script tag", "We do not support dynamically injecting a tag that loads Dart code."). I also found this fixed issue claiming: "The initial one [use case] is deferred loading, to avoid massive downloads when some code is needed only later, or perhaps only needed in some situations. We now have a mechanism for this.". Unfortunately, I couldn't find anything on how to implement this. Does anyone know anything about this?
Update Sep 2014: this has been fixed!
Dart now easily supports deferred loading with special import... deferred syntax. For example:
import analytics.dart deferred as analytics
void main(){
analytics.loadLibrary.then((_) { // future
// code ready
enableAnalyticsControl()
});
}
Here is an official tutorial about using deferred loading.
I'm afraid what you're trying to do is still not possible (assuming you're not using dart2js that is) .
See this issue.
As Kasper said in comment 3, so far this has been discussed a deployment feature which you will get with dart2dart. The VMs involvement in supporting this ends with giving the dart2dart generated code access to loading sources lazily through a library call. This library API still needs to be specified though.
If you are using dart2js this can be done. Here is a blog post on how to do this.
const lazy = const DeferredLibrary('reverser', uri: './part.js');
Which will then let you call lazy.load().then((_) { ...
I'm currently mapping my ZF1 applications to ZF2 and was wondering if there is a similar function like $this->view->getScriptPath() from ZF1 in ZF2? I spend already my half day, but didn't find a good solution. It would also be fine to get at least the basePath of the Module or the template folder of the Module.
Based on the follow-up questions, what you are really looking for is the path to a given template file. This is actually relatively easy, assuming you're using the default PhpRenderer: you grab the resolver, and resolve the path.
If you're inside a view script already, the following should work:
$path = $this->resolver($templateName);
If you're elsewhere, you need access to either the PhpRenderer, or the ViewResolver. If you have access to the service manager, pull the ViewResolver service, and call resolve() on it:
$resolver = $services->get('ViewResolver');
$path = $resolver->resolve($templateName);
This is superior to knowing where the module lives, as the developer may have chosen to override the template within the application; the resolver will know where even the new location is.