stub out angular app with webpack 4

This commit is contained in:
Kyle Spearrin 2018-06-04 23:10:41 -04:00
parent 425029783b
commit bf796fe80c
16 changed files with 8486 additions and 7132 deletions

15
.editorconfig Normal file
View File

@ -0,0 +1,15 @@
# EditorConfig is awesome: http://EditorConfig.org
# top-most EditorConfig file
root = true
# Unix-style newlines with a newline ending every file
[*]
end_of_line = lf
insert_final_newline = true
# Set default charset
[*.{js,ts,scss,html}]
charset = utf-8
indent_style = space
indent_size = 4

211
.gitignore vendored
View File

@ -1,202 +1,13 @@
## Ignore Visual Studio temporary files, build results, and
## files generated by popular Visual Studio add-ons.
# User-specific files
*.suo
*.user
*.userosscache
*.sln.docstates
# User-specific files (MonoDevelop/Xamarin Studio)
*.userprefs
# Build results
[Dd]ebug/
[Dd]ebugPublic/
[Rr]elease/
[Rr]eleases/
x64/
x86/
build/
bld/
[Bb]in/
[Oo]bj/
# Visual Studo 2015 cache/options directory
.vs/
# MSTest test Results
[Tt]est[Rr]esult*/
[Bb]uild[Ll]og.*
# NUNIT
*.VisualState.xml
TestResult.xml
# Build Results of an ATL Project
[Dd]ebugPS/
[Rr]eleasePS/
dlldata.c
*_i.c
*_p.c
*_i.h
*.ilk
*.meta
*.obj
*.pch
*.pdb
*.pgc
*.pgd
*.rsp
*.sbr
*.tlb
*.tli
*.tlh
*.tmp
*.tmp_proj
*.log
*.vspscc
*.vssscc
.builds
*.pidb
*.svclog
*.scc
# Chutzpah Test files
_Chutzpah*
# Visual C++ cache files
ipch/
*.aps
*.ncb
*.opensdf
*.sdf
*.cachefile
# Visual Studio profiler
*.psess
*.vsp
*.vspx
# TFS 2012 Local Workspace
$tf/
# Guidance Automation Toolkit
*.gpState
# ReSharper is a .NET coding add-in
_ReSharper*/
*.[Rr]e[Ss]harper
*.DotSettings.user
# JustCode is a .NET coding addin-in
.JustCode
# TeamCity is a build add-in
_TeamCity*
# DotCover is a Code Coverage Tool
*.dotCover
# NCrunch
_NCrunch_*
.*crunch*.local.xml
# MightyMoose
*.mm.*
AutoTest.Net/
# Web workbench (sass)
.sass-cache/
# Installshield output folder
[Ee]xpress/
# DocProject is a documentation generator add-in
DocProject/buildhelp/
DocProject/Help/*.HxT
DocProject/Help/*.HxC
DocProject/Help/*.hhc
DocProject/Help/*.hhk
DocProject/Help/*.hhp
DocProject/Help/Html2
DocProject/Help/html
# Click-Once directory
publish/
# Publish Web Output
*.[Pp]ublish.xml
*.azurePubxml
# TODO: Comment the next line if you want to checkin your web deploy settings
# but database connection strings (with potential passwords) will be unencrypted
*.pubxml
*.publishproj
# NuGet Packages
*.nupkg
# The packages folder can be ignored because of Package Restore
**/packages/*
# except build/, which is used as an MSBuild target.
!**/packages/build/
# Uncomment if necessary however generally it will be regenerated when needed
#!**/packages/repositories.config
# Windows Azure Build Output
csx/
*.build.csdef
# Windows Store app package directory
AppPackages/
# Others
*.[Cc]ache
ClientBin/
[Ss]tyle[Cc]op.*
~$*
*~
*.dbmdl
*.dbproj.schemaview
*.pfx
*.publishsettings
node_modules/
bower_components/
lib/
.vs
.idea
.DS_Store
node_modules
npm-debug.log
vwd.webinfo
css/
dist/
# RIA/Silverlight projects
Generated_Code/
# Backup & report files from converting an old project file
# to a newer Visual Studio version. Backup files are not needed,
# because we have git ;-)
_UpgradeReport_Files/
Backup*/
UpgradeLog*.XML
UpgradeLog*.htm
# SQL Server files
*.mdf
*.ldf
# Business Intelligence projects
*.rdl.data
*.bim.layout
*.bim_*.settings
# Microsoft Fakes
FakesAssemblies/
# Node.js Tools for Visual Studio
.ntvs_analysis.dat
# Visual Studio 6 build log
*.plg
# Visual Studio 6 workspace options file
*.opt
# Other
src/js/*.min.js
webfonts/
*.crx
*.pem
*.zip
build/

14949
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@ -1,56 +1,73 @@
{
"name": "bitwarden",
"version": "1.27.0",
"env": "Production",
"name": "bitwarden-web",
"version": "2.0.0",
"scripts": {
"sub:init": "git submodule update --init --recursive",
"sub:update": "git submodule update --remote",
"sub:pull": "git submodule foreach git pull",
"postinstall": "npm run sub:init",
"build": "webpack --config webpack.config.js",
"build:watch": "webpack-serve --config webpack.config.js",
"build:prod": "cross-env NODE_ENV=production webpack --config webpack.config.js",
"build:prod:watch": "cross-env NODE_ENV=production webpack-serve --config webpack.config.js",
"dist": "npm run build:prod && gulp dist",
"lint": "tslint src/**/*.ts || true",
"lint:fix": "tslint src/**/*.ts --fix",
"test": "karma start --single-run",
"test:watch": "karma start"
},
"devDependencies": {
"connect": "3.6.5",
"lodash": "4.17.4",
"gulp": "3.9.1",
"gulp-concat": "2.6.1",
"gulp-cssmin": "0.2.0",
"gulp-less": "3.3.2",
"gulp-rename": "1.2.2",
"gulp-uglify": "3.0.0",
"gulp-gh-pages": "git+https://github.com/tekd/gulp-gh-pages.git#update-dependency",
"gulp-preprocess": "2.0.0",
"gulp-ng-annotate": "2.0.0",
"gulp-ng-config": "1.5.0",
"gulp-connect": "5.0.0",
"gulp-json-editor": "2.2.2",
"jshint": "2.9.5",
"gulp-jshint": "2.0.4",
"rimraf": "2.6.2",
"run-sequence": "2.2.0",
"merge-stream": "1.0.1",
"jquery": "3.2.1",
"font-awesome": "4.7.0",
"bootstrap": "3.3.7",
"angular": "1.6.7",
"angular-resource": "1.6.7",
"angular-sanitize": "1.6.7",
"angular-ui-bootstrap": "2.5.6",
"angular-ui-router": "0.4.2",
"angular-jwt": "0.1.9",
"angular-cookies": "1.6.7",
"admin-lte": "2.3.11",
"angular-toastr": "2.1.1",
"angular-bootstrap-show-errors": "2.3.0",
"angular-messages": "1.6.7",
"ngstorage": "0.3.11",
"papaparse": "4.3.6",
"clipboard": "1.7.1",
"ngclipboard": "1.1.2",
"angulartics": "1.5.0",
"angulartics-google-analytics": "0.4.0",
"node-forge": "0.7.1",
"webpack-stream": "4.0.0",
"angular-stripe": "5.0.0",
"angular-credit-cards": "3.1.6",
"browserify": "14.5.0",
"vinyl-source-stream": "1.1.0",
"gulp-derequire": "2.1.0",
"exposify": "0.5.0",
"@angular/compiler-cli": "5.2.0",
"@ngtools/webpack": "1.10.2",
"@types/lunr": "2.1.5",
"@types/node-forge": "0.6.10",
"@types/papaparse": "4.1.33",
"@types/webcrypto": "^0.0.28",
"angular2-template-loader": "^0.6.2",
"clean-webpack-plugin": "^0.1.19",
"copy-webpack-plugin": "^4.5.1",
"cross-env": "^5.1.4",
"css-loader": "^0.28.11",
"extract-text-webpack-plugin": "next",
"file-loader": "^1.1.11",
"html-loader": "^0.5.5",
"html-webpack-plugin": "^3.2.0",
"node-sass": "^4.7.2",
"sass-loader": "^7.0.2",
"style-loader": "^0.21.0",
"ts-loader": "^4.3.1",
"tslint": "^5.10.0",
"tslint-loader": "^3.6.0",
"typescript": "^2.7.2",
"webpack": "^4.10.2",
"webpack-cli": "^3.0.2",
"webpack-serve": "^1.0.2"
},
"dependencies": {
"@angular/animations": "5.2.0",
"@angular/common": "5.2.0",
"@angular/compiler": "5.2.0",
"@angular/core": "5.2.0",
"@angular/forms": "5.2.0",
"@angular/http": "5.2.0",
"@angular/platform-browser": "5.2.0",
"@angular/platform-browser-dynamic": "5.2.0",
"@angular/router": "5.2.0",
"@angular/upgrade": "5.2.0",
"angular2-toaster": "4.0.2",
"angulartics2": "5.0.1",
"core-js": "2.4.1",
"duo_web_sdk": "git+https://github.com/duosecurity/duo_web_sdk.git",
"angular-promise-polyfill": "0.0.4"
"font-awesome": "4.7.0",
"lunr": "2.1.6",
"mousetrap": "1.6.1",
"ngx-infinite-scroll": "0.8.4",
"node-forge": "0.7.1",
"papaparse": "4.3.5",
"rxjs": "5.5.6",
"sweetalert": "2.1.0",
"tldjs": "2.0.0",
"web-animations-js": "2.3.1",
"zone.js": "0.8.19"
}
}

