This project is the basis for the creation of an npm module containing a "complete" Gulp build setup for an AngularJS application using Sass. Your application source and test files can be written in JavaScript or TypeScript. If it's TypeScript, it will be validated and then compiled to JavaScript.
The goal of this tool is to provide the handy workflow for developing Angular based applications (no matter what language you use - JavaScript or TypeScript) and ensure the profound checking of the code quality at the same time. The module orchestrates a collection of Gulp build functionality into a single npm dependency and makes it easier for developers to have and maintain the build setup for own Angular projects.
The Gript Newsgroup is the place for announcements and discussion about Gript's features. Feel free to join.
The project includes a sample application to make it possible to test the build setup.
The local sample application exemplifies the needed structure for applications supported by the gript
npm package.
The sample application resides in the app
folder.
The index.html
in the app
folder is especially important - it contains markers where generated files will be included.
- JavaScript validation using ESLint,
- TypeScript validation (TSLint) and incremental compilation,
- scss validation (scss-lint) and compilation,
- HTML validation using htmllint,
- unit tests performed using Karma and PhantomJS (tests can be written in JavaScript or TypeScript),
- unit testing coverage metered by Istanbul,
- HTML partials pre-loading into the Angular
$templateCache
, - includes custom generated Modernizr script
- full concatenation/minification for all production JS and CSS files,
- Live-reload capability: web app is auto-refreshed if HTML, TypeScript or scss files change,
- watch tasks: if your source files change, they will be checked for errors, compiled and then injected into your application, Gript uses Chokidar which notices the changes instantly, keeping the CPU usage down at the same time,
- contains the mock server based on
YAML/JSON/JS
configuration files. Refer to the Mock Server section for usage guidelines. - contains the locked set of specific
npm
dependencies, to minimize "the dependency hell".
The use of the this Gulp build tool is based on applications code being structured according to Google's Best Practice Recommendations for Angular App Structure. The primary directories and files are:
|---- /app
| |
| |---- components
| |---- sections
| |---- img
| |---- styles
| |---- resources
| |---- lib
| |---- index.html
| |---- app.js
| |---- .eslint.rc.yml
| |---- constants.json
|---- /bower_components
|---- /target
| |---- dist
| |---- tmp
|---- /mocks
|---- gulpfile.js
|---- bower.json
|---- package.json
|---- .eslint.rc.yml
|---- .scsslint.rc.yml
|---- tslint.json
|---- .htmllint.rc
which means:
app
: contains the application source codeapp/sections
: contains the subsections of the application codeapp/components
: contains the components (directives, services etc.) embedded in the applicationapp/app.js
orapp/App.ts
: the entry point of the Angular applicationapp/resources
: the place for other resources, like translation files. This will be copied to /target/distapp/lib
: the place for JavaScript libraries not coming from Bower. It will be excluded from linting.app/constants.json
: optional constants file from which Angular constants module will be generatedbower_components
: libraries downloaded by Bowernode_modules
: tools downloaded by npmtarget/tmp
: contains generated files (compiled TypeScript, compiled scss styles, Angular templates etc.)target/dist
: contains app distribution packagemocks
: contains your mock services definitions.gulpfile.js
: the build files importing the Gulp tasks defined in thenode_modules/gript
bower.json
: contains Bower dependencies.eslint.rc.yml
: contains rules for es-linter (ESLint). Cascading rules configuration is possible..scsslint.rc.yml
: contains rules for scss linter (scss-lint)tslint.json
: rules for the TypeScript linter (TSLint).htmllint.rc
: rules for the HTML linter (htmllint)
To make use of the gript
npm module define the dependency to gript
in the package.json
file in your own application:
"dependencies": {
"gulp": "3.9.0",
"gript": "~0.0.38",
....
together with your other npm dependencies. Gript is available in the npm repository.
Running the command
`npm install --save-dev`
will include gript
in your node_modules
folder and make it available for development.
The tool comes with a guide for the enabling of the build tool in your project.
The supported Angular application is built by Gulp, which is controlled by the gulpfile.js
.
Gript includes a sample Gulp file, located in the sample_configs
directory.
There are also example configuration files for Bower
, es-lint
, and scss-lint
in the sample_configs
directory.
This sample_configs/gulpfile.js
can be used as a starter for your project. This is where you define the dependency to gript
module and specify the options for the build process of your own application:
var gulp = require('gulp');
require('gript')(gulp);
// Set the config to use across the gulp build
gulp.config = {
repository: 'http://git.nykreditnet.net/scm/dist/xpa-no-specified-project.git',
app: {
module: 'yourApp',
constantsFile: 'app/constants.json'
},
server: {
module: 'yourApp',
configFile: 'app/config.json'
},
partials: ['app/**/*.html'],
server: {
port: 8080,
host: 'localhost',
livereload: {
port: 35729
}
},
serverDist: {
port: 8080,
host: 'localhost'
},
proxy: {
port: 8001,
hostHeader: 'gript',
targetURL: 'http://gript'
},
mocks: {
location: 'localhost',
stubs: 8050,
tls: 8443,
admin: 8051,
relativeFilesPath: true,
files: [
'mocks/*.{json,yaml,js}'
]
},
typeScript: {
compilerOptions: {
noImplicitAny: true,
target: "es5",
sourceMap: true,
declarationFiles: true,
noExternalResolve: false,
sortOutput: true,
removeComments: false,
preserveConstEnums: true
}
},
minification: {
html: {
removeEmptyAttributes: false,
collapseBooleanAttributes: false,
collapseWhitespace: true,
caseSensitive: true
},
css: {
safe: true,
autoprefixer: false,
discardUnused: false,
reduceIdents: false,
mergeIdents: false
},
javascript: {
mangle: true,
preserveComments: false
}
},
modernizr: {
//cssprefix: true, // add this line to fix conflicts with bootstrap (e.g not adding class 'hidden' to html tag)
options: [
'addTest',
'html5printshiv',
'testProp',
'fnBind',
'setClasses'
],
'feature-detects': []
},
fontsScan: [
'bower_components/font-awesome',
'bower_components/bootstrap-sass-official'
]
karma: {
browsers: ['PhantomJS']
}
};
Be sure to set values for the configuration in your copy of the sample_configs/gulpfile.js
.
These values are:
app.module
: mandatory name of the project. It's being used as a module name when generating Angular modules, like$templateCache
or constants modules.repository
the GIT url of your application, used in therelease
andprerelease
tasks.partials
is a glob pattern to specify what files should bne considered as Angular$templateCache
templates. Refer to the Partials section for details.server
configuration options for the web server like port number, live reload port number, host name etc.serverDist
configuration options for the web server started fromdist
by usingserver:dist
task.proxy
optional proxy port, host header and target URL configuration. The proxy will start only if you specifyproxy
section in yourgulpfile.js
.mocks
mock server configurationtypescript
typescript compilation optionsminification
minification related options
You may kickstart your project by copying sample_configs/gulpfile.js
to the root of your own project.
This gives you a very simple build configuration as a starting scenario.
NOTE: If you have no tests the
gulp test
command will fail, until you create your first piece of logic and its corresponding test.
The default task builds an application and then starts the development server. Your source code (TypeScript, HTML, scss) will be watched for changes, and - if neccessary, compiled and injected into the index.html
.
Just by running
gulp
you are ready to start developing your project.
The gulpfile.js
from Gript contains also these specific tasks:
- build : builds the application for the development
- dist : builds and minifies the application for the deployment. The application will be copied to
target/dist
directory. - ts : compiles your app TypeScript files
- partials : compiles HTML partials into Angular's
$templateCache
Javascript files. All files matchingpartials
config glob are considered as templates. - styles : compiles scss files
- inject : injects Bower dependencies, compiled HTML partials, TypeScript and scss into your app's
index.html
. Files will be injected according to the marking in theindex.html
file. Refer to the Files injection section of this readme for details.- inject-bower : downloads and injects Bower dependencies
- inject-styles : compiles and injects scss styles
- inject-partials : compiles HTML partials into Angular's
$templateCache
and then injects them into theindex.html
- inject-js : complies the TypesScript and then injects all JavaScript files
- lint : runs linters on the HTML, scss, Javascript and TypeScript source files. Refer to the Linting section for possible options.
- lint-js
- lint-scss
- lint-ts
- lint-html
- test : runs the unit tests through Karma - NOTE: fails if no tests are available. Refer to the Testing section for details.
- clean : removes the whole
target
directory (temporary generated files and distribution package)- clean-dist : removes the
target/dist
directory (the distribution package) - clean-tmp : removes the
target/tmp
directory (all temporary generated files) - clean-js : removes the
target/tmp/js
directory (compiled TypeScript files) - clean-partials : removes the
target/tmp/partials
directory (Angular's$templateCache
Javascript files) - clean-styles : removes the
target/tmp/styles
directory (compiled scss files) - clean-bower : removes the
bower_components
directory
- clean-dist : removes the
- fonts : searches for all
eot
,ttf
,woff
,woff2
files, flattens the directory structure and copies them into your app. It will search the wholebower_components
directory, unless you configure it otherwise in thefontsScan
array in the config section of thegulpfile.js
. - images : copies all image files into the
dist
directory - watch : watches the source code for changes and runs the relevant task(s) whenever something changes
- server : starts a development server
- server:dist : starts a server using the deployment directory (
target/dist
) - mocks : starts a server with mock services. Refer to the Mock server section for guidelines.
- modernizr : builds custom Modernizr script and injects it into
index.html
- config : creates an optional Angular constants module with values from the file specified in
gulp.config.app.constantsFile
. The default isapp/constants.json
.
You can list all of the available tasks by running the command:
gulp --tasks
Gript will automatically run your tests using Karma. Your tests can be written in JavaScript or TypeScript (they will be compiled first). Tests filenames must end in test
or Test
(for example PortfolioServiceTest.ts
, PortfolioService_test.ts
, portfolioService_test.js
).
Your tests will be executed using headless, PhantomJS browser. You can customize this behavior altogether with other Karma options in the karma
section of the gulpfile.js
.
Refer to Karma Configuration docs for possible options and values.
For example, if you need to run your tests under Chrome browser, amend the default configuration:
karma: {
frameworks: ['jasmine', 'sinon', 'angular-filesort'],
plugins: [
'karma-jasmine',
'karma-sinon',
'karma-angular-filesort',
'karma-phantomjs-launcher',
'karma-chrome-launcher',
'karma-junit-reporter',
'karma-coverage',
'karma-ng-html2js-preprocessor'
],
browsers: ['Chrome']
}
The partials
task will create Angular $templateCache
files from your HTML files. The resulting JavaScript files will be created in the target/tmp/partials
directory.
These files will then be injected into the index.html
file, according to <!-- inject:partials --><!-- endinject -->
markings.
The dist
task will minify and concatenate them with other JavaScript files from your application.
Gript considers all HTML files in the app
directory (except the index.html
) as partials by default. You can change this behaviour by setting up the partials
configuration value in the gulpfile.js
. This may come in handy when you don't want a specific HTML file to be converted to Angular $templateCache
partial.
For example:
partials: ['app/**/*.html', '!app/sections/welcome/testOauth.html']
will generate $templateCache
from all HTML files except the app/sections/welcome/testOauth.html
.
Take note that all files excluded from partials generation will be just copied to the target
directory. At the same time, all files considered as partials will not be copied - after the conversion to JavaScript we don't need them anymore.
To ensure the profound checking of the code quality of your application, Gript will check all your HTML, scss, TypeScript and JavaScript files.
The linting process is executed during the build, and is also included in the watch
task, to re-lint the file on the fly, after you change it.
The number of configuration files are being used to customize the linting options:
.eslint.yml
contains configuration for the powerful JavaScript linter, the ESLint. Refer to the Options section for avaialable options..scss-lint.yml
contains configuration for scss linter, the scss-lint. Referer to the Configuration for options.tslint.json
contains options for TSLint. Refer here for the description of rules..htmllintrc
contains setup for htmllint. Refer to the options for possible settings.
For your convenience, Gript contains sample configuration files for all linters in the sample_configs
directory.
During the linting process, Gript generates Checkstyle-like XML reports in the target
directory:
es-lint-result.xml
html-lint-result.xml
scss-lint-result.xml
ts-lint-result.xml
The reports from tests execution and code coverage are also generated into the target
directory:
cobertura-coverage.xml
test-results.xml
You can use linting, test and coverage reports in your continuous integration setup, like Jenkins for example.
During the build process, Gript will analyse your JavaScript and CSS files and generate custom Modernizr.
The custom script will be injected into the index.html
.
You can customize the script generation by changing options in the modernizr
section of the gulpfile.js
.
Refer to the Modernizr build options for possible values.
If you develop your app in the TypeScript, files will be compiled and then injected. The example setup uses DefinitelyTyped
to get the TypeScript types definitions. They are being downloaded by Bower into the bower_components/DefinitelyTyped
directory, which is excluded from the TypeScript linting.
The resulting JavaScript files will be placed in the target/tmp/js
directory.
You can customize your TypeScript compile options using the typeScript
section in the gulpfile.js
.
Refer to the Compiler-Options section in the TypeScript documentation for available options.
After executing a dist
task, all resulting HTML, CSS and JavaScript files will be concatenated and minified.
You can customize the minification options by modyfying the minification
section in your gulpfile.js
.
- HTML files will be minified using html-minifer. See the html-minifier docs for available options.
- CSS files will be minified with cssnano. Refer to the documentation for possible optimisations.
- JavaScript will be compressed with UglifyJS. Refere to the gulp-uglify module docs for help how to set options.
By default, all TypeScript, scss and HTML files will be compiled and injected into your app's index.html
file.
The target/tmp
directory is the place for the compilation output:
target/tmp/js
: will contain compiled TypeScript filestarget/tmp/partials
: will contain all HTML partials from your Angular app compiled into Angular$templateCache
.target/tmp/styles
: will contain compiled scss files
Compiled scripts and styles will then be injected into the app's index.html
according to the injection markings:
<!-- bower:css --><!-- endbower -->
: Bower CSS dependencies<!-- inject:css --><!-- endinject -->
: compiled scss files<!-- bower:js --><!-- endbower -->
: Bower JS dependencies<!-- inject:js --><!-- endinject -->
: TypeScript files compiled into JS<!-- inject:partials --><!-- endinject -->
: HTML partials compiled into Angular's$templateCache
.
After executing the dist
task, all the stylesheets and JavaScripts will be minimized and concatenated.
The result will be injected into target/dist/index.html
according to these injection markings:
<!-- build:css styles/vendor.css --><!-- endbuild -->
: vendor stylesheets (frombower_components
)<!-- build:css styles/main.css --><!-- endbuild -->
: your own stylesheets<!-- build:js scripts/vendor.js --><!-- endbuild -->
: vendor scripts (frombower_components
)<!-- build:js scripts/main.js --><!-- endbuild -->
: your own scripts
Refer to app/index.html
or sample_configs/index.html
for an example how to define these markings.
The mock server implementation in Gript is using stubby4node.
It's a highly configurable server for mocking/stubbing external systems during development.
Gript takes endpoint descriptors in the form of a YAML or JSON files that tell it how to respond to incoming requests.
For each incoming request, configured endpoints are checked in-order until a match is found.
The endpoints can contain regular expressions, any of HTTP methods, queries, headers, dynamic token interpolation, defined fake response latency and so on.
The response can be parametrized or served from a file - the possiblities are endless.
Refer to the Stubby endpoint configuration section for assistance how to define your own endpoints.
By default, the mocks
Gulp task will start together with the server
and server:dist
tasks.
Gript contains some simple endpoints definitions in the mocks
and sample_config/mocks
directory to get you started.
You can customize the mocks directory name and server ports in the mocks
section of your gulpfile.js
.
To create new mocked service, simply put the new definition of the endpoint into the mocks
folder.
You can disable the mock server by using --nomocks
option when executing any of the tasks, for example:
gulp --nomocks
Gript makes use of node-gyp which is a cross-platform command-line tool written in Node.js for compiling native addon modules for Node.js. To use node-gyp you will need some external dependencies, depending on your platform:
On Unix
- python (v2.7 recommended, v3.x.x is not supported)
- make
- A proper C/C++ compiler toolchain, like GCC
On Mac OS X
-
python (v2.7 recommended, v3.x.x is not supported). It's already installed by default on Mac OS X.
-
You also need to install the Command Line Tools via Xcode. You can find this under the menu Xcode -> Preferences -> Downloads. (This step will install gcc and the related toolchain containing make)
-
for scss-lint to work properly, you need
scss-lint
Ruby gem installed:$ gem install scss_lint
Windows
- Python (v2.7.10 recommended, v3.x.x is not supported). Make sure that you have a
PYTHON
environment variable, and it is set to drive:\path\to\python.exe not to a folder
Windows XP/Vista/7
- Microsoft Visual Studio C++ 2013 (Express version works well). If the install fails, try uninstalling any C++ 2010 x64&x86 Redistributable that you have installed first. If you get errors that the 64-bit compilers are not installed you may also need the compiler update for the Windows SDK 7.1
Windows 7/8
- Microsoft Visual Studio C++ 2013 for Windows Desktop (Express version works well)
Windows 10
- Install the latest version of npm
- Install Python 2.7 from https://www.python.org/download/releases/2.7/ and make sure its on the System Path
- Install Visual Studio Community 2015 Edition. (Custom Install, Select Visual C++ during the installation)
- Set the environment variable
GYP_MSVS_VERSION=2015
- Run the command prompt as Administrator $ npm install (--msvs_version=2015) <-- Shouldn't be needed if you have set GYP_MSVS_VERSION env If the above steps have not worked or you are unsure please visit http://www.serverpals.com/blog/building-using-node-gyp-with-visual-studio-express-2015-on-windows-10-pro-x64 for a full walkthrough
All Windows Versions
-
For 64-bit builds of node and native modules you will also need the Windows 7 64-bit SDK
-
You may need to run one of the following commands if your build complains about WindowsSDKDir not being set, and you are sure you have already installed the SDK:
call "C:\Program Files\Microsoft SDKs\Windows\v7.1\bin\Setenv.cmd" /Release /x86 call "C:\Program Files\Microsoft SDKs\Windows\v7.1\bin\Setenv.cmd" /Release /x64
The gulpfile.js
for the gript
npm module is located in the root of the project. It contains a Gulp task to package and the verify the npm module:
- create-package creates the npm package
- verify-package verifies its contents
After that the npm module is ready to be published to the npm
repository.
The Gript logo contains modified version of the Link icon licensed under Creative Commons license.