Merge pull request #231 from NicolasConstant/topic_auto-update
Topic auto update
272
angular.json
|
@ -1,145 +1,149 @@
|
|||
{
|
||||
"$schema": "./node_modules/@angular/cli/lib/config/schema.json",
|
||||
"version": 1,
|
||||
"newProjectRoot": "projects",
|
||||
"projects": {
|
||||
"sengi": {
|
||||
"root": "",
|
||||
"sourceRoot": "src",
|
||||
"projectType": "application",
|
||||
"architect": {
|
||||
"build": {
|
||||
"builder": "@angular-devkit/build-angular:browser",
|
||||
"options": {
|
||||
"outputPath": "dist",
|
||||
"index": "src/index.html",
|
||||
"main": "src/main.ts",
|
||||
"tsConfig": "src/tsconfig.app.json",
|
||||
"polyfills": "src/polyfills.ts",
|
||||
"assets": [
|
||||
"src/assets",
|
||||
"src/favicon.ico"
|
||||
],
|
||||
"styles": [
|
||||
"src/sass/styles.scss",
|
||||
"node_modules/@ctrl/ngx-emoji-mart/picker.css"
|
||||
],
|
||||
"stylePreprocessorOptions": {
|
||||
"includePaths": [
|
||||
"./src/sass",
|
||||
"./node_modules/bootstrap/scss"
|
||||
]
|
||||
},
|
||||
"scripts": []
|
||||
},
|
||||
"configurations": {
|
||||
"production": {
|
||||
"optimization": true,
|
||||
"outputHashing": "all",
|
||||
"sourceMap": false,
|
||||
"extractCss": true,
|
||||
"namedChunks": false,
|
||||
"aot": true,
|
||||
"extractLicenses": true,
|
||||
"vendorChunk": false,
|
||||
"buildOptimizer": true,
|
||||
"fileReplacements": [
|
||||
{
|
||||
"replace": "src/environments/environment.ts",
|
||||
"with": "src/environments/environment.prod.ts"
|
||||
}
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
"serve": {
|
||||
"builder": "@angular-devkit/build-angular:dev-server",
|
||||
"options": {
|
||||
"browserTarget": "sengi:build"
|
||||
},
|
||||
"configurations": {
|
||||
"production": {
|
||||
"browserTarget": "sengi:build:production"
|
||||
}
|
||||
}
|
||||
},
|
||||
"extract-i18n": {
|
||||
"builder": "@angular-devkit/build-angular:extract-i18n",
|
||||
"options": {
|
||||
"browserTarget": "sengi:build"
|
||||
}
|
||||
},
|
||||
"test": {
|
||||
"builder": "@angular-devkit/build-angular:karma",
|
||||
"options": {
|
||||
"main": "src/test.ts",
|
||||
"karmaConfig": "./karma.conf.js",
|
||||
"polyfills": "src/polyfills.ts",
|
||||
"tsConfig": "src/tsconfig.spec.json",
|
||||
"scripts": [],
|
||||
"styles": [
|
||||
"src/sass/styles.scss"
|
||||
],
|
||||
"assets": [
|
||||
"src/assets",
|
||||
"src/favicon.ico"
|
||||
],
|
||||
"stylePreprocessorOptions": {
|
||||
"includePaths": [
|
||||
"./src/sass",
|
||||
"./node_modules/bootstrap/scss"
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
"lint": {
|
||||
"builder": "@angular-devkit/build-angular:tslint",
|
||||
"options": {
|
||||
"tsConfig": [
|
||||
"src/tsconfig.app.json",
|
||||
"src/tsconfig.spec.json"
|
||||
],
|
||||
"exclude": [
|
||||
"**/node_modules/**"
|
||||
]
|
||||
}
|
||||
"$schema": "./node_modules/@angular/cli/lib/config/schema.json",
|
||||
"version": 1,
|
||||
"newProjectRoot": "projects",
|
||||
"projects": {
|
||||
"sengi": {
|
||||
"root": "",
|
||||
"sourceRoot": "src",
|
||||
"projectType": "application",
|
||||
"architect": {
|
||||
"build": {
|
||||
"builder": "@angular-devkit/build-angular:browser",
|
||||
"options": {
|
||||
"outputPath": "dist",
|
||||
"index": "src/index.html",
|
||||
"main": "src/main.ts",
|
||||
"tsConfig": "src/tsconfig.app.json",
|
||||
"polyfills": "src/polyfills.ts",
|
||||
"assets": [
|
||||
"src/assets",
|
||||
"src/favicon.ico",
|
||||
"src/manifest.json"
|
||||
],
|
||||
"styles": [
|
||||
"src/sass/styles.scss",
|
||||
"node_modules/@ctrl/ngx-emoji-mart/picker.css"
|
||||
],
|
||||
"stylePreprocessorOptions": {
|
||||
"includePaths": [
|
||||
"./src/sass",
|
||||
"./node_modules/bootstrap/scss"
|
||||
]
|
||||
},
|
||||
"scripts": []
|
||||
},
|
||||
"configurations": {
|
||||
"production": {
|
||||
"optimization": true,
|
||||
"outputHashing": "all",
|
||||
"sourceMap": false,
|
||||
"extractCss": true,
|
||||
"namedChunks": false,
|
||||
"aot": true,
|
||||
"extractLicenses": true,
|
||||
"vendorChunk": false,
|
||||
"buildOptimizer": true,
|
||||
"fileReplacements": [
|
||||
{
|
||||
"replace": "src/environments/environment.ts",
|
||||
"with": "src/environments/environment.prod.ts"
|
||||
}
|
||||
],
|
||||
"serviceWorker": true,
|
||||
"ngswConfigPath": "src/ngsw-config.json"
|
||||
}
|
||||
}
|
||||
},
|
||||
"sengi-e2e": {
|
||||
"root": "e2e",
|
||||
"sourceRoot": "e2e",
|
||||
"projectType": "application",
|
||||
"architect": {
|
||||
"e2e": {
|
||||
"builder": "@angular-devkit/build-angular:protractor",
|
||||
"options": {
|
||||
"protractorConfig": "./protractor.conf.js",
|
||||
"devServerTarget": "sengi:serve"
|
||||
}
|
||||
},
|
||||
"lint": {
|
||||
"builder": "@angular-devkit/build-angular:tslint",
|
||||
"options": {
|
||||
"tsConfig": [
|
||||
"e2e/tsconfig.e2e.json"
|
||||
],
|
||||
"exclude": [
|
||||
"**/node_modules/**"
|
||||
]
|
||||
}
|
||||
}
|
||||
"serve": {
|
||||
"builder": "@angular-devkit/build-angular:dev-server",
|
||||
"options": {
|
||||
"browserTarget": "sengi:build"
|
||||
},
|
||||
"configurations": {
|
||||
"production": {
|
||||
"browserTarget": "sengi:build:production"
|
||||
}
|
||||
}
|
||||
},
|
||||
"extract-i18n": {
|
||||
"builder": "@angular-devkit/build-angular:extract-i18n",
|
||||
"options": {
|
||||
"browserTarget": "sengi:build"
|
||||
}
|
||||
},
|
||||
"test": {
|
||||
"builder": "@angular-devkit/build-angular:karma",
|
||||
"options": {
|
||||
"main": "src/test.ts",
|
||||
"karmaConfig": "./karma.conf.js",
|
||||
"polyfills": "src/polyfills.ts",
|
||||
"tsConfig": "src/tsconfig.spec.json",
|
||||
"scripts": [],
|
||||
"styles": [
|
||||
"src/sass/styles.scss"
|
||||
],
|
||||
"assets": [
|
||||
"src/assets",
|
||||
"src/favicon.ico",
|
||||
"src/manifest.json"
|
||||
],
|
||||
"stylePreprocessorOptions": {
|
||||
"includePaths": [
|
||||
"./src/sass",
|
||||
"./node_modules/bootstrap/scss"
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
"lint": {
|
||||
"builder": "@angular-devkit/build-angular:tslint",
|
||||
"options": {
|
||||
"tsConfig": [
|
||||
"src/tsconfig.app.json",
|
||||
"src/tsconfig.spec.json"
|
||||
],
|
||||
"exclude": [
|
||||
"**/node_modules/**"
|
||||
]
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"defaultProject": "sengi",
|
||||
"schematics": {
|
||||
"@schematics/angular:component": {
|
||||
"prefix": "app",
|
||||
"styleext": "scss"
|
||||
"sengi-e2e": {
|
||||
"root": "e2e",
|
||||
"sourceRoot": "e2e",
|
||||
"projectType": "application",
|
||||
"architect": {
|
||||
"e2e": {
|
||||
"builder": "@angular-devkit/build-angular:protractor",
|
||||
"options": {
|
||||
"protractorConfig": "./protractor.conf.js",
|
||||
"devServerTarget": "sengi:serve"
|
||||
}
|
||||
},
|
||||
"@schematics/angular:directive": {
|
||||
"prefix": "app"
|
||||
"lint": {
|
||||
"builder": "@angular-devkit/build-angular:tslint",
|
||||
"options": {
|
||||
"tsConfig": [
|
||||
"e2e/tsconfig.e2e.json"
|
||||
],
|
||||
"exclude": [
|
||||
"**/node_modules/**"
|
||||
]
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"defaultProject": "sengi",
|
||||
"schematics": {
|
||||
"@schematics/angular:component": {
|
||||
"prefix": "app",
|
||||
"styleext": "scss"
|
||||
},
|
||||
"@schematics/angular:directive": {
|
||||
"prefix": "app"
|
||||
}
|
||||
}
|
||||
}
|
|
@ -36,7 +36,9 @@
|
|||
"@angular/http": "^7.2.7",
|
||||
"@angular/platform-browser": "^7.2.7",
|
||||
"@angular/platform-browser-dynamic": "^7.2.7",
|
||||
"@angular/pwa": "^0.12.4",
|
||||
"@angular/router": "^7.2.7",
|
||||
"@angular/service-worker": "^7.2.7",
|
||||
"@ctrl/ngx-emoji-mart": "^0.17.0",
|
||||
"@fortawesome/angular-fontawesome": "^0.3.0",
|
||||
"@fortawesome/fontawesome-svg-core": "^1.2.13",
|
||||
|
@ -89,6 +91,7 @@
|
|||
"productName": "Sengi",
|
||||
"appId": "org.sengi.desktop",
|
||||
"artifactName": "${productName}-${version}-${os}.${ext}",
|
||||
"npmRebuild": false,
|
||||
"directories": {
|
||||
"output": "release"
|
||||
},
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
<div class="drag-and-drop" *ngIf="drag" (dragover)="dragover($event)" (drop)="drop($event)"
|
||||
<div class="drag-and-drop" *ngIf="drag" (dragover)="dragover($event)" (drop)="drop($event)"
|
||||
[ngClass]="{'drag-and-drop__on-drag': drag2 === true }">
|
||||
<!-- (dragleave)="dragleave($event)" -->
|
||||
<div class="drag-and-drop__card">
|
||||
|
@ -10,6 +10,12 @@
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div class="auto-update" [class.auto-update__activated]="updateAvailable">
|
||||
<div class="auto-update__display">
|
||||
<div class="auto-update__display--text">A new version is available!</div> <a href class="auto-update__display--reload" (click)="loadNewVersion()">reload</a> <a href class="auto-update__display--close" (click)="closeAutoUpdate()"><fa-icon [icon]="faTimes"></fa-icon></a>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<app-media-viewer id="media-viewer" *ngIf="openedMediaEvent" [openedMediaEvent]="openedMediaEvent"
|
||||
(closeSubject)="closeMedia()" (dragenter)="dragenter($event)"></app-media-viewer>
|
||||
|
||||
|
|
|
@ -97,4 +97,75 @@ app-streams-selection-footer {
|
|||
right: 0;
|
||||
bottom: 0;
|
||||
left: 50px;
|
||||
}
|
||||
|
||||
.auto-update {
|
||||
transition: all .2s;
|
||||
transition-timing-function: ease-in;
|
||||
|
||||
position: absolute;
|
||||
height: 70px;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: -80px;
|
||||
z-index: 999999999;
|
||||
|
||||
&__activated {
|
||||
// opacity: 1;
|
||||
transition: all .25s;
|
||||
transition-timing-function: ease-out;
|
||||
bottom: 0px;
|
||||
}
|
||||
|
||||
&__display {
|
||||
position: relative;
|
||||
// height: 30px;
|
||||
width: 300px;
|
||||
// margin: 0 auto 30px auto;
|
||||
margin: auto;
|
||||
border-radius: 2px;
|
||||
color: rgba(rgb(0, 4, 24), 1);
|
||||
background: #ffffff;
|
||||
|
||||
box-shadow: 0px 0px 10px rgb(0, 0, 0);
|
||||
|
||||
&--text {
|
||||
display: inline-block;
|
||||
padding: 5px 10px;
|
||||
}
|
||||
|
||||
&--reload {
|
||||
transition: all .2s;
|
||||
position: absolute;
|
||||
right: 30px;
|
||||
|
||||
padding: 5px 10px;
|
||||
text-decoration: none;
|
||||
color: #ffffff;
|
||||
background-color: #3e455f;
|
||||
|
||||
&:hover {
|
||||
background-color: #1d202c;
|
||||
}
|
||||
}
|
||||
|
||||
&--close {
|
||||
transition: all .2s;
|
||||
position: absolute;
|
||||
right: 0;
|
||||
|
||||
display: inline-block;
|
||||
padding: 5px 10px;
|
||||
text-decoration: none;
|
||||
border-top-right-radius: 2px;
|
||||
border-bottom-right-radius: 2px;
|
||||
|
||||
color: #ffffff;
|
||||
background-color: #3e455f;
|
||||
|
||||
&:hover {
|
||||
background-color: #1d202c;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -2,6 +2,7 @@ import { Component, OnInit, OnDestroy } from '@angular/core';
|
|||
import { Subscription, Observable, Subject } from 'rxjs';
|
||||
import { debounceTime, map } from 'rxjs/operators';
|
||||
import { Select } from '@ngxs/store';
|
||||
import { faTimes } from "@fortawesome/free-solid-svg-icons";
|
||||
// import { ElectronService } from 'ngx-electron';
|
||||
|
||||
import { NavigationService, LeftPanelType, OpenLeftPanelEvent } from './services/navigation.service';
|
||||
|
@ -9,6 +10,7 @@ import { StreamElement } from './states/streams.state';
|
|||
import { OpenMediaEvent } from './models/common.model';
|
||||
import { ToolsService } from './services/tools.service';
|
||||
import { MediaService } from './services/media.service';
|
||||
import { ServiceWorkerService } from './services/service-worker.service';
|
||||
|
||||
@Component({
|
||||
selector: 'app-root',
|
||||
|
@ -16,26 +18,33 @@ import { MediaService } from './services/media.service';
|
|||
styleUrls: ['./app.component.scss']
|
||||
})
|
||||
export class AppComponent implements OnInit, OnDestroy {
|
||||
faTimes = faTimes;
|
||||
title = 'Sengi';
|
||||
floatingColumnActive: boolean;
|
||||
tutorialActive: boolean;
|
||||
// mediaViewerActive: boolean = false;
|
||||
openedMediaEvent: OpenMediaEvent
|
||||
updateAvailable: boolean;
|
||||
|
||||
private columnEditorSub: Subscription;
|
||||
private openMediaSub: Subscription;
|
||||
private streamSub: Subscription;
|
||||
private dragoverSub: Subscription;
|
||||
private updateAvailableSub: Subscription;
|
||||
|
||||
@Select(state => state.streamsstatemodel.streams) streamElements$: Observable<StreamElement[]>;
|
||||
|
||||
constructor(
|
||||
private readonly serviceWorkerService: ServiceWorkerService,
|
||||
private readonly toolsService: ToolsService,
|
||||
private readonly mediaService: MediaService,
|
||||
private readonly navigationService: NavigationService) {
|
||||
}
|
||||
|
||||
ngOnInit(): void {
|
||||
this.updateAvailableSub = this.serviceWorkerService.newAppVersionIsAvailable.subscribe((updateAvailable) => {
|
||||
this.updateAvailable = updateAvailable;
|
||||
});
|
||||
|
||||
this.streamSub = this.streamElements$.subscribe((streams: StreamElement[]) => {
|
||||
if (streams && streams.length === 0) {
|
||||
this.tutorialActive = true;
|
||||
|
@ -65,7 +74,7 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
.pipe(
|
||||
debounceTime(1500)
|
||||
)
|
||||
.subscribe(() => {
|
||||
.subscribe(() => {
|
||||
this.drag = false;
|
||||
})
|
||||
}
|
||||
|
@ -75,6 +84,7 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
this.columnEditorSub.unsubscribe();
|
||||
this.openMediaSub.unsubscribe();
|
||||
this.dragoverSub.unsubscribe();
|
||||
this.updateAvailableSub.unsubscribe();
|
||||
}
|
||||
|
||||
closeMedia() {
|
||||
|
@ -96,7 +106,6 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
return false;
|
||||
}
|
||||
dragover(event): boolean {
|
||||
// console.warn('dragover');
|
||||
event.stopPropagation();
|
||||
event.preventDefault();
|
||||
this.dragoverSubject.next(true);
|
||||
|
@ -112,4 +121,14 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
this.mediaService.uploadMedia(selectedAccount, files);
|
||||
return false;
|
||||
}
|
||||
|
||||
loadNewVersion(): boolean {
|
||||
this.serviceWorkerService.loadNewAppVersion();
|
||||
return false;
|
||||
}
|
||||
|
||||
closeAutoUpdate(): boolean {
|
||||
this.updateAvailable = false;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -79,6 +79,8 @@ import { ScheduledStatusesComponent } from './components/floating-column/schedul
|
|||
import { ScheduledStatusComponent } from './components/floating-column/scheduled-statuses/scheduled-status/scheduled-status.component';
|
||||
import { StreamNotificationsComponent } from './components/stream/stream-notifications/stream-notifications.component';
|
||||
import { NotificationComponent } from './components/floating-column/manage-account/notifications/notification/notification.component';
|
||||
import { ServiceWorkerModule } from '@angular/service-worker';
|
||||
import { environment } from '../environments/environment';
|
||||
|
||||
|
||||
const routes: Routes = [
|
||||
|
@ -167,7 +169,8 @@ const routes: Routes = [
|
|||
]),
|
||||
NgxsStoragePluginModule.forRoot(),
|
||||
ContextMenuModule.forRoot(),
|
||||
HotkeyModule.forRoot()
|
||||
HotkeyModule.forRoot(),
|
||||
ServiceWorkerModule.register('ngsw-worker.js', { enabled: environment.production })
|
||||
],
|
||||
providers: [AuthService, NavigationService, NotificationService, MastodonWrapperService, MastodonService, StreamingService],
|
||||
bootstrap: [AppComponent],
|
||||
|
|
|
@ -0,0 +1,12 @@
|
|||
import { TestBed } from '@angular/core/testing';
|
||||
|
||||
import { ServiceWorkerService } from './service-worker.service';
|
||||
|
||||
xdescribe('ServiceWorkerService', () => {
|
||||
beforeEach(() => TestBed.configureTestingModule({}));
|
||||
|
||||
it('should be created', () => {
|
||||
const service: ServiceWorkerService = TestBed.get(ServiceWorkerService);
|
||||
expect(service).toBeTruthy();
|
||||
});
|
||||
});
|
|
@ -0,0 +1,49 @@
|
|||
import { Injectable, ApplicationRef } from '@angular/core';
|
||||
import { SwUpdate } from '@angular/service-worker';
|
||||
import { first } from 'rxjs/operators';
|
||||
import { interval, concat, BehaviorSubject } from 'rxjs';
|
||||
|
||||
@Injectable({
|
||||
providedIn: 'root'
|
||||
})
|
||||
export class ServiceWorkerService {
|
||||
|
||||
newAppVersionIsAvailable = new BehaviorSubject<boolean>(false);
|
||||
|
||||
private isListening = false;
|
||||
|
||||
constructor(appRef: ApplicationRef, updates: SwUpdate) {
|
||||
|
||||
//https://angular.io/guide/service-worker-communications
|
||||
|
||||
updates.available.subscribe(event => {
|
||||
console.log('current version is', event.current);
|
||||
console.log('available version is', event.available);
|
||||
|
||||
this.newAppVersionIsAvailable.next(true);
|
||||
});
|
||||
|
||||
// Allow the app to stabilize first, before starting polling for updates with `interval()`.
|
||||
// const updateCheckTimer$ = interval(10 * 1000);
|
||||
// const appIsStable$ = appRef.isStable; //.pipe(first(isStable => isStable === true));
|
||||
// const everySixHoursOnceAppIsStable$ = concat(appIsStable$, updateCheckTimer$);
|
||||
// everySixHoursOnceAppIsStable$.subscribe(() => {
|
||||
// updates.checkForUpdate();
|
||||
// });
|
||||
|
||||
const updateCheckTimer$ = interval(6 * 60 * 60 * 1000);
|
||||
|
||||
appRef.isStable.subscribe(() => {
|
||||
if (this.isListening) return;
|
||||
this.isListening = true;
|
||||
|
||||
updateCheckTimer$.subscribe(() => {
|
||||
updates.checkForUpdate();
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
loadNewAppVersion() {
|
||||
document.location.reload();
|
||||
}
|
||||
}
|
After Width: | Height: | Size: 1.2 KiB |
After Width: | Height: | Size: 1.4 KiB |
After Width: | Height: | Size: 1.4 KiB |
After Width: | Height: | Size: 1.7 KiB |
After Width: | Height: | Size: 3.5 KiB |
After Width: | Height: | Size: 4.9 KiB |
After Width: | Height: | Size: 792 B |
After Width: | Height: | Size: 958 B |
|
@ -50,6 +50,8 @@
|
|||
}
|
||||
}
|
||||
</style>
|
||||
<link rel="manifest" href="manifest.json">
|
||||
<meta name="theme-color" content="#1976d2">
|
||||
</head>
|
||||
|
||||
<body ondragstart="return false;" ondrop="return false;">
|
||||
|
@ -59,5 +61,6 @@
|
|||
<div></div>
|
||||
</div>
|
||||
</app-root>
|
||||
<noscript>Please enable JavaScript to continue using this application.</noscript>
|
||||
</body>
|
||||
</html>
|
|
@ -5,8 +5,13 @@ import { AppModule } from './app/app.module';
|
|||
import { environment } from './environments/environment';
|
||||
|
||||
if (environment.production) {
|
||||
enableProdMode();
|
||||
enableProdMode();
|
||||
}
|
||||
|
||||
platformBrowserDynamic().bootstrapModule(AppModule)
|
||||
.catch(err => console.log(err));
|
||||
.then(() => {
|
||||
if ('serviceWorker' in navigator && environment.production) {
|
||||
navigator.serviceWorker.register('./ngsw-worker.js');
|
||||
}
|
||||
})
|
||||
.catch(err => console.log(err));
|
||||
|
|
|
@ -0,0 +1,51 @@
|
|||
{
|
||||
"name": "sengi",
|
||||
"short_name": "sengi",
|
||||
"theme_color": "#1976d2",
|
||||
"background_color": "#fafafa",
|
||||
"display": "standalone",
|
||||
"scope": "/",
|
||||
"start_url": "/",
|
||||
"icons": [
|
||||
{
|
||||
"src": "assets/icons/icon-72x72.png",
|
||||
"sizes": "72x72",
|
||||
"type": "image/png"
|
||||
},
|
||||
{
|
||||
"src": "assets/icons/icon-96x96.png",
|
||||
"sizes": "96x96",
|
||||
"type": "image/png"
|
||||
},
|
||||
{
|
||||
"src": "assets/icons/icon-128x128.png",
|
||||
"sizes": "128x128",
|
||||
"type": "image/png"
|
||||
},
|
||||
{
|
||||
"src": "assets/icons/icon-144x144.png",
|
||||
"sizes": "144x144",
|
||||
"type": "image/png"
|
||||
},
|
||||
{
|
||||
"src": "assets/icons/icon-152x152.png",
|
||||
"sizes": "152x152",
|
||||
"type": "image/png"
|
||||
},
|
||||
{
|
||||
"src": "assets/icons/icon-192x192.png",
|
||||
"sizes": "192x192",
|
||||
"type": "image/png"
|
||||
},
|
||||
{
|
||||
"src": "assets/icons/icon-384x384.png",
|
||||
"sizes": "384x384",
|
||||
"type": "image/png"
|
||||
},
|
||||
{
|
||||
"src": "assets/icons/icon-512x512.png",
|
||||
"sizes": "512x512",
|
||||
"type": "image/png"
|
||||
}
|
||||
]
|
||||
}
|
|
@ -0,0 +1,27 @@
|
|||
{
|
||||
"index": "/index.html",
|
||||
"assetGroups": [
|
||||
{
|
||||
"name": "app",
|
||||
"installMode": "prefetch",
|
||||
"resources": {
|
||||
"files": [
|
||||
"/favicon.ico",
|
||||
"/index.html",
|
||||
"/*.css",
|
||||
"/*.js"
|
||||
]
|
||||
}
|
||||
}, {
|
||||
"name": "assets",
|
||||
"installMode": "lazy",
|
||||
"updateMode": "prefetch",
|
||||
"resources": {
|
||||
"files": [
|
||||
"/assets/**",
|
||||
"/*.(eot|svg|cur|jpg|png|webp|gif|otf|ttf|woff|woff2|ani)"
|
||||
]
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|