Require Modernizr with Webpack - javascript

Trying to use WebPack inside grunt to get all my javascript, css and other stuff build and put in a proper places. Experiencing the following problem while using require('modernizer') inside one of my javascript files that is included in one of modules in my Gruntfile.js. The error is the following:
Fatal error: EMFILE, too many open files ../about/node_modules/modernizr/node_modules/file/lib/file.js'
When I use ulimit to increase the number of files to work with, other errors appear. In my package.json i have the following:
"dependencies": {
"jquery": "^2.1.1",
"jquery-ui": "^1.10.5",
"modernizr": "^2.8.3"
}
Is there a way to use Modernizer from pack to include it modules without using this directive on page:
<script type="text/javascript" src="{portal:createUrl('/_public/about/js/modernizr/modernizr.custom.flexbox.js')}"></script>
?
Thanks in advance!

First of all, just flagging that you should call require('modernizr') instead of require('modernizer').
Secondly, to answer your question “Is there a way to use Modernizer from pack to include it modules without using this directive on page?
Yes there is. It's the script-loader. It basically allows you to require a library, and execute it as if it were inside a <script> tag. You'd use it by calling:
UPDATE 2017-12-27
require('script-loader');
require('script-loader!modernizr');
PREVIOUSLY
require('script-loader');
require('script!modernizr');
Remember to install script-loader in advance, by calling npm install script-loader --save in your command line.

Related

Issue adding third-party (external ) js lib in angular5

I am working on to add jsplumb community js library version with the angular 5 application (Angular CLI: 1.6.1).
With the first build without any configuration to tsconfig.json I get the following error.
ERROR in src/app/jsplumb/jsplumb.component.ts(4,25): error TS6143: Module '../../../node_modules/jsplumb/dist/js/jsplumb.js' was resolved to 'D:/myproj/angular5/myapp/node_modules/jsplumb/dist/js/jsplumb.js', but '--allowJs' is not set.
With "allowJs":true in the tsconfig.json get the following error
ERROR in error TS5055: Cannot write file 'D:/myproj/angular5/myapp/node_modules/jsplumb/dist/js/jsplumb.js' because it would overwrite input file.
Adding a tsconfig.json file will help organize projects that contain both TypeScript and JavaScript files. Learn more at https://aka.ms/tsconfig.
As per tsconfig FAQ
Why am I getting the error TS5055: Cannot write file 'xxx.js' because it would overwrite input file.
with an outDir ("outDir": "./dist/out-tsc") this issue should be resolved. This is already set in my tsconfig.
If we add noEmit to true it simply builds the application, not including any js we get a blank white screen.
Let me know if anyone has tried to include external js with new angular cli and face the same kind of error and what is the solution for the same.
Without any additional option added to tsconfig.json if I try to modify any ts file the application will compile with success and I am able to work. But this does not help while running ng build, to create a deployable binary.
Update Workaround: until the fix in CLI is available. For development (ng serve) remove allowJs from tsconfig.json, when ever you get an error with adding allowJs simply modify a ts file to recompile the applicaiton, this time will compile with success. For production or distribution add back the allowJs to tsconfig.json run the application run with ng build --prod --watch=auto you should see the error about overriding the JS file in node_module, simple modify a ts file it should rebuild as --watch=auto is there in command but this time with sucess.
If you're trying to import a library to Angular 2+, you should do it inside angular-cli.json.
There you have a scripts key where you should configure the desired imports. They are generally like:
{
...
"scripts": [
"../node_modules/MODULE/file.js"
],
...
}
Also you can import the library (not recommended) inside your main index.html, using <script src="/path_relative_to_root/file.js">
https://github.com/angular/angular-cli/wiki/angular-cli
https://github.com/angular/angular-cli/wiki/stories-global-scripts
Angular Cli Webpack, How to add or bundle external js files?
have you tried upgrading it to angular 6? maybe they fixed this in the new version.
ng update #angular/cli

Set up tests with Typescript and Ava : bad require

I'm setting up AVA with Typescript to tests my JS code. Internally, I'm first calling TSC to compile my files, then call AVA with babel-register to test them (Babel register allowing require to be resolved).
"ava": "tsc && ava testJs/**/*.spec.js"
testJs being the output folder of Ts. My problem is that, even thought everything pretty much work, I have this kind of statement, usually picked up by Webpack :
import "./index.page.css";
Webpack gently require it, but babel-register doesn't. I had to change the behavior to accept .css file as noop. Here is the issue : because I'm using tsc as a compiler, those files are not copied at all in testJs, meaning they are not available in the first place.
I wanted to know what would be the best way to solve this, as I think copy-pasting the whole folder (to have all files available) just to execute tests is a bit of an overkill. Especially since, if I suddenly import a .json file (for example)I will have new problems.
For example, is there a way to tell babel-register to ignore require it cant resolve instead of breaking ?
Thanks !
You can use ignore-styles to ignore certain types of requires. By default it ignores all kinds of CSS and images (full list) and you can customise it to ignore other extensions as well.
You simply require it before babel-register in your AVA config.

