javascript
development, document
Company / Organization: becke.ch
(I suggest to use here your domain name (or company name) which is registered and globally unique)
Scope: 0.0 (language=en;language=default;technology=js;organization=becke.ch;)
(ID and key/values of the scope this Module / Artifact / Component / Work-Product is valid for. The ID is as well part of the name of this Module / Artifact / Component / Work-Product i.e. is exposed towards outside of the Module / Artifact / Component / Work-Product. See as well: [1] and [2])
Version: 1.0.0
(Major[.Minor[.Patch[Build]]] – e.g. 2.3.5-0041 – the Major[.Minor] version is as well exposed towards outside of the Module / Artifact / Component / Work-Product. Different “.Patches” respective “.Build” versions are described in the same Major[.Minor] Module / Artifact / Component / Work-Product using substructures. In the current context the substructures would be reflected in sub-chapters. See as well: [1] and [2])
File-name: becke-ch--javascript--s0-0-v1-0.odt
Document Version History
Version | Date | Author | Description |
1.0.0 | 15.11.2015 | Raoul Becke | Initial version |
Module / Artifact / Component / Work-Product Version History
Version | Date | Author | Requirements | Components Changed |
1.0.0 | 15.11.2015 | Raoul Becke | Create documentation on JavaScript with the following content: Directory & Naming Convention, NPM (Package Manager for Java-Script) (Installation, Setup, Directory Structure, Unit Testing, Intellij, Workflow, Publishing), YARN, Private registry/repository (Nexus Repository OSS), Separate File versus In-Line HTML, Data Structure (Types, Pointers, String, Function, DOM), Object Orientation (Inheritance), Functionality (Parameters, Recursive Function, Nested Function, Copy-Paste, Log, RegExp, Cursor Positioning, Contenteditable), Performance, JSON, TypeScript, AngularJS 1 (Download, Documentation, Java, View, Controller, Scope, Filter, Directive, JSON, TreeView, Call Function, Server Communication), Angular 2 | This document |
Illustration Index
Illustration Index
Illustration 1: Illustration sample 6
Index of Tables
Index of Tables
Table 1: Table sample 6
Table 2: References 9
Table 3: Glossary 9
This document captures all the issues and solutions I’ve come across so far during my JavaScript path.
AngularJS: angularjs/controller/becke-ch--PRODUCT--sX-Y-Z-vA-B--USECASE--pl--client.js
•Controller: angularjs/controller/becke-ch--PRODUCT--sX-Y-Z-vA-B--USECASE--pl--client--controller--...js
•Directive: angularjs/directive/becke-ch--PRODUCT--sX-Y-Z-vA-B--USECASE--pl--client--directive--...js
•Filter: angularjs/directive/becke-ch--PRODUCT--sX-Y-Z-vA-B--USECASE--pl--client--filter--...js
•Model: angularjs/directive/becke-ch--PRODUCT--sX-Y-Z-vA-B--USECASE--pl--client--model--...js
•Service: angularjs/directive/becke-ch--PRODUCT--sX-Y-Z-vA-B--USECASE--pl--client--service--...js
Further context root sub-directories:
•css
•img
•lib
•view: view/becke-ch--PRODUCT--sX-Y-Z-vA-B--USECASE--pl--client--main.js
https://ponyfoo.com/articles/choose-grunt-gulp-or-npm
npm makes it easy for JavaScript developers to share and reuse code, and it makes it easy to update the code that you're sharing.
...
Node.js® is a JavaScript runtime built on Chrome's V8 JavaScript engine. Node.js uses an event-driven, non-blocking I/O model that makes it lightweight and efficient. Node.js' package ecosystem, npm, is the largest ecosystem of open source libraries in the world.
…
http://openmymind.net/2012/2/3/Node-Require-and-Exports/
http://wesbos.com/javascript-modules/
…
In Node, things are only visible to other things in the same file. By things, I mean variables, functions, classes and class members.
the fundamental Node building block is called a module which maps directly to a file
To expose things we use module.exports and export everything we want:
becke-ch--regex--s0-0-v1--base--pl--lib.js:
function Regex(pattern, flags) {
this.pattern = pattern;
this.flags = flags;
if (!pattern) {
this.regex = new RegExp(pattern, flags);
}
this.regexGroupStructure = getRegexCompleteGroupingStructure(pattern);
try {
this.regex = new RegExp(this.regexGroupStructure[0][2], flags);
} catch (e) {
new RegExp(pattern, flags);
}
}
function initialize() {
if (!(typeof module === "undefined")) {
module.exports = Regex;
}
}
initialize();
Important to mention here is that I want to use the JavaScript as well outside of Node in plain old JavaScript environment and therefore I put the module-export into an initializer function which checks whether we are in a Node environment or a plain JavaScript environment!
require is used to load a module, which is why its return value is typically assigned to a variable:
var assert = require('assert');
var Regex = require('../src/becke-ch--regex--s0-0-v1--base--pl--lib');
describe('exec', function () {
it('regex abcdef applied on abcdef', function () {
var pattern = 'abcdef';
var str = 'abcdef';
var regex = new Regex(pattern);
var result = regex.exec(str);
var regexp = new RegExp(pattern);
var resultp = regexp.exec(str);
//console.log(result);
assert.equal(resultp.length, result.length);
assert.equal(resultp.input, result.input);
for (var i = 0; i < resultp.length; i++) {
assert.equal(resultp[i], result[i]);
}
assert.equal(1, result.index.length);
assert.equal(0, result.index[0]);
});
});
…
https://docs.npmjs.com/getting-started/installing-node
https://nodejs.org/en/download/
Download to: /tool/node-v4.2.4-linux-x64.tar.gz
Extract to: /tool/node-v4.2.4-linux-x64
Installing Node.js
If you're using Mac or Windows, the best way to install Node.js is to use one of the installers from nodejs.org. If you're using Linux, you can use the installer, or you can check NodeSource's binary distributions to see whether or not there's a more recent version that works with your system.
Test: Run node -v. The version should be higher than v0.10.32.
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v1:/tool/node-v4.2.4-linux-x64/bin$ ./node -v
v4.2.4
https://github.com/nodejs/node-v0.x-archive/issues/3911
admin--s0-v1@hp-elitebook-840-g1--s0-v1:/tool/node-v4.2.4-linux-x64/bin$ sudo ln -s /tool/node-v4.2.4-linux-x64/bin/node /usr/bin/
Or alternatively:
root@hp-elitebook-840-g1--s0-v1:~# vi /etc/profile
...
export PATH=/tool/node-v4.2.4-linux-x64/bin:$PATH
...
Installing new version of Node.js
The same steps as mentioned above can be performed and the /etc/profile needs to be update to point to the new path (alternatively the following approach can be used to support multiple Node.js versions: https://nodecasts.io/update-node-js/ )
Updating npm
Node comes with npm installed so you should have a version of npm. However, npm gets updated more frequently than Node does, so you'll want to make sure it's the latest version.
Test: Run npm -v. The version should be higher than 2.1.8.
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v1:/tool/node-v4.2.4-linux-x64/bin$ ./npm -v
2.14.12
The current stable version of npm is 3.5.2
To upgrade, run: [sudo] npm install npm@latest -g
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v1:/tool/node-v4.2.4-linux-x64/bin$ ./npm install npm@latest -g
/tool/node-v4.2.4-linux-x64/bin/npm -> /tool/node-v4.2.4-linux-x64/lib/node_modules/npm/bin/npm-cli.js
npm@3.5.2 /tool/node-v4.2.4-linux-x64/lib/node_modules/npm
And then everything looks fine (but you first need to log-out-log-in or restart in order that the changes in profile are picked up!):
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v1:~$ node -v
v4.2.4
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v1:~$ npm -v
3.5.2
Once the local/custom registry is set up – see chapter 5.2 - point yarn to local/custom registry (https://github.com/yarnpkg/yarn/issues/606):
npm config set registry http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-2-v3-0--npm-group
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:~$ npm config set registry http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-2-v3-0--npm-group
Double check your local “.yarnrc” file to make sure everything worked fine:
vi .npmrc
...
registry=http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-2-v3-0--npm-group
...
https://docs.npmjs.com/getting-started/installing-npm-packages-locally
…
There are two ways to install npm packages: locally or globally. You choose which kind of installation to use based on how you want to use the package.
If you want to depend on the package from your own module using something like Node.js' require, then you want to install locally, which is npm install's default behavior. On the other hand, if you want to use it as a command line tool, something like the grunt CLI, then you want to install it globally.
…
http://stackoverflow.com/questions/5926672/where-does-npm-install-packages
…
Global libraries
You can run npm list -g to see where global libraries are installed.
On Unix systems they are normally placed in /usr/local/lib/node or /usr/local/lib/node_modules when installed globally. If you set the NODE_PATH environment variable to this path, the modules can be found by node.
Windows XP - %USERPROFILE%\Application Data\npm\node_modules
Windows 7 - %AppData%\npm\node_modules
Non-global libraries
Non-global libraries are installed the node_modules sub folder in the folder you are currently in.
You can run npm list to see the installed non-global libraries for your current location.
…
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:~$ npm list -g
/media/disk-ssd--s0-v1/tool/node-v4.2.4-linux-x64/lib
└─┬ npm@3.5.2
├── abbrev@1.0.7
├── ansi-regex@2.0.0
…
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:~$ npm –help
…
npm@3.5.2 /media/disk-ssd--s0-v1/tool/node-v4.2.4-linux-x64/lib/node_modules/npm
...
For now and for npm modules I go with a very simple directory structure: “src” and “test” as follows:
/**
* This class is an extension of the standard {@link RegExp} class adding missing functionality.
* For further descriptions see the corresponding overridden methods.
* @param {string|RegExp} [pattern]
* @param {string} [options]
* @constructor
* @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/RegExp
* @see http://www.ecma-international.org/ecma-262/6.0/#sec-regexp-regular-expression-objects
*/
function Regex(pattern, options) {
…
/**
* Based on {@link RegExp#exec} but instead of simply getting "index" in the return which only tells the starting of
* the first group (0 group) we are getting "index[0..n]" which tells us the starting index of each matching group.
* @param {string} [str]
* @return {Object} {string[0..n], index:number[0..n], input:string}
* @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/RegExp/exec
*/
Regex.prototype.exec = function (str) {
…
http://stackoverflow.com/questions/30716438/default-home-text-and-content-for-jsdoc
1.Create directory “template” in module root folder (e.g. “/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib/template”)
2.Copy directory “node_modules/jsdoc/templates/default” to “template”
3.Edit “template/default/publish.js”
Replace:
generate('Home',
packages.concat(
[{kind: 'mainpage', readme: opts.readme, longname: (opts.mainpagetitle) ? opts.mainpagetitle : 'Main Page'}]
).concat(files),
indexUrl);
With:
generate('<a href="http://www--s0-v1.becke.ch/tool/becke-ch--regex--s0-v1/becke-ch--regex--s0-0-v1--homepage--pl--client/" style="font-family: Neuropol; font-size: 50pt">becke.ch</a>',
packages.concat(
[{kind: 'mainpage', readme: opts.readme, longname: (opts.mainpagetitle) ? opts.mainpagetitle : 'Main Page'}]
).concat(files),
indexUrl);
Pro: We now have the correct header, font and hyperlink!
Cons: The whole URL is as well put in the window title :-(
4.From directory “data/becke-ch--style--s0-v1/font” copy the fonts: neuropol-webfont.eot, neuropol-webfont.ttf and neuropol-webfont.woff to directory “template/default/static/fonts”
5.Edit “template/default/static/styles/jsdoc-default.css”
Insert on top the following font definition:
@font-face {
font-family: 'Neuropol';
src: url('../fonts/neuropol-webfont.eot?') format('eot'), url('../fonts/neuropol-webfont.woff') format('woff'), url('../fonts/neuropol-webfont.ttf') format('truetype');
}
The following JSDoc:
/**
* Simply invokes the inherited method {@linkcode RegExp[Symbol.search]}.
* @param {string} str
* @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/RegExp/@@search
* @see http://www.ecma-international.org/ecma-262/6.0/#sec-regexp.prototype-@@search
*/
Regex.prototype[Symbol.search] = function (str) {
Will produce the following result:
This is a problem because [undefined] does not tell us which function we are looking at!
To fix this put an alias for the function name:
/**
* Simply invokes the inherited method {@linkcode RegExp[Symbol.search]}.
* @param {string} str
* @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/RegExp/@@search
* @see http://www.ecma-international.org/ecma-262/6.0/#sec-regexp.prototype-@@search
* @alias Regex.search
*/
Regex.prototype[Symbol.search] = function (str) {
And now the result looks as follows:
At least we know which function we are looking at. The only cons here is that there is (static) written in front of the function name which is not correct.
https://www.jetbrains.com/help/idea/2017.1/creating-documentation-comments.html
6. Place the caret before the declaration.
7. Type the opening block comment /**, and press Enter.
8. Add meaningful description of parameters and return values.
https://www.npmjs.com/package/jsdoc
package.json
…
"scripts": {
"build": "jsdoc src -d doc -R README.md"
},
"devDependencies": {
...
"jsdoc": "latest"
}
…
Installation:
npm install
Generate:
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib$ npm run build
> becke-ch--regex--s0-0-v1--base--pl--lib@1.0.20 build /media/disk-ssd--s0-v1/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib
> jsdoc src -d doc
https://gist.github.com/jxson/1784669#file-readme-md
http://usejsdoc.org/about-including-readme.html
package.json
…
"scripts": {
"build": "jsdoc src -d doc -R README.md"
},
"devDependencies": {
...
"jsdoc": "latest"
}
…
https://glebbahmutov.com/blog/unit-test-node-code-in-10-seconds/
https://semaphoreci.com/community/tutorials/getting-started-with-node-js-and-mocha
9.Edit the current package.json file and add the following development dependency:
{
"name": "becke-ch--regex--s0-0-v1--base--pl--lib",
"version": "1.0.0",
"description": "Extension of JavaScript RegExp adding missing functionality",
"keywords": ["Regular Expression", "RegExp", "Regex", "exec"],
"main": "./src/becke-ch--regex--s0-0-v1--base--pl--lib.js",
"repository": {
"url": "file:///ws/tool/becke-ch--regex--s0-v1",
"type": "git"
},
"author": "Raoul Becke <regex--s0-v1@becke.ch> (http://becke.ch/tool/becke-ch--regex--s0-v1/)",
"license": "SEE LICENSE IN LICENSE",
"publishConfig": {
"registry": "http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-1-v3-0--npm-hosted/"
},
"./src"
],
"devDependencies": {
"mocha": "^3.2.0"
}
}
10.run “yarn” (or “npm install”) to download and install the package
Alternatively you can install the module from the command line:
npm install --save-dev mocha
11.Change into the test directory: “cd test” and run “../node_modules/mocha/bin/mocha becke-ch--regex--s0-0-v1--base--pl--lib--test.js”
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib/test$ ../node_modules/mocha/bin/mocha becke-ch--regex--s0-0-v1--base--pl--lib--test.js
exec
✓ regex abcdef applied on abcdef
✓ regex abcdef applied on 00abcdef
…
52 passing (18ms)
Mocha allows you to use any assertion library you wish. Currently, we’re using Node.js’ built-in assert module:
var assert = require('assert');
var Regex = require('../src/becke-ch--regex--s0-0-v1--base--pl--lib');
describe('exec', function () {
it('regex abcdef applied on abcdef', function () {
var pattern = 'abcdef';
var str = 'abcdef';
var regex = new Regex(pattern);
var result = regex.exec(str);
var regexp = new RegExp(pattern);
var resultp = regexp.exec(str);
//console.log(result);
assert.equal(resultp.length, result.length);
assert.equal(resultp.input, result.input);
for (var i = 0; i < resultp.length; i++) {
assert.equal(resultp[i], result[i]);
}
assert.equal(1, result.index.length);
assert.equal(0, result.index[0]);
});
});
After the steps above haven been performed and once NPM and Node.js are on the PATH, IntelliJ IDEA discovers them automatically and the user can go ahead creating a “Node.js and NPM” Project/Module - see IntelliJ Documentation.
in File | Settings | Languages & Frameworks | Node.js and NPM, press ellipsis button next to 'Node interpreter' field
in Node.js Interpreters dialog that opens, open 'Node Interpreter' dropdown, choose latest node interpreter
https://docs.npmjs.com/getting-started/creating-node-modules#
https://docs.npmjs.com/files/package.json
…
name
The most important things in your package.json are the name and version fields. Those are actually required, and your package won't install without them. The name and version together form an identifier that is assumed to be completely unique.
Some rules:
The name must be less than or equal to 214 characters. This includes the scope for scoped packages.
The name can't start with a dot or an underscore.
New packages must not have uppercase letters in the name.
The name ends up being part of a URL, an argument on the command line, and a folder name. Therefore, the name can't contain any non-URL-safe characters.
A name can be optionally prefixed by a scope, e.g. @myorg/mypackage. See npm-scope for more detail.
Npm-scope, Scoped packages
All npm packages have a name. Some package names also have a scope. A scope follows the usual rules for package names (url-safe characters, no leading dots or underscores). When used in package names, preceded by an @-symbol and followed by a slash, e.g.
@somescope/somepackagename
Installing scoped packages
Scoped packages are installed to a sub-folder of the regular installation folder, e.g. if your other packages are installed in node_modules/packagename, scoped modules will be in node_modules/@myorg/packagename.
npm install:
npm install @myorg/mypackage
Or in package.json:
"dependencies": {
"@myorg/mypackage": "^1.3.0"
}
Actually I prefer to have the organization as part of the name (becke-ch--regex--s0-0-v1--base--pl--lib) and not working with scoped packages because this is more portable when moving away from npm or simply working on javascript files!
description
Put a description in it. It's a string. This helps people discover your package, as it's listed in npm search.
keywords
Put keywords in it. It's an array of strings. This helps people discover your package as it's listed in npm search.
homepage
The url to the project homepage.
bugs
The url to your project's issue tracker and / or the email address to which issues should be reported.
{ "url" : "https://github.com/owner/project/issues"
, "email" : "project@hostname.com"
}
license
You should specify a license for your package so that people know how they are permitted to use it, and any restrictions you're placing on it.
{ "license" : "(ISC OR GPL-3.0)" }
If you are using a license that hasn't been assigned an SPDX identifier, or if you are using a custom license, use a string value like this one:
{ "license" : "SEE LICENSE IN <filename>" }
Then include a file named <filename> at the top level of the package.
Finally, if you do not wish to grant others the right to use a private or unpublished package under any terms:
{ "license": "UNLICENSED"}
people fields: author, contributors
The "author" is one person. "contributors" is an array of people. A "person" is an object with a "name" field and optionally "url" and "email", like this:
{ "name" : "Barney Rubble"
, "email" : "b@rubble.com"
, "url" : "http://barnyrubble.tumblr.com/"
}
files
The "files" field is an array of files to include in your project.
You can also provide a ".npmignore" file in the root of your package or in subdirectories, which will keep files from being included, even if they would be picked up by the files array. The .npmignore file works just like a .gitignore.
Certain files are always included, regardless of settings:
package.json
README (and its variants)
CHANGELOG (and its variants)
LICENSE / LICENCE
repository
Specify the place where your code lives. This is helpful for people who want to contribute. If the git repo is on GitHub, then the npm docs command will be able to find you.
Do it like this:
"repository" :
{ "type" : "git"
, "url" : "https://github.com/npm/npm.git"
}
"repository" :
{ "type" : "svn"
, "url" : "https://v8.googlecode.com/svn/trunk/"
}
Private modules respective source code that should not (yet) be published public should point to the local code repository as follows:
"repository": {"url":"file:///ws/tool/becke-ch--regex--s0-v1","type":"git"},
Once the module is published public a next step could be to publish as well the source code public.
Imagine that you have just finished enterprise app and you will have to support it for 3-5 years. You definitely don't want to depend on someone's npm module which can tomorrow disappear and you can't update your app anymore.
Or you have your private modules which are not accessible from internet and you can't build your app on Internet. Or maybe you don't want to depend with your final build on npm service for some reasons.
You can find pros and cons in this Addy Osmani article (although it is about Bower, it is almost the same situation). And I will end with quote from Bower homepage and Addy's article:
“If you aren’t authoring a package that is intended to be consumed by others (e.g., you’re building a web app), you should always check installed packages into source control.”
…
I would recommend against checking in node_modules because of packages like PhantomJS and node-sass for example, which install the appropriate binary for the current system.
This means that if one Dev runs npm install on Linux and checks in node_modules – it won't work for another Dev who clones the repo on Windows.
...
dependencies
Dependencies are specified in a simple object that maps a package name to a version range.
{ "dependencies" :
{ "foo" : "1.0.0 - 2.9999.9999"
, "bar" : ">=1.0.2 <2.1.2"
, "baz" : ">1.0.2 <=2.3.4"
, "boo" : "2.0.1"
, "qux" : "<1.0.0 || >=2.3.1 <2.4.5 || >=2.5.2 <3.0.0"
, "asd" : "http://asdf.com/asdf.tar.gz"
, "til" : "~1.2"
, "elf" : "~1.2.3"
, "two" : "2.x"
, "thr" : "3.3.x"
, "lat" : "latest"
, "dyl" : "file:../dyl"
}
}
URLs as Dependencies
You may specify a tarball URL in place of a version range.
devDependencies
If someone is planning on downloading and using your module in their program, then they probably don't want or need to download and build the external test or documentation framework that you use.
peerDependencies
In some cases, you want to express the compatibility of your package with a host tool or library, while not necessarily doing a require of this host.
bundledDependencies
Array of package names that will be bundled when publishing the package.
optionalDependencies
If a dependency can be used, but you would like npm to proceed if it cannot be found or fails to install, then you may put it in the optionalDependencies object.
engines
You can specify the version of node that your stuff works on:
{ "engines" : { "node" : ">=0.10.3 <0.12" } }
os
You can specify which operating systems your module will run on:
"os" : [ "darwin", "linux" ]
cpu
If your code only runs on certain cpu architectures, you can specify which ones.
"cpu" : [ "x64", "ia32" ]
preferGlobal
If your package is primarily a command-line application that should be installed globally, then set this value to true to provide a warning if it is installed locally.
private
If you set "private": true in your package.json, then npm will refuse to publish it.
publishConfig
This is a set of config values that will be used at publish-time. It's especially handy if you want to set the tag, registry or access, so that you can ensure that a given package is not tagged with "latest", published to the global public registry or that a scoped module is private by default.
Any config values can be overridden, but of course only "tag", "registry" and "access" probably matter for the purposes of publishing.
registry
Default: https://registry.npmjs.org/
Type: url
The base URL of the npm package registry.
Private modules respective modules that should not (yet) be published public I would point to the local repository as follows:
"registry" : "http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-1-v3-0--npm-hosted/"
}
OPTIONAL
main
The main field is a module ID that is the primary entry point to your program.
bin
A lot of packages have one or more executable files that they'd like to install into the PATH.
man
Specify either a single file or an array of filenames to put in place for the man program to find.
directories
The CommonJS Packages spec details a few ways that you can indicate the structure of your package using a directories object.
scripts
The "scripts" property is a dictionary containing script commands that are run at various times in the lifecycle of your package.
config
A "config" object can be used to set configuration parameters used in package scripts that persist across upgrades.
...
https://docs.npmjs.com/getting-started/creating-node-modules
npm init
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib$ npm init
This utility will walk you through creating a package.json file.
It only covers the most common items, and tries to guess sensible defaults.
See `npm help json` for definitive documentation on these fields
and exactly what they do.
Use `npm install <pkg> --save` afterwards to install a package and
save it as a dependency in the package.json file.
Press ^C at any time to quit.
name: (becke-ch--regex--s0-0-v1--base--pl--lib)
version: (1.0.0)
description: Extension of JavaScript RegExp adding missing functionality
entry point: (index.js)
test command:
git repository:
keywords: Regular Expression, RegExp, Regex, exec
author: Raoul Becke <regex--s0-v1@becke.ch> (http://becke.ch/tool/becke-ch--regex--s0-v1/)
license: (ISC) SEE LICENSE IN LICENSE
About to write to /media/disk-ssd--s0-v1/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v2--base--pl--lib/package.json:
{
"name": "becke-ch--regex--s0-0-v1--base--pl--lib",
"version": "1.0.0",
"description": "Extension of JavaScript RegExp adding missing functionality",
"main": "index.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"keywords": [
"Regular",
"Expression",
"RegExp",
"Regex",
"exec"
],
"author": "Raoul Becke <regex--s0-v1@becke.ch> (http://becke.ch/tool/becke-ch--regex--s0-v1/)",
"license": "SEE LICENSE IN LICENSE"
}
Is this ok? (yes) yes
Adapt & extend the missing properties:
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib$ vi package.json
{
"name": "becke-ch--regex--s0-0-v1--base--pl--lib",
"version": "1.0.0",
"description": "Extension of JavaScript RegExp adding missing functionality",
"main": "index.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"keywords": [
"Regular",
"Expression",
"RegExp",
"Regex",
"exec"
],
"repository": "file:///ws/tool/becke-ch--regex--s0-v1",
"repository": {"url":"file:///ws/tool/becke-ch--regex--s0-v1","type":"git"},
"author": "Raoul Becke <regex--s0-v1@becke.ch> (http://becke.ch/tool/becke-ch--regex--s0-v1/)",
"license": "SEE LICENSE IN becke-ch—regex--s0-v1--license.txt"
"registry" : "http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-1-v3-0--npm-hosted/"
}
}
Creating a new npm module from scratch is not well supported respective see https://intellij-support.jetbrains.com/hc/requests/907710 : “When going to "New Module", selecting "Node.js and NPM" I only have the choice "Node.js Express App" and when I choose that I get a lot of node-modules downloaded and "dependencies" that I don't need”
Therefore there are 2 possibilities:
•New | Module | Static Web | Static Web
◦And within the module perform “yarn init” (see above)
•Or another approach is the one described here:
1.File → New Module → From Existing Sources …
2.Select the directory where you invoked previously “yarn init” e.g. /ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib
3.Select “Create module from existing sources”
4.Source files for project have been found. Leave default which is all directories selected.
This is an alternative installation procedure which actually brings no additional benefit. There exists currently no option to create an empty/minimal npm module:
1.Select “Static Web”
2.Select “Static Web”
3.Enter module name: becke-ch--<element>--sX-Y-vZ--<UseCase>--pl--client|clientlib|server|serverlib|lib (e.g. becke-ch--regex--s0-0-v1--base--pl--lib)
4.And finally go into this new empty directory and create a new npm-/yarn-module as described above
https://docs.npmjs.com/getting-started/publishing-npm-packages
This step is only required when publishing to central NPM repository:
Create an NPM Account: https://www.npmjs.com/signup
•Name: becke.ch
•Public Email: npm--s0-v1@becke.ch
•Username: becke.ch
•Password: y...
Create an NPM Account: https://www.npmjs.com/signup
•Name: becke-ch--npm--s0-v1
•Public Email: npm--s0-v1@becke.ch
•Username: becke-ch--npm--s0-v1
•Password: y...
Alternatively you can create a user with:
npm adduser
•Usename: becke.ch
•Password: y...
•Email (this IS public): npm--s0-v1@becke.ch
Alternatively you can create a user with:
npm adduser
•Usename: becke-ch--npm--s0-v1
•Password: y...
•Email (this IS public): npm--s0-v1@becke.ch
Adding user to default repository:
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib$ npm adduser
Username: becke-ch--npm--s0-v1
Password:
Email: (this IS public) npm--s0-v1@becke.ch
Logged in as becke-ch--npm--s0-v1 on http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-2-v3-0--npm-group.
Adding user to private repository: http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-1-v3-0--npm-hosted
npm adduser --registry=http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-1-v3-0--npm-hosted
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib$ npm adduser --registry=http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-1-v3-0--npm-hosted
Username: becke-ch--npm--s0-v1
Password:
Email: (this IS public) npm--s0-v1@becke.ch
Logged in as becke-ch--npm--s0-v1 on http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-1-v3-0--npm-hosted.
This step is only required when publishing to central NPM repository:
If you created a user on the web-site, use npm login to store the credentials on the client:
npm login
Make sure you created a user – see chapter: 5.2.8.1.
https://books.sonatype.com/nexus-book/reference/npm-deploying-packages.html
Since the .npmrc file usually contains a registry value intended only for getting new packages, a simple way to override this value is to provide a registry to the publish command:
npm publish --registry http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-1-v3-0--npm-hosted/
Alternately, you can edit your package.json file and add a publishConfig section:
vi package.json
…
"publishConfig": {
"registry": "http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-1-v3-0--npm-hosted/"
},
...
Publishing requires authentication. It can be configured by adding an _auth value to .npmrc. The value has to be generated by base64-encoding the string of username:password. You can create this encoded string with the command line call openssl e.g.: for the default admin user:
echo -n 'admin:admin123' | openssl base64
echo -n 'becke-ch--npm--s0-v1:y...' | openssl base64
After this the base64 encoded credentials can be found in between the begin and end certificate lines in the output file:
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:~$ echo -n 'admin:admin123' | openssl base64
YWRtaW46YWRtaW4xMjM=
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/download/becke-ch--repo-nexus--s1-0-v3/log$ echo -n 'becke-ch--npm--s0-v1:y...' | openssl base64
YmVja2UtY2gtLW5wbS0tczAtdjE6eXMxNTExNjI=
Once you have the encoded credentials the value as well as author information can then be added to the .npmrc file:
vi .npmrc
#registry=http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-2-v3-0--npm-group
init.author.email = npm--s0-v1@becke.ch
init.author.url = http://becke.ch
# an email is required to publish npm packages
email=npm--s0-v1@becke.ch
_auth=YmVja2UtY2gtLW5wbS0tczAtdjE6eXMxNTExNjI=
Use npm publish to publish the package.
Note that everything in the directory will be included unless it is ignored by a local .gitignore or .npmignore file as described in npm-developers.
Also make sure there isn't already a package with the same name, owned by somebody else.
npm publish
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib$ npm publish
+ becke-ch--regex--s0-0-v1--base--pl--lib@1.0.15
Once a package is published to the private registry in the repository manager, any other developers or build servers, that access it via the repository group have instant access to the packages.
ERROR: npm ERR! need auth You need to authorize this machine using `npm adduser`
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib$ npm publish
npm ERR! Linux 4.9.0-040900-generic
npm ERR! argv "/media/disk-ssd--s0-v1/tool/node-v6.10.1-linux-x64/bin/node" "/tool/node-v6.10.1-linux-x64/bin/npm" "publish"
npm ERR! node v6.10.1
npm ERR! npm v3.10.10
npm ERR! code ENEEDAUTH
npm ERR! need auth auth required for publishing
npm ERR! need auth You need to authorize this machine using `npm adduser`
npm ERR! Please include the following file with any support request:
npm ERR! /media/disk-ssd--s0-v1/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib/npm-debug.log
SOLUTION: https://books.sonatype.com/nexus-book/reference/npm-deploying-packages.html
See chapter: 3.9.3.3 and 3.9.3.4
ERROR: npm ERR! publish Failed PUT 400
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib$ npm publish
npm ERR! publish Failed PUT 400
npm ERR! Linux 4.9.0-040900-generic
npm ERR! argv "/media/disk-ssd--s0-v1/tool/node-v6.10.1-linux-x64/bin/node" "/tool/node-v6.10.1-linux-x64/bin/npm" "publish"
npm ERR! node v6.10.1
npm ERR! npm v3.10.10
npm ERR! code E400
npm ERR! Repository does not allow updating assets: becke-ch--repo-nexus--s1-0-1-v3-0--npm-hosted : repository
npm ERR!
npm ERR! If you need help, you may report this error at:
npm ERR! <https://github.com/npm/npm/issues>
npm ERR! Please include the following file with any support request:
npm ERR! /media/disk-ssd—s0-v1/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib/npm-debug.log
When consulting the nexus trace log:
2017-04-12 15:53:56,688+0200 WARN [qtp2010031162-54] becke-ch--npm--s0-v1 com.sonatype.nexus.repository.npm.internal.NpmHandlers - Error: PUT /becke-ch--regex--s0-0-v1--base--pl--lib: Status{successful=false, code=400, message='null'} - Repository does not allow updating assets: becke-ch--repo-nexus--s1-0-1-v3-0--npm-hosted
org.sonatype.nexus.repository.IllegalOperationException: Repository does not allow updating assets: becke-ch--repo-nexus--s1-0-1-v3-0--npm-hosted
at org.sonatype.nexus.repository.storage.StorageTxImpl.attachBlob(StorageTxImpl.java:622) [org.sonatype.nexus.repository:3.2.1.01]
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) [na:1.8.0_92]
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) [na:1.8.0_92]
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) [na:1.8.0_92]
at java.lang.reflect.Method.invoke(Method.java:498) [na:1.8.0_92]
at org.sonatype.nexus.common.stateguard.SimpleMethodInvocation.proceed(SimpleMethodInvocation.java:53) [org.sonatype.nexus.common:3.2.1.01]
...
SOLUTION: The version number needs to be incremented:
package.json:
"version": "1.0.21",
In the NPM repository a package can only be deprecated: https://docs.npmjs.com/cli/deprecate
To delete a package in the nexus repository:
1.Go to “Browse → Components” and select the repository where the component should be deleted (e.g. “http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-2-v3-0--npm-hosted”):
2.Select the component in the version that should get deleted (e.g. name: “becke-ch—regex--s0-0-v1--base--pl--lib” & version: “1.0.15”):
3.And click “Delete Component”:
4.And confirm with “Yes”
5.If not already logged in, log in as admin user (actually you will get an error that you do not have the required privileges and therefore after logging in as administrator click again on “Delete component”):
http://blog.cliffano.com/2012/06/13/publishing-node-js-module-to-ivy-repository/
Update (23/08/2012): The instruction below is for Bob v0.5.x or newer.
Create an ivy.xml file template in your Node.js module project’s root directory If you’re upgrading from Bob v0.4.x, all you need to do is remove the $ from the parameter syntax.
[code lang=“xml”] <?xml version=“1.0” encoding=“ISO-8859-1”?> [/code]
Create a .bob.json file in your project directory, specifying ivy.xml location and details of the Ivy repository server If you’re upgrading from Bob v0.4.x, you need to move ivy.xml to the project’s root directory, and modify .bob.json by removing packagemeta, change template structure, renaming deploy to publish, adding publish.type: ivy .
[code lang=“javascript”] { “template”: [“.bob/artifact/ivy.xml”], “publish”: { “type”: “ivy”, “user”: “username”, “key”: “path/to/keyfile”, “host”: “hostname”, “port”: portnumber, “dir”: “/path/to/ivy/repo/${name}/${version}” } } [/code]
Run Bob If you’re upgrading from Bob v0.4.x, simply replace template package package-meta ssh-mkdir deploy targets, with package publish
bob package publish
This will create /path/to/ivy/repo/modulename/version/ directory with the following files:
modulename.tar.gz
modulename.tar.gz.md5
modulename.tar.gz.sha1
ivy.xml
ivy.xml.md5
ivy.xml.sha1
This module can then be referenced as com.company.modulename, and used just like any other artifact using Ivy.
If the repository is accessible via HTTP, then you can also specify the Ivy artifact as a dependency of another Node.js module in its package.json file:
[code lang=“javascript”] { “dependencies”: { “modulename”: “http://ivyserver/com/company/modulename/version/modulename-version.tar.gz", } } [/code]
Despite my dislike towards XML configuration files, Ivy has worked just fine all these years and I’ve been using it to store various types of artifacts. Even though its main popularity is within the Java community, you can store pretty much anything there (YMMV).
https://github.com/cliffano/bob
…
Ultra Fast. Yarn caches every package it downloads so it never needs to download it again. It also parallelizes operations to maximize resource utilization so install times are faster than ever.
Mega Secure. Yarn uses checksums to verify the integrity of every installed package before its code is executed.
Super Reliable. Using a detailed, but concise, lockfile format, and a deterministic algorithm for installs, Yarn is able to guarantee that an install that worked on one system will work exactly the same way on any other system.
...
https://www.slant.co/topics/1488/versus/~npm-browserify_vs_yarn_vs_bower
...
https://yarnpkg.com/en/docs/getting-started
https://yarnpkg.com/en/docs/install#linux-tab
Debian / Ubuntu:
1.Configure the repository (because yarn is not in the default repository list):
curl -sS https://dl.yarnpkg.com/debian/pubkey.gpg | sudo apt-key add -
echo "deb https://dl.yarnpkg.com/debian/ stable main" | sudo tee /etc/apt/sources.list.d/yarn.list
admin--s0-v1@hp-elitebook-840-g1--s0-v3:~$ curl -sS https://dl.yarnpkg.com/debian/pubkey.gpg | sudo apt-key add -
[sudo] password for admin--s0-v1:
OK
admin--s0-v1@hp-elitebook-840-g1--s0-v3:~$ echo "deb https://dl.yarnpkg.com/debian/ stable main" | sudo tee /etc/apt/sources.list.d/yarn.list
deb https://dl.yarnpkg.com/debian/ stable main
2.Install
sudo apt-get update && sudo apt-get install yarn
admin--s0-v1@hp-elitebook-840-g1--s0-v3:~$ sudo apt-get update && sudo apt-get install yarn
…
The following additional packages will be installed:
libuv1 nodejs
The following NEW packages will be installed:
libuv1 nodejs yarn
0 upgraded, 3 newly installed, 0 to remove and 15 not upgraded.
Need to get 4'958 kB of archives.
After this operation, 39.4 MB of additional disk space will be used.
Do you want to continue? [Y/n] Y
…
Setting up libuv1:amd64 (1.8.0-1) ...
Setting up yarn (0.20.3-1) ...
Setting up nodejs (4.2.6~dfsg-1ubuntu4.1) ...
update-alternatives: using /usr/bin/nodejs to provide /usr/bin/js (js) in auto mode
Processing triggers for libc-bin (2.23-0ubuntu5) ...
3.Test that Yarn is installed by running:
yarn --version
admin--s0-v1@hp-elitebook-840-g1--s0-v3:~$ yarn --version
0.20.3
Once the local/custom registry is set up – see chapter 5.2 - point yarn to local/custom registry (https://github.com/yarnpkg/yarn/issues/606):
yarn config set registry http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-2-v3-0--npm-group//
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:~$ yarn config set registry http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-2-v3-0--npm-group//
yarn config v0.20.3
success Set "registry" to "http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-2-v3-0--npm-group//".
Done in 0.05s.
IMPORTANT – the URL needs to end with double slash “…//”!
Double check your local “.yarnrc” file to make sure everything worked fine:
vi .yarnrc
...
registry "http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-2-v3-0--npm-group//"
...
in File | Settings | Languages & Frameworks | Node.js and NPM, press ellipsis button next to 'Node interpreter' field
in Node.js Interpreters dialog that opens, open 'NPM package:' dropdown, choose your Yarn package there (see screenshot); if it's not there, use browse button to choose Yarn package folder
https://yarnpkg.com/en/docs/yarn-workflow
Regarding package.json format see chapter: 3.9.1
https://yarnpkg.com/en/docs/creating-a-project
yarn init
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib$ yarn init
yarn init v0.20.3
question name (becke-ch--regex--s0-0-v1--base--pl--lib): [enter]
question version (1.0.0): [enter]
question description: Extension of JavaScript RegExp adding missing functionality
question entry point (index.js): [enter]
question repository url: file:///ws/tool/becke-ch--regex--s0-v1
question author: Raoul Becke <regex--s0-v1@becke.ch>
question license (MIT): SEE LICENSE IN becke-ch--regex--s0-v1--license.txt
success Saved package.json
Done in 236.27s.
Adapt & extend the missing properties: See chapter: 3.9.2
See chapter 3.9.2.1 respective 3.9.2.2.
After many attempts I gave up publishing a package to my private repository with “yarn publish” and instead now using “npm publish” to publish my package! See chapter: 3.9.3
See long discussions on: https://github.com/yarnpkg/yarn/issues/521
https://yarnpkg.com/en/docs/publishing-a-package
This step is only required when publishing to central NPM repository:
Create an NPM Account: https://www.npmjs.com/signup
•Name: becke.ch
•Public Email: npm--s0-v1@becke.ch
•Username: becke.ch
•Password: y...
This step is only required when publishing to central NPM repository:
yarn login
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib$ yarn login
yarn login v0.22.0
question npm username: becke-ch--npm--s0-v1
question npm email: npm--s0-v1@becke.ch
Done in 36.23s.
yarn publish
First you will be asked to enter a new version to publish:
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib$ yarn publish
yarn publish v0.20.3
[1/4] Bumping version...
info Current version: 1.0.0
question New version: 1.0.1
Next you will be asked to enter your npm username, email and password:
question npm username: becke.ch
question npm email: npm--s0-v1@becke.ch
question npm password:
ERROR Incorrect username or password.
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--base--pl--lib$ yarn publish
yarn publish v0.20.3
[1/4] Bumping version...
info Current version: 1.0.0
question New version: 1.0.1
info New version: 1.0.1
[2/4] Logging in...
question npm username: becke.ch
question npm email: npm--s0-v1@becke.ch
question npm password:
error Incorrect username or password.
info Visit https://yarnpkg.com/en/docs/cli/publish for documentation about this command.
The nexus repository request log, error message looks as follows:
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/download/becke-ch--repo-nexus--s1-0-v3/log$ tail -f request.log
127.0.0.1 - - [06/Apr/2017:18:46:54 +0200] "PUT /repository/becke-ch--repo-nexus--s1-0-2-v3-0--npm-group//-/user/org.couchdb.user:becke.ch HTTP/1.1" 401 0 1 "yarn/0.20.3 npm/? node/v6.10.1 linux x64"
After adding user “becke.ch” to the nexus repository (see 5.2.8) the error message looks as follows:
127.0.0.1 - - [06/Apr/2017:20:53:43 +0200] "POST /service/extdirect/poll/rapture_State_get HTTP/1.1" 200 77 3 "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:52.0) Gecko/20100101 Firefox/52.0"
127.0.0.1 - becke.ch [06/Apr/2017:20:53:57 +0200] "PUT /repository/becke-ch--repo-nexus--s1-0-2-v3-0--npm-group//-/user/org.couchdb.user:becke.ch HTTP/1.1" 201 129 15 "yarn/0.20.3 npm/? node/v6.10.1 linux x64"
127.0.0.1 - - [06/Apr/2017:20:53:57 +0200] "PUT /repository/becke-ch--repo-nexus--s1-0-2-v3-0--npm-group//becke-ch--regex--s0-0-v1--base--pl--lib HTTP/1.1" 401 0 1 "yarn/0.20.3 npm/? node/v6.10.1 linux x64"
https://yarnpkg.com/en/docs/cli/upgrade
Upgrades packages to their latest version based on the specified range.
Important: Nexus needs to be running because we are using Nexus as our private & proxy repository!
yarn upgrade
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--homepage--pl--client$ yarn upgrade
yarn upgrade v0.22.0
[1/4] Resolving packages...
warning protractor > jasmine > glob > minimatch@0.3.0: Please update to minimatch 3.0.2 or higher to avoid a RegExp DoS issue
warning lite-server > browser-sync > localtunnel > request > node-uuid@1.4.8: Use uuid module instead
[2/4] Fetching packages...
warning fsevents@1.1.1: The platform "linux" is incompatible with this module.
info "fsevents@1.1.1" is an optional dependency and failed compatibility check. Excluding it from installation.
[3/4] Linking dependencies...
[4/4] Rebuilding all packages...
success Saved lockfile.
success Saved 380 new dependencies.
├─ @angular/common@4.0.2
…
└─ zone.js@0.8.5
Done in 12.14s.
ERROR: Couldn't find package "..." on the "npm" registry.
SOLUTION: Check and fix the .npmrc configuration
vi /home/raoul-becke--s0-v1/.npmrc
init.author.name=becke.ch
init.author.email=npm--s0-v1@becke.ch
init.author.url=http://becke.ch
email=npm--s0-v1@becke.ch
//registry.npmjs.org/:_authToken=163827b9-2ea0-49ec-9ade-fdca02068065
registry=http://localhost:8081/repository/becke-ch--repo-nexus--s1-0-2-v3-0--npm-group
always-auth=true
_auth=YmVja2UtY2gtLW5wbS0tczAtdjE6eXMxNTExNjI=
There exists different private npm registry/repository implementations but none of them is fully supported anymore which is a problem considering the NPM API changes. I started with the “official” “npm-registry-couchapp” but besides that the installation is a little bit complex the first thing that is mentioned is that it is deprecated:
http://www.clock.co.uk/blog/how-to-create-a-private-npmjs-repository
https://github.com/npm/npm-registry-couchapp/blob/master/README.md
https://docs.npmjs.com/misc/registry
…
deprecation notice: as npm has scaled, the registry architecture has gradually migrated towards a complex distributed architecture, of which npm-registry-couchapp is only a small part. FOSS is an important part of npm, and over time we plan on exposing more APIs, and better documenting the existing API.
...
Then I almost started using “sinopia”:
https://www.npmjs.com/package/sinopia
https://entwickler.de/online/javascript/sinopia-184560.html
which has some good resonance in the NPM community BUT again it is deprecated and the fork “verdaccio” had a lot of discussions but not so much progress:
https://github.com/rlidwka/sinopia/issues/376
And therefore finally I switched over to “Nexus 3” which:
•Resonance: Has some good feedback in the NPM community
•Free: The “Nexus Repository OSS” repository manager is for free and if required additional professional support can be bought “Nexus Repository Pro” which I think is a good deal.
See as well: http://larrymyers.com/tech/2016/06/05/private-npm-with-nexus.html
…
In past years I would have recommended using Sinopia, or something like Nodejitsu. In two years the landscape has changed quite a bit and there are better alternatives now.
While you can pay npm, Inc (i.e. npm the company) $7/month to host your private packages, my recommendation would be to host Nexus 3 yourself. It provides all the functionality of NPM, while giving you more control and flexibility over how you would like to host your private npm modules.
...
Required packages:
•build-essential
•autoconf
•automake
•libtool
•erlang
•libicu-dev
•libmozjs-dev libmozjs185-dev
•libcurl4-openssl-dev
apt list --installed | grep -E 'build-essential|autoconf|automake|libtool|erlang|libicu-dev|libmozjs185-dev|libcurl4-openssl-dev'
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/data/db/apache-couchdb-1.6.1$ apt list --installed | grep -E 'build-essential|autoconf|automake|libtool|erlang|libicu-dev|libmozjs-dev|libcurl4-openssl-dev'
WARNING: apt does not have a stable CLI interface. Use with caution in scripts.
build-essential/xenial,now 12.1ubuntu2 amd64 [installed,automatic]
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/data/db/apache-couchdb-1.6.1$ apt search .*libmoz.*
Sorting... Done
Full Text Search... Done
libmozilla-ldap-perl/xenial 1.5.3-2build2 amd64
LDAP Perl module for the OpenLDAP C SDK
…
libmozjs185-dev/xenial 1.8.5-1.0.0+dfsg-4.5 amd64
Spidermonkey javascript library - development headers
sudo apt-get install build-essential autoconf automake libtool erlang libicu-dev libmozjs185-dev libcurl4-openssl-dev
admin--s0-v1@hp-elitebook-840-g1--s0-v3:~$ sudo apt-get install build-essential autoconf automake libtool erlang libicu-dev libcurl4-openssl-dev
Reading package lists... Done
Building dependency tree
Reading state information... Done
build-essential is already the newest version (12.1ubuntu2).
build-essential set to manually installed.
The following packages were automatically installed and are no longer required:
linux-headers-4.4.0-53 linux-headers-4.4.0-53-generic linux-headers-4.4.0-57 linux-headers-4.4.0-57-generic linux-headers-4.4.0-59 linux-headers-4.4.0-59-generic linux-image-4.4.0-53-generic
linux-image-4.4.0-57-generic linux-image-4.4.0-59-generic linux-image-extra-4.4.0-53-generic linux-image-extra-4.4.0-57-generic linux-image-extra-4.4.0-59-generic linux-signed-image-4.4.0-53-generic
linux-signed-image-4.4.0-57-generic linux-signed-image-4.4.0-59-generic
Use 'sudo apt autoremove' to remove them.
The following additional packages will be installed:
autotools-dev ca-certificates-java default-jre-headless erlang-asn1 erlang-base erlang-common-test erlang-corba erlang-crypto erlang-debugger erlang-dev erlang-dialyzer erlang-diameter erlang-edoc
erlang-eldap erlang-erl-docgen erlang-et erlang-eunit erlang-examples erlang-gs erlang-ic erlang-ic-java erlang-inets erlang-jinterface erlang-megaco erlang-mnesia erlang-mode erlang-observer erlang-odbc
erlang-os-mon erlang-parsetools erlang-percept erlang-public-key erlang-reltool erlang-runtime-tools erlang-snmp erlang-src erlang-ssh erlang-ssl erlang-syntax-tools erlang-test-server erlang-tools
erlang-typer erlang-webtool erlang-wx erlang-xmerl icu-devtools java-common libjs-jquery-metadata libjs-jquery-tablesorter libltdl-dev libodbc1 libsctp1 libwxbase3.0-0v5 libwxgtk3.0-0v5 m4
openjdk-8-jre-headless
Suggested packages:
autoconf-archive gnu-standards autoconf-doc default-jre erlang-manpages erlang-doc xsltproc fop libcurl4-doc libcurl3-dbg libidn11-dev libkrb5-dev libldap2-dev librtmp-dev libssl-dev zlib1g-dev icu-doc
libtool-doc libmyodbc odbc-postgresql tdsodbc unixodbc-bin lksctp-tools gfortran | fortran95-compiler gcj-jdk openjdk-8-jre-jamvm fonts-ipafont-gothic fonts-ipafont-mincho ttf-wqy-microhei | ttf-wqy-zenhei
fonts-indic
The following NEW packages will be installed:
autoconf automake autotools-dev ca-certificates-java default-jre-headless erlang erlang-asn1 erlang-base erlang-common-test erlang-corba erlang-crypto erlang-debugger erlang-dev erlang-dialyzer
erlang-diameter erlang-edoc erlang-eldap erlang-erl-docgen erlang-et erlang-eunit erlang-examples erlang-gs erlang-ic erlang-ic-java erlang-inets erlang-jinterface erlang-megaco erlang-mnesia erlang-mode
erlang-observer erlang-odbc erlang-os-mon erlang-parsetools erlang-percept erlang-public-key erlang-reltool erlang-runtime-tools erlang-snmp erlang-src erlang-ssh erlang-ssl erlang-syntax-tools
erlang-test-server erlang-tools erlang-typer erlang-webtool erlang-wx erlang-xmerl icu-devtools java-common libcurl4-openssl-dev libicu-dev libjs-jquery-metadata libjs-jquery-tablesorter libltdl-dev libodbc1
libsctp1 libtool libwxbase3.0-0v5 libwxgtk3.0-0v5 m4 openjdk-8-jre-headless
0 upgraded, 62 newly installed, 0 to remove and 2 not upgraded.
Need to get 81.3 MB of archives.
After this operation, 286 MB of additional disk space will be used.
Get source:
cd /data/db
wget http://mirror.switch.ch/mirror/apache/dist/couchdb/source/2.0.0/apache-couchdb-2.0.0.tar.gz
Extract:
tar xvzf apache-couchdb-2.0.0.tar.gz
Compile:
cd apache-couchdb-2.0.0
./configure
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/data/db/apache-couchdb-2.0.0$ ./configure
==> configuring couchdb in rel/couchdb.config
You have configured Apache CouchDB, time to relax. Relax.
make release
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/data/db/apache-couchdb-2.0.0$ make release
==> couch_epi (compile)
…
==> rel (generate)
ERROR: Unable to generate spec: read file info /usr/lib/erlang/man/man1/x86_64-linux-gnu-gcov-tool.1.gz failed
ERROR: Unexpected error: rebar_abort
ERROR: generate failed while processing /media/disk-ssd--s0-v1/data/db/apache-couchdb-2.0.0/rel: rebar_abort
Makefile:234: recipe for target 'release' failed
make: *** [release] Error 1
…
https://github.com/emqtt/emqttd/issues/530
https://bugs.launchpad.net/ubuntu/+source/erlang/+bug/1600780
…
Temporary solution:
$ sudo touch /usr/lib/erlang/man/man1/gcov-tool-5.1.gz
…
WARN: 'generate' command does not apply to directory /media/disk-ssd--s0-v1/data/db/apache-couchdb-2.0.0
... done
You can now copy the rel/couchdb directory anywhere on your system.
Start CouchDB with ./bin/couchdb from within that directory.
Add couch db system user for NPM repository:
adduser --system \
--shell /bin/bash \
--group --gecos \
"CouchDB v2.0 Administrator for NPM repository" apache-couchdb—npm--s0-v2
root@hp-elitebook-840-g1--s0-v3:~# adduser --system \
> --shell /bin/bash \
> --group --gecos \
> "CouchDB v2.0 Administrator for NPM repository" apache-couchdb--npm--s0-v2
Adding system user `apache-couchdb--npm--s0-v2' (UID 128) ...
Adding new group `apache-couchdb--npm--s0-v2' (GID 134) ...
Adding new user `apache-couchdb--npm--s0-v2' (UID 128) with group `apache-couchdb--npm--s0-v2' ...
Creating home directory `/home/apache-couchdb--npm--s0-v2' ...
Copy, change owner, change permission and update permissions for ini files:
cp -r /data/db/apache-couchdb-2.0.0/rel/couchdb /home/apache-couchdb—npm--s0-v2
chown -R apache-couchdb--npm--s0-v2:apache-couchdb--npm--s0-v2 /home/apache-couchdb—npm—s0-v2/couchdb
find /home/apache-couchdb--npm--s0-v2/couchdb -type d -exec chmod 0770 {} \;
chmod 0644 /home/apache-couchdb--npm--s0-v2/couchdb/etc/*
Todo
Add couch db system user for NPM repository:
adduser --system \
--shell /bin/bash \
--group --gecos \
"CouchDB v2.0 Administrator for NPM repository" apache-couchdb—npm--s0-v2
root@hp-elitebook-840-g1--s0-v3:~# adduser --system \
> --shell /bin/bash \
> --group --gecos \
> "CouchDB v2.0 Administrator for NPM repository" apache-couchdb--npm--s0-v2
Adding system user `apache-couchdb--npm--s0-v2' (UID 128) ...
Adding new group `apache-couchdb--npm--s0-v2' (GID 134) ...
Adding new user `apache-couchdb--npm--s0-v2' (UID 128) with group `apache-couchdb--npm--s0-v2' ...
Creating home directory `/home/apache-couchdb--npm--s0-v2' ...
Copy, change owner, change permission and update permissions for ini files:
cp -r /data/db/apache-couchdb-2.0.0/rel/couchdb /home/apache-couchdb—npm--s0-v2
chown -R apache-couchdb--npm--s0-v2:apache-couchdb--npm--s0-v2 /home/apache-couchdb—npm—s0-v2/couchdb
find /home/apache-couchdb--npm--s0-v2/couchdb -type d -exec chmod 0770 {} \;
chmod 0644 /home/apache-couchdb--npm--s0-v2/couchdb/etc/*
Start:
sudo -i -u apache-couchdb--npm--s0-v2 couchdb/bin/couchdb
apache-couchdb--npm--s0-v2@hp-elitebook-840-g1--s0-v3:~/couchdb$ ./bin/couchdb
[info] 2017-02-12T19:46:57.535421Z couchdb@localhost <0.7.0> -------- Application couch_log started on node couchdb@localhost
…
[error] 2017-02-12T19:47:02.783205Z couchdb@localhost emulator -------- Error in process <0.456.0> on node couchdb@localhost with exit value:
{database_does_not_exist,[{mem3_shards,load_shards_from_db,"_users",[{file,"src/mem3_shards.erl"},{line,327}]},{mem3_shards,load_shards_from_disk,1,[{file,"src/mem3_shards.erl"},{line,315}]},{mem3_shards,load_shards_from_disk,2,[{file,"src/mem3_shards.erl"},{line,331}]},{mem3_shards,for_docid,3,[{file,"src/mem3_shards.erl"},{line,87}]},{fabric_doc_open,go,3,[{file,"src/fabric_doc_open.erl"},{line,38}]},{chttpd_auth_cache,ensure_auth_ddoc_exists,2,[{file,"src/chttpd_auth_cache.erl"},{line,187}]},{chttpd_auth_cache,listen_for_changes,1,[{file,"src/chttpd_auth_cache.erl"},{line,134}]}]}
…
Single Node Setup: Will fix the error: “couchdb@localhost emulator -------- Error in process <0.456.0> on node couchdb@localhost with exit value: {database_does_not_exist” ...”
http://stackoverflow.com/questions/41553458/couchdb-2-0-installation-error
curl -X PUT http://127.0.0.1:5984/_users
curl -X PUT http://127.0.0.1:5984/_replicator
curl -X PUT http://127.0.0.1:5984/_global_changes
…
root@hp-elitebook-840-g1--s0-v3:~# curl -X PUT http://127.0.0.1:5984/_users
{"ok":true}
root@hp-elitebook-840-g1--s0-v3:~# curl -X PUT http://127.0.0.1:5984/_replicator
{"ok":true}
root@hp-elitebook-840-g1--s0-v3:~# curl -X PUT http://127.0.0.1:5984/_global_changes
{"ok":true}
secure_rewrites: This option allow to isolate databases via subdomains:
[httpd]
secure_rewrites = true
root@hp-elitebook-840-g1--s0-v3:/home/apache-couchdb--npm--s0-v2/couchdb/etc# vi local.ini
…
[httpd]
...
secure_rewrites = true
...
Ready, set, link, defaults.
sudo ln -s /usr/local/etc/init.d/couchdb /etc/init.d
sudo update-rc.d couchdb defaults
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:~$ cd /app
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/app$ git clone git://github.com/npm/npm-registry-couchapp
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/app/npm-registry-couchapp$ npm install
…
loadDep:underscore → 200 ▀ ╢████████████████████████████████████████░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░╟
npm WARN deprecated node-uuid@1.4.7: use uuid module instead
npm WARN prefer global coffee-script@1.12.3 should be installed with -g
npm-registry-couchapp@2.6.12 /media/disk-ssd--s0-v1/app/npm-registry-couchapp
├─┬ couchapp@0.11.0
│ ├── coffee-script@1.12.3
│ ├─┬ connect@3.5.1
│ │ ├─┬ debug@2.2.0
│ │ │ └── ms@0.7.1
│ │ ├─┬ finalhandler@0.5.1
│ │ │ ├── escape-html@1.0.3
│ │ │ ├─┬ on-finished@2.3.0
…
│ ├── tmatch@3.0.0
│ ├── trivial-deferred@1.0.1
│ └── yapool@1.0.0
└─┬ which@1.2.12
└── isexe@1.1.2
Based on the documentation: http://books.sonatype.com/nexus-book/3.2/pdf/nxbook-pdf.pdf
Java: Nexus Repository Manager requires Java 8.
NFS: Mounting the storage directory via NFS can have negative performance and stability effects.
Component: A component is a resource like a library or a framework that is used as part of your software application at run-time, integration or unit test execution time or required as part of your build process. It could be an entire application or a static resource like an image.
Assets Assets are the material addition to all this metadata. The actual archive file is an asset associated
with the component. Many formats have a one-to-one mapping for component to asset.
For example a typical JAR component in a Maven repository is defined at least by the POM and the JAR files - both of which constitute separate assets belonging to the same components.
Components in Repositories A wide variety of components exists and more are continuously created by the open source community as well as proprietary vendors. There are libraries and frameworks written in various languages on different platforms that are used for application development every day. It has become a default pattern to build applications by combining the features of multiple components with your own custom components containing your application code to create an application for a specific domain.
In order to ease the consumption and usage of components, they are aggregated into collections of components. These are called a repository and are typically available on the internet as a service. On different platforms terms such as registry and others are used for the same concept.
1.Download: https://www.sonatype.com/download-oss-sonatype
2.Extract e.g. into directory: /app/nexus-3.2.1-01-unix
3.mv folder up: mv /app/nexus-3.2.1-01-unix/nexus-3.2.1-01 /app/nexus-3.2.1-01
4.vi /app/nexus-3.2.1-01/bin/nexus
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:~$ vi /app/nexus-3.2.1-01/bin/nexus
…
# Uncomment the following line to override the JVM search sequence
INSTALL4J_JAVA_HOME_OVERRIDE=/tool/jdk1.8.0_92/
...
5.(Optional) Install nexus as a service
vi /etc/systemd/system/nexus.service
[Unit]
Description=nexus service
After=network.target
[Service]
Type=forking
ExecStart=/app/nexus-3.2.1-01/bin/nexus start
ExecStop=/app/nexus-3.2.1-01/bin/nexus stop
User=nexus
Restart=on-abort
[Install]
WantedBy=multi-user.target
sudo systemctl daemon-reload
sudo systemctl enable nexus.service
1.Configuring the Data Directory
In the configuration file change the values of -Dkaraf.data, -Djava.io.tmpdir, and -XX:LogFile to designate an absolute path you prefer to use.
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:~$ vi /app/nexus-3.2.1-01/bin/nexus.vmoptions
...
#-XX:LogFile=../sonatype-work/nexus3/log/jvm.log
-XX:LogFile=/download/becke-ch--repo-nexus--s1-0-v3/log/jvm.log
#-Dkaraf.data=../sonatype-work/nexus3
-Dkaraf.data=/download/becke-ch--repo-nexus--s1-0-v3
#-Djava.io.tmpdir=../sonatype-work/nexus3/tmp
-Djava.io.tmpdir=/download/becke-ch--repo-nexus--s1-0-v3/tmp
…
1.Start nexus on the command-line versus as a service
a.nexus command-line
cd /app/nexus-3.2.1-01/bin
./nexus run
b.nexus as a service
sudo systemctl start nexus.service
2.The start was successful if we get the following output:
…
2017-02-24 06:22:51,667+0100 INFO [jetty-main-1] *SYSTEM org.eclipse.jetty.server.ServerConnector - Started ServerConnector@1fe50351{HTTP/1.1,[http/1.1]}{0.0.0.0:8081}
2017-02-24 06:22:51,667+0100 INFO [jetty-main-1] *SYSTEM org.eclipse.jetty.server.Server - Started @31558ms
2017-02-24 06:22:51,668+0100 INFO [jetty-main-1] *SYSTEM org.sonatype.nexus.bootstrap.jetty.JettyServer -
-------------------------------------------------
Started Sonatype Nexus OSS 3.2.1-01
-------------------------------------------------
...
You can as well check the log file for this output:
vi /download/repo--s1-0-v3/log/nexus.log
3.And when logging into http://localhost:8081 you should get the following web page:
4.The login / sign-in into the administration console is as follows: Click on “Sign In”:
a.Login: admin
b.Password: admin123
1.Select the Repositories item in the Repository sub menu of the Administration menu.
2.Click “Create repository” and select “npm (proxy)”:
3.Enter the following values and leave the rest default:
a.Name: Use the name given in the setup (becke-ch--repo-nexus--s1-0-v3) with additional scope, version and use-case classification: becke-ch--repo-nexus--s1-0-0-v3-0--npm-proxy
b.Remote Storage: https://registry.npmjs.org/
Follow step 1. of the previous chapter and then:
1.Click “Create repository” and select “npm (hosted)”
2.Enter the following values and leave the rest default:
Follow step 1. of the previous chapter and then:
1.Click “Create repository” and select “npm (group)”
2.Enter the following values and leave the rest default:
•ID: becke-ch--npm--s0-v1
•First name: Npm
•Last name: User (npm--s0-v1)
•Email: npm--s0-v1@becke.ch
•Password: y…
•Status: Active
•Roles: nx-admin
ERROR: http://localhost:8081/ not working!
SOLUTION: REBOOT?! OR “/etc/init.d/network-manager restart”?!
I could not find the solution to the problem until I restarted my computer. I only saw that the log got stuck:
...
2017-02-23 05:30:19,306+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.extender.NexusLifecycleManager - Start SERVICES
2017-02-23 05:30:19,363+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.blobstore.file.internal.BlobStoreMetricsStoreImpl - Blob store metrics file /media/disk-ssd--s0-v1/app/tmp/sonatype-work/nexus3/blobs/default/557F8812-3A328744-044A793D-F4658F72-ACF89806-metrics.properties not found - initializing at zero.
2017-02-23 05:30:19,768+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.internal.httpclient.HttpClientManagerImpl - Using default configuration: HttpClientConfiguration{connection=null, proxy=null, authentication=null}
2017-02-23 05:30:19,912+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.elasticsearch.internal.NodeProvider - Creating node with config: /media/disk-ssd—s0-v1/app/tmp/nexus-3.2.1-01/etc/fabric/elasticsearch.yml
INSTEAD I should have got:
...
2017-02-23 06:00:00,249+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.extender.NexusLifecycleManager - Start SERVICES
2017-02-23 06:00:00,330+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.blobstore.file.internal.BlobStoreMetricsStoreImpl - Blob store metrics file /media/disk-ssd--s0-v1/app/tmp/sonatype-work/nexus3/blobs/default/4717CE09-220528FD-A966D80E-6FF3B018-AB79E310-metrics.properties not found - initializing at zero.
2017-02-23 06:00:00,795+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.internal.httpclient.HttpClientManagerImpl - Using default configuration: HttpClientConfiguration{connection=null, proxy=null, authentication=null}
2017-02-23 06:00:00,949+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.elasticsearch.internal.NodeProvider - Creating node with config: /media/disk-ssd--s0-v1/app/tmp/nexus-3.2.1-01/etc/fabric/elasticsearch.yml
2017-02-23 06:00:01,045+0100 WARN [FelixStartLevel] *SYSTEM org.elasticsearch.common - Unable to get a valid mac address, will use a dummy address
2017-02-23 06:00:01,456+0100 INFO [FelixStartLevel] *SYSTEM org.elasticsearch.node - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] version[2.4.3], pid[4855], build[d38a34e/2016-12-07T16:28:56Z]
2017-02-23 06:00:01,456+0100 INFO [FelixStartLevel] *SYSTEM org.elasticsearch.node - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] initializing ...
2017-02-23 06:00:01,460+0100 INFO [FelixStartLevel] *SYSTEM org.elasticsearch.plugins - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] modules [], plugins [content-auth-plugin], sites []
2017-02-23 06:00:01,478+0100 INFO [FelixStartLevel] *SYSTEM org.elasticsearch.env - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] using [1] data paths, mounts [[/media/disk-ssd--s0-v1 (/dev/sda3)]], net usable_space [78.5gb], net total_space [441.3gb], spins? [no], types [ext4]
2017-02-23 06:00:01,478+0100 INFO [FelixStartLevel] *SYSTEM org.elasticsearch.env - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] heap size [1.1gb], compressed ordinary object pointers [true]
2017-02-23 06:00:02,533+0100 INFO [FelixStartLevel] *SYSTEM org.elasticsearch.node - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] initialized
2017-02-23 06:00:02,534+0100 INFO [FelixStartLevel] *SYSTEM org.elasticsearch.node - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] starting ...
2017-02-23 06:00:02,536+0100 INFO [FelixStartLevel] *SYSTEM org.elasticsearch.transport - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] publish_address {local[1]}, bound_addresses {local[1]}
2017-02-23 06:00:02,540+0100 INFO [FelixStartLevel] *SYSTEM org.elasticsearch.discovery - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] nexus/9tg5_g-aQlqnLCStYqrE8g
2017-02-23 06:00:02,546+0100 INFO [elasticsearch[4717CE09-220528FD-A966D80E-6FF3B018-AB79E310][clusterService#updateTask][T#1]] *SYSTEM org.elasticsearch.cluster.service - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] new_master {4717CE09-220528FD-A966D80E-6FF3B018-AB79E310}{9tg5_g-aQlqnLCStYqrE8g}{local}{local[1]}{local=true, master=true}, reason: local-disco-initial_connect(master)
2017-02-23 06:00:02,551+0100 INFO [FelixStartLevel] *SYSTEM org.elasticsearch.node - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] started
2017-02-23 06:00:02,595+0100 INFO [elasticsearch[4717CE09-220528FD-A966D80E-6FF3B018-AB79E310][clusterService#updateTask][T#1]] *SYSTEM org.elasticsearch.gateway - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] recovered [0] indices into cluster_state
2017-02-23 06:00:02,816+0100 INFO [elasticsearch[4717CE09-220528FD-A966D80E-6FF3B018-AB79E310][clusterService#updateTask][T#1]] *SYSTEM org.elasticsearch.cluster.metadata - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] [2e9a1e67e8a325bcd6ee9f6790ff6c769e791d56] creating index, cause [api], templates [], shards [1]/[0], mappings [component]
2017-02-23 06:00:02,950+0100 INFO [elasticsearch[4717CE09-220528FD-A966D80E-6FF3B018-AB79E310][clusterService#updateTask][T#1]] *SYSTEM org.elasticsearch.cluster.metadata - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] [73ae44bc066b6a7a33b4435641d8229b9b66495a] creating index, cause [api], templates [], shards [1]/[0], mappings [component]
2017-02-23 06:00:03,054+0100 INFO [elasticsearch[4717CE09-220528FD-A966D80E-6FF3B018-AB79E310][clusterService#updateTask][T#1]] *SYSTEM org.elasticsearch.cluster.routing.allocation - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] Cluster health status changed from [RED] to [GREEN] (reason: [shards started [[2e9a1e67e8a325bcd6ee9f6790ff6c769e791d56][0], [2e9a1e67e8a325bcd6ee9f6790ff6c769e791d56][0]] ...]).
2017-02-23 06:00:03,096+0100 INFO [elasticsearch[4717CE09-220528FD-A966D80E-6FF3B018-AB79E310][clusterService#updateTask][T#1]] *SYSTEM org.elasticsearch.cluster.metadata - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] [51196dce51055df9247e1973e443b68c84549dd9] creating index, cause [api], templates [], shards [1]/[0], mappings [component]
2017-02-23 06:00:03,143+0100 INFO [elasticsearch[4717CE09-220528FD-A966D80E-6FF3B018-AB79E310][clusterService#updateTask][T#1]] *SYSTEM org.elasticsearch.cluster.routing.allocation - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] Cluster health status changed from [RED] to [GREEN] (reason: [shards started [[51196dce51055df9247e1973e443b68c84549dd9][0]] ...]).
2017-02-23 06:00:03,178+0100 INFO [elasticsearch[4717CE09-220528FD-A966D80E-6FF3B018-AB79E310][clusterService#updateTask][T#1]] *SYSTEM org.elasticsearch.cluster.metadata - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] [3d781e8165513bfe7db3d7eaab3991b9ebec763b] creating index, cause [api], templates [], shards [1]/[0], mappings [component]
2017-02-23 06:00:03,238+0100 INFO [elasticsearch[4717CE09-220528FD-A966D80E-6FF3B018-AB79E310][clusterService#updateTask][T#1]] *SYSTEM org.elasticsearch.cluster.metadata - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] [b2b9b8f06274052a44b61ef3c7e887f0961d99c6] creating index, cause [api], templates [], shards [1]/[0], mappings [component]
2017-02-23 06:00:03,296+0100 INFO [elasticsearch[4717CE09-220528FD-A966D80E-6FF3B018-AB79E310][clusterService#updateTask][T#1]] *SYSTEM org.elasticsearch.cluster.routing.allocation - [4717CE09-220528FD-A966D80E-6FF3B018-AB79E310] Cluster health status changed from [RED] to [GREEN] (reason: [shards started [[b2b9b8f06274052a44b61ef3c7e887f0961d99c6][0]] ...]).
2017-02-23 06:00:03,324+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.quartz.internal.orient.JobStoreImpl - Instance name: nexus; ID: 4717CE09-220528FD-A966D80E-6FF3B018-AB79E310
2017-02-23 06:00:03,324+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.quartz.internal.orient.JobStoreImpl - Initialized
2017-02-23 06:00:03,331+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.quartz.internal.QuartzSchedulerSPI - Quartz Scheduler v2.2.2
2017-02-23 06:00:03,335+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.extender.NexusLifecycleManager - Start CAPABILITIES
2017-02-23 06:00:03,591+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.extender.NexusLifecycleManager - Start TASKS
2017-02-23 06:00:03,594+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.quartz.internal.QuartzSchedulerSPI - Scheduler put into ready mode
2017-02-23 06:00:03,716+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.quartz.internal.task.QuartzTaskInfo - Task 'Storage facet cleanup' [repository.storage-facet-cleanup] : state=WAITING
2017-02-23 06:00:03,792+0100 INFO [FelixStartLevel] *SYSTEM org.sonatype.nexus.scheduling.internal.TaskSchedulerImpl - Task 'Storage facet cleanup' [repository.storage-facet-cleanup] scheduled: cron
2017-02-23 06:00:03,834+0100 INFO [jetty-main-1] *SYSTEM org.sonatype.nexus.bootstrap.osgi.BootstrapListener - Initialized
2017-02-23 06:00:03,848+0100 INFO [jetty-main-1] *SYSTEM org.sonatype.nexus.rapture.internal.RaptureWebResourceBundle - UI plugin descriptors:
2017-02-23 06:00:03,849+0100 INFO [jetty-main-1] *SYSTEM org.sonatype.nexus.rapture.internal.RaptureWebResourceBundle - nexus-rapture
2017-02-23 06:00:03,850+0100 INFO [jetty-main-1] *SYSTEM org.sonatype.nexus.rapture.internal.RaptureWebResourceBundle - nexus-proximanova-plugin
2017-02-23 06:00:03,850+0100 INFO [jetty-main-1] *SYSTEM org.sonatype.nexus.rapture.internal.RaptureWebResourceBundle - nexus-coreui-plugin
2017-02-23 06:00:03,851+0100 INFO [jetty-main-1] *SYSTEM org.sonatype.nexus.rapture.internal.RaptureWebResourceBundle - nexus-proui-plugin
2017-02-23 06:00:03,861+0100 INFO [jetty-main-1] *SYSTEM org.sonatype.nexus.internal.webresources.WebResourceServlet - Max-age: 30 days (2592000 seconds)
2017-02-23 06:00:03,884+0100 INFO [jetty-main-1] *SYSTEM com.softwarementors.extjs.djn.servlet.DirectJNgineServlet - Servlet GLOBAL configuration: debug=false, providersUrl=service/extdirect, minify=false, batchRequestsMultithreadingEnabled=true, batchRequestsMinThreadsPoolSize=16, batchRequestsMaxThreadsPoolSize=80, batchRequestsMaxThreadsPerRequest=8, batchRequestsMaxThreadKeepAliveSeconds=60, gsonBuilderConfiguratorClass=org.sonatype.nexus.extdirect.internal.ExtDirectGsonBuilderConfigurator, dispatcherClass=com.softwarementors.extjs.djn.servlet.ssm.SsmDispatcher, jsonRequestProcessorThreadClass=org.sonatype.nexus.extdirect.internal.ExtDirectJsonRequestProcessorThread, contextPath=--not specified: calculated via Javascript--, createSourceFiles=true
2017-02-23 06:00:03,894+0100 INFO [jetty-main-1] *SYSTEM com.softwarementors.extjs.djn.servlet.DirectJNgineServlet - Servlet GLOBAL configuration: registryConfiguratorClass=
2017-02-23 06:00:03,913+0100 INFO [jetty-main-1] *SYSTEM com.softwarementors.extjs.djn.jscodegen.CodeFileGenerator - Creating source files for APIs...
2017-02-23 06:00:04,062+0100 INFO [jetty-main-1] *SYSTEM org.sonatype.nexus.siesta.SiestaServlet - JAX-RS RuntimeDelegate: org.sonatype.nexus.siesta.internal.resteasy.SisuResteasyProviderFactory@25045fce
2017-02-23 06:00:04,110+0100 INFO [jetty-main-1] *SYSTEM org.jboss.resteasy.plugins.validation.i18n - RESTEASY008550: Unable to find CDI supporting ValidatorFactory. Using default ValidatorFactory
2017-02-23 06:00:04,153+0100 INFO [jetty-main-1] *SYSTEM org.sonatype.nexus.siesta.SiestaServlet - Initialized
2017-02-23 06:00:04,156+0100 INFO [jetty-main-1] *SYSTEM org.sonatype.nexus.repository.httpbridge.internal.ViewServlet - Initialized
2017-02-23 06:00:04,192+0100 INFO [jetty-main-1] *SYSTEM org.eclipse.jetty.server.handler.ContextHandler - Started o.e.j.w.WebAppContext@5aa5841c{/,file:///media/disk-ssd--s0-v1/app/tmp/nexus-3.2.1-01/public/,AVAILABLE}
2017-02-23 06:00:04,230+0100 INFO [jetty-main-1] *SYSTEM org.eclipse.jetty.server.ServerConnector - Started ServerConnector@5e5b5f24{HTTP/1.1,[http/1.1]}{0.0.0.0:8081}
2017-02-23 06:00:04,230+0100 INFO [jetty-main-1] *SYSTEM org.eclipse.jetty.server.Server - Started @35364ms
2017-02-23 06:00:04,230+0100 INFO [jetty-main-1] *SYSTEM org.sonatype.nexus.bootstrap.jetty.JettyServer -
-------------------------------------------------
Started Sonatype Nexus OSS 3.2.1-01
So basically it seems that if there are issue with the network card respective rather the (blody) OS (Ubuntu 16.04.2 LTS) connecting to the network card (see http://askubuntu.com/questions/761180/wifi-doesnt-work-after-suspend-after-16-04-upgrade ) that the NEXUS cannot start respective that the “org.elasticsearch.common” is blocking the startup process! In this case either restart the network-manager “/etc/init.d/network-manager restart” or if this does not help reboot the computer.
ERROR: 4.3.1. NpmProxyFacetImpl - Failed to fetch: https://registry.npmjs.org/...
2017-04-01 20:47:00,082+0200 WARN [qtp239892311-148] *UNKNOWN com.sonatype.nexus.repository.npm.internal.NpmProxyFacetImpl - Failed to fetch: https://registry.npmjs.org/when/-/when-3.7.8.tgz
java.net.SocketTimeoutException: Read timed out
…
2017-04-01 20:47:00,962+0200 WARN [qtp239892311-47] *UNKNOWN org.sonatype.nexus.repository.httpbridge.internal.ViewServlet - Service failure
org.sonatype.nexus.blobstore.api.BlobStoreException: java.net.SocketTimeoutException: Read timed out
at org.sonatype.nexus.blobstore.file.internal.FileBlobStore.create(FileBlobStore.java:316) [na:na]
…
Caused by: java.net.SocketTimeoutException: Read timed out
at java.net.SocketInputStream.socketRead0(Native Method) [na:1.8.0_92]
at java.net.SocketInputStream.socketRead(SocketInputStream.java:116) [na:1.8.0_92]
…
2017-04-01 20:47:01,459+0200 WARN [qtp239892311-48] *UNKNOWN org.sonatype.nexus.repository.httpbridge.internal.ViewServlet - Service failure
org.eclipse.jetty.io.EofException: null
at org.eclipse.jetty.io.ChannelEndPoint.flush(ChannelEndPoint.java:197) [org.eclipse.jetty.io:9.3.7.v20160115]
at org.eclipse.jetty.io.WriteFlusher.flush(WriteFlusher.java:419) [org.eclipse.jetty.io:9.3.7.v20160115]
...
“SOLUTION”: I had to stop and restart nexus several times and even had to reboot the computer :-(
file:///data/doc/html/SELFHTML/tq.htm
...
Mit <script language="JavaScript"> leiten Sie einen Bereich für JavaScript innerhalb einer HTML-Datei ein (script = Quelltext, language = Sprache). Dahinter - am besten in der nächsten Zeile - sollten Sie mit <!-- einen Kommentar einleiten. Dadurch erreichen Sie, daß ältere WWW-Browser, die JavaScript nicht kennen, den folgenden JavaScript-Code ignorieren und nicht irrtümlich als Text innerhalb der HTML-Datei interpretieren.
Am Ende eines JavaScript-Bereichs schließen Sie mit //--> den Kommentar und mit </script> den Bereich für den Programmcode.
...
HTML:
<html>
<head>
...
<script language="JavaScript">
<!--
...
//-->
</script>
...
</head>
<body>
...
</body>
</html>
file:///data/doc/html/SELFHTML/tq.htm
...
Der Unterschied ist lediglich, daß der JavaScript-Code in einer separaten Datei steht. Dazu notieren Sie im einleitenden <script>-Tag die Angabe src= (src = source = Quelle). Dahinter folgt, in Anführungszeichen, der Name der separaten Datei mit dem Quellcode. Ebenfalls notieren sollten Sie die Angabe zum Mime-Type der eingebundenen Datei. Mit type="text/javascript" bestimmen Sie den Mime-Type für JavaScript-Dateien.
Die Datei mit dem Quellcode muß eine reine ASCII-Datei sein und sollte die Dateinamenerweiterung .js erhalten. Die Datei sollte nichts anderes als JavaScript-Code enthalten.
...
HTML:
<html>
<head>
...
<script language="JavaScript" src="quadrat.js" type="text/javascript">
...
</head>
<body>
...
</body>
</html>
http://stackoverflow.com/questions/11922383/access-process-nested-objects-arrays-or-json
JavaScript has only one data type which can contain multiple values: Object. An Array is a special form of object.
(Plain) Objects have the form
{key: value, key: value, ...}
Arrays have the form
[value, value, ...]
Both arrays and objects expose a key -> value structure. Keys in an array must be numeric, whereas any string can be used as key in objects. The key-value pairs are also called the "properties".
Properties can be accessed either using dot notation
var value = obj.someProperty;
or bracket notation, if the property name would not be a valid JavaScript identifier name [spec], or the name is the value of a variable:
// the space is not a valid character in identifier names
var value = obj["some Property"];
// property name as variable
var name = "some Property";
var value = obj[name];
For that reason, array elements can only be accessed using bracket notation:
var value = arr[5]; // arr.5 would be a syntax error
// property name / index as variable
var x = 5;
var value = arr[x];
http://stackoverflow.com/questions/5999998/how-can-i-check-if-a-javascript-variable-is-function-type
http://stackoverflow.com/questions/899574/which-is-best-to-use-typeof-or-instanceof
if (!(newSubstringFunctionArray instanceof Array)) {
newSubstringFunctionArray = [newSubstringFunctionArray];
}
…
if (typeof newSubstringFunction === 'string') {
...
} else if (newSubstringFunction instanceof Function) {
var args = [resultExec[newSubstringFunctionIndex]];
for (var j = 0; j < resultExec.length; j++) {
args.push(resultExec[j]);
}
for (var k = 0; j < resultExec.index.length; k++) {
args.push(resultExec.index[k]);
}
args.push(str);
computedString += newSubstringFunction.apply(this, args);
}
Object (pointer) comparison: ==: Object pointers can be compared using the double equal sign: ==
BUT there is no way to get the numerical value of a pointer and using this for example in a hash-map - see the following articles:
http://stackoverflow.com/questions/1068834/object-comparison-in-javascript
http://stackoverflow.com/questions/17382427/are-there-pointers-in-javascript
http://stackoverflow.com/questions/10892322/javascript-hashtable-use-object-key
http://stackoverflow.com/questions/8931967/is-there-a-deterministic-equivalent-of-json-stringify
http://stackoverflow.com/questions/10892322/javascript-hashtable-use-object-key/10908885#10908885
http://stackoverflow.com/questions/17872317/javascript-variables-as-object-pointers
http://stackoverflow.com/questions/201183/how-to-determine-equality-for-two-javascript-objects
http://stackoverflow.com/questions/10231868/pointers-in-javascript
http://www.w3schools.com/js/js_strings.asp
https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Global_Objects/String/charAt
index
An integer between 0 and 1-less-than the length of the string. If no index is provided, charAt() will use 0.
Return value
A string representing the character at the specified index; empty string if index is out of range.
http://stackoverflow.com/questions/8935632/check-if-character-is-number
while (charAt >= '0' && charAt <= '9') {
int += charAt;
posIndexOrigIndex[0]++;
charAt = regex.charAt(posIndexOrigIndex[0]);
}
http://stackoverflow.com/questions/154059/how-do-you-check-for-an-empty-string-in-javascript
http://stackoverflow.com/questions/2381456/javascript-how-to-check-if-a-string-is-empty
Check for empty string:
if (newSubstringFunctionArray[0] || newSubstringFunctionArray[0] === "")
if (int.indexOf('8') >= 0 || int.indexOf('9') >= 0) {
//if it is a non octal digit then treat it as simple number
tmpStr += int;
} else {
//otherwise it is a character escape
tmpStr += '\\' + 'x' + ("0" + (parseInt(int, 8).toString(16))).slice(-2).toUpperCase();
}
http://www.w3schools.com/js/js_strings.asp
Code | Outputs |
\' | single quote |
\" | double quote |
\\ | backslash |
\n | new line |
\r | carriage return |
\t | tab |
\b | backspace |
\f | form feed |
https://mathiasbynens.be/notes/javascript-escapes
Octal escape sequences
Any character with a character code lower than 256 (i.e. any character in the extended ASCII range) can be escaped using its octal-encoded character code, prefixed with \. (Note that this is the same range of characters that can be escaped through hexadecimal escapes.)
To use the same example, the copyright symbol ('©') has character code 169, which gives 251 in octal notation, so you could write it as '\251'.
Hexadecimal escape sequences
Any character with a character code lower than 256 (i.e. any character in the extended ASCII range) can be escaped using its hex-encoded character code, prefixed with \x. (Note that this is the same range of characters that can be escaped through octal escapes.)
Hexadecimal escapes are four characters long. They require exactly two characters following \x. If the hexadecimal character code is only one character long (this is the case for all character codes smaller than 16, or 10 in hex), you’ll need to pad it with a leading 0.
For example, the copyright symbol ('©') has character code 169, which gives A9 in hex, so you could write it as '\xA9'.
http://stackoverflow.com/questions/57803/how-to-convert-decimal-to-hex-in-javascript
if (int.indexOf('8') >= 0 || int.indexOf('9') >= 0) {
//if it is a non octal digit then treat it as simple number
tmpStr += int;
} else {
//otherwise it is a character escape
tmpStr += '\\' + 'x' + ("0" + (parseInt(int, 8).toString(16))).slice(-2).toUpperCase();
}
https://www.w3schools.com/js/js_function_invocation.asp
http://stackoverflow.com/questions/6001149/how-to-execute-a-method-passed-as-parameter-to-function
http://adripofjavascript.com/blog/drips/invoking-javascript-functions-with-call-and-apply.html
} else if (newSubstringFunction instanceof Function) {
var args = [resultExec[newSubstringFunctionIndex]];
for (var j = 0; j < resultExec.length; j++) {
args.push(resultExec[j]);
}
for (var k = 0; j < resultExec.index.length; k++) {
args.push(resultExec.index[k]);
}
args.push(str);
computedString += newSubstringFunction.apply(this, args);
}
call & apply: https://www.w3schools.com/js/js_function_invocation.asp
Both methods take an owner object as the first argument. The only difference is that call() takes the function arguments separately, and apply() takes the function arguments in an array.
In JavaScript strict mode, the first argument becomes the value of this in the invoked function, even if the argument is not an object.
In "non-strict" mode, if the value of the first argument is null or undefined, it is replaced with the global object.
With call() or apply() you can set the value of this, and invoke a function as a new method of an existing object.
http://www.w3schools.com/jsref/dom_obj_all.asp
Property / Method | Description |
element.accessKey | Sets or returns the accesskey attribute of an element |
element.addEventListener() | Attaches an event handler to the specified element |
element.appendChild() | Adds a new child node, to an element, as the last child node |
element.attributes | Returns a NamedNodeMap of an element's attributes |
element.blur() | Removes focus from an element |
element.childElementCount | Returns the number of child elements an element has |
element.childNodes | Returns a collection of an element's child nodes (including text and comment nodes) |
element.children | Returns a collection of an element's child element (excluding text and comment nodes) |
element.classList | Returns the class name(s) of an element |
element.className | Sets or returns the value of the class attribute of an element |
element.click() | Simulates a mouse-click on an element |
element.clientHeight | Returns the height of an element, including padding |
element.clientLeft | Returns the width of the left border of an element |
element.clientTop | Returns the width of the top border of an element |
element.clientWidth | Returns the width of an element, including padding |
element.cloneNode() | Clones an element |
element.compareDocumentPosition() | Compares the document position of two elements |
element.contains() | Returns true if a node is a descendant of a node, otherwise false |
element.contentEditable | Sets or returns whether the content of an element is editable or not |
element.dir | Sets or returns the value of the dir attribute of an element |
element.firstChild | Returns the first child node of an element |
element.firstElementChild | Returns the first child element of an element |
element.focus() | Gives focus to an element |
element.getAttribute() | Returns the specified attribute value of an element node |
element.getAttributeNode() | Returns the specified attribute node |
element.getElementsByClassName() | Returns a collection of all child elements with the specified class name |
element.getElementsByTagName() | Returns a collection of all child elements with the specified tag name |
element.getFeature() | Returns an object which implements the APIs of a specified feature |
element.hasAttribute() | Returns true if an element has the specified attribute, otherwise false |
element.hasAttributes() | Returns true if an element has any attributes, otherwise false |
element.hasChildNodes() | Returns true if an element has any child nodes, otherwise false |
element.id | Sets or returns the value of the id attribute of an element |
element.innerHTML | Sets or returns the content of an element |
element.insertBefore() | Inserts a new child node before a specified, existing, child node |
element.isContentEditable | Returns true if the content of an element is editable, otherwise false |
element.isDefaultNamespace() | Returns true if a specified namespaceURI is the default, otherwise false |
element.isEqualNode() | Checks if two elements are equal |
element.isSameNode() | Checks if two elements are the same node |
element.isSupported() | Returns true if a specified feature is supported on the element |
element.lang | Sets or returns the value of the lang attribute of an element |
element.lastChild | Returns the last child node of an element |
element.lastElementChild | Returns the last child element of an element |
element.namespaceURI | Returns the namespace URI of an element |
element.nextSibling | Returns the next node at the same node tree level |
element.nextElementSibling | Returns the next element at the same node tree level |
element.nodeName | Returns the name of a node |
element.nodeType | Returns the node type of a node |
element.nodeValue | Sets or returns the value of a node |
element.normalize() | Joins adjacent text nodes and removes empty text nodes in an element |
element.offsetHeight | Returns the height of an element, including padding, border and scrollbar |
element.offsetWidth | Returns the width of an element, including padding, border and scrollbar |
element.offsetLeft | Returns the horizontal offset position of an element |
element.offsetParent | Returns the offset container of an element |
element.offsetTop | Returns the vertical offset position of an element |
element.ownerDocument | Returns the root element (document object) for an element |
element.parentNode | Returns the parent node of an element |
element.parentElement | Returns the parent element node of an element |
element.previousSibling | Returns the previous node at the same node tree level |
element.previousElementSibling | Returns the previous element at the same node tree level |
element.querySelector() | Returns the first child element that matches a specified CSS selector(s) of an element |
element.querySelectorAll() | Returns all child elements that matches a specified CSS selector(s) of an element |
element.removeAttribute() | Removes a specified attribute from an element |
element.removeAttributeNode() | Removes a specified attribute node, and returns the removed node |
element.removeChild() | Removes a child node from an element |
element.replaceChild() | Replaces a child node in an element |
element.removeEventListener() | Removes an event handler that has been attached with the addEventListener() method |
element.scrollHeight | Returns the entire height of an element, including padding |
element.scrollIntoView() | Scrolls the specified element into the visible area of the browser window |
element.scrollLeft | Sets or returns the number of pixels an element's content is scrolled horizontally |
element.scrollTop | Sets or returns the number of pixels an element's content is scrolled vertically |
element.scrollWidth | Returns the entire width of an element, including padding |
element.setAttribute() | Sets or changes the specified attribute, to the specified value |
element.setAttributeNode() | Sets or changes the specified attribute node |
element.style | Sets or returns the value of the style attribute of an element |
element.tabIndex | Sets or returns the value of the tabindex attribute of an element |
element.tagName | Returns the tag name of an element |
element.textContent | Sets or returns the textual content of a node and its descendants |
element.title | Sets or returns the value of the title attribute of an element |
element.toString() | Converts an element to a string |
|
|
nodelist.item() | Returns the node at the specified index in a NodeList |
nodelist.length | Returns the number of nodes in a NodeList |
http://www.w3schools.com/jsref/prop_node_nodetype.asp
becke-ch--angularjs--s0-0-0-v1-0--directive--pl--client--contenteditable-table.js:
…
function getCursorOffset(elem, anchorNode, cursorOffset) {
if (elem == anchorNode) {
if (elem.nodeName === 'DIV' || elem.nodeName === 'BR') {
newLine++;
}
return [cursorOffset, true];
}
if (elem.nodeType == 3) {
return [cursorOffset + elem.length, false];
}
if (elem.nodeName === 'DIV' || elem.nodeName === 'BR') {
newLine++;
}
var children = elem.childNodes;
if (children) {
for (var i = 0; i < children.length; i++) {
var result = getCursorOffset(children[i], anchorNode, cursorOffset);
if (result[1]) {
return result;
}
cursorOffset = result[0];
}
}
return [cursorOffset, false];
}
...
http://www.w3schools.com/jsref/prop_node_nodename.asp
becke-ch--angularjs--s0-0-0-v1-0--directive--pl--client--contenteditable-table.js:
…
function getCursorOffset(elem, anchorNode, cursorOffset) {
if (elem == anchorNode) {
if (elem.nodeName === 'DIV' || elem.nodeName === 'BR') {
newLine++;
}
return [cursorOffset, true];
}
if (elem.nodeType == 3) {
return [cursorOffset + elem.length, false];
}
if (elem.nodeName === 'DIV' || elem.nodeName === 'BR') {
newLine++;
}
var children = elem.childNodes;
if (children) {
for (var i = 0; i < children.length; i++) {
var result = getCursorOffset(children[i], anchorNode, cursorOffset);
if (result[1]) {
return result;
}
cursorOffset = result[0];
}
}
return [cursorOffset, false];
}
...
https://developer.mozilla.org/en-US/docs/Learn/JavaScript/Objects/Inheritance
function Regex(pattern, options) {
RegExp.call(pattern, options);
if (pattern instanceof RegExp) {
pattern = pattern.source;
}
if (pattern) {
this.regexGroupStructure = getRegexCompleteGroupingStructure(pattern);
this.regex = new RegExp(this.regexGroupStructure[0][2], options);
} else {
this.regex = new RegExp(pattern, options);
}
}
Regex.prototype = Object.create(RegExp.prototype);
Regex.prototype.constructor = Regex;
Regex.prototype.exec = function (str) {
…
}
ERROR: Uncaught TypeError: RegExp.prototype.source getter called on non-RegExp object
CAUSE:
function Regex(pattern, options) {
RegExp.call(this, pattern, options);
if (this.source) {
this.regexGroupStructure = getRegexCompleteGroupingStructure(this.source);
this.regex = new RegExp(this.regexGroupStructure[0][2], options);
} else {
this.regex = new RegExp(this.source, options);
}
}
Regex.prototype = Object.create(RegExp.prototype);
Regex.prototype.constructor = Regex;
ALL ATTEMPTS: “Object.getOwnPropertyDescriptor(RegExp.prototype, 'source').get.call(this)” or similar according to http://stackoverflow.com/questions/23077569/proper-way-to-call-superclass-functions-from-subclass failed. Actually already just “this.source” should already have been working! So it seems something is preventing this.
SOLUTION (WORKAROUND): COMPOSITION:
function Regex(pattern, options) {
if (pattern instanceof RegExp) {
this.source = pattern.source;
} else {
this.source = pattern;
}
if (this.source) {
this.regexGroupStructure = getRegexCompleteGroupingStructure(this.source);
try {
this.regex = new RegExp(this.regexGroupStructure[0][2], options);
} catch (e) {
new RegExp(this.source, flags);
}
} else {
this.regex = new RegExp(this.source, options);
}
this.ignoreCase = this.regex.ignoreCase;
}
Regex.prototype = Object.create(RegExp.prototype, {
source: {
value: null,
enumerable: true,
configurable: true,
writable: true
},
ignoreCase: {
value: null,
enumerable: true,
configurable: true,
writable: true
}
});
Regex.prototype.constructor = Regex;
Regex.prototype.constructor = Regex;
http://www.w3schools.com/js/js_function_parameters.asp
Arguments are Passed by Value
The parameters, in a function call, are the function's arguments.
JavaScript arguments are passed by value: The function only gets to know the values, not the argument's locations.
If a function changes an argument's value, it does not change the parameter's original value.
Changes to arguments are not visible (reflected) outside the function.
Objects are Passed by Reference
In JavaScript, object references are values.
Because of this, objects will behave like they are passed by reference:
If a function changes an object property, it changes the original value.
Changes to object properties are visible (reflected) outside the function.
...
Parameter Rules
JavaScript function definitions do not specify data types for parameters.
JavaScript functions do not perform type checking on the passed arguments.
JavaScript functions do not check the number of arguments received.
...
Parameter Defaults
If a function is called with missing arguments (less than declared), the missing values are set to: undefined
...
http://stackoverflow.com/questions/3010840/loop-through-array-in-javascript
For example transforming the following data structure:
[
{
"label": "User Left", "id": "role1", "children": [
{"label": "subUser1", "id": "role11", "children": []},
{
"label": "subUser2 Left", "id": "role12", "children": [
{
"label": "subUser2-1", "id": "role121", "children": [
{"label": "subUser2-1-1", "id": "role1211", "children": []},
{"label": "subUser2-1-2", "id": "role1212", "children": []}
]
}
]
}
]
},
{"label": "Admin", "id": "role2", "children": []},
{"label": "Guest", "id": "role3", "children": []}
];
Into a map using the “id” field as index:
function resolve(treeStructure, treeMap) {
for (var i = 0; i < treeStructure.length; i++) {
console.log(treeStructure[i].id);
treeMap[treeStructure[i].id] = treeStructure[i];
if (treeStructure[i].children.length > 0) {
resolve(treeStructure[i].children, treeMap)
}
}
return treeMap;
};
TypeError: Cannot set property 'role11' of undefined
at resolve (two_tree_test_selection_button_map.html:107)
at resolve (two_tree_test_selection_button_map.html:109)
at new <anonymous> (two_tree_test_selection_button_map.html:147)
at Object.e [as invoke] (angular.min.js:39)
at L.instance (angular.min.js:81)
at M (angular.min.js:61)
at h (angular.min.js:54)
at h (angular.min.js:54)
at angular.min.js:54
at angular.min.js:20
CAUSE & SOLUTION: The cause for this error was that in the recursive function see above I forgot 1 parameter:
function resolve(treeStructure, treeMap) {
for (var i = 0; i < treeStructure.length; i++) {
console.log(treeStructure[i].id);
treeMap[treeStructure[i].id] = treeStructure[i];
if (treeStructure[i].children.length > 0) {
resolve(treeStructure[i].children, treeMap)
}
}
return treeMap;
};
Therefore the first invocation from outside was working fine but the second recursive invocation failed. This is the problem in JavaScript: http://www.w3schools.com/js/js_function_parameters.asp
...
Parameter Rules
JavaScript function definitions do not specify data types for parameters.
JavaScript functions do not perform type checking on the passed arguments.
JavaScript functions do not check the number of arguments received.
...
Parameter Defaults
If a function is called with missing arguments (less than declared), the missing values are set to: undefined
...
Regex.prototype.exec = function (str) {
var result = [];
result.index = [];
var resultRegex = this.regex.exec(str);
if (!resultRegex) {
return resultRegex;
}
result[0] = resultRegex[0];
result.index[0] = resultRegex.index;
result.input = str;
var execInternal = function (strPosition, regexGroupStructureChildren) {
var currentStrPos = strPosition;
for (var i = 0; i < regexGroupStructureChildren.length; i++) {
var index = regexGroupStructureChildren[i][0];
var originalIndex = regexGroupStructureChildren[i][1];
if (originalIndex) {
result[originalIndex] = resultRegex[index];
if (typeof result[originalIndex] === "undefined") {
result.index[originalIndex] = undefined;
} else {
result.index[originalIndex] = currentStrPos;
}
}
if (regexGroupStructureChildren[i][3]) {
execInternal(currentStrPos, regexGroupStructureChildren[i][3]);
}
if (typeof resultRegex[index] !== "undefined") {
currentStrPos += resultRegex[index].length;
}
}
};
if (this.regexGroupStructure[0][3]) {
execInternal(0, this.regexGroupStructure[0][3]);
}
return result;
};
The inner function is created / allocated each time the outer function is called.
http://stackoverflow.com/questions/19779752/javascript-nested-function-performance
…
No. There is no "wasting" problem without an actual test-case that shows otherwise. This idiom (of nested and anonymous functions) is very common in JavaScript and very well-optimized for.
Nested functions provide many benefits including self-documenting code, smaller self-contained lexical scopes, and other code isolation/organization advantages.
...
http://stackoverflow.com/questions/28652563/nested-helper-functions-and-performance
…
In the case of simple helpers, it's good to keep them local because it means you can make them suitable just for your special case and not worry about the extra cruft of a general function
...
Is based on https://w3c.github.io/editing/execCommand.html
http://stackoverflow.com/questions/400212/how-do-i-copy-to-the-clipboard-in-javascript
...
The JavaScript document.execCommand('copy') support has grown, see the links below for browser updates:
IE10+ (although this document indicates some support was there from IE5.5+).
Google Chrome 43+ (~April 2015)
Mozilla Firefox 41+ (shipping ~September 2015)
Opera 29+ (based on Chromium 42, ~April 2015)
...
JavaScript library: https://github.com/zenorocha/clipboard.js
<!-- 1. Define some markup -->
<button class="btnnn" data-clipboard-text="1">Copy</button>
<button class="btnnn" data-clipboard-text="2">Copy</button>
<button class="btnnn" data-clipboard-text="3">Copy</button>
<!-- 2. Include library -->
<script src="../lib/clipboard.min.js"></script>
<!-- 3. Instantiate clipboard by passing a string selector -->
<script>
var clipboard = new Clipboard('.btnnn');
clipboard.on('success', function (e) {
console.log(e);
});
clipboard.on('error', function (e) {
console.log(e);
});
</script>
...
http://www.sitepoint.com/javascript-copy-to-clipboard/
The output of console.log e.g.
$scope.$watch( 'abc.currentNode', function( newObj, oldObj ) {
console.log('hello');
if( $scope.abc && angular.isObject($scope.abc.currentNode) ) {
console.log( 'Node Selected!!' );
console.log( $scope.abc.currentNode );
window.alert($scope.abc.currentNode);
}
}, false);
Is displayed browser specific:
Open the: Developer Tools: Ctrl+Shift+I: And on the top select the tab “Console”:
file:///media/disk-ssd--s0-v1/data/doc/html/SELFHTML/tgcg.htm
http://www.w3schools.com/js/js_regexp.asp
http://www.w3schools.com/jsref/jsref_obj_regexp.asp
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Regular_Expressions
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/RegExp/exec
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String/replace
http://stackoverflow.com/questions/2593637/how-to-escape-regular-expression-in-javascript
becke-ch—js--s0-0-0-v1-0--util--pl--client--regex.js:
//(\u{2003}) - is the unicode value for   - Unicode in Regular Expression (flag 'u') is supported in ECMAScript 6!!!
// https://mathiasbynens.be/notes/es6-unicode-regex
var regexHtmlToText = RegExp('( )|(\u{2003})|( )|(&)|(<)|(>)|(<br>)|(<div>)|(<[^>]*>)', 'gmu');
// In Java respective Web-Kit the unicode regex support is a little bit different i.e. instead of '\u{2003}' and flag 'u' it is '\u2003' without any flag
var regexHtmlToText = RegExp('( )|(\u2003)|( )|(&)|(<)|(>)|(<br>)|(<div>)|(<[^>]*>)', 'gm');
var regexHtmlToTextStringArray = [undefined, ' ', '\t', '\t', '&', '<', '>', '\n', '\n', ''];
…
var groupStringArray = regex.exec(string);
while (groupStringArray) {
if (lastIndex < groupStringArray.index) {
...
}
//We ignore the matching group 0 which is matching the whole expression
for (var i = 1; i < groupStringArray.length; i++) {
...
}
lastIndex = regex.lastIndex;
groupStringArray = regex.exec(string);
}
https://mathiasbynens.be/notes/es6-unicode-regex
…
Unicode-aware regular expressions in ECMAScript 6
ECMAScript 6 introduces two new flags for regular expressions:
y enables ‘sticky’ matching.
u enables various Unicode-related features.
...
becke-ch—js--s0-0-0-v1-0--util--pl--client--regex.js:
//(\u{2003}) - is the unicode value for   - Unicode in Regular Expression (flag 'u') is supported in ECMAScript 6!!!
// https://mathiasbynens.be/notes/es6-unicode-regex
//(\u{00A0}) - is the unicode value for Line-Feed which is the equivalent to
// http://www.adamkoch.com/2009/07/25/white-space-and-character-160/var regexHtmlToText = RegExp('( )|(\u{2003})|( )|(&)|(<)|(>)|(<br>)|(<div>)|(<[^>]*>)', 'gmu');
// In Java respective Web-Kit the unicode regex support is a little bit different i.e. instead of '\u{2003}' and flag 'u' it is '\u2003' without any flag
var regexHtmlToText = RegExp('( )|(\u2003)|( )|(&)|(<)|(>)|(<br>)|(<div>)|(<[^>]*>)', 'gm');
Because in HTML the tabulator ‘\t’ is not supported we use the EM space instead:  
BUT when copying “ ” into a text field it is converted to an EM-Space character: \u{2003}
http://www.rexegg.com/regex-capture.html
Back references above \9 behave strange and different in every language. In Java-Script they are treated as back-reference if the group is existing otherwise they are treated as character escape sequence.
http://help.dottoro.com/ljikwsqs.php
https://developer.mozilla.org/en-US/docs/Web/API/Range/setStart
https://developer.mozilla.org/en-US/docs/Web/API/HTMLInputElement/setSelectionRange
http://stackoverflow.com/questions/1181700/set-cursor-position-on-contenteditable-div
http://stackoverflow.com/questions/3972014/get-caret-position-in-contenteditable-div
http://stackoverflow.com/questions/7991474/calculate-position-of-selected-text-javascript-jquery
document object: http://help.dottoro.com/ljwxewvs.php
getRangeAt method (selectionRange): http://help.dottoro.com/ljjmnrqr.php
createRange method (document, XMLDocument): http://help.dottoro.com/ljhcexoj.php
Range object: http://help.dottoro.com/ljxsqnoi.php
TextRange object (Only IE & Opera): http://help.dottoro.com/ljgbbkjf.php
becke-ch--angularjs--s0-0-0-v1-0--directive--pl--client--contenteditable-table.js:
var windowSelection = window.getSelection();
if (windowSelection && windowSelection.rangeCount > 0) {
cursorPosition = windowSelection.getRangeAt(0).startOffset;
newLine = 0;
if (element[0] == windowSelection.anchorNode) {
//special handling on top node i.e. dealing with empty new-lines
topNodeCursorPosition = cursorPosition;
} else {
topNodeCursorPosition = -1;
cursorPosition += getCursorOffset(element[0], windowSelection.anchorNode, 0)[0];
}
}
var windowSelection = window.getSelection();
if (windowSelection && windowSelection.rangeCount > 0) {
if (topNodeCursorPosition >= 0) {
//special handling on top node i.e. dealing with empty new-lines
var range = document.createRange();
var sel = window.getSelection();
range.setStart(element[0], topNodeCursorPosition);
range.collapse(true);
sel.removeAllRanges();
sel.addRange(range);
} else {
setCursor(element[0], cursorPosition);
}
}
function getCursorOffset(elem, anchorNode, cursorOffset) {
if (elem == anchorNode) {
if (elem.nodeName === 'DIV' || elem.nodeName === 'BR') {
newLine++;
}
return [cursorOffset, true];
}
if (elem.nodeType == 3) {
return [cursorOffset + elem.length, false];
}
if (elem.nodeName === 'DIV' || elem.nodeName === 'BR') {
newLine++;
}
var children = elem.childNodes;
if (children) {
for (var i = 0; i < children.length; i++) {
var result = getCursorOffset(children[i], anchorNode, cursorOffset);
if (result[1]) {
return result;
}
cursorOffset = result[0];
}
}
return [cursorOffset, false];
}
function setCursor(elem, cursorPos) {
if (elem.nodeType == 3) {
if (elem.length > cursorPos || (elem.length == cursorPos && newLine == 0)) {
var range = document.createRange();
var sel = window.getSelection();
range.setStart(elem, cursorPos);
range.collapse(true);
sel.removeAllRanges();
sel.addRange(range);
return [cursorPos, true];
}
return [cursorPos - elem.length, false];
}
if (elem.nodeName === 'DIV' || elem.nodeName === 'BR') {
if (newLine == 0 && cursorPos == 0) {
var range = document.createRange();
var sel = window.getSelection();
range.setStart(elem, cursorPos);
range.collapse(true);
sel.removeAllRanges();
sel.addRange(range);
return [cursorPos, true];
}
newLine--;
}
var children = elem.childNodes;
if (children) {
for (var i = 0; i < children.length; i++) {
var result = setCursor(children[i], cursorPos);
if (result[1]) {
return result;
}
cursorPos = result[0];
}
}
return [cursorPos, false];
}
The following function retrieves the entire text of a HTML page:
<script type="text/javascript">
function getBodyText(element) {
if (typeof window.getSelection != "undefined") {
bodyRange = document.createRange();
bodyRange.selectNodeContents(document.body);
bodyText = bodyRange.toString();
} else if (typeof document.selection != "undefined" &&
(sel = document.selection).type != "Control") {
bodyRange = document.body.createTextRange();
bodyText = bodyRange.text;
}
BodyTextTO.setText(bodyText);
BodyTextTO.markTransferCompleted();
}
</script>
The text is then stored in the transfer object: “BodyTextTO.setText(bodyText); ” which was initially injected from the underlying framework: JavaFX (see “becke-ch--java--s0-0-v1-0”) or Android (see “”) or ...
The function itself is invoked as follows: “getBodyText(document.body)”
The following function the start and end of the selected text:
<script type="text/javascript">
function getSelectionStartEnd(element) {
var start = 0, end = 0;
var sel, range, priorRange;
if (typeof window.getSelection != "undefined") {
range = window.getSelection().getRangeAt(0);
priorRange = range.cloneRange();
priorRange.selectNodeContents(element);
priorRange.setEnd(range.startContainer, range.startOffset);
start = priorRange.toString().length;
end = start + range.toString().length;
} else if (typeof document.selection != "undefined" &&
(sel = document.selection).type != "Control") {
range = sel.createRange();
priorRange = document.body.createTextRange();
priorRange.moveToElementText(element);
priorRange.setEndPoint("EndToStart", range);
start = priorRange.text.length;
end = start + range.text.length;
}
SelectionStartEndTO.setStart(start);
SelectionStartEndTO.setEnd(end);
SelectionStartEndTO.markTransferCompleted();
}
</script>
The text is then stored in the transfer object: “SelectionStartEndTO.setStart(start); ” which was initially injected from the underlying framework: JavaFX (see “becke-ch--java--s0-0-v1-0”) or Android (see “”) or ...
The function itself is invoked as follows: “getSelectionStartEnd(document.body)”
http://stackoverflow.com/questions/442404/retrieve-the-position-x-y-of-an-html-element
http://help.dottoro.com/ljvmcrrn.php
http://xahlee.info/js/js_get_elements.html
http://www.w3schools.com/jsref/met_element_getattribute.asp
http://www.w3schools.com/jsref/dom_obj_all.asp
http://www.w3schools.com/jsref/met_document_getelementsbytagname.asp
...
<script type="text/javascript">
//<![CDATA[
function getReferencesInformation() {
var reference = document.getElementsByTagName("a");
for (i = 0; i < reference.length; i++) {
referenceHref = reference[i].getAttribute("href");
referenceText = reference[i].innerHTML;
var rect = reference[i].getBoundingClientRect();
referenceXPosition = rect.left;
ReferenceListTO.add(referenceHref,referenceText,referenceXPosition);
}
}
//]]>
</script>
...
http://www.w3schools.com/tags/att_global_contenteditable.asp
http://html5doctor.com/the-contenteditable-attribute/
https://medium.engineering/why-contenteditable-is-terrible-122d8a40e480#.s1lea1mj6
…
The contenteditable attribute specifies whether the content of an element is editable or not.
Note: When the contenteditable attribute is not set on an element, the element will inherit it from its parent.
...
http://www.computerhope.com/issues/ch000074.htm
becke-ch—diff--s0-0-1-v1-0--singlepage--pl--client--main.html
<td class="logo-header"><a href="http://www.becke.ch" style="text-decoration: none">becke.ch</a></td>
ERROR: Error: [ng:areq] Argument 'GreetingController' is not a function, got undefined
http://errors.angularjs.org/1.5.0-beta.1/ng/areq?p0=GreetingController&p1=not%20a%20function%2C%20got%20undefined
at angular.js:68
at assertArg (angular.js:1796)
at assertArgFn (angular.js:1806)
at angular.js:9173
at setupControllers (angular.js:8237)
at nodeLinkFn (angular.js:8277)
at compositeLinkFn (angular.js:7687)
at compositeLinkFn (angular.js:7691)
at compositeLinkFn (angular.js:7691)
at compositeLinkFn (angular.js:7691)
REASON & SOLUTION: http://stackoverflow.com/questions/25895235/angularjs-error-ngareq-argument-homecontroller-is-not-a-function-got-und
The reason and solution was that I had 2 times “ng-app” defined!
<html lang="en" ng-app>
<head>
<meta charset="UTF-8">
<title>Title</title>
<!--script language="JavaScript" src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0-beta.1/angular.min.js"
type="text/javascript"></script-->
<script language="JavaScript" src="../lib/angular.min.js"
type="text/javascript"></script>
</head>
<body>
<div ng-app="jsonApp">
<div ng-controller="jsonController">
...
https://developers.google.com/web/tools/chrome-devtools/rendering-tools/
http://www.w3schools.com/js/js_json.asp
JSON is a format for storing and transporting data.
JSON is often used when data is sent from a server to a web page.
What is JSON?
• JSON stands for JavaScript Object Notation
• JSON is lightweight data interchange format
• JSON is language independent *
• JSON is "self-describing" and easy to understand
JSON Example
var text = '{ "employees" : [' +
'{ "firstName":"John" , "lastName":"Doe" },' +
'{ "firstName":"Anna" , "lastName":"Smith" },' +
'{ "firstName":"Peter" , "lastName":"Jones" } ]}';
The JSON Format Evaluates to JavaScript Objects
The JSON format is syntactically identical to the code for creating JavaScript objects.
Because of this similarity, a JavaScript program can easily convert JSON data into native JavaScript objects.
Converting a JSON Text to a JavaScript Object
Use the JavaScript built-in function JSON.parse() to convert the string into a JavaScript object:
var obj = JSON.parse(text);
https://www.ietf.org/rfc/rfc4627.txt
Code | Outputs |
\" | double quote |
\\ | backslash |
\n | new line |
\r | carriage return |
\t | tab |
\b | backspace |
\f | form feed |
\/ | forward slash |
|
|
…
The representation of strings is similar to conventions used in the C
family of programming languages. A string begins and ends with
quotation marks. All Unicode characters may be placed within the
quotation marks except for the characters that must be escaped:
quotation mark, reverse solidus, and the control characters (U+0000
through U+001F).
…
string = quotation-mark *char quotation-mark
char = unescaped /
escape (
%x22 / ; " quotation mark U+0022
%x5C / ; \ reverse solidus U+005C
%x2F / ; / solidus U+002F
%x62 / ; b backspace U+0008
%x66 / ; f form feed U+000C
%x6E / ; n line feed U+000A
%x72 / ; r carriage return U+000D
%x74 / ; t tab U+0009
%x75 4HEXDIG ) ; uXXXX U+XXXX
escape = %x5C ; \
quotation-mark = %x22 ; "
unescaped = %x20-21 / %x23-5B / %x5D-10FFFF
...
https://de.wikipedia.org/wiki/TypeScript
...
TypeScript ist eine vom Unternehmen Microsoft entwickelte Programmiersprache, die auf den Vorschlägen zum zukünftigen ECMAScript-6-Standard[2](JavaScript) basiert. Sprachkonstrukte von Typescript, wie Klassen, Interfaces, Vererbung, Module, anonyme Funktionen, Generics und eine statische Typisierung sollen auch in ECMAScript 6 übernommen werden.[3]
Der von Microsoft entwickelte TypeScript-Compiler kompiliert TypeScript-Code nach ECMA Script 3 (ES3), optional auch nach ECMA Script 5 (ES5). Jeder JavaScript-Code ist auch gültiger TypeScript-Code, sodass gängige JavaScript-Bibliotheken (wie z. B. jQuery oder AngularJS) auch in Typescript verwendet werden können.[3]
TypeScript unterstützt mit Modulen das Kapseln von Klassen, Interfaces, Funktionen und Variablen in eigene Namensräume. Dabei wird zwischen internen und externen Modulen unterschieden. Interne Module lehnen sich an die Modul-Spezifikation aus ECMAScript 6 an, wohingegen externe Module eine JavaScript-Bibliothek (AMD oder CommonJS) nutzen.
...
https://en.wikipedia.org/wiki/TypeScript
...
TypeScript is a free and open source programming language developed and maintained by Microsoft. It is a strict superset of JavaScript, and adds optional static typing and class-based object-oriented programming to the language. Anders Hejlsberg, lead architect of C# and creator of Delphi and Turbo Pascal, has worked on the development of TypeScript.[2][3][4][5] TypeScript may be used to develop JavaScript applications for client-side or server-side (Node.js) execution.
TypeScript is designed for development of large applications and transcompiles to JavaScript.[6] As TypeScript is a superset of JavaScript, any existing JavaScript programs are also valid TypeScript programs.
In this sense TypeScript is a preview of what to expect of ECMAScript 6. A unique aspect not in the proposal, but added to TypeScript, is optional static typing that enables static language analysis, which facilitates tooling and IDE support.
TypeScript is a language extension that adds features to ECMAScript 5. Additional features include:
Type annotations and compile-time type checking
Type inference
Type erasure
Interfaces
Enumerated type
Mixin
Generic
Namespaces
Tuple
Await
The following features are backported from ECMAScript 6:
Classes
Modules[23]
Abbreviated "arrow" syntax for anonymous functions
Optional parameters and default parameters
TypeScript compiles to ES3-compatible JavaScript.[24] By default the compiler targets ECMAScript 3, the current prevailing standard, and is also able to generate constructs used in ECMAScript 5.
Type annotations
TypeScript provides static typing through type annotations to enable type checking at compile time. This is optional and can be ignored to use the regular dynamic typing of JavaScript.
function add(left: number, right: number): number {
return left + right;
}
The annotations for the primitive types are number, boolean and string. Weakly- or dynamically-typed structures are of type any.
The TypeScript compiler makes use of type inference to infer types when types are not given.
Declaration files
When a TypeScript script gets compiled there is an option to generate a declaration file (with the extension .d.ts) that functions as an interface to the components in the compiled JavaScript. In the process the compiler strips away all function and method bodies and preserves only the signatures of the types that are exported. The resulting declaration file can then be used to describe the exported virtual TypeScript types of a JavaScript library or module when a third-party developer consumes it from TypeScript.
The concept of declaration files is analogous to the concept of header file found in C/C++.
declare module arithmetics {
add(left: number, right: number): number;
subtract(left: number, right: number): number;
multiply(left: number, right: number): number;
divide(left: number, right: number): number;
}
Classes
TypeScript supports ECMAScript 6 classes that integrate the optional type annotations support.
class Person {
private name: string;
private age: number;
private salary: number;
constructor(name: string, age: number, salary: number) {
this.name = name;
this.age = age;
this.salary = salary;
}
toString(): string {
return `${this.name} (${this.age}) (${this.salary})`; // As of version 1.4
}
}
Generics
TypeScript supports generic programming.[26]
Modules and namespaces
TypeScript distinguishes between modules and namespaces. Both features in TypeScript support encapsulation of classes, interfaces, functions and variables into containers. Namespaces (formerly internal modules) utilizes immediately-invoked function expression of JavaScript to encapsulate code, whereas modules (formerly external modules) leverage JavaScript library patterns to do so (AMD or CommonJS).
Compiler
The TypeScript compiler, named tsc, is written in TypeScript that can be compiled into regular JavaScript that can be executed in any JavaScript engine in any host, such as a browser.
IDE and editor support
JetBrains supports TypeScript with code completion, refactoring and debugging in its IDEs built on IntelliJ platform, such as PhpStorm 6, WebStorm 6, and IntelliJ IDEA,[30] as well as their Visual Studio Add-in and extension, ReSharper 8.1.[31]
Integration with build automation tools
Using plug-ins, TypeScript can be integrated with build automation tools, including Grunt (grunt-ts[32]), Apache Maven (TypeScript Maven Plugin[33]) and Gradle (TypeScript Gradle Plugin[34]).
…
ERROR: error TS2345: Argument of type ... is not assignable to parameter of type ...
src/app/app.component.ts(76,280): error TS2345: Argument of type 'string[]' is not assignable to parameter of type '(substring: string, ...args: any[]) => string'.
Type 'string[]' provides no match for the signature '(substring: string, ...args: any[]): string'
src/app/app.component.ts
...
str: string;
pattern: string;
flags: string;
replacementStrings: string;
replacementStringArray: string[];
result: string;
}
...
this.replace.str.replace(new Regex(this.replace.pattern, this.replace.flags), (this.replace.replacementStringArray));
…
SOLUTION: any
...
export class Replace {
pattern: string;
flags: string;
replacementStrings: string;
replacementStringArray: any;
result: string;
}
...
this.replace.str.replace(new Regex(this.replace.pattern, this.replace.flags), (this.replace.replacementStringArray));
…
Build:
•Minified: Minified and obfuscated version of the AngularJS base code. Use this in your deployed application (but only if you can't use Google's CDN)
•Uncompressed: The main AngularJS source code, as is. Useful for debugging and development purpose, but should ideally not be used in your deployed application
•Zipped: The zipped version of the Angular Build, which contains both the builds of AngularJS, as well as documentation and other extras
CDN: Why Google CDN?
While downloading and using the AngularJS source code is great for development, we recommend that you source the script from Google's CDN (Content Delivery Network) in your deployed, customer facing app whenever possible. You get the following advantages for doing so:
•Better Caching: If you host AngularJS yourself, your users will have to download the source code at-least once. But if the browser sees that you are referring to Google CDN's version of AngularJS, and your user has visited another app which uses AngularJS, then he can avail the benefits of caching, and thus reduce one download, speeding up his overall experience!
•Decreased Latency: Google's CDN distributes your static content across the globe, in various diverse, physical locations. It increases the odds that the user gets a version of AngularJS served from a location near him, thus reducing overall latency.
•Increased Parallelism: Using Google's CDN reduces one request to your domain. Depending on the browser, the number of parallel requests it can make to a domain is restricted (as low as 2 in IE 7). So it can make a gigantic difference in loading times for users of those browsers.
What is Bower?
Bower is a package manager for client-side JavaScript components. For more info please see: https://github.com/bower/bower
http://stackoverflow.com/questions/16263195/how-to-run-angularjs-documentation-localy
…
1. Download the zipped version of the Angular.JS Build, which contains both the builds of AngularJS, as well as documentation and other extras.
2. Unzip the Angular.JS docs folder.
3. Download and install Node.JS.
Using Mac Terminal, install the npm package http-server globally so that it can be run from the command line.
$ npm install -g http-server
cd to the Angular.JS docs folder and start-up http-server.
$ http-server -a 127.0.0.1
Starting up http-server, serving ./ on: http://127.0.0.1:8080
Use your browser to view the docs @ http://127.0.0.1:8080/index-production.html
…
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:~$ npm install -g http-server
/media/disk-ssd--s0-v1/tool/node-v4.2.4-linux-x64/bin/http-server -> /media/disk-ssd--s0-v1/tool/node-v4.2.4-linux-x64/lib/node_modules/http-server/bin/http-server
/media/disk-ssd--s0-v1/tool/node-v4.2.4-linux-x64/bin/hs -> /media/disk-ssd--s0-v1/tool/node-v4.2.4-linux-x64/lib/node_modules/http-server/bin/http-server
/media/disk-ssd--s0-v1/tool/node-v4.2.4-linux-x64/lib
└─┬ http-server@0.9.0
├── colors@1.0.3
├── corser@2.0.1
├─┬ ecstatic@1.4.1
│ ├── he@0.5.0
│ ├── mime@1.3.4
│ ├── minimist@1.2.0
│ └── url-join@1.1.0
├─┬ http-proxy@1.14.0
│ ├── eventemitter3@1.2.0
│ └── requires-port@1.0.0
├── opener@1.4.1
├─┬ optimist@0.6.1
│ ├── minimist@0.0.10
│ └── wordwrap@0.0.3
├─┬ portfinder@0.4.0
│ ├── async@0.9.0
│ └─┬ mkdirp@0.5.1
│ └── minimist@0.0.8
└─┬ union@0.4.4
└── qs@2.3.3
ERROR: "GET /angular.min.js" Error (404): "Not found"
[Tue Aug 23 2016 18:10:11 GMT+0200 (CEST)] "GET /angular.min.js" Error (404): "Not found"
[Tue Aug 23 2016 18:10:11 GMT+0200 (CEST)] "GET /angular-animate.js" Error (404): "Not found"
[Tue Aug 23 2016 18:10:11 GMT+0200 (CEST)] "GET /angular-animate.js" "Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Ubuntu Chromium/51.0.2704.79 Chrome/51.0.2704.79 Safari/537.36"
[Tue Aug 23 2016 18:10:11 GMT+0200 (CEST)] "GET /angular-animate.js" Error (404): "Not found"
SOLUTION: Copy these files from the parent-directory into the docs directory.
1.Create a gradle java module e.g.
2.Create the following folder respective sub-folder “/.../becke-ch--test--s0-0-v1--angularjs--pl/src/main/resources/lib” (the subfolder “lib” is not required i.e. the resources respective javascript files could as well be placed directly into the directory “resources” but in order to have a clean structure I suggest to put them into a sub-folder called “lib”):
a.Copy the angularjs javascript library “angular.js” (for development and debugging) or “angular.min.js” into this folder.
Actually I suggest in the application i.e. html file to reference “angular.min.js” and in the IDE use the “angular.js” if possible
3.Alternatively (but not suggested because of off-line capability) if the JavaFX (or Swing) client supports remote loading of Java-Script add the following (google) CDN directive to the html page:
Same procedure as “setup rich client” with the following differences:
1. Create a gradle web module. (artifact id I used “becke-ch--test--s0-1-v1--angularjs--pl” (i.e. scope S0-1 to differentiate from rich client)
2./3. In a web application I suggest to use the (google) CDN because of caching and performance or alternatively create a folder “/.../becke-ch--test--s0-1-v1--angularjs--pl/src/main/webapp/resources” and put the JS file there.
<!DOCTYPE html>
<html lang="en" ng-app>
<head>
<meta charset="UTF-8">
<title>Title</title>
<script language="JavaScript" src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0-beta.1/angular.js"
type="text/javascript"></script>
</head>
<body>
<div>
<label>Name:</label>
<input type="text" ng-model="yourName" placeholder="Enter a name here">
<hr>
<h1>Hello {{yourName}}!</h1>
</div>
</body>
</html>
Modularization:
becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client--main.html:
…
<head>
<meta charset="UTF-8">
<title>becke.ch compare tool</title>
<script language="JavaScript">
var url = "http://www--s0-v1.becke.ch/becke-ch--diff--s0-0-v1--singlepage--pl--server-1.1/main-view-json/";
var downloadUrl = "http://www--s0-v1.becke.ch/becke-ch--diff--s0-0-v1--singlepage--pl--server-1.1/download-result";
//-->
</script>
<script language="JavaScript" src="../lib/angular.js" type="text/javascript"></script>
<script language="JavaScript" src="../lib/angular.treeview.js" type="text/javascript"></script>
<script language="JavaScript" src="../lib/angular-sanitize.min.js" type="text/javascript"></script>
<script language="JavaScript" src="../js/util/becke-ch--js--s0-0-0-v1-0--util--pl--client--regex.js"
type="text/javascript"></script>
<script language="JavaScript" src="../angularjs/becke-ch--angularjs--s0-0-0-v1-0--module--pl--client.js"
type="text/javascript"></script>
<script language="JavaScript"
src="../becke-ch--diff--s0-0-v1--singlepage--pl--client/becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client.js"
type="text/javascript"></script>
<script language="JavaScript"
src="../becke-ch--diff--s0-0-v1--singlepage--pl--client/model/becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client--model.js"
type="text/javascript"></script>
<script language="JavaScript"
src="../becke-ch--diff--s0-0-v1--singlepage--pl--client/service/becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client--service.js"
type="text/javascript"></script>
<script language="JavaScript"
src="../angularjs/filter/becke-ch--angularjs--s0-0-0-v1-0--filter--pl--client--trust-html.js"
type="text/javascript"></script>
<script language="JavaScript"
src="../angularjs/directive/becke-ch--angularjs--s0-0-0-v1-0--directive--pl--client--file-model.js"
type="text/javascript"></script>
<script language="JavaScript"
src="../angularjs/directive/becke-ch--angularjs--s0-0-0-v1-0--directive--pl--client--contenteditable-table.js"
type="text/javascript"></script>
<script language="JavaScript"
src="../becke-ch--diff--s0-0-v1--singlepage--pl--client/controller/becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client--controller.js"
type="text/javascript"></script>
<link rel="stylesheet" media="all" type="text/css" id="angular.treeview" href="../css/angular.treeview.css">
<link rel="stylesheet" media="all" type="text/css" id="default-styles" href="../css/default-styles.css">
</head>
...
becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client.js:
angular.module('becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client', ['becke-ch--angularjs--s0-0-0-v1-0--directive--pl--module', 'becke-ch--angularjs--s0-0-0-v1-0--filter--pl--module', 'angularTreeview', 'ngSanitize']);
becke-ch--angularjs--s0-0-0-v1-0--module--pl--client.js:
angular.module('becke-ch--angularjs--s0-0-0-v1-0--directive--pl--module', []);
angular.module('becke-ch--angularjs--s0-0-0-v1-0--filter--pl--module', []);
https://docs.angularjs.org/error/$injector/unpr
This error results from the $injector being unable to resolve a required dependency. To fix this, make sure the dependency is defined and spelled correctly.
https://docs.angularjs.org/api/ng/directive/ngInit
The ngInit directive allows you to evaluate an expression in the current scope.
This directive can be abused to add unnecessary amounts of logic into your templates. There are only a few appropriate uses of ngInit, such as for aliasing special properties of ngRepeat, as seen in the demo below; and for injecting data via server side scripting. Besides these few cases, you should use controllers rather than ngInit to initialize values on a scope.
The problem actually is that the module and its structure which is located in the view part of the controller:
...
<html lang="en" ng-app="treeApp">
...
<div ng-controller="treeController">
...
<div
data-angular-treeview="true"
data-tree-id="abc"
data-tree-model="treedata"
data-node-id="id"
data-node-label="label"
data-node-children="children">
</div>
<div ng-init="childTreeArray.push(abc)"></div>
...
Is initialized after the controller was initialized and therefore the module structure and its variables are empty at the time the controller is initialized and the solution is to put ng-init after the module initialization in the view part.
OR better: http://stackoverflow.com/questions/15458609/execute-function-on-page-load
Use: angular.element(document).ready(function () { ... });
var treeApp = angular.module('treeApp', ['angularTreeview']);
...
treeApp.controller('treeController', function ($scope) {
...
angular.element(document).ready(function () {
$scope.childTreeArray.push($scope.abc);
});
});
Change it from ng-keypress to ng-keydown!
...
<html lang="en" ng-app="treeApp">
<head>
...
</head>
<body ng-controller="parentTreeController" ng-keydown="keydownEvent($event)">
...
http://stackoverflow.com/questions/19911378/how-to-watch-for-a-keypress-combination-in-angularjs
http://stackoverflow.com/questions/23651954/how-to-detect-pressed-keys-on-the-click-of-angularjs
HTML: becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client--main.html
…
<html lang="en" ng-app="becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client">
<head>
…
<script language="JavaScript" src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0/angular.min.js"
type="text/javascript"></script>
…
</head>
<body id="diffControllerId" ng-controller="diffController" ng-keydown="keydownEvent($event)"
style="font-family: Arial;">
…
</body>
</html>
Controller:
angular.module('becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client').controller('diffController', ['$scope', 'diffService', function ($scope, diffService) {
…
//Keydown event function
$scope.keydownEvent = function (clickEvent) {
//$scope.clickEvent = simpleKeys(clickEvent);
for (i = 0; i < $scope.childTreeArray.length; i++) {
if ($scope.childTreeArray[i]) {
if (clickEvent.shiftKey && clickEvent.ctrlKey && clickEvent.keyCode == 38) {
//cursor up
$scope.childTreeArray[i].moveSelectionUp();
} else if (clickEvent.shiftKey && clickEvent.ctrlKey && clickEvent.keyCode == 40) {
//cursor down
$scope.childTreeArray[i].moveSelectionDown();
} else if (clickEvent.shiftKey && clickEvent.ctrlKey && clickEvent.keyCode == 39) {
//cursor right
$scope.childTreeArray[i].expandSelection();
} else if (clickEvent.shiftKey && clickEvent.ctrlKey && clickEvent.keyCode == 37) {
//cursor left
$scope.childTreeArray[i].collapseSelection();
} else if (clickEvent.shiftKey && clickEvent.ctrlKey && clickEvent.keyCode == 13) {
//enter
//$scope.childTreeArray[i].collapseSelection();
if ($scope.childTreeArray[i].currentNode &&
$scope.childTreeArray[i].currentNode.selected == 'selected') {
$scope.showHideTree();
if ($scope.hideTree) {
$scope.showProgressIcon[0] = true;
$scope.diffInput.absolutePath = $scope.childTreeArray[i].currentNode.absolutePath;
$scope.diffInput.diffAction = 'diffTreeEntry';
$scope.diffOutput.treeFrom = $scope.treeFrom;
$scope.diffOutput.treeTo = $scope.treeTo;
//diffService.post($scope.sessionId, $scope.diffOption, $scope.securityQuestion,
// $scope.diffInput, $scope.diffOutput, $scope.url, $scope.showProgressIcon);
diffService.post($scope.sessionId, $scope.diffOption, $scope.securityQuestion,
$scope.diffInput, $scope.diffOutput, url, $scope.showProgressIcon);
}
break;
}
}
}
}
};
…
}]);
https://docs.angularjs.org/api/ng/directive/ngRepeat
...
The ngRepeat directive instantiates a template once per item from a collection. Each template instance gets its own scope, where the given loop variable is set to the current collection item, and $index is set to the item index or key.
...
HTML: becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client--main.html
…
<html lang="en" ng-app="becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client">
<head>
…
<script language="JavaScript" src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0/angular.min.js"
type="text/javascript"></script>
…
</head>
<body id="diffControllerId" ng-controller="diffController" ng-keydown="keydownEvent($event)"
style="font-family: Arial;">
…
<table border width="100%"
style="font-family:'Courier New', Courier, monospace; table-layout: fixed; word-wrap: break-word;">
<colgroup>
<col width="50%">
<col width="50%">
</colgroup>
<tr>
<th>{{diffInput.fileFrom}}</th>
<th>{{diffInput.fileTo}}</th>
</tr>
<tr ng-repeat="resultTableRowJson in diffOutput.resultTableRowsJson">
<td>
<div ng-bind-html="resultTableRowJson.fromHtmlText | trust_html"></div>
</td>
<td>
<div ng-bind-html="resultTableRowJson.toHtmlText | trust_html"></div>
</td>
</tr>
</table>
…
</body>
</html>
Alternative solutions:
https://docs.angularjs.org/api/ng/directive/ngRepeat
…
ngRepeat uses $watchCollection to detect changes in the collection. When a change happens, ngRepeat then makes the corresponding changes to the DOM:
When an item is added, a new instance of the template is added to the DOM.
When an item is removed, its template instance is removed from the DOM.
When items are reordered, their respective templates are reordered in the DOM.
To minimize creation of DOM elements, ngRepeat uses a function to "keep track" of all items in the collection and their corresponding DOM elements. For example, if an item is added to the collection, ngRepeat will know that all other items already have DOM elements, and will not re-render them.
The default tracking function (which tracks items by their identity) does not allow duplicate items in arrays. This is because when there are duplicates, it is not possible to maintain a one-to-one mapping between collection items and DOM elements.
If you do need to repeat duplicate items, you can substitute the default tracking behavior with your own using the track by expression.
For example, you may track items by the index of each item in the collection, using the special scope property $index:
<div ng-repeat="n in [42, 42, 43, 43] track by $index">
{{n}}
</div>
...
<tr ng-repeat="resultTableRowJson in diffOutput.resultTableRowsJson track by $index">
http://www.codelord.net/2014/04/15/improving-ng-repeat-performance-with-track-by/
…
Why would Angular do this? Behind the scenes ngRepeat adds a $$hashKey property to each task to keep track of it. If you replace the original tasks with new tasks objects from the server, even if those are in fact totally identical to your original tasks, they won’t have the $$hashKey property and so ngRepeat won’t know they represent the same elements.
…
If the records have a unique id then “track by” this id to make sure that only the records that have been added or removed are added or removed from the list and not the whole list is rebuilt:
<tr ng-repeat="resultTableRowJson in diffOutput.resultTableRowsJson track by resultTableRowJson.id">
Service: becke-ch—diff--s0-0-0-v1-0--singlepage--pl--client--service.js:
angular.module('becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client').service('diffService', ['$http', function ($http) {
this.post = function (sessionId, diffOption, securityQuestion, diffInput, diffOutput, url,
showProgressIcon) {
…
$http.post(url, fd, {
transformRequest: angular.identity,
headers: {'Content-Type': undefined}
})
.then(function successCallback(response) {
…
diffOutput.resultTableRowsJson = response.data['resultTableRowsJson'];
…
};
}]);
Error: [ngRepeat:dupes] http://errors.angularjs.org/1.5.0/ngRepeat/dupes?p0=resultTableRowJson%20in…sultTableRowsJson%20track%20by%20resultTableRowJson.id&p1=undefined&p2=%7B
at Error (native)
at https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0/angular.min.js:6:416
at https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0/angular.min.js:292:254
at https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0/angular.min.js:137:302
at m.$digest (https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0/angular.min.js:138:399)
at m.$apply (https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0/angular.min.js:141:341)
at g (https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0/angular.min.js:94:139)
at t (https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0/angular.min.js:98:260)
at XMLHttpRequest.u.onload (https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0/angular.min.js:99:297)
SOLUTION: http://stackoverflow.com/questions/24977103/duplicates-in-a-repeater-are-not-allowed-on-ng-repeat
…
If I may add an additional reason as to why this can occur...
If you are doing this with a JS object [] or {}
and you are passing it in to a directive like this
<my-directive my-attribute="{{ myObject }}"></my-directive>
Inside the directive you must turn myObject back into an object by doing this
...
controller: function( $scope ){
$scope.links = $scope.$eval( $scope.myObject );
....
Then the HTML and ng-repeat will work
...
<span class="" ng-repeat="link in links">
...
ngRepeat does not know how to repeat over a single string.
…
Service: becke-ch—diff—s0-0-0-v1-0--singlepage--pl--client--service.js:
Instead of:
diffOutput.resultTableRowsJson = response.data['resultTableRowsJson'];
Use:
diffOutput.resultTableRowsJson = eval(response.data['resultTableRowsJson']);
http://webiks.com/the-war-of-good-vs-eval-or-eval-vs-eval/
…
Eval… the ultimate bane. Nothing can be said that wasn’t said before. The bottom line is – stay away from it. Ok, so you don’t know why it is bad for mankind (or JS apps)? Do you know what’s it good for?
Security issue – someone can inject a code that would be eval‘d and then executed…
1. Performance – no optimization until runtime, caching issues – you name it.
2. Bad architecture – debugging becomes a mess…
3. These are the 3 major issues mentioned over the web. You can look for more and post below.
Ok, now to the point – this is an angular post, and there’s a $ sign in the title, so this means angular has some solution for us, right?
Angular’s $scope has a very powerful function that’s called… $eval. Now, this function works much like the (bad) old eval, only it is good 🙂
In short, instead of this:
eval('myObj.' + property);
Use the angular $eval:
$scope.$eval(property, myObj)
...
https://docs.angularjs.org/guide/controller
http://stackoverflow.com/questions/16802857/angularjs-saving-data-between-routes/16806510#16806510
There exist 2 ways to share data between controllers:
•Services: https://docs.angularjs.org/guide/services
•Parent & Child Controller: Scope inheritance: https://docs.angularjs.org/guide/controller
I prefer due to simplicity using scope inheritance - placing the scope objects to be shared into the parent controller.
http://stackoverflow.com/questions/11952579/watch-multiple-scope-attributes
https://docs.angularjs.org/api/ng/type/%24rootScope.Scope#%24watchGroup
...
$scope.$watchGroup(['tree_id.currentNodeHead', 'tree_id.currentNodeHead.collapsed'], function
(newObj, oldObj) {
console.log('hello currentNodeHead');
if ($scope.tree_id && angular.isObject($scope.tree_id.currentNodeHead)) {
console.log('currentNodeHead Node Selected!!');
console.log($scope.tree_id.currentNodeHead);
}
}, false);
...
http://stackoverflow.com/questions/9381926/angularjs-insert-html-into-view
You can also create a filter like so:
var app = angular.module("demoApp", ['ngResource']);
app.filter("trust_html", ['$sce', function($sce) {
return function(htmlCode){
return $sce.trustAsHtml(htmlCode);
}
}]);
Then in the view
<div ng-bind-html="whatever_needs_to_be_sanitized | trust_html"></div>
https://docs.angularjs.org/guide/directive
Directives enable the user to create new HTML tags and accordingly create new reusable components.
directive: To create a directive use the function “directive” which takes as input:
•Name of directive: Naming convention: Camel Case: While the directive name is written camel-case the resulting html-tag name is lowercase separated by dashes “-”.
•Function: Object: The second parameter is the functionality of the directive returned as function object.
JavaScript:
...
var myApp = angular.module('testApp', []);
myApp.directive('fileModel', ['$parse', function ($parse) {
return {
restrict: 'A',
link: function (scope, element, attrs) {
var model = $parse(attrs.fileModel);
var modelSetter = model.assign;
element.bind('change', function () {
scope.$apply(function () {
modelSetter(scope, element[0].files[0]);
});
});
}
};
}]);
...
HTML:
<input type="file" file-model="myFile"/>
http://outbottle.com/angularjs-isolate-scope-pass-by-reference/
https://docs.angularjs.org/api/ng/service/$compile#-scope-
https://jsfiddle.net/joshdmiller/FHVD9/
http://stackoverflow.com/questions/14619884/angularjs-passing-object-to-directive
http://stackoverflow.com/questions/32052984/define-function-inside-angular-directives-isolated-scope
…
The scope property can be false, true, or an object:
false (default): No scope will be created for the directive. The directive will use its parent's scope.
true: A new child scope that prototypically inherits from its parent will be created for the directive's element. If multiple directives on the same element request a new scope, only one new scope is created.
{...} (an object hash): A new "isolate" scope is created for the directive's element. The 'isolate' scope differs from normal scope in that it does not prototypically inherit from its parent scope. This is useful when creating reusable components, which should not accidentally read or modify data in the parent scope.
...
becke-ch--angularjs--s0-0-0-v1-0--directive--pl--client--contenteditable-table.js:
becke_ch__angularjs__s0_0_0_v1_0__directive__pl__client__contenteditable_modified_element = undefined;
//contenteditable directive: http://stackoverflow.com/questions/14561676/angularjs-and-contenteditable-two-way-binding-doesnt-work-as-expected
angular.module('becke-ch--angularjs--s0-0-0-v1-0--directive--pl--module').directive('contenteditable', function () {
return {
restrict: 'A', // only activate on element attribute
scope: {
tablemodel: '=', // a pointer to the table-model / table-data we are working on
tableFunctionHtmlModelRowColumn: '=' // the function that should be executed
// the function takes as input parameter the html of the current cell, the table-model, the row and column
// we are currently working on. And returns the modified html that we use to update the cell
// OR if nothing/undefined is returned then the cell is not updated
},
require: '?ngModel', // get a hold of NgModelController
link: function (scope, element, attrs, ngModel) {
...
// Listen for change events to enable binding
element.on('blur keyup change', function () {
becke_ch__angularjs__s0_0_0_v1_0__directive__pl__client__contenteditable_modified_element = element;
scope.$apply(read);
});
function read() {
var html = element.html();
if (attrs.stripBr && html == '<br>') {
html = '';
}
var htmlNew = scope.tableFunctionHtmlModelRowColumn(html, scope.tablemodel, attrs.row, attrs.column);
if (htmlNew) {
ngModel.$setViewValue(htmlNew);
}
}
…
}
};
});
becke-ch--diff--s0-0-1-v1-0--singlepage--pl--client--main.html:
<div contenteditable ng-model="resultTableRowJson.fromToHtmlText[0]"
tablemodel="diffOutput.resultTableRowsJson" row="{{$index}}" column="0"
table-function-html-model-row-column="diffResultHtmlTableRowJson"></div>
becke-ch--angularjs--s0-0-0-v1-0--directive--pl--client--contenteditable-table.js:
becke_ch__angularjs__s0_0_0_v1_0__directive__pl__client__contenteditable_modified_element = undefined;
//contenteditable directive: http://stackoverflow.com/questions/14561676/angularjs-and-contenteditable-two-way-binding-doesnt-work-as-expected
angular.module('becke-ch--angularjs--s0-0-0-v1-0--directive--pl--module').directive('contenteditable', function () {
return {
restrict: 'A', // only activate on element attribute
scope: {
tablemodel: '=', // a pointer to the table-model / table-data we are working on
tableFunctionHtmlModelRowColumn: '=' // the function that should be executed
// the function takes as input parameter the html of the current cell, the table-model, the row and column
// we are currently working on. And returns the modified html that we use to update the cell
// OR if nothing/undefined is returned then the cell is not updated
},
require: '?ngModel', // get a hold of NgModelController
link: function (scope, element, attrs, ngModel) {
...
// Listen for change events to enable binding
element.on('blur keyup change', function (event) {
var keyCode = event.which || event.keyCode;
console.log(keyCode); element.on('blur keyup change', function () {
if (keyCode === 13) {
cursorPosition++;
}
becke_ch__angularjs__s0_0_0_v1_0__directive__pl__client__contenteditable_modified_element = element;
scope.$apply(read);
});
…
}
};
});
http://stackoverflow.com/questions/28583651/contenteditable-with-ng-model-doesnt-work
http://mehrantm.blogspot.ch/2013/10/how-make-two-way-binding-to-your.html
becke-ch--angularjs--s0-0-0-v1-0--directive--pl--client--contenteditable-table.js:
becke_ch__angularjs__s0_0_0_v1_0__directive__pl__client__contenteditable_modified_element = undefined;
//contenteditable directive: http://stackoverflow.com/questions/14561676/angularjs-and-contenteditable-two-way-binding-doesnt-work-as-expected
angular.module('becke-ch--angularjs--s0-0-0-v1-0--directive--pl--module').directive('contenteditable', function () {
return {
restrict: 'A', // only activate on element attribute
scope: {
tablemodel: '=', // a pointer to the table-model / table-data we are working on
tableFunctionHtmlModelRowColumn: '=' // the function that should be executed
// the function takes as input parameter the html of the current cell, the table-model, the row and column
// we are currently working on. And returns the modified html that we use to update the cell
// OR if nothing/undefined is returned then the cell is not updated
},
require: '?ngModel', // get a hold of NgModelController
link: function (scope, element, attrs, ngModel) {
...
if (!ngModel) return; // do nothing if no ng-model
// Specify how UI should be updated
ngModel.$render = function () {
element.html(ngModel.$viewValue || '');
if (becke_ch__angularjs__s0_0_0_v1_0__directive__pl__client__contenteditable_modified_element == element) {
var windowSelection = window.getSelection();
if (windowSelection && windowSelection.rangeCount > 0) {
if (topNodeCursorPosition >= 0) {
//special handling on top node i.e. dealing with empty new-lines
var range = document.createRange();
var sel = window.getSelection();
range.setStart(element[0], topNodeCursorPosition);
range.collapse(true);
sel.removeAllRanges();
sel.addRange(range);
} else {
setCursor(element[0], cursorPosition);
}
}
}
};
// Listen for change events to enable binding
element.on('blur keyup change', function () {
becke_ch__angularjs__s0_0_0_v1_0__directive__pl__client__contenteditable_modified_element = element;
scope.$apply(read);
});
…
}
};
});
becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client--main.html:
<div contenteditable ng-model="resultTableRowJson.fromToHtmlText[0]"
tablemodel="diffOutput.resultTableRowsJson" row="{{$index}}" column="0"
table-function-html-model-row-column="diffResultHtmlTableRowJson"></div>
ERROR: Error: [$injector:unpr] Unknown provider: trust_htmlFilterProvider <- trust_htmlFilter
angular.js:12546 Error: [$injector:unpr] Unknown provider: trust_htmlFilterProvider <- trust_htmlFilter
http://errors.angularjs.org/1.5.0-beta.1/$injector/unpr?p0=trust_htmlFilterProvider%20%3C-%20trust_htmlFilter
at http://localhost:8080/becke-ch--diff--s0-0-v1--singlepage--pl--server-1.1/lib/angular.js:68:12
…
SOLUTION: https://docs.angularjs.org/error/$injector/unpr
Instead of:
angular.module('becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client', []).directive('contenteditable', function () {…
Use:
angular.module('becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client').directive('contenteditable', function () {...
…
An unknown provider error can also be caused by accidentally redefining a module using the angular.module API, as shown in the following example.
angular.module('myModule', [])
.service('myCoolService', function () { /* ... */ });
angular.module('myModule', [])
// myModule has already been created! This is not what you want!
.directive('myDirective', ['myCoolService', function (myCoolService) {
// This directive definition throws unknown provider, because myCoolService
// has been destroyed.
}]);
To fix this problem, make sure you only define each module with the angular.module(name, [requires]) syntax once across your entire project. Retrieve it for subsequent use with angular.module(name). The fixed example is shown below.
angular.module('myModule', [])
.service('myCoolService', function () { /* ... */ });
angular.module('myModule')
.directive('myDirective', ['myCoolService', function (myCoolService) {
// This directive definition does not throw unknown provider.
}]);
...
ERROR: angular.js:12546 Error: [$rootScope:inprog] $digest already in progress
http://errors.angularjs.org/1.5.0-beta.1/$rootScope/inprog?p0=%24digest
at angular.js:68
at beginPhase (angular.js:16415)
at Scope.$apply (angular.js:16156)
at HTMLDivElement.<anonymous> (becke-ch--angularjs--s0-0-0-v1-0--directive--pl--client--contenteditable-table.js:54)
at HTMLDivElement.eventHandler (angular.js:3299)
at setCursor (becke-ch--angularjs--s0-0-0-v1-0--directive--pl--client--contenteditable-table.js:148)
at setCursor (becke-ch--angularjs--s0-0-0-v1-0--directive--pl--client--contenteditable-table.js:168)
at ngModel.$render (becke-ch--angularjs--s0-0-0-v1-0--directive--pl--client--contenteditable-table.js:42)
at Object.ngModelWatch (angular.js:25508)
at Scope.$digest (angular.js:15887)
ISSUE: The issue here is that one directive cell influences the other and they both fire a $digest simultaneously!
SOLUTION: Introduce global locking variable:
becke-ch--angularjs--s0-0-0-v1-0--directive--pl--client--contenteditable-table.js:
becke_ch__angularjs__s0_0_0_v1_0__directive__pl__client__contenteditable_modified_element = undefined;
//contenteditable directive: http://stackoverflow.com/questions/14561676/angularjs-and-contenteditable-two-way-binding-doesnt-work-as-expected
angular.module('becke-ch--angularjs--s0-0-0-v1-0--directive--pl--module').directive('contenteditable', function () {
return {
restrict: 'A', // only activate on element attribute
scope: {
tablemodel: '=', // a pointer to the table-model / table-data we are working on
tableFunctionHtmlModelRowColumn: '=' // the function that should be executed
// the function takes as input parameter the html of the current cell, the table-model, the row and column
// we are currently working on. And returns the modified html that we use to update the cell
// OR if nothing/undefined is returned then the cell is not updated
},
require: '?ngModel', // get a hold of NgModelController
link: function (scope, element, attrs, ngModel) {
…
// Specify how UI should be updated
ngModel.$render = function () {
element.html(ngModel.$viewValue || '');
if (becke_ch__angularjs__s0_0_0_v1_0__directive__pl__client__contenteditable_modified_element == element) {
var windowSelection = window.getSelection();
if (windowSelection && windowSelection.rangeCount > 0) {
if (topNodeCursorPosition >= 0) {
//special handling on top node i.e. dealing with empty new-lines
var range = document.createRange();
var sel = window.getSelection();
range.setStart(element[0], topNodeCursorPosition);
range.collapse(true);
sel.removeAllRanges();
sel.addRange(range);
} else {
setCursor(element[0], cursorPosition);
}
}
// $timeout(function () {
// // anything you want can go here and will safely be run on the next digest.
// });
}
};
...
// Listen for change events to enable binding
element.on('blur keyup change', function (event) {
var keyCode = event.which || event.keyCode;
becke_ch__angularjs__s0_0_0_v1_0__directive__pl__client__contenteditable_modified_element = element;
scope.$apply(read);
});
…
}
};
});
https://docs.angularjs.org/api/ng/filter/json
Allows you to convert a JavaScript object into JSON string.
This filter is mostly useful for debugging. When using the double curly notation the binding is automatically converted to JSON.
Usage
In HTML Template Binding
{{ json_expression | json : spacing}}
In JavaScript
$filter('json')(object, spacing)
Arguments
•object: Any JavaScript object (including arrays and primitive types) to filter.
•spacing: number: The number of spaces to use per indentation, defaults to 2.
Returns: string: JSON string.
Deserializes a JSON string.
Usage
angular.fromJson(json);
Arguments
json: string: JSON string to deserialize.
Returns: Object, Array, string, number: Deserialized JSON string.
http://stackoverflow.com/questions/3020094/how-should-i-escape-strings-in-json
http://www.ietf.org/rfc/rfc4627.txt
...
Escape it according to the RFC. JSON is pretty liberal: The only characters you must escape are \, ", and control codes (anything less than U+0020).
This structure of escaping is specific to JSON. You'll need a JSON specific function. All of the escapes can be written as \uXXXX where XXXX is the UTF-16 code unit¹ for that character. There are a few shortcuts, such as \\, which work as well. (And they result in a smaller and clearer output.)
For full details, see the RFC.
¹JSON's escaping is built on JS, so it uses \uXXXX, where XXXX is a UTF-16 code unit. For code points outside the BMP, this means encoding surrogate pairs, which can get a bit hairy. (Or, you can just output the character directly, since JSON's encoded for is Unicode text, and allows these particular characters.)
...
public static String getJsonString(String str) {
if (str == null) {
return null;
}
// str = str.replace("\\", "\\\\");
// str = str.replace("\"", "\\\"");
// str = str.replace("\n", "");
// return str;
StringBuilder stringBuilder = new StringBuilder();
for (int i = 0; i < str.length(); i++) {
switch (str.charAt(i)) {
case '\\':
stringBuilder.append("\\\\");
break;
case '"':
stringBuilder.append("\\\"");
break;
case '\n':
break;
default:
if (str.charAt(i) <= 20) {
stringBuilder.append("\\u").append(String.format("%04d", ((int) str.charAt(i))));
} else {
stringBuilder.append(str.charAt(i));
}
}
}
return stringBuilder.toString();
}
Converting characters to integers in Java
http://stackoverflow.com/questions/19388037/converting-characters-to-integers-in-java
http://stackoverflow.com/questions/275711/add-leading-zeroes-to-number-in-java
stringBuilder.append("\\u").append(String.format("%04d", ((int) str.charAt(i))));
https://github.com/eu81273/angular.treeview
http://jsfiddle.net/eu81273/8LWUc/
http://stackoverflow.com/questions/15847726/is-there-a-simple-way-to-use-button-to-navigate-page-as-a-link-does-in-angularjs
http://www.w3schools.com/jsref/prop_loc_href.asp
...
<button ng-click="download('unifiedDiff')">download</button>
$scope.download = function (format){
location.href = downloadUrl+'?sessionId='+$scope.sessionId[0]+'&format='+format;
};
...
http://stackoverflow.com/questions/23648458/call-angularjs-function-using-jquery-javascript
http://stackoverflow.com/questions/18758997/call-angular-function-with-jquery
HTML:
<html lang="en" ng-app="becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client">
<head>
...
<script language="JavaScript" src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0-beta.1/angular.min.js" type="text/javascript"></script>
...
</head>
<body id="diffControllerId" ng-controller="diffController" ng-keydown="keydownEvent($event)" style="font-family: Arial;">
...
</body>
</html>
AngularJS: Controller: Method:
angular.module('becke-ch--diff--s0-0-0-v1-0--singlepage--pl--client').controller('diffController', ['$scope', 'diffService', function ($scope, diffService) {
...
$scope.diffFromTo = function (diffAction,fileFrom,fileTo) {
$scope.diffInput.fileFrom = fileFrom;
$scope.diffInput.fileTo = fileTo;
$scope.diff(diffAction);
};
...
}]);
Java-Script (JavaFX):
...
webEngine.getLoadWorker().stateProperty().addListener(new ChangeListener<Worker.State>() {
@Override
public void changed(ObservableValue<? extends Worker.State> observableValue, Worker.State state, Worker.State newState) {
if (newState == Worker.State.SUCCEEDED) {
JSObject jsobj = (JSObject) webEngine.executeScript("window");
jsobj.setMember("java", new Bridge(primaryStage));
webEngine.executeScript("console.log = function(message)\n" +
"{\n" +
" java.log(message);\n" +
"};");
File f;
String leftFileCmd = getParameters().getNamed().get(LEFT_FILE_CMD);
if (leftFileCmd != null) {
f = new File(leftFileCmd);
if (f.canRead()) {
Preferences.userRoot().node(USER_PREFERENCES_ROOT).put(LEFT_FILE, f.getParent());
} else {
leftFileCmd = null;
}
}
String rightFileCmd = getParameters().getNamed().get(RIGHT_FILE_CMD);
if (rightFileCmd != null) {
f = new File(rightFileCmd);
if (f.canRead()) {
Preferences.userRoot().node(USER_PREFERENCES_ROOT).put(RIGHT_FILE, f.getParent());
} else {
rightFileCmd = null;
}
}
if(leftFileCmd!=null & rightFileCmd!=null){
webEngine.executeScript("angular.element(document.getElementById('diffControllerId')).scope()" +
".diffFromTo('diffFiles','"+leftFileCmd+"','"+rightFileCmd+"');");
webEngine.executeScript("angular.element(document.getElementById('diffControllerId')).scope()" +
".$apply();");
}
}
}
});
ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
URL location = classLoader.getResource("view/becke-ch--diff--s0-0-1-v1-0--singlepage--pl--client--main.html");
webEngine.load(location.toString());
...
$apply(): The final invocation of “$apply()” is very important in JavaFX otherwise the AngularJS method is not correctly invoked!
https://uncorkedstudios.com/blog/multipartformdata-file-upload-with-angularjs
HTML:
<div ng-controller="diffController">
<td><input type="file" file-model="diffInput.fileFrom"/></td>
<td><input type="file" file-model="diffInput.fileTo"/></td>
</div>
JavaScript:
myApp.directive('fileModel', ['$parse', function ($parse) {
return {
restrict: 'A',
link: function (scope, element, attrs) {
var model = $parse(attrs.fileModel);
var modelSetter = model.assign;
element.bind('change', function () {
scope.$apply(function () {
modelSetter(scope, element[0].files[0]);
});
});
}
};
}]);
diffApp.service('diffService', ['$http', function ($http) {
this.post = function (sessionId, diffOption, securityQuestion, diffInput, diffOutput, url,
showProgressIcon) {
if (!diffInput.diffAction) {
return;
}
var fd = new FormData();
fd.append('sessionId', sessionId[0]);
fd.append('lineFilterPatternFrom', diffOption.lineFilterPatternFrom);
fd.append('lineFilterPatternTo', diffOption.lineFilterPatternTo);
fd.append('lineFilterCapturingGroupsFrom', diffOption.lineFilterCapturingGroupsFrom);
fd.append('lineFilterCapturingGroupsTo', diffOption.lineFilterCapturingGroupsTo);
fd.append('lineFilterCapturingGroupsActionFrom', diffOption.lineFilterCapturingGroupsActionFrom);
fd.append('lineFilterCapturingGroupsActionTo', diffOption.lineFilterCapturingGroupsActionTo);
fd.append('overallFilterPatternFrom', diffOption.overallFilterPatternFrom);
fd.append('overallFilterPatternTo', diffOption.overallFilterPatternTo);
fd.append('overallFilterCapturingGroupsFrom', diffOption.overallFilterCapturingGroupsFrom);
fd.append('overallFilterCapturingGroupsTo', diffOption.overallFilterCapturingGroupsTo);
fd.append('overallFilterCapturingGroupsActionFrom', diffOption.overallFilterCapturingGroupsActionFrom);
fd.append('overallFilterCapturingGroupsActionTo', diffOption.overallFilterCapturingGroupsActionTo);
fd.append('secureQuestionResult', securityQuestion.secureQuestionResult);
if (diffInput.diffAction == 'diffText') {
fd.append('fromText', diffInput.fromText);
fd.append('toText', diffInput.toText);
diffOutput.treedataFrom[0] = undefined;
diffOutput.treedataTo[0] = undefined;
} else if (diffInput.diffAction == 'diffFiles') {
fd.append('fileFrom', diffInput.fileFrom);
fd.append('fileTo', diffInput.fileTo);
diffOutput.treedataFrom[0] = undefined;
diffOutput.treedataTo[0] = undefined;
} else if (diffInput.diffAction == 'diffTreeEntry') {
fd.append('relativePath', diffInput.relativePath);
} else {
return;
}
$http.post(url, fd, {
transformRequest: angular.identity,
headers: {'Content-Type': undefined}
})
.then(function successCallback(response) {
sessionId[0] = response.data['sessionId'];
securityQuestion.leftOperand = response.data['secureQuestionOperandLeft'];
securityQuestion.operator = response.data['secureQuestionOperation'];
securityQuestion.rightOperand = response.data['secureQuestionOperandRight'];
diffOutput.message = response.data['messageResult'];
diffOutput.html = response.data['htmlResult'];
if (response.data['messageResult']) {
diffOutput.treedataFrom[0] = undefined;
diffOutput.treedataTo[0] = undefined;
}
if (response.data['fileEntryLinkedJsonFrom']) {
diffOutput.treedataFrom[0] = response.data['fileEntryLinkedJsonFrom'][0];
//treeFrom.calculateTreeNavigationStructure();
diffOutput.treeFrom.calculateTreeNavigationStructure();
}
if (response.data['fileEntryLinkedJsonTo']) {
diffOutput.treedataTo[0] = response.data['fileEntryLinkedJsonTo'][0];
//treeTo.calculateTreeNavigationStructure();
diffOutput.treeTo.calculateTreeNavigationStructure();
}
showProgressIcon[0] = false;
}
, function errorCallback(response) {
diffOutput.message = response.statusText;
showProgressIcon[0] = false;
});
};
myApp.controller('myCtrl', ['$scope', 'fileUpload', function ($scope, fileUpload) {
$scope.diff = function (diffAction) {
$scope.showProgressIcon[0] = true;
$scope.diffInput.diffAction = diffAction;
$scope.diffOutput.treeFrom = $scope.treeFrom;
$scope.diffOutput.treeTo = $scope.treeTo;
diffService.post($scope.sessionId, $scope.diffOption, $scope.securityQuestion,
$scope.diffInput, $scope.diffOutput, $scope.url, $scope.showProgressIcon);
};
$http: session: When uploading using $http service the session construct is not working:
myApp.service('fileUpload', ['$http', function ($http) {
this.uploadFileToUrl = function (file, uploadUrl) {
var fd = new FormData();
fd.append('text','this is some text');
fd.append('file', file);
$http.post(uploadUrl, fd, {
transformRequest: angular.identity,
headers: {'Content-Type': undefined}
})
.success(function (data) {
console.log('success');
console.log(data);
})
.error(function () {
console.log('error');
});
}
}]);
Servlet: Session:
Integer counter = (Integer) req.getSession().getAttribute("counter");
if(counter == null){
counter = 1;
req.getSession().setAttribute("counter", counter);
} else {
counter ++;
System.out.println("counter" + counter);
}
Instead create an own session store using static variables:
String sessionId = req.getParameter("sessionId");
Map<String, Object> session = SESSION_STORE.get(sessionId);
if (sessionId == null || session == null) {
sessionId = UUID.randomUUID().toString();
session = new HashMap<String, Object>();
SESSION_STORE.put(sessionId, session);
}
Integer counter = (Integer) session.get("counter");
if (counter == null) {
System.out.println("Initialize counter");
counter = 1;
session.put("counter", counter);
} else {
counter++;
System.out.println("counter" + counter);
}
AngularJS:
myApp.service('fileUpload', ['$http', function ($http) {
this.uploadFileToUrl = function (sessionId, file, uploadUrl) {
var fd = new FormData();
fd.append('sessionId',sessionId[0]);
fd.append('text','this is some text');
fd.append('file', file);
$http.post(uploadUrl, fd, {
transformRequest: angular.identity,
headers: {'Content-Type': undefined}
})
.success(function (data) {
console.log('success');
sessionId[0] = data['sessionId'];
})
.error(function () {
console.log('error');
});
}
}]);
AngularJS: JavaScript: Issue Client Side: XMLHttpRequest cannot load http://localhost:8080/becke-ch--test--s0-0-v1--json--sl-1.0/jsonservice. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://localhost:63342' is therefore not allowed access.
myApp.controller('jsonController', function ($scope, $http) {
//myApp.controller('jsonController', function ($scope) {
$http.get('http://localhost:8080/becke-ch--test--s0-0-v1--json--sl-1.0/jsonservice').success(function (data) {
$scope.phones = data;
});
// $http({method: 'GET', url: 'http://localhost:8080/becke-ch--test--s0-0-v1--json--sl-1.0/jsonservice',
// headers:{
// 'Access-Control-Allow-Origin': '*',
// 'Access-Control-Allow-Methods': 'GET, POST, PUT, DELETE, OPTIONS',
// 'Access-Control-Allow-Headers': 'Content-Type, X-Requested-With',
// 'X-Random-Shit':'123123123'
// }})
// .success(function(d){ console.log( "yay" ); })
// .error(function(d){ console.log( "nope" ); });
});
SOLUTION: The solution here was to add a header on the server side to allow CORS - details see document “becke-ch--java--s0-0-v1-0”
The approach to fix the header on Client Side DID NOT WORK! I.e. the following apporaches were a waste of time:
$http({method: 'GET', url: 'http://localhost:8080/becke-ch--test--s0-0-v1--json--sl-1.0/jsonservice',
headers:{
'Access-Control-Allow-Origin': '*',
'Access-Control-Allow-Methods': 'GET, POST, PUT, DELETE, OPTIONS',
'Access-Control-Allow-Headers': 'Content-Type, X-Requested-With',
'X-Random-Shit':'123123123'
}})
.success(function(d){ console.log( "yay" ); })
.error(function(d){ console.log( "nope" ); });
Respective:
myApp.config(['$httpProvider', function($httpProvider) {
$httpProvider.defaults.useXDomain = true;
delete $httpProvider.defaults.headers.common['X-Requested-With'];
}
]);
“SOLUTION” (not recommended): Disable CORS in Web-Browser:
:~$ /opt/google/chrome/chrome --disable-web-security
http://jimfrenette.com/2015/04/angularjs-version-2/
At ng-conf 2015 last month it was announced that AngularJS 1.X will continue to reside at angularjs.org and Angular 2.0 will be hosted at angular.io. The new version of Angular is not a major update, it is a complete rewrite.
Quickstart: Typescript: https://angular.io/docs/ts/latest/quickstart.html
Alternatively you can use Java-Script: https://angular.io/docs/js/latest/quickstart.html
Typescript: Typescript is probably the best way to develop larger Java-Script applications!
In the remaining chapters we will try to develop Angular 2 using typescript!
There are 2 different ways to perform the setup: Quickstart and CLI. I first started with the quickstart but then encountered issues with deployment and therefore decided to go with CLI. BUT with CLI I encountered issues during setup: “Project name "becke-ch--regex--s0-0-v1--homepage--pl--client" is not valid. New project names must start with a letter, and must contain only alphanumeric characters or dashes. When adding a dash the segment after the dash must also start with a letter.”. And therefore I finally decided to go with Quickstart.
Quickstart Setup:
1.Download & Extract https://github.com/angular/quickstart/archive/master.zip
2.Delete the non essential files:
a.xargs rm -rf < non-essential-files.osx.txt
i.“.git”: The .git directory only exists if we clone it. If we download then there is no such directory.
ii.“.gitignore”: Actually I would not delete this file because it tells which file should not be removed!
iii.“LICENSE”: We can remove the license file respective replace it with our own license file or alternatively update the package.json file with “{ "license": "UNLICENSED"}”
iv.“src/favicon.ico”: There is a bug in the “non-essential-files.osx.txt” file. The favicon.ico is removed in the wrong location.
v.“.travis.yml”, “bs-config.e2e.json”, “CHANGELOG.md”, “e2e”, “favicon.ico”, “karma.conf.js”, “karma-test-shim.js”, “non-essential-files.txt”, “protractor.config.js”, “README.md”: These files can be deleted without any further comment.
b.rm src/app/*.spec*.ts
c.rm non-essential-files.osx.txt
CLI Setup:
1.Verify that you are running at least node 6.9.x and npm 3.x.x by running node -v and npm -v in a terminal/console window. Older versions produce errors, but newer versions are fine.
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:~$ node -v
v4.2.4
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:~$ npm -v
3.5.2
2.Update respective install new version according to chapter 3.2 (and don’t forget to update /etc/profiles and restart).
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:~$ node -v
v6.10.1
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:~$ npm -v
3.10.10
3.Install the Angular CLI globally: npm install -g @angular/cli
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:~$ npm install -g @angular/cli
/media/disk-ssd--s0-v1/tool/node-v6.10.1-linux-x64/bin/ng -> /media/disk-ssd--s0-v1/tool/node-v6.10.1-linux-x64/lib/node_modules/@angular/cli/bin/ng
> node-sass@4.5.2 install /media/disk-ssd--s0-v1/tool/node-v6.10.1-linux-x64/lib/node_modules/@angular/cli/node_modules/node-sass
> node scripts/install.js
Downloading binary from https://github.com/sass/node-sass/releases/download/v4.5.2/linux-x64-48_binding.node
Download complete ] - :
Binary saved to /media/disk-ssd--s0-v1/tool/node-v6.10.1-linux-x64/lib/node_modules/@angular/cli/node_modules/node-sass/vendor/linux-x64-48/binding.node
Caching binary to /home/raoul-becke--s0-v1/.npm/node-sass/4.5.2/linux-x64-48_binding.node
> node-sass@4.5.2 postinstall /media/disk-ssd--s0-v1/tool/node-v6.10.1-linux-x64/lib/node_modules/@angular/cli/node_modules/node-sass
> node scripts/build.js
Binary found at /media/disk-ssd--s0-v1/tool/node-v6.10.1-linux-x64/lib/node_modules/@angular/cli/node_modules/node-sass/vendor/linux-x64-48/binding.node
Testing binary
Binary is fine
/media/disk-ssd--s0-v1/tool/node-v6.10.1-linux-x64/lib
└─┬ @angular/cli@1.0.0
├── @ngtools/json-schema@1.0.5
├─┬ @ngtools/webpack@1.3.0
│ ├── enhanced-resolve@3.1.0
…
├── webpack-merge@2.6.1
└── zone.js@0.7.8
npm WARN optional SKIPPING OPTIONAL DEPENDENCY: fsevents@^1.0.0 (node_modules/@angular/cli/node_modules/chokidar/node_modules/fsevents):
npm WARN notsup SKIPPING OPTIONAL DEPENDENCY: Unsupported platform for fsevents@1.1.1: wanted {"os":"darwin","arch":"any"} (current: {"os":"linux","arch":"x64"})
Node.js and npm are essential to modern web development with Angular and other platforms. Node powers client development and build tools. The npm package manager, itself a node application, installs JavaScript libraries.
npm is a popular package manager and Angular application developers rely on it to acquire and manage the libraries their apps require.
We specify the packages we need in an npm package.json file.
To install the package manager NPM (and Node.js) - follow instructions in chapter 3.
Quickstart Setup:
1.Copy the (essential) files from the initial setup (see previous chapter) into the the project folder:
2.Edit the package.json file. IntelliJ: When using IntelliJ then TSC (TypeScript) is not really needed because it is already built into intellij – but nevertheless it does not harm.
{
"name": "becke-ch--PRODUCT--sX-Y-vZ--USECASE--pl--client",
"version": "1.0.0",
"description": "becke-ch--PRODUCT--sX-Y-vZ--USECASE--pl--client description",
"scripts": {
"build": "tsc -p src/",
"build:watch": "tsc -p src/ -w",
"build:e2e": "tsc -p e2e/",
"serve": "lite-server -c=bs-config.json",
"serve:e2e": "lite-server -c=bs-config.e2e.json",
"prestart": "npm run build",
"start": "concurrently \"npm run build:watch\" \"npm run serve\"",
"pree2e": "npm run build:e2e",
"e2e": "concurrently \"npm run serve:e2e\" \"npm run protractor\" --kill-others --success first",
"preprotractor": "webdriver-manager update",
"protractor": "protractor protractor.config.js",
"pretest": "npm run build",
"test": "concurrently \"npm run build:watch\" \"karma start karma.conf.js\"",
"pretest:once": "npm run build",
"test:once": "karma start karma.conf.js --single-run",
"lint": "tslint ./src/**/*.ts -t verbose"
},
"keywords": [becke-ch--PRODUCT--sX-Y-vZ--USECASE--pl--client keywords],
"author": "Raoul Becke <PRODUCT--sX-vZ@becke.ch> (http://becke.ch/tool/becke-ch--PRODUCT--sX-vZ/)",
"license": "UNLICENSED",
"dependencies": {
"@angular/common": "~4.0.0",
"@angular/compiler": "~4.0.0",
"@angular/core": "~4.0.0",
"@angular/forms": "~4.0.0",
"@angular/http": "~4.0.0",
"@angular/platform-browser": "~4.0.0",
"@angular/platform-browser-dynamic": "~4.0.0",
"@angular/router": "~4.0.0",
"angular-in-memory-web-api": "~0.3.0",
"systemjs": "0.19.40",
"core-js": "^2.4.1",
"rxjs": "5.0.1",
"zone.js": "^0.8.4"
},
"devDependencies": {
"concurrently": "^3.2.0",
"lite-server": "^2.2.2",
"typescript": "~2.1.0",
"canonical-path": "0.0.2",
"tslint": "^3.15.1",
"lodash": "^4.16.4",
"jasmine-core": "~2.4.1",
"karma": "^1.3.0",
"karma-chrome-launcher": "^2.0.0",
"karma-cli": "^1.0.1",
"karma-jasmine": "^1.0.2",
"karma-jasmine-html-reporter": "^0.2.2",
"protractor": "~4.0.14",
"rimraf": "^2.5.4",
"@types/node": "^6.0.46",
"@types/jasmine": "2.5.36"
},
"repository": {
"url": "file:///ws/tool|app/becke-ch--PRODUCT--sX-vZ",
"type": "git"
}
}
3.Run “yarn” (or “npm install”) to install all packages used for development
The size used for development (devDependencies) is very large! 154MB!
CLI Setup:
1.Change into the parent of the project directory
2.Generate a new project and skeleton application by running the following commands: ng new becke-ch—PRODUCT--sX-Y-vZ--USECASE--pl--client
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij$ ng new becke-ch--regex--s0-0-v1--homepage--pl--client
Project name "becke-ch--regex--s0-0-v1--homepage--pl--client" is not valid. New project names must start with a letter, and must contain only alphanumeric characters or dashes. When adding a dash the segment after the dash must also start with a letter.
becke-ch--regex--s0-0-v1--homepage--pl--client
^
And due to this error we fall back again to quickstart sample! I’ve reported this problem here: https://github.com/angular/angular-cli/issues/3680
Nevertheless if we would have proceeded we would have got the following:
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij$ ng new becke-ch-regex-s00-v1-homepage-pl-client
installing ng
create .editorconfig
create README.md
create src/app/app.component.css
create src/app/app.component.html
create src/app/app.component.spec.ts
create src/app/app.component.ts
create src/app/app.module.ts
create src/assets/.gitkeep
create src/environments/environment.prod.ts
create src/environments/environment.ts
create src/favicon.ico
create src/index.html
create src/main.ts
create src/polyfills.ts
create src/styles.css
create src/test.ts
create src/tsconfig.app.json
create src/tsconfig.spec.json
create src/typings.d.ts
create .angular-cli.json
create e2e/app.e2e-spec.ts
create e2e/app.po.ts
create e2e/tsconfig.e2e.json
create .gitignore
create karma.conf.js
create package.json
create protractor.conf.js
create tsconfig.json
create tslint.json
Directory is already under version control. Skipping initialization of git.
Installing packages for tooling via npm.
Installed packages for tooling via npm.
You can `ng set --global packageManager=yarn`.
Project 'becke-ch-regex-s00-v1-homepage-pl-client' successfully created.
All guides and cookbooks have at least 3 core files:
•src/app/app.component.ts: It is the root component of what will become a tree of nested components as the application evolves.
•src/app/app.module.ts: Defines AppModule, the root module that tells Angular how to assemble the application. Right now it declares only the AppComponent. Soon there will be more components to declare.
•src/main.ts: Compiles the application with the JIT compiler and bootstraps the application's main module (AppModule) to run in the browser. The JIT compiler is a reasonable choice during the development of most projects and it's the only viable choice for a sample running in a live-coding environment like Plunker. You'll learn about alternative compiling and deployment options later in the documentation.
Files outside src/ concern building, deploying, and testing your app. They include configuration files and external dependencies.
Files inside src/ "belong" to your app. Add new Typescript, HTML and CSS files inside the src/ directory, most of them inside src/app, unless told to do otherwise.
The Component is the most fundamental of Angular concepts. A component manages a view - a piece of the web page where we display information to the user and respond to user feedback.
Technically, a component is a class that controls a view template. We'll write a lot of them as we build Angular apps. This is our first attempt so we'll keep it ridiculously simple.
Create an application source sub-folder
We like to keep our application code in a sub-folder off the root called app/. Execute the following command in the console window.
mkdir app
cd app
Add the component file
Now add a file named app.component.ts and paste the following lines:
app/app.component.ts
import {Component} from '@angular/core';
@Component({
selector: 'my-app',
template: '<h1>Hello {{name}}</h1>'
})
export class AppComponent { name = 'Angular'; }
Let's review this file in detail, starting at the bottom where we define a class.
The Component class
At the bottom of the file is an empty, do-nothing class named AppComponent. When we're ready to build a substantive application, we can expand this class with properties and application logic. Our AppComponent class is empty because we don't need it to do anything in this QuickStart.
Modules
Angular apps are modular. They consist of many files each dedicated to a purpose.
Most application files export one thing such as a component. Our app.component file exports the AppComponent.
app/app.component.ts (export)
export class AppComponent { name = 'Angular'; }
The act of exporting turns the file into a module. The name of the file (without extension) is usually the name of the module. Accordingly, 'app.component' is the name of our first module.
A more sophisticated application would have child components that descended from AppComponent in a visual tree. A more sophisticated app would have more files and modules, at least as many as it had components.
Quickstart isn't sophisticated; one component is all we need. Yet modules play a fundamental organizational role in even this small app.
Modules rely on other modules. In TypeScript Angular apps, when we need something provided by another module, we import it. When another module needs to refer to AppComponent, it imports the AppComponent symbol like this:
app/boot.ts (import)
import {AppComponent} from './app.component'
Angular is also modular. It is a collection of library modules. Each library is itself a module made up of several, related feature modules.
When we need something from Angular, we import it from an Angular library module. We need something from Angular right now to help us define metadata about our component.
Component Metadata
A class becomes an Angular component when we give it metadata. Angular needs the metadata to understand how to construct the view and how the component interacts with other parts of the application.
We define a component's metadata with the Angular Component function. We access that function by importing it from the primary Angular library,angular2/core.
app/app.component.ts (import)
import {Component} from '@angular/core';
In TypeScript we apply that function to the class as a decorator by prefixing it with the @ symbol and invoking it just above the component class:
app/app.component.ts (metadata)
@Component({
selector: 'my-app',
template: '<h1>My First Angular 2 App</h1>'
})
@Component tells Angular that this class is an Angular component. The configuration object passed to the @Component method has two fields, a selector and a template.
The selector specifies a simple CSS selector for a host HTML element named my-app. Angular creates and displays an instance of our AppComponent wherever it encounters a my-app element in the host HTML.
Remember the my-app selector! We'll need that information when we write our index.html
The template property holds the component's companion template. A template is a form of HTML that tells Angular how to render a view. Our template is a single line of HTML announcing "My First Angular App".
Now we need something to tell Angular to load this component.
1.npm start
This command runs the TypeScript compiler in "watch mode", recompiling automatically when the code changes. The command simultaneously launches the app in a browser and refreshes the browser when the code changes.
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--homepage--pl--client$ npm start
> becke-ch--regex--s0-0-v1--homepage--pl--client@1.0.0 prestart /media/disk-ssd--s0-v1/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--homepage--pl--client
> npm run build
> becke-ch--regex--s0-0-v1--homepage--pl--client@1.0.0 build /media/disk-ssd--s0-v1/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--homepage--pl--client
> tsc -p src/
> becke-ch--regex--s0-0-v1--homepage--pl--client@1.0.0 start /media/disk-ssd--s0-v1/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--homepage--pl--client
> concurrently "npm run build:watch" "npm run serve"
[0]
[0] > becke-ch--regex--s0-0-v1--homepage--pl--client@1.0.0 build:watch /media/disk-ssd--s0-v1/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--homepage--pl--client
[0] > tsc -p src/ -w
[0]
[1]
[1] > becke-ch--regex--s0-0-v1--homepage--pl--client@1.0.0 serve /media/disk-ssd--s0-v1/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--homepage--pl--client
[1] > lite-server -c=bs-config.json
[1]
[1] ** browser-sync config **
[1] { injectChanges: false,
[1] files: [ './**/*.{html,htm,css,js}' ],
[1] watchOptions: { ignored: 'node_modules' },
[1] server:
[1] { baseDir: 'src',
[1] middleware: [ [Function], [Function] ],
[1] routes: { '/node_modules': 'node_modules' } } }
[1] [BS] Access URLs:
[1] -------------------------------------
[1] Local: http://localhost:3000
[1] External: http://10.255.8.221:3000
[1] -------------------------------------
[1] UI: http://localhost:3001
[1] UI External: http://10.255.8.221:3001
[1] -------------------------------------
[1] [BS] Serving files from: src
[1] [BS] Watching files...
[1] 17.04.01 21:46:39 200 GET /index.html
[1] 17.04.01 21:46:39 200 GET /styles.css
[1] 17.04.01 21:46:39 200 GET /core-js/client/shim.min.js
…
http://www.codelord.net/2015/09/10/angular-2-migration-path-what-we-know/
ES5, ES6 and TypeScript: The core team highly recommends doing Angular 2 in TypeScript. How hard will the conversion be? What will happen to those of us that decide to stay with ES5/6? They say all options will work, but we haven’t seen a lot of love for these setups yet.
https://angular.io/docs/ts/latest/quickstart.html
We must guide the TypeScript compiler with very specific settings.
Add a tsconfig.json file to the project folder and copy/paste the following:
"compilerOptions": {
"target": "ES5",
"module": "system",
"moduleResolution": "node",
"sourceMap": true,
"emitDecoratorMetadata": true,
"experimentalDecorators": true,
"removeComments": false,
"noImplicitAny": false
},
"exclude": [
"node_modules"
]
}
Add a new file , boot.ts, to the app/ folder as follows:
app/boot.ts
import {bootstrap} from 'angular2/platform/browser'
import {AppComponent} from './app.component'
bootstrap(AppComponent);
We need two things to launch the application:
Angular's browser bootstrap function
The application root component that we just wrote.
We import both. Then we call bootstrap, passing in the root component type, AppComponent.
Learn why we import bootstrap from angular2/platform/browser and why we create a separate boot.ts file in the appendix below.
We've asked Angular to launch the app in a browser with our component at the root. Where will Angular put it?
Angular displays our application in a specific location on our index.html. It's time to create that file.
We won't put our index.html in the app/ folder. We'll locate it up one level, in the project root folder.
cd ..
Now create theindex.html file and paste the following lines:
index.html
<head>
<title>Angular 2 QuickStart</title>
<!-- 1. Load libraries -->
<script src="node_modules/angular2/bundles/angular2-polyfills.js"></script>
<script src="node_modules/systemjs/dist/system.src.js"></script>
<script src="node_modules/rxjs/bundles/Rx.js"></script>
<script src="node_modules/angular2/bundles/angular2.dev.js"></script>
<!-- 2. Configure SystemJS -->
<script>
System.config({
packages: {
app: {
format: 'register',
defaultExtension: 'js'
}
}
});
System.import('app/boot')
.then(null, console.error.bind(console));
</script>
</head>
<!-- 3. Display the application -->
<body>
<my-app>Loading...</my-app>
</body>
</html>
There are three noteworthy sections of HTML:
We load the JavaScript libraries we need. angular2-polyfills.js and Rx.js are needed by Angular 2.
We configure something called System and ask it to import the boot file we just wrote.
We add the <my-app> tag in the <body>. This is where our app lives!
Something has to find and load our application modules. We're using SystemJS to do that. There are other choices and we're not saying SystemJS is the best. We like it and it works.
The specifics of SystemJS configuration are out of bounds. We'll briefly describe this particular configuration in the appendix below.
When Angular calls the bootstrap function in boot.ts, it reads the AppComponent metadata, finds the my-app selector, locates an element tag named my-app, and loads our application between those tags.
http://stackoverflow.com/questions/36155723/how-to-import-a-npm-package-in-an-angular2-component
https://medium.com/@s_eschweiler/using-external-libraries-with-angular-2-87e06db8e5d1
Create typings file: src/app/custom.typings.d.ts
Import typings file into: src/main.ts
///<reference path="./app/custom.typings.d.ts"/>
import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
import { AppModule } from './app/app.module';
platformBrowserDynamic().bootstrapModule(AppModule);
The following is not working!
<!DOCTYPE html>
<html>
<head>
<base href="/">
<!--link rel="stylesheet" media="all" type="text/css" id="default-styles"
href="http://becke.ch/data/becke-ch--style--s0-v1/style/default-styles.css"-->
<link rel="stylesheet" media="all" type="text/css" id="default-styles"
href="http://localhost/data/becke-ch--style--s0-v1/style/default-styles.css">
<!--<link rel="stylesheet" media="all" type="text/css" id="default-styles"-->
<!--href="http://becke.ch/data/becke-ch--style--s0-v1/style/default-styles.css">-->
<!--<link rel="stylesheet" media="all" type="text/css" id="custom-styles" href="styles.css">-->
<script src="node_modules/becke-ch--regex--s0-0-v1--base--pl--lib/src/becke-ch--regex--s0-0-v1--base--pl--lib.js"></script>
<script>
System.import('main.js').catch(function (err) {
console.error(err);
});
</script>
</head>
<body>
…
<my-app>Loading AppComponent content here ...</my-app>
…
</body>
</html>
src/app/app.component.ts
import {Component} from '@angular/core';
export class Replace {
str: string;
pattern: string;
flags: string;
replacementStrings: string;
replacementStringArray: string[];
}
@Component({
selector: 'my-app',
template: `"<code><input [(ngModel)]="replace.str" placeholder="string">".replace(new Regex("<input [(ngModel)]="replace.pattern" placeholder="pattern">", "<input [(ngModel)]="replace.flags" placeholder="flags">"), [<input [(ngModel)]="replace.replacementStrings" placeholder='undefined, replacementString1, undefined, replacementString3, ...'>]) <button (click)="replaceClicked()">Replace</button></code>`
//template: `hello`
})
export class AppComponent {
replace: Replace = {
str: "",
pattern: "",
flags: "",
replacementStrings: "",
replacementStringArray: []
};
replaceClicked() {
console.log('"' + this.replace.str + '".replace(new Regex(' + '"' + this.replace.pattern + '", ' + '"' + this.replace.flags + '"), [' + this.replace.replacementStrings + '])');
console.log(new Regex('([ ]*,)|([ ]*undefined[ ]*,)|([ ]*undefined[ ]*,)'));
}
}
Option A is not working!
Option A: This is the preferred method because everything is located in one place!
src/app/app.component.ts
import {Component} from '@angular/core';
import * as Regex from 'node_modules/becke-ch--regex--s0-0-v1--base--pl--lib/src/becke-ch--regex--s0-0-v1--base--pl--lib.js';
export class Replace {
str: string;
pattern: string;
flags: string;
replacementStrings: string;
replacementStringArray: string[];
}
@Component({
selector: 'my-app',
template: `"<code><input [(ngModel)]="replace.str" placeholder="string">".replace(new Regex("<input [(ngModel)]="replace.pattern" placeholder="pattern">", "<input [(ngModel)]="replace.flags" placeholder="flags">"), [<input [(ngModel)]="replace.replacementStrings" placeholder='undefined, replacementString1, undefined, replacementString3, ...'>]) <button (click)="replaceClicked()">Replace</button></code>`
//template: `hello`
})
export class AppComponent {
replace: Replace = {
str: "",
pattern: "",
flags: "",
replacementStrings: "",
replacementStringArray: []
};
replaceClicked() {
console.log('"' + this.replace.str + '".replace(new Regex(' + '"' + this.replace.pattern + '", ' + '"' + this.replace.flags + '"), [' + this.replace.replacementStrings + '])');
console.log(new Regex('([ ]*,)|([ ]*undefined[ ]*,)|([ ]*undefined[ ]*,)'));
}
}
Option B: Map Declaration in systemjs.config.js
/**
* System configuration for Angular samples
* Adjust as necessary for your application needs.
*/
System.config({
paths: {
// paths serve as alias
'npm:': 'node_modules/'
},
// map tells the System loader where to look for things
map: {
// our app is within the app folder
'app': 'app',
// angular bundles
'@angular/core': 'npm:@angular/core/bundles/core.umd.js',
'@angular/common': 'npm:@angular/common/bundles/common.umd.js',
'@angular/compiler': 'npm:@angular/compiler/bundles/compiler.umd.js',
'@angular/platform-browser': 'npm:@angular/platform-browser/bundles/platform-browser.umd.js',
'@angular/platform-browser-dynamic': 'npm:@angular/platform-browser-dynamic/bundles/platform-browser-dynamic.umd.js',
'@angular/http': 'npm:@angular/http/bundles/http.umd.js',
'@angular/router': 'npm:@angular/router/bundles/router.umd.js',
'@angular/forms': 'npm:@angular/forms/bundles/forms.umd.js',
// other libraries
'rxjs': 'npm:rxjs',
'angular-in-memory-web-api': 'npm:angular-in-memory-web-api/bundles/in-memory-web-api.umd.js',
// private libraries
'Regex': 'npm:becke-ch--regex--s0-0-v1--base--pl--lib/src/becke-ch--regex--s0-0-v1--base--pl--lib.js'
},
// packages tells the System loader how to load when no filename and/or no extension
packages: {
app: {
defaultExtension: 'js',
meta: {
'./*.js': {
loader: 'systemjs-angular-loader.js'
}
}
},
rxjs: {
defaultExtension: 'js'
}
}
});
})(this);
src/app/app.component.ts
import {Component} from '@angular/core';
import * as Regex from 'Regex';
export class Replace {
str: string;
pattern: string;
flags: string;
replacementStrings: string;
replacementStringArray: string[];
}
@Component({
selector: 'my-app',
template: `"<code><input [(ngModel)]="replace.str" placeholder="string">".replace(new Regex("<input [(ngModel)]="replace.pattern" placeholder="pattern">", "<input [(ngModel)]="replace.flags" placeholder="flags">"), [<input [(ngModel)]="replace.replacementStrings" placeholder='undefined, replacementString1, undefined, replacementString3, ...'>]) <button (click)="replaceClicked()">Replace</button></code>`
//template: `hello`
})
export class AppComponent {
replace: Replace = {
str: "",
pattern: "",
flags: "",
replacementStrings: "",
replacementStringArray: []
};
replaceClicked() {
var regex: any;
console.log('"' + this.replace.str + '".replace(new Regex(' + '"' + this.replace.pattern + '", ' + '"' + this.replace.flags + '"), [' + this.replace.replacementStrings + '])');
console.log(new Regex('([ ]*,)|([ ]*undefined[ ]*,)|([ ]*undefined[ ]*,)'));
}
}
ERROR: src/app/app.component.ts(2,19): error TS2307: Cannot find module ...
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--homepage--pl--client$ npm start
> becke-ch--regex--s0-0-v1--homepage--pl--client@1.0.0 prestart /media/disk-ssd--s0-v1/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--homepage--pl--client
> npm run build
> becke-ch--regex--s0-0-v1--homepage--pl--client@1.0.0 build /media/disk-ssd--s0-v1/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch--regex--s0-0-v1--homepage--pl--client
> tsc -p src/
src/app/app.component.ts(2,19): error TS2307: Cannot find module 'rgx'.
npm ERR! Linux 4.9.0-040900-generic
npm ERR! argv "/media/disk-ssd--s0-v1/tool/node-v6.10.1-linux-x64/bin/node" "/media/disk-ssd--s0-v1/tool/node-v6.10.1-linux-x64/bin/npm" "run" "build"
npm ERR! node v6.10.1
npm ERR! npm v3.10.10
npm ERR! code ELIFECYCLE
npm ERR! becke-ch--regex--s0-0-v1--homepage--pl--client@1.0.0 build: `tsc -p src/`
npm ERR! Exit status 2
...
SOLUTION: See chapters above! First the Typescript definitions needs to be solved!
AND the following import statement is not allowed: import * as Regex from 'node_modules/becke-ch--regex--s0-0-v1--base--pl--lib/src/becke-ch--regex--s0-0-v1--base--pl--lib.js';
ERROR: Browser: ERROR TypeError: Regex_1.default is not a constructor
ERROR TypeError: Regex_1.default is not a constructor
Stack trace:
AppComponent.prototype.replaceClicked@http://localhost:3000/app/app.component.js:37:17
View_AppComponent_0/<@ng:///AppModule/AppComponent.ngfactory.js:592:21
viewDef/handleEvent@http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:11812:98
callWithDebugContext@http://localhost:3000/node_modules/@angular/core/bundles/core.umd.js:13020:39
...
CAUSE: import Regex from 'Regex';
SOLUTION: import * as Regex from 'Regex';
import {NgModule} from '@angular/core';
import {BrowserModule} from '@angular/platform-browser';
import {FormsModule} from '@angular/forms'; // <-- NgModel lives here
import {AppComponent} from './app.component';
@NgModule({
imports: [
BrowserModule,
FormsModule // <-- import the FormsModule before binding with [(ngModel)]
],
declarations: [AppComponent],
bootstrap: [AppComponent]
})
export class AppModule {
}
src/app/app.component.ts
import {Component} from '@angular/core';
import * as Regex from 'Regex';
export class Replace {
str: string;
pattern: string;
flags: string;
replacementStrings: string;
replacementStringArray: any;
result: string;
}
@Component({
selector: 'my-app',
template: `
<code>"<textarea [(ngModel)]="replace.str" placeholder="string"></textarea>".replace(new
Regex("<input [(ngModel)]="replace.pattern" placeholder="pattern">", "<input maxlength="5" size="5" [(ngModel)]="replace.flags" placeholder="flags">"),
[<input [(ngModel)]="replace.replacementStrings" placeholder='array of replacement strings'>])
<button (click)="replaceClicked()">Replace</button><br>{{replace.result}}
</code>
`
//template: `hello`
})
export class AppComponent {
replace: Replace = {
str: "",
pattern: "",
flags: "g",
replacementStrings: "",
replacementStringArray: undefined,
result: ""
};
replaceClicked() {
var pattern: string;
var regex: any;
var match: any;
pattern = '((,)|([ ]+,)|([ ]*undefined[ ]*,)|([ ]*null[ ]*,)|([ ]*(\'|")(.*?[^\\\\])\\7[ ]*,)|(.*?,))|(($)|([ ]+$)|([ ]*undefined[ ]*$)|([ ]*null[ ]*$)|([ ]*(\'|")(.*?[^\\\\])\\16[ ]*$)|(.*?$))';
regex = new Regex(pattern, 'g');
this.replace.replacementStringArray = [];
for (var i = 0; i < match.length; i++) {
if (match[i][2] || match[i][3] || match[i][4]) {
this.replace.replacementStringArray.push(undefined);
} else if (match[i][11] === "" || match[i][12] || match[i][13]) {
this.replace.replacementStringArray.push(undefined);
break;
} else if (match[i][5]) {
this.replace.replacementStringArray.push(null);
} else if (match[i][14]) {
this.replace.replacementStringArray.push(null);
break;
} else if (match[i][8]) {
this.replace.replacementStringArray.push(match[i][8]);
} else if (match[i][17]) {
this.replace.replacementStringArray.push(match[i][17]);
break;
} else {
var errorStr = 'Error: The replacement string: [' + this.replace.replacementStrings + '] has wrong format! The array of replacement strings needs to be separated by ", " commas and the replacement strings need to be enclosed with double quote: " or single quote: \'. Empty, undefined and null replacement strings are allowed.';
console.error(errorStr);
this.replace.result = errorStr;
return;
}
}
this.replace.result = '"' + this.replace.str + '".replace(new Regex(' + '"' + this.replace.pattern + '", ' + '"' + this.replace.flags + '"), [' + this.replace.replacementStringArray + '])' + '=' + this.replace.str.replace(new Regex(this.replace.pattern, this.replace.flags), (this.replace.replacementStringArray));
}
}
Quickstart: https://angular.io/docs/ts/latest/guide/deployment.html
First time steps:
1.Create project folder in apache htdocs: mkdir .../htdocs/becke-ch--PRODUCT--sX-Y-vZ--USECASE--pl--client
Repetitive steps:
1.In the project folder: .../becke-ch--PRODUCT--sX-vZ/intellij/becke-ch--PRODUCT--sX-Y-vZ--USECASE--pl--client
a.Edit "./src/index.html":
Replace:
<base href="/">
With:
<base href="/becke-ch--PRODUCT--sX-Y-vZ--USECASE--pl--client/">
https://wiki.selfhtml.org/wiki/HTML/Kopfdaten/base
The HTML <base href="..."/> specifies a base path for resolving relative URLs to assets such as images, scripts, and style sheets. For example, given the <base href="/my/app/">, the browser resolves a URL such as some/place/foo.jpg into a server request for my/app/some/place/foo.jpg. During navigation, the Angular router uses the base href as the base path to component, template, and module files.
b.Synchronize the files: rsync -rt --include="*.js" --include="*.html" --include="*.css" --exclude="*.*" ./src/ $HTDOCS_DIR/$PROJECT_NAME/
c.Synchronize the package.json file: rsync -rt ./package.json .../htdocs/becke-ch--PRODUCT--sX-Y-vZ--USECASE--pl--client/
d.Apache: Routed apps must fallback to index.html: rsync -rt ./.htaccess .../htdocs/becke-ch--PRODUCT--sX-Y-vZ--USECASE--pl--client/
Angular apps are perfect candidates for serving with a simple static HTML server. You don't need a server-side engine to dynamically compose application pages because Angular does that on the client-side.
If the app uses the Angular router, you must configure the server to return the application's host page (index.html) when asked for a file that it does not have.
A routed application should support "deep links". A deep link is a URL that specifies a path to a component inside the app. For example, http://www.mysite.com/heroes/42 is a deep link to the hero detail page that displays the hero with id: 42.
.htaccess:
# If an existing asset or directory is requested go to it as it is
RewriteCond %{DOCUMENT_ROOT}%{REQUEST_URI} -f [OR]
RewriteCond %{DOCUMENT_ROOT}%{REQUEST_URI} -d
RewriteRule ^ - [L]
# If the requested resource doesn't exist, use index.html
RewriteRule ^ /index.html
2.In the apache htdocs project folder: ../htdocs/becke-ch--PRODUCT--sX-Y-vZ--USECASE--pl--client/
CLI:
Regular build: ng build
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch-regex-s00-v1-homepage-pl-client$ ng build
Hash: 22ab123030d28682903e
Time: 6201ms
chunk {0} polyfills.bundle.js, polyfills.bundle.js.map (polyfills) 158 kB {4} [initial] [rendered]
chunk {1} main.bundle.js, main.bundle.js.map (main) 3.61 kB {3} [initial] [rendered]
chunk {2} styles.bundle.js, styles.bundle.js.map (styles) 9.77 kB {4} [initial] [rendered]
chunk {3} vendor.bundle.js, vendor.bundle.js.map (vendor) 2.07 MB [initial] [rendered]
chunk {4} inline.bundle.js, inline.bundle.js.map (inline) 0 bytes [entry] [rendered]
Production build: ng build -prod
raoul-becke--s0-v1@hp-elitebook-840-g1--s0-v3:/ws/tool/becke-ch--regex--s0-v1/intellij/becke-ch-regex-s00-v1-homepage-pl-client$ ng build -prod
Hash: 4b374a830ac5dda3f509
Time: 6845ms
chunk {0} polyfills.2d45a4c73c85e24fe474.bundle.js (polyfills) 158 kB {4} [initial] [rendered]
chunk {1} main.784fc4769c9bf48884ad.bundle.js (main) 21.5 kB {3} [initial] [rendered]
chunk {2} styles.d41d8cd98f00b204e980.bundle.css (styles) 69 bytes {4} [initial] [rendered]
chunk {3} vendor.57570798817e1962b74d.bundle.js (vendor) 1.1 MB [initial] [rendered]
chunk {4} inline.5dee7671c6f764541e4f.bundle.js (inline) 0 bytes [entry] [rendered]
http://www.typescriptlang.org/
http://www.codelord.net/2015/09/10/angular-2-migration-path-what-we-know/
ES5, ES6 and TypeScript: The core team highly recommends doing Angular 2 in TypeScript. How hard will the conversion be? What will happen to those of us that decide to stay with ES5/6? They say all options will work, but we haven’t seen a lot of love for these setups yet.
http://blog.thoughtram.io/angular/2015/10/24/upgrading-apps-to-angular-2-using-ngupgrade.html
This is an interesting one. When we saw Angular 2 code the very first time, some of us were scared because all of a sudden there were classes and decorators. Despite the fact that we don’t have have to write our Angular 2 apps in TypeScript (as explained in this article), ES2015 is the next standardized version, which means we will write it sooner or later anyways.
We wrote about how to write Angular in ES2015 today and if we do plan to upgrade but can’t do it right now, we should definitely write our new components in ES2015 or TypeScript.
That being said, it doesn’t really make sense to upgrade existing code to ES2015 or TypeScript. Even though it seems to be a logical step in preparation for upgrade, it doesn’t help us in any way to take the existing and large code base and upgrade it to ES2015 or TypeScript first, before we upgrade the application to Angular 2.
If we have to upgrade to Angular 2, it probably makes more sense to just rewrite component by component, without touching the existing code base. But this of course depends on how big our application is.
Again, this is just a language upgrade and it doesn’t really help with the upgrade itself, however, it helps us and our team to get used to the new languages features as we’re building components with it.
https://github.com/npm/npm/blob/2e3776bf5676bc24fec6239a3420f377fe98acde/doc/files/package.json.md#devdependencies
dependencies are installed on both:
npm install from a directory that contains package.json
npm install $package on any other directory
devDependencies are:
also installed on npm install on a directory that contains package.json, unless you pass the --production flag (go upvote Gayan Charith's answer)
not installed on npm install "$package" on any other directory, unless you give it the --dev option.
peerDependencies:
before 3.0: are always installed if missing, and raise an error if multiple incompatible versions of the dependency would be used by different dependencies.
expected starting on 3.0 (untested): give a warning if missing on npm install, and you have to solve the dependency yourself manually. When running, if the dependency is missing, you get an error (mentioned by @nextgentech)
http://angularjs.blogspot.ch/2015/08/angular-1-and-angular-2-coexistence.html
https://docs.google.com/document/d/1xvBZoFuNq9hsgRhPPZOJC-Z48AHEbIBPlOCBTSD8m0Y/edit#
http://www.codelord.net/2015/09/10/angular-2-migration-path-what-we-know/
http://www.codelord.net/2015/10/07/angular-2-preparation-killing-controllers/
http://blog.thoughtram.io/angular/2015/10/24/upgrading-apps-to-angular-2-using-ngupgrade.html
Here’s a list of changes that are crucial when thinking about upgrading:
Components - Components are the new building blocks when creating applications with Angular 2. Almost everything is a component, even our application itself.
Inputs/Outputs - Components communicate via inputs and outputs, if they run in the Browser, these are element properties and events. Our article on demystifying Angular 2’s Template syntax explains how they work.
Content Projection - Basically the new transclusion, but more aligned with the Web Components standard.
Dependency Injection - Instead of having a single injector for our entire application, in Angular 2 each component comes with its own injector. We have a dedicated article on that too.
Reference | Location | Remarks |
http://www.becke.ch/convention/naming/ch_becke_convention_naming_s1_v0_9.pdf | Describes the naming convention that should be used. | |
http://www.becke.ch/convention/scopeandversion/ch_becke_convention_scope_and_version_s1_v0_9.pdf | Describes the scope and version convention that should be applied. |
Terms / Abbreviations / Acronyms | Description |
|
|