View File

@ -0,0 +1,24 @@
import { NgModule } from '@angular/core';
import {
RouterModule,
Routes,
} from '@angular/router';
import { VaultComponent } from './vault/vault.component';
const routes: Routes = [
{ path: '', redirectTo: '/vault', pathMatch: 'full' },
{
path: 'vault',
component: VaultComponent,
},
];
@NgModule({
imports: [RouterModule.forRoot(routes, {
useHash: true,
/*enableTracing: true,*/
})],
exports: [RouterModule],
})
export class AppRoutingModule { }

21
src/app/app.component.ts Normal file
View File

@ -0,0 +1,21 @@
import {
ToasterConfig,
ToasterContainerComponent,
} from 'angular2-toaster';
import { Angulartics2GoogleAnalytics } from 'angulartics2/ga';
import {
Component,
} from '@angular/core';
import { Router } from '@angular/router';
@Component({
selector: 'app-root',
styles: [],
template: `
<router-outlet></router-outlet>`,
})
export class AppComponent {
constructor() {
}
}

32
src/app/app.module.ts Normal file
View File

@ -0,0 +1,32 @@
import 'core-js';
import 'zone.js/dist/zone';
import { AppRoutingModule } from './app-routing.module';
import { NgModule } from '@angular/core';
import { FormsModule } from '@angular/forms';
import { BrowserModule } from '@angular/platform-browser';
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
import { AppComponent } from './app.component';
import { VaultComponent } from './vault/vault.component';
@NgModule({
imports: [
BrowserModule,
BrowserAnimationsModule,
FormsModule,
AppRoutingModule,
],
declarations: [
AppComponent,
VaultComponent,
],
entryComponents: [
],
providers: [],
bootstrap: [AppComponent],
})
export class AppModule { }