"Uncaught ReferenceError: require is not defined" with Angular 2/webpack

I am working an HTML template from a graphic design company into my Angular 2 project using node and webpack.
The HTML pulls in various scripts like this:
<script src="js/jquery.icheck.min.js"></script>
<script src="js/waypoints.min.js"></script>
so I am requiring them in my component.ts:
var icheckJs = require('../js/jquery.icheck.min');
var waypointsJs = require('../js/waypoints.min');
There are several other scripts too and some SASS which appears to be working correctly.
webpack is happy and build it all and an 'npm start' is successful too. However, when it reaches the browser, I get this complaint:
Uncaught ReferenceError: require is not defined node_modules/angular2/platform/browser.js:1 Uncaught ReferenceError: require is not defined
which is actually thrown by this line from url.js:
var punycode = require('punycode');
Is this a CommonJs require? I hadn't used this in web development before a few weeks ago so I'm still untangling the various requires from webback, CommonJs et at.
An extract from my webpack.config.js for the .js loader looks like this:
{ test: /\.js$/, loader: 'script' }
How do I work around this error?
WebPack can do this alone. You need to make sure you load the initial chunk first using a script src tag. It will typically be the value of the entry: key in the WebPack config with -bundle appended. If you're not doing explicit chunking, your entry chunk should be both an initial and entry chunk and have the WebPack runtime in it. The WebPack runtime contains and loads the require function before your code runs.
Your components or whatever you're requiring need to be required from the entry file since your scripts will start there. Basically, if you're not explicitly chunking, the entry point JS file is the only one you can include with script src. Everything else needs to be required from it. What you include will typically have bundle in the JS filename. By default, it should be main-bundle.js.
For anyone that is looking for an answer but the above doesn't work:
Short
Add or Replace current target in webpack.config.js to target: 'web'
A bit longer
Webpack has different targets, if you've experimented with this and changed your target to node it will use 'require' to load chuncks.
The best thing is to make your target (or to add) target: 'web' in your webpack.config.js. This is the default target and loads your chuncks in a way the browser can handle.
I eventually found this solution here.
You can do this in one line assumed that you have
the bundle in dist/bundle.js
the source file client code that will render the page in the browser in
client/client.js
webpack && webpack ./client/client.js dist/bundle.js \
&& webpack-dev-server --progress --color
You need to run webpack again since if some sources in the library change you will get the last changes then in the dist/bundle.js package (of course you can add like a grunt file watch task for this). webpack-dev-server will run the server then.

Webpack: Make dependency using another dependency instead of its own subdependency

I am using webpack to build my app and I use a library (eventemitter4) that itself depends on another library (underscore).
However, I am already using in my application an alternative to underscore (lodash and more exactly the es6 version).
I would like eventemitter4 to use this later library and avoid including in my build the two.
I install my dependencies using npm install. As a result, underscore is bundled as a subdirectory inside the eventemitter4's directory.
It tried to set aliases but I could not make it work:
alias: {
"underscore": "lodash-es",
"lodash": "lodash-es",
"~/underscore": "lodash-es"
}
raises
ERROR in ./~/eventemitter4/index.js
Module not found: Error: Cannot resolve module 'lodash-es' in /Users/me/myapp/node_modules/eventemitter4
# ./~/eventemitter4/index.js 6:2-23
If I do not add "~/underscore": "lodash-es", the sub-underscore is included instead of lodash.
Any idea?
Thank you very much for your help.
I actually found the reason. The alias was working. The cause of the error was that lodash-es does not provide a main attribute in his package.json (it only provides an esnext:main which is not recognised by webpack).
I solve the issue by using:
alias: {
"underscore": "lodash-es",
"lodash": "lodash-es/lodash",
"~/underscore": "lodash-es"
}

What to do when wiredep doesn't work

I've recently started using bower and wiredep.
These guys play nicely together and usually work a treat.
I've come across the odd occasion where wiredep is not able to add the dependency, a recent example is:
"dependencies": {
"slimScroll": "https://github.com/rochal/jQuery-slimScroll.git#~1.3.6",
}
Is there a way to help wiredep wire these dependencies?
Not sure why this was down voted.
The problem in this instance was that the package did not specify a main property in the bower.json
For anyone interested you can add an override to your bower.json, adding in the main that was missing from the original package.
"overrides": {
"slimScroll":{
"main":["jquery.slimscroll.js"]
}
}
Just saw another example: The bootstrap 3.3.5 bower package does not reference any css files in the main property as a result wiredep can't add the css.
Wiredep checks bower.json of every package and based on that, performs the operation. If there's no dependency information then wiredep simply ignores the package.
You can manually add those file or try alternative - inject.

Categories

Resources