implement search service
This commit is contained in:
parent
e7c6fbf423
commit
e3ca470a6a
2
jslib
2
jslib
|
@ -1 +1 @@
|
||||||
Subproject commit 4ca7a9709e9ccd0e67ce09309ae605f2057bf089
|
Subproject commit 8448b48cd7c65c3d7891bc00246e27777daaeb58
|
|
@ -172,9 +172,9 @@
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"@types/lunr": {
|
"@types/lunr": {
|
||||||
"version": "2.1.5",
|
"version": "2.1.6",
|
||||||
"resolved": "https://registry.npmjs.org/@types/lunr/-/lunr-2.1.5.tgz",
|
"resolved": "https://registry.npmjs.org/@types/lunr/-/lunr-2.1.6.tgz",
|
||||||
"integrity": "sha512-esk3CG25hRtHsVHm+LOjiSFYdw8be3uIY653WUwR43Bro914HSimPgPpqgajkhTJ0awK3RQfaIxP7zvbtCpcyg==",
|
"integrity": "sha512-Bz6fUhX1llTa7ygQJN3ttoVkkrpW7xxSEP7D7OYFO/FCBKqKqruRUZtJzTtYA0GkQX13lxU5u+8LuCviJlAXkQ==",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"@types/node": {
|
"@types/node": {
|
||||||
|
@ -6273,9 +6273,9 @@
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"lunr": {
|
"lunr": {
|
||||||
"version": "2.1.6",
|
"version": "2.3.1",
|
||||||
"resolved": "https://registry.npmjs.org/lunr/-/lunr-2.1.6.tgz",
|
"resolved": "https://registry.npmjs.org/lunr/-/lunr-2.3.1.tgz",
|
||||||
"integrity": "sha512-ydJpB8CX8cZ/VE+KMaYaFcZ6+o2LruM6NG76VXdflYTgluvVemz1lW4anE+pyBbLvxJHZdvD1Jy/fOqdzAEJog=="
|
"integrity": "sha1-ETYWorYC3cEJMqe/ik5uV+v+zfI="
|
||||||
},
|
},
|
||||||
"magic-string": {
|
"magic-string": {
|
||||||
"version": "0.22.5",
|
"version": "0.22.5",
|
||||||
|
|
|
@ -26,7 +26,7 @@
|
||||||
"@angular/compiler-cli": "5.2.0",
|
"@angular/compiler-cli": "5.2.0",
|
||||||
"@ngtools/webpack": "1.10.2",
|
"@ngtools/webpack": "1.10.2",
|
||||||
"@types/jquery": "^3.3.2",
|
"@types/jquery": "^3.3.2",
|
||||||
"@types/lunr": "2.1.5",
|
"@types/lunr": "^2.1.6",
|
||||||
"@types/node": "8.0.19",
|
"@types/node": "8.0.19",
|
||||||
"@types/node-forge": "0.6.10",
|
"@types/node-forge": "0.6.10",
|
||||||
"@types/papaparse": "4.1.33",
|
"@types/papaparse": "4.1.33",
|
||||||
|
@ -73,7 +73,7 @@
|
||||||
"duo_web_sdk": "git+https://github.com/duosecurity/duo_web_sdk.git",
|
"duo_web_sdk": "git+https://github.com/duosecurity/duo_web_sdk.git",
|
||||||
"font-awesome": "4.7.0",
|
"font-awesome": "4.7.0",
|
||||||
"jquery": "3.3.1",
|
"jquery": "3.3.1",
|
||||||
"lunr": "2.1.6",
|
"lunr": "2.3.1",
|
||||||
"mousetrap": "1.6.1",
|
"mousetrap": "1.6.1",
|
||||||
"ngx-infinite-scroll": "0.8.4",
|
"ngx-infinite-scroll": "0.8.4",
|
||||||
"node-forge": "0.7.1",
|
"node-forge": "0.7.1",
|
||||||
|
|
|
@ -33,6 +33,7 @@ import { I18nService } from 'jslib/abstractions/i18n.service';
|
||||||
import { LockService } from 'jslib/abstractions/lock.service';
|
import { LockService } from 'jslib/abstractions/lock.service';
|
||||||
import { PasswordGenerationService } from 'jslib/abstractions/passwordGeneration.service';
|
import { PasswordGenerationService } from 'jslib/abstractions/passwordGeneration.service';
|
||||||
import { PlatformUtilsService } from 'jslib/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib/abstractions/platformUtils.service';
|
||||||
|
import { SearchService } from 'jslib/abstractions/search.service';
|
||||||
import { SettingsService } from 'jslib/abstractions/settings.service';
|
import { SettingsService } from 'jslib/abstractions/settings.service';
|
||||||
import { SyncService } from 'jslib/abstractions/sync.service';
|
import { SyncService } from 'jslib/abstractions/sync.service';
|
||||||
import { TokenService } from 'jslib/abstractions/token.service';
|
import { TokenService } from 'jslib/abstractions/token.service';
|
||||||
|
@ -70,7 +71,7 @@ export class AppComponent implements OnDestroy, OnInit {
|
||||||
private platformUtilsService: PlatformUtilsService, private ngZone: NgZone,
|
private platformUtilsService: PlatformUtilsService, private ngZone: NgZone,
|
||||||
private lockService: LockService, private storageService: StorageService,
|
private lockService: LockService, private storageService: StorageService,
|
||||||
private cryptoService: CryptoService, private collectionService: CollectionService,
|
private cryptoService: CryptoService, private collectionService: CollectionService,
|
||||||
private routerService: RouterService) { }
|
private routerService: RouterService, private searchService: SearchService) { }
|
||||||
|
|
||||||
ngOnInit() {
|
ngOnInit() {
|
||||||
this.ngZone.runOutsideAngular(() => {
|
this.ngZone.runOutsideAngular(() => {
|
||||||
|
@ -157,6 +158,7 @@ export class AppComponent implements OnDestroy, OnInit {
|
||||||
this.passwordGenerationService.clear(),
|
this.passwordGenerationService.clear(),
|
||||||
]);
|
]);
|
||||||
|
|
||||||
|
this.searchService.clearIndex();
|
||||||
this.authService.logOut(async () => {
|
this.authService.logOut(async () => {
|
||||||
this.analytics.eventTrack.next({ action: 'Logged Out' });
|
this.analytics.eventTrack.next({ action: 'Logged Out' });
|
||||||
if (expired) {
|
if (expired) {
|
||||||
|
|
|
@ -11,6 +11,7 @@ import { ApiService } from 'jslib/abstractions/api.service';
|
||||||
import { CipherService } from 'jslib/abstractions/cipher.service';
|
import { CipherService } from 'jslib/abstractions/cipher.service';
|
||||||
import { I18nService } from 'jslib/abstractions/i18n.service';
|
import { I18nService } from 'jslib/abstractions/i18n.service';
|
||||||
import { PlatformUtilsService } from 'jslib/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib/abstractions/platformUtils.service';
|
||||||
|
import { SearchService } from 'jslib/abstractions/search.service';
|
||||||
|
|
||||||
import { CipherData } from 'jslib/models/data/cipherData';
|
import { CipherData } from 'jslib/models/data/cipherData';
|
||||||
import { Cipher } from 'jslib/models/domain/cipher';
|
import { Cipher } from 'jslib/models/domain/cipher';
|
||||||
|
@ -29,10 +30,13 @@ export class CiphersComponent extends BaseCiphersComponent {
|
||||||
organization: Organization;
|
organization: Organization;
|
||||||
accessEvents = false;
|
accessEvents = false;
|
||||||
|
|
||||||
constructor(cipherService: CipherService, analytics: Angulartics2,
|
protected allCiphers: CipherView[] = [];
|
||||||
|
|
||||||
|
constructor(searchService: SearchService, analytics: Angulartics2,
|
||||||
toasterService: ToasterService, i18nService: I18nService,
|
toasterService: ToasterService, i18nService: I18nService,
|
||||||
platformUtilsService: PlatformUtilsService, private apiService: ApiService) {
|
platformUtilsService: PlatformUtilsService, cipherService: CipherService,
|
||||||
super(cipherService, analytics, toasterService, i18nService, platformUtilsService);
|
private apiService: ApiService) {
|
||||||
|
super(searchService, analytics, toasterService, i18nService, platformUtilsService, cipherService);
|
||||||
}
|
}
|
||||||
|
|
||||||
async load(filter: (cipher: CipherView) => boolean = null) {
|
async load(filter: (cipher: CipherView) => boolean = null) {
|
||||||
|
@ -60,12 +64,24 @@ export class CiphersComponent extends BaseCiphersComponent {
|
||||||
this.loaded = true;
|
this.loaded = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
applyFilter(filter: (cipher: CipherView) => boolean = null) {
|
async applyFilter(filter: (cipher: CipherView) => boolean = null) {
|
||||||
if (this.organization.isAdmin) {
|
if (this.organization.isAdmin) {
|
||||||
super.applyFilter(filter);
|
await super.applyFilter(filter);
|
||||||
} else {
|
} else {
|
||||||
const f = (c: CipherView) => c.organizationId === this.organization.id && (filter == null || filter(c));
|
const f = (c: CipherView) => c.organizationId === this.organization.id && (filter == null || filter(c));
|
||||||
super.applyFilter(f);
|
await super.applyFilter(f);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
search(timeout: number = null) {
|
||||||
|
if (!this.organization.isAdmin) {
|
||||||
|
return super.search(timeout);
|
||||||
|
}
|
||||||
|
this.searchPending = false;
|
||||||
|
if (this.searchText == null || this.searchText.trim().length < 2) {
|
||||||
|
this.ciphers = this.allCiphers;
|
||||||
|
} else {
|
||||||
|
this.ciphers = this.searchService.searchCiphersBasic(this.allCiphers, this.searchText);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -139,6 +139,7 @@ export class VaultComponent implements OnInit {
|
||||||
|
|
||||||
filterSearchText(searchText: string) {
|
filterSearchText(searchText: string) {
|
||||||
this.ciphersComponent.searchText = searchText;
|
this.ciphersComponent.searchText = searchText;
|
||||||
|
this.ciphersComponent.search(200);
|
||||||
}
|
}
|
||||||
|
|
||||||
editCipherAttachments(cipher: CipherView) {
|
editCipherAttachments(cipher: CipherView) {
|
||||||
|
|
|
@ -39,6 +39,7 @@ import { FolderService } from 'jslib/services/folder.service';
|
||||||
import { ImportService } from 'jslib/services/import.service';
|
import { ImportService } from 'jslib/services/import.service';
|
||||||
import { LockService } from 'jslib/services/lock.service';
|
import { LockService } from 'jslib/services/lock.service';
|
||||||
import { PasswordGenerationService } from 'jslib/services/passwordGeneration.service';
|
import { PasswordGenerationService } from 'jslib/services/passwordGeneration.service';
|
||||||
|
import { SearchService } from 'jslib/services/search.service';
|
||||||
import { SettingsService } from 'jslib/services/settings.service';
|
import { SettingsService } from 'jslib/services/settings.service';
|
||||||
import { StateService } from 'jslib/services/state.service';
|
import { StateService } from 'jslib/services/state.service';
|
||||||
import { SyncService } from 'jslib/services/sync.service';
|
import { SyncService } from 'jslib/services/sync.service';
|
||||||
|
@ -67,6 +68,7 @@ import {
|
||||||
PasswordGenerationService as PasswordGenerationServiceAbstraction,
|
PasswordGenerationService as PasswordGenerationServiceAbstraction,
|
||||||
} from 'jslib/abstractions/passwordGeneration.service';
|
} from 'jslib/abstractions/passwordGeneration.service';
|
||||||
import { PlatformUtilsService as PlatformUtilsServiceAbstraction } from 'jslib/abstractions/platformUtils.service';
|
import { PlatformUtilsService as PlatformUtilsServiceAbstraction } from 'jslib/abstractions/platformUtils.service';
|
||||||
|
import { SearchService as SearchServiceAbstraction } from 'jslib/abstractions/search.service';
|
||||||
import { SettingsService as SettingsServiceAbstraction } from 'jslib/abstractions/settings.service';
|
import { SettingsService as SettingsServiceAbstraction } from 'jslib/abstractions/settings.service';
|
||||||
import { StateService as StateServiceAbstraction } from 'jslib/abstractions/state.service';
|
import { StateService as StateServiceAbstraction } from 'jslib/abstractions/state.service';
|
||||||
import { StorageService as StorageServiceAbstraction } from 'jslib/abstractions/storage.service';
|
import { StorageService as StorageServiceAbstraction } from 'jslib/abstractions/storage.service';
|
||||||
|
@ -93,13 +95,15 @@ const apiService = new ApiService(tokenService, platformUtilsService,
|
||||||
const environmentService = new EnvironmentService(apiService, storageService);
|
const environmentService = new EnvironmentService(apiService, storageService);
|
||||||
const userService = new UserService(tokenService, storageService);
|
const userService = new UserService(tokenService, storageService);
|
||||||
const settingsService = new SettingsService(userService, storageService);
|
const settingsService = new SettingsService(userService, storageService);
|
||||||
|
export let searchService: SearchService = null;
|
||||||
const cipherService = new CipherService(cryptoService, userService, settingsService,
|
const cipherService = new CipherService(cryptoService, userService, settingsService,
|
||||||
apiService, storageService, i18nService, platformUtilsService);
|
apiService, storageService, i18nService, platformUtilsService, () => searchService);
|
||||||
const folderService = new FolderService(cryptoService, userService, apiService, storageService,
|
const folderService = new FolderService(cryptoService, userService, apiService, storageService,
|
||||||
i18nService, cipherService);
|
i18nService, cipherService);
|
||||||
const collectionService = new CollectionService(cryptoService, userService, storageService, i18nService);
|
const collectionService = new CollectionService(cryptoService, userService, storageService, i18nService);
|
||||||
|
searchService = new SearchService(cipherService, platformUtilsService);
|
||||||
const lockService = new LockService(cipherService, folderService, collectionService,
|
const lockService = new LockService(cipherService, folderService, collectionService,
|
||||||
cryptoService, platformUtilsService, storageService, messagingService, null);
|
cryptoService, platformUtilsService, storageService, messagingService, searchService, null);
|
||||||
const syncService = new SyncService(userService, apiService, settingsService,
|
const syncService = new SyncService(userService, apiService, settingsService,
|
||||||
folderService, cipherService, cryptoService, collectionService, storageService, messagingService,
|
folderService, cipherService, cryptoService, collectionService, storageService, messagingService,
|
||||||
async (expired: boolean) => messagingService.send('logout', { expired: expired }));
|
async (expired: boolean) => messagingService.send('logout', { expired: expired }));
|
||||||
|
@ -188,6 +192,7 @@ export function initFactory(): Function {
|
||||||
{ provide: StorageServiceAbstraction, useValue: storageService },
|
{ provide: StorageServiceAbstraction, useValue: storageService },
|
||||||
{ provide: StateServiceAbstraction, useValue: stateService },
|
{ provide: StateServiceAbstraction, useValue: stateService },
|
||||||
{ provide: ExportServiceAbstraction, useValue: exportService },
|
{ provide: ExportServiceAbstraction, useValue: exportService },
|
||||||
|
{ provide: SearchServiceAbstraction, useValue: searchService },
|
||||||
{ provide: ImportServiceAbstraction, useValue: importService },
|
{ provide: ImportServiceAbstraction, useValue: importService },
|
||||||
{ provide: CryptoFunctionServiceAbstraction, useValue: cryptoFunctionService },
|
{ provide: CryptoFunctionServiceAbstraction, useValue: cryptoFunctionService },
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
<ng-container *ngIf="(ciphers | searchCiphers: searchText) as searchedCiphers">
|
<ng-container *ngIf="ciphers">
|
||||||
<table class="table table-hover table-list table-ciphers" *ngIf="searchedCiphers.length > 0">
|
<table class="table table-hover table-list table-ciphers" *ngIf="ciphers.length > 0">
|
||||||
<tbody>
|
<tbody>
|
||||||
<tr *ngFor="let c of searchedCiphers">
|
<tr *ngFor="let c of ciphers">
|
||||||
<td (click)="checkCipher(c)" class="table-list-checkbox" *ngIf="!organization">
|
<td (click)="checkCipher(c)" class="table-list-checkbox" *ngIf="!organization">
|
||||||
<input type="checkbox" [(ngModel)]="c.checked">
|
<input type="checkbox" [(ngModel)]="c.checked">
|
||||||
</td>
|
</td>
|
||||||
|
@ -52,7 +52,7 @@
|
||||||
</tr>
|
</tr>
|
||||||
</tbody>
|
</tbody>
|
||||||
</table>
|
</table>
|
||||||
<div class="no-items" *ngIf="searchedCiphers.length === 0">
|
<div class="no-items" *ngIf="ciphers.length === 0">
|
||||||
<i class="fa fa-spinner fa-spin text-muted" *ngIf="!loaded" title="{{'loading' | i18n}}"></i>
|
<i class="fa fa-spinner fa-spin text-muted" *ngIf="!loaded" title="{{'loading' | i18n}}"></i>
|
||||||
<ng-container *ngIf="loaded">
|
<ng-container *ngIf="loaded">
|
||||||
<p>{{'noItemsInList' | i18n}}</p>
|
<p>{{'noItemsInList' | i18n}}</p>
|
||||||
|
|
|
@ -12,6 +12,7 @@ import { Angulartics2 } from 'angulartics2';
|
||||||
import { CipherService } from 'jslib/abstractions/cipher.service';
|
import { CipherService } from 'jslib/abstractions/cipher.service';
|
||||||
import { I18nService } from 'jslib/abstractions/i18n.service';
|
import { I18nService } from 'jslib/abstractions/i18n.service';
|
||||||
import { PlatformUtilsService } from 'jslib/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib/abstractions/platformUtils.service';
|
||||||
|
import { SearchService } from 'jslib/abstractions/search.service';
|
||||||
|
|
||||||
import { CiphersComponent as BaseCiphersComponent } from 'jslib/angular/components/ciphers.component';
|
import { CiphersComponent as BaseCiphersComponent } from 'jslib/angular/components/ciphers.component';
|
||||||
|
|
||||||
|
@ -38,10 +39,10 @@ export class CiphersComponent extends BaseCiphersComponent implements OnDestroy
|
||||||
|
|
||||||
private searchPipe: SearchCiphersPipe;
|
private searchPipe: SearchCiphersPipe;
|
||||||
|
|
||||||
constructor(cipherService: CipherService, protected analytics: Angulartics2,
|
constructor(searchService: SearchService, protected analytics: Angulartics2,
|
||||||
protected toasterService: ToasterService, protected i18nService: I18nService,
|
protected toasterService: ToasterService, protected i18nService: I18nService,
|
||||||
protected platformUtilsService: PlatformUtilsService) {
|
protected platformUtilsService: PlatformUtilsService, protected cipherService: CipherService) {
|
||||||
super(cipherService);
|
super(searchService);
|
||||||
this.searchPipe = new SearchCiphersPipe(platformUtilsService);
|
this.searchPipe = new SearchCiphersPipe(platformUtilsService);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -167,6 +167,7 @@ export class VaultComponent implements OnInit {
|
||||||
|
|
||||||
filterSearchText(searchText: string) {
|
filterSearchText(searchText: string) {
|
||||||
this.ciphersComponent.searchText = searchText;
|
this.ciphersComponent.searchText = searchText;
|
||||||
|
this.ciphersComponent.search(200);
|
||||||
}
|
}
|
||||||
|
|
||||||
async editCipherAttachments(cipher: CipherView) {
|
async editCipherAttachments(cipher: CipherView) {
|
||||||
|
|
Loading…
Reference in New Issue