11
src/app/main.ts Normal file
View File

@ -0,0 +1,11 @@
import { enableProdMode } from '@angular/core';
import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
// tslint:disable-next-line
require('../scss/styles.scss');
import { AppModule } from './app.module';
// enableProdMode(); // TODO: if production
platformBrowserDynamic().bootstrapModule(AppModule);

View File

@ -0,0 +1 @@
<b>The vault!!</b>

View File

@ -0,0 +1,11 @@
import {
Component,
} from '@angular/core';
@Component({
selector: 'app-vault',
templateUrl: 'vault.component.html',
})
export class VaultComponent {
}

3
src/global.d.ts vendored Normal file
View File

@ -0,0 +1,3 @@
declare function escape(s: string): string;
declare function unescape(s: string): string;
declare var require: any;

View File

@ -5,7 +5,7 @@
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no" />
<meta name="theme-color" content="#3c8dbc">
<base href="/" />
<base href="" />
<title page-title>Bitwarden Web Vault</title>
@ -17,7 +17,9 @@
</head>
<body>
<app-root>
Loading...
</app-root>
</body>
</html>

3
src/scss/styles.scss Normal file
View File

@ -0,0 +1,3 @@
body {
background-color: gray;
}

28
tsconfig.json Normal file
View File

@ -0,0 +1,28 @@
{
"compilerOptions": {
"moduleResolution": "node",
"noImplicitAny": true,
"emitDecoratorMetadata": true,
"experimentalDecorators": true,
"module": "es6",
"target": "ES2016",
"allowJs": true,
"sourceMap": true,
"types": [],
"baseUrl": ".",
"paths": {
"jslib/*": [ "jslib/src/*" ],
"@angular/*": [ "node_modules/@angular/*" ],
"angular2-toaster": [ "node_modules/angular2-toaster" ],
"angulartics2": [ "node_modules/angulartics2" ]
}
},
"exclude": [
"node_modules",
"jslib/node_modules",
"dist",
"jslib/dist",
"build",
"jslib/spec"
]
}

53
tslint.json Normal file
View File

