To compress js files via gulp I have tried using both gulp modules
gulp-uglifyjs
gulp-uglify
but it changes the variable I define.
for eg:
var app = angular.module('myApp', [])
.config(function($interpolateProvider){
$interpolateProvider.startSymbol('{[').endSymbol(']}');
});
is compressed to:
var app = angular.module("myApp",[])
.config(function(n){n.startSymbol("{[").endSymbol("]}")});
while using Angularjs with Twig I have to change the mustaches {{ }} to {[ ]} and the angularjs doesn't recognize the n instead of $interpolateProvider.
Any suggestions how to tell uglifyjs not to change my variables while compression?
This is when you need to include ng-min task into your build as well as it will protect your angular from minification problems.
Or by hand, but thats just silly...
var app = angular.module('myApp', []).config(['$interpolateProvider', function($interpolateProvider){
$interpolateProvider.startSymbol('{[').endSymbol(']}');
}
]);
Some docs on Angular minification issues scroll down to 'A Note on Minification.'
Related
im very new to Angular and i started a test Project with Angular Cli.
All works fine but i have installed a 3.rd Party Module (angular-ui-carousel).
Now i get following error:
Uncaught ReferenceError: angular is not defined
at Module../node_modules/angular-ui-carousel/dist/ui-carousel.js (ui-carousel.js:21)
ui.carousel.js (only the first rows..)
'use strict';
(function (angular) {
// Create all modules and define dependencies to make sure they exist
// and are loaded in the correct order to satisfy dependency injection
// before all nested files are concatenated by Gulp
// Config
angular.module('ui.carousel.config', []).value('ui.carousel.config', {
debug: true
});
// Modules
angular.module('ui.carousel.providers', []);
angular.module('ui.carousel.controllers', []);
angular.module('ui.carousel.directives', []);
angular.module('ui.carousel', ['ui.carousel.config', 'ui.carousel.directives', 'ui.carousel.controllers', 'ui.carousel.providers']);
})(angular); //error points here
'use strict';
is there any workaround to run this module in Angular 6?
You're confusing Angular and AngularJS.
angular. references are applicable to AngularJS(AngularJS 1.x)
And Angular(Angular 2+) don't have angular. references.
angular-ui-carousel is a library for AngularJS and NOT Angular
Please consider using some other library that is meant for Angular, like ng-simple-slideshow
I'm working on an existing (and working) Angular 1.5.5 app. It's very small and has a controller, a directive and a couple of services, all split into individual files.
I'd now like to move to Webpack and make the minimum number of changes to the app to support that. A lot of the Webpack/Angular demos I've found have been about creating a new Angular app with web pack built in from the start, but I don't want to rebuild the existing app, just make whatever changes are necessary to use a webpack-produced bundle. It's also using regular JS, whereas most of the tutorials I've seen are for ES6.
I've got grunt-webpack installed and working, it's creating the bundle.js file and I can see inside the bundle that it's pulling in Angular, Angular-aria and Angular-animate (my module dependencies)
However, when I run the site I see an error:
Uncaught TypeError: angular.module is not a function
My webpack task is as follows:
module.exports = {
dist: {
entry: './Static/js/Ng/app.js',
output: {
path: './Static/dist/js',
filename: 'bundle.js'
}
}
};
As I say, the actual Webpack bundling seems to be working as expected and creates the bundle.js file.
The main entry file (app.js) is as follows:
(function () {
'use strict';
var angular = require('../vendor/angular.js');
var ngAria = require('../vendor/angular-aria.js');
var ngAnimate = require('../vendor/angular-animate.js');
angular.module('app', [ngAria, ngAnimate]);
}());
If I log out the angular variable in this file, it's just an empty object, even though I can see the Angular source in the bundle.
What am I missing?
You probably shadow the global angular property by your local var angular variable. Try this:
(function () {
'use strict';
require('../vendor/angular.js');
require('../vendor/angular-aria.js');
require('../vendor/angular-animate.js');
angular.module('app', [ngAria, ngAnimate]);
}());
ASP.NET (or gulp) will take care of bundling and minification. However, the problem i came across is rather different. Per Angular2's tutorials, the view HTML is embedded within the component itself. There is a way, using TypeScript, to separate that into a .ts and .html files. Here's how:
...
/// <reference path="./view-declaration.d.ts" />
...
import {html} from '/app.html!text';
...
#Component({
...
template: html
})
...
And faking .html as a module in view-declaration.d.ts file:
declare module '/app.html!text' {
var html:string;
return default html;
}
This is using SystemJS with its text plugin. This will not generate System.register for .html files which means HTMLs can't be bundled along the transpiled .js files.
So questions is, how do you separate the HTML from JavaScript, but also be able to bundle them properly?
Also to note, this approach is just the same as setting the templateUrl on your component. Both of which defeat the purpose of bundling and reduction of server hits per component. The offered solution from Angular2 is to use string and set template on a component. This is pretty far from reality of junior developers and code reviews (yea not gonna get the whole code base in order to run and see if browser complains about a non-closed tag!).
This is gulp plugin which I think can solve your issue.
look at:
https://github.com/ludohenin/gulp-inline-ng2-template
the advantage you keep having a clean html file using templateUrl during development. And this task can be part of your production\staging -minified - gulp build task.
e.g (Part of my build tasks!)
var inlineNg2Template = require('gulp-inline-ng2-template');
gulp.task('build-prod', ['build.lib'], function () {
var tsProject = typescript.createProject('./tsconfig.json', { typescript: require('typescript') });
var tsSrcInlined = gulp.src([webroot + '**/*.ts'], { base: webroot })
.pipe(inlineNg2Template({ base: webroot }));
return eventStream.merge(tsSrcInlined, gulp.src('Typings/**/*.ts'))
.pipe(sourcemaps.init())
.pipe(typescript(tsProject))
.pipe(sourcemaps.write())
.pipe(gulp.dest(webroot));
});
As it turns out, you'll need to use templateUrl for development, but replace that with template during the bundling and minification. This is the gulp task for the job:
var gulp = require('gulp'); //install 'gulp' via npm
var uglify = require('gulp-uglify'); //install 'gulp-uglify' via npm
var concat = require('gulp-concat'); //install 'gulp-concat' via npm
var replace = require('gulp-replace'); //install 'gulp-replace' via npm
var fs = require("fs"); //already available in Visual Studio and of course NodeJS
gulp.task('bundle:js', function () {
return gulp
.src([
"file1.js",
"file2.js"
])
.pipe(replace(/templateUrl.*\'/g, function (matched) {
var fileName = matched.match(/\/.*html/g).toString();
var fileContent = fs.readFileSync(fileName, "utf8");
return 'template:\'' + fileContent.replace(/\r\n/g, '') + '\'';
}))
.pipe(concat('file.min.js'))
.pipe(gulp.dest('my bundle folder'))
.pipe(uglify())
.pipe(gulp.dest('my bundle folder'));
});
This is to match .html files and the template URL, but it can be tweaked if needed.
Your template file app.html.ts can export the html template as a string.
export const htmlTemplate = `
<p>My app</p>
`;
Then your component (app.component.ts) can import the template inline.
import { Component } from '#angular/core';
import { htmlTemplate } from './app.html';
#Component({
selector: 'my-app',
template: htmlTemplate,
})
...
This approach:
allows for in-lining of templates at compilation, avoiding the additional network request that using "templateUrl" adds and allowing templates to be minified and bundled with other js
allows templates to live in external files for code clarity and scaling
can be easily migrated to a plain HTML file once Typescript "import file as string" functionality is in place
allows Webstorm html syntax highlighting to still work correctly
See blog from Angular University
I just got started with Foundation for Apps, but I was having trouble adding my angular controllers in a separate folder and using them.
I have this current structure in my assets' js folder:
js/
app.js //this has all the controllers etc. by chaining
but I want it to be
js/
app.js
controllers/
home.controller.js
main.controller.js
I don't want to keep a single large js file developed by chaining my controllers, services etc. I want a more modular structure as specified.
When I changed it to the modular structure, I got following three errors:
1. 'HomeCtrl' not defined.
2. Uncaught SyntaxError: Unexpected token < at the 1st line of home.controller.js
3. Resource interpreted as Script but transferred with MIME type text/html: "http://localhost:8079/assets/js/home.controller.js". at the point where I am including 'home.controller.js' in index.html
Here's my template:
---
name: home
url: /
controller: HomeCtrl
---
<div class="grid-container">
<h1>Welcome to Foundation for Apps!</h1>
<p class="lead">This is version <strong>1.1 Weisshorn</strong>.</p>
</div>
home.controller.js:
app.controller('HomeCtrl', ['$scope', function($scope) {
$scope.temp = 'hello';
}]);
app.js:
var app = angular.module('application', [
'ui.router',
'ngAnimate',
'foundation',
'foundation.dynamicRouting',
'foundation.dynamicRouting.animations'
])
.config(config)
.run(run)
;
config.$inject = ['$urlRouterProvider', '$locationProvider'];
function config($urlProvider, $locationProvider) {
$urlProvider.otherwise('/');
$locationProvider.html5Mode({
enabled:false,
requireBase: false
});
}
function run() {
FastClick.attach(document.body);
}
To solve this I tried adding my controller reference in gulpfile.js by referring this
I also referred this but I still cannot get it to work. Any idea what I am doing wrong?
Inside gulpfile.js check this line. You'll see that only client/assets/js/app.js is used when coupling your minimized file. You need to make it copy all your controller's .js files too :
// These files are for your app's JavaScript
appJS: [
'client/assets/js/app.js',
'./client/assets/js/controllers/*.js',
]
You can also use an angular module to hold all your controllers & services then injecting it to your app module. This is how I'm using it here and this is how it is also done in this great ready to use Fork : https://github.com/CreativityKills/foundation-apps-template
Note: remember to restart gulp after each modify of its config file and check if your code has been well included in the built JS file ( by default is /build/assets/js/app.js )
I have an Angular, Node based app. It uses Jade for templating. I want to hide or show chunks of my page depending on the NODE_ENV variable that I use to start node with.
Something like this (not sure about how to check "else not" with ng-if):
div(ng-if="testingmode")
{{somescopevar}}
div(ng-if != "testingmode")
{{differentscopevar}}
The kicker is that testingmode is determined by what the NODE_ENV variable is. I can access that variable within my jade templates but don't know how to get it into my Angular scope.
tl;dr: How do I get NODE_ENV into my Angular scope?
Personally I would create an api call that returns that value, and then have angular grab it in a controller using $http.
In your node routes:
app.get('/nodeenv', function(req, res, next){
return res.json({ env: app.get('env') });
});
In your angular controller:
$http.get('/nodeenv').success(function(data){
$scope.myEnvironment = data.env;
});
UPDATE:
A new way I have been doing this with newer projects is generating my root index file as a template in node (eg. with doT templates). Then passing any constants into the template to be loaded directly into angular. Below is the way you could pass in the environment for example:
index.def
<html>
<head><!-- head stuff --></head>
<body>
<div>scripts and content go here</div>
<!-- initialise any templated constants -->
<script>
angular.module('mymodule').constant('globals', {
env: '{{=it.env}}'
});
</script>
</body>
</html>
As an alternative you could put this in your build system with gulp-replace. I'm sure grunt has a similar feature.
index.html
<script>
var ENV = 'NODE_ENV'; // replaced by gulp
</script>
gulpfile.js
gulp.task('setEnv', function(){
gulp.src(['index.html'])
.pipe(replace(/NODE_ENV/g, process.env.NODE_ENV))
.pipe(gulp.dest('build/index.html'));
});
Haven't test the exact code, but you get the gist.