@ -0,0 +1,53 @@
{
"extends": "tslint:recommended",
"rules": {
"align": [ true, "statements", "members" ],
"ban-types": {
"options": [
[ "Object", "Avoid using the `Object` type. Did you mean `object`?" ],
[ "Boolean", "Avoid using the `Boolean` type. Did you mean `boolean`?" ],
[ "Number", "Avoid using the `Number` type. Did you mean `number`?" ],
[ "String", "Avoid using the `String` type. Did you mean `string`?" ],
[ "Symbol", "Avoid using the `Symbol` type. Did you mean `symbol`?" ]
]
},
"member-access": [ true, "no-public" ],
"member-ordering": [
true,
{
"order": [
"public-static-field",
"public-static-method",
"protected-static-field",
"protected-static-method",
"private-static-field",
"private-static-method",
"public-instance-field",
"protected-instance-field",
"private-instance-field",
"public-constructor",
"protected-constructor",
"private-constructor",
"public-instance-method",
"protected-instance-method",
"private-instance-method"
]
}
],
"no-empty": [ true, "allow-empty-catch" ],
"object-literal-sort-keys": false,
"object-literal-shorthand": [ true, "never" ],
"prefer-for-of": false,
"quotemark": [ true, "single" ],
"whitespace": [
true,
"check-branch",
"check-decl",
"check-module",
"check-operator",
"check-preblock",
"check-separator",
"check-type"
]
}
}

131
webpack.config.js Normal file
View File

@ -0,0 +1,131 @@
const path = require('path');
const webpack = require('webpack');
const CleanWebpackPlugin = require('clean-webpack-plugin');
const HtmlWebpackPlugin = require('html-webpack-plugin');
const CopyWebpackPlugin = require('copy-webpack-plugin');
const ExtractTextPlugin = require('extract-text-webpack-plugin');
const AngularCompilerPlugin = require('@ngtools/webpack').AngularCompilerPlugin;
if (process.env.NODE_ENV == null) {
process.env.NODE_ENV = 'development';
}
const ENV = process.env.ENV = process.env.NODE_ENV;
const isVendorModule = (module) => {
if (!module.context) {
return false;
}
return module.context.indexOf('node_modules') !== -1;
};
const extractCss = new ExtractTextPlugin({
filename: '[name].css',
disable: false,
allChunks: true,
});
const moduleRules = [
{
test: /\.ts$/,
enforce: 'pre',
loader: 'tslint-loader',
},
{
test: /\.(html)$/,
loader: 'html-loader',
},
{
test: /\.scss$/,
use: extractCss.extract({
use: [
{
loader: 'css-loader',
},
{
loader: 'sass-loader',
},
],
publicPath: '../',
}),
},
];
const plugins = [
new CleanWebpackPlugin([
path.resolve(__dirname, 'build/*'),
]),
// ref: https://github.com/angular/angular/issues/20357
new webpack.ContextReplacementPlugin(/\@angular(\\|\/)core(\\|\/)esm5/,
path.resolve(__dirname, './src')),
new HtmlWebpackPlugin({
template: './src/index.html',
filename: 'index.html',
chunks: ['vendor', 'main'],
}),
new CopyWebpackPlugin([
{ from: './src/images', to: 'images' },
]),
new webpack.SourceMapDevToolPlugin({
filename: '[name].js.map',
include: ['main.js'],
}),
extractCss,
new webpack.DefinePlugin({
'process.env': {
'ENV': JSON.stringify(ENV)
}
}),
];
if (ENV === 'production') {
moduleRules.push({
test: /(?:\.ngfactory\.js|\.ngstyle\.js|\.ts)$/,
loader: '@ngtools/webpack',
});
plugins.push(new AngularCompilerPlugin({
tsConfigPath: 'tsconfig.json',
entryModule: 'src/app/app.module#AppModule',
sourceMap: true,
}));
} else {
moduleRules.push({
test: /\.ts$/,
loaders: ['ts-loader', 'angular2-template-loader'],
exclude: path.resolve(__dirname, 'node_modules'),
});
}
const config = {
mode: ENV,
entry: {
'main': './src/app/main.ts',
},
resolve: {
extensions: ['.ts', '.js'],
alias: {
jslib: path.join(__dirname, 'jslib/src'),
},
symlinks: false,
modules: [path.resolve('node_modules')],
},
output: {
filename: '[name].js',
path: path.resolve(__dirname, 'build'),
},
optimization: {
splitChunks: {
cacheGroups: {
vendor: {
test: isVendorModule,
name: 'vendor',
chunks: 'initial',
enforce: true,
}
}
}
},
module: { rules: moduleRules },
plugins: plugins,
};
module.exports = config;