From cc6d643d30ba813d1dfdeeebe64a7ecea49d5a1b Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Fran=C3=A7ois=20Agneray?= <francois.agneray@lam.fr>
Date: Mon, 6 Sep 2021 15:19:17 +0200
Subject: [PATCH] Search multiple => done

---
 .../components/result/overview.component.html |  8 +++++-
 .../components/result/overview.component.ts   |  7 +++++
 .../abstract-search-multiple.component.ts     | 18 +++++++++---
 .../containers/position.component.html        |  4 +--
 .../containers/result-multiple.component.html |  1 +
 .../containers/result-multiple.component.ts   |  2 --
 .../store/actions/search-multiple.actions.ts  |  1 +
 .../store/effects/search-multiple.effects.ts  | 28 +++++++++++++++++--
 .../store/reducers/search-multiple.reducer.ts |  4 +++
 .../metamodel/selectors/dataset.selector.ts   |  5 ++++
 10 files changed, 67 insertions(+), 11 deletions(-)

diff --git a/client/src/app/instance/search-multiple/components/result/overview.component.html b/client/src/app/instance/search-multiple/components/result/overview.component.html
index d1414ccf..91b90040 100644
--- a/client/src/app/instance/search-multiple/components/result/overview.component.html
+++ b/client/src/app/instance/search-multiple/components/result/overview.component.html
@@ -24,7 +24,7 @@
         </div>
         <hr class="my-4">
         <div class="text-center">
-            <a routerLink="/search-multiple/position" [queryParams]="queryParams" class="btn btn-lg btn-outline-primary">
+            <a routerLink="/instance/{{ instanceSelected }}/search-multiple/position" class="btn btn-lg btn-outline-primary">
                 <span class="fas fa-undo"></span> Try something else
             </a>
         </div>
@@ -61,6 +61,12 @@
                         </span>
                         <span *ngIf="getCountByDataset(dataset.name) < 2"> object found</span>
                         <span *ngIf="getCountByDataset(dataset.name) > 1"> objects found</span>
+                        <hr *ngIf="getCountByDataset(dataset.name) > 0" class="my-4">
+                        <div *ngIf="getCountByDataset(dataset.name) > 0" class="text-center">
+                            <a routerLink="/instance/{{ instanceSelected }}/search/result/{{ dataset.name }}" [queryParams]="getCsQueryParams()"  class="btn btn-outline-primary">
+                                <span class="fas fa-forward"></span> Go to result
+                            </a>
+                        </div>
                     </li>
                 </ul>
             </div>
diff --git a/client/src/app/instance/search-multiple/components/result/overview.component.ts b/client/src/app/instance/search-multiple/components/result/overview.component.ts
index a2f64652..e85af4d2 100644
--- a/client/src/app/instance/search-multiple/components/result/overview.component.ts
+++ b/client/src/app/instance/search-multiple/components/result/overview.component.ts
@@ -17,6 +17,7 @@ import { ConeSearch, SearchMultipleDatasetLength, SearchMultipleQueryParams } fr
     templateUrl: 'overview.component.html'
 })
 export class OverviewComponent {
+    @Input() instanceSelected: string;
     @Input() datasetFamilyList: DatasetFamily[];
     @Input() datasetList: Dataset[];
     @Input() coneSearch: ConeSearch;
@@ -84,4 +85,10 @@ export class OverviewComponent {
     getCountByDataset(dname: string): number {
         return this.dataLength.find(datasetLength => datasetLength.datasetName === dname).length;
     }
+
+    getCsQueryParams() {
+        return {
+            cs: `${this.coneSearch.ra}:${this.coneSearch.dec}:${this.coneSearch.radius}`
+        }
+    }
 }
diff --git a/client/src/app/instance/search-multiple/containers/abstract-search-multiple.component.ts b/client/src/app/instance/search-multiple/containers/abstract-search-multiple.component.ts
index 31963675..d8bbadd4 100644
--- a/client/src/app/instance/search-multiple/containers/abstract-search-multiple.component.ts
+++ b/client/src/app/instance/search-multiple/containers/abstract-search-multiple.component.ts
@@ -1,7 +1,7 @@
 import { Directive, OnDestroy, OnInit } from '@angular/core';
 
 import { Store } from '@ngrx/store';
-import { Observable } from 'rxjs';
+import { Observable, Subscription } from 'rxjs';
 
 import { Dataset, DatasetFamily } from 'src/app/metamodel/models';
 import { ConeSearch, SearchMultipleQueryParams } from '../../store/models';
@@ -14,6 +14,7 @@ import * as coneSearchSelector from 'src/app/instance/store/selectors/cone-searc
 
 @Directive()
 export abstract class AbstractSearchMultipleComponent implements OnInit, OnDestroy {
+    public pristine: Observable<boolean>;
     public instanceSelected: Observable<string>;
     public datasetFamilyListIsLoading: Observable<boolean>;
     public datasetFamilyListIsLoaded: Observable<boolean>;
@@ -26,14 +27,17 @@ export abstract class AbstractSearchMultipleComponent implements OnInit, OnDestr
     public coneSearch: Observable<ConeSearch>;
     public queryParams: Observable<SearchMultipleQueryParams>;
 
+    private datasetListSubscription: Subscription;
+
     constructor(protected store: Store<{ }>) {
+        this.pristine = this.store.select(searchMultipleSelector.selectPristine);
         this.instanceSelected = this.store.select(instanceSelector.selectInstanceNameByRoute);
         this.datasetFamilyListIsLoading = store.select(datasetFamilySelector.selectDatasetFamilyListIsLoading);
         this.datasetFamilyListIsLoaded = store.select(datasetFamilySelector.selectDatasetFamilyListIsLoaded);
         this.datasetFamilyList = store.select(datasetFamilySelector.selectAllDatasetFamilies);
         this.datasetListIsLoading = this.store.select(datasetSelector.selectDatasetListIsLoading);
         this.datasetListIsLoaded = this.store.select(datasetSelector.selectDatasetListIsLoaded);
-        this.datasetList = this.store.select(datasetSelector.selectAllDatasets);
+        this.datasetList = this.store.select(datasetSelector.selectAllConeSearchDatasets);
         this.currentStep = this.store.select(searchMultipleSelector.selectCurrentStep)
         this.selectedDatasets = this.store.select(searchMultipleSelector.selectSelectedDatasets);
         this.coneSearch = this.store.select(coneSearchSelector.selectConeSearch);
@@ -41,8 +45,14 @@ export abstract class AbstractSearchMultipleComponent implements OnInit, OnDestr
     }
     
     ngOnInit() {
-        Promise.resolve(null).then(() => this.store.dispatch(searchMultipleActions.initSearch()));
+        this.datasetListSubscription = this.datasetListIsLoaded.subscribe(datasetListIsLoaded =>  {
+            if (datasetListIsLoaded) {
+                Promise.resolve(null).then(() => this.store.dispatch(searchMultipleActions.initSearch()));
+            }
+        })
     }
 
-    ngOnDestroy() { }
+    ngOnDestroy() {
+        this.datasetListSubscription.unsubscribe();
+    }
 }
diff --git a/client/src/app/instance/search-multiple/containers/position.component.html b/client/src/app/instance/search-multiple/containers/position.component.html
index cb9ef95a..c12f7eee 100644
--- a/client/src/app/instance/search-multiple/containers/position.component.html
+++ b/client/src/app/instance/search-multiple/containers/position.component.html
@@ -1,7 +1,7 @@
-<app-spinner *ngIf="(datasetFamilyListIsLoading | async) || (datasetListIsLoading | async)">
+<app-spinner *ngIf="(pristine | async) || (datasetFamilyListIsLoading | async) || (datasetListIsLoading | async)">
 </app-spinner>
 
-<div *ngIf="(datasetFamilyListIsLoaded | async) && (datasetListIsLoaded | async)" class="row mt-4">
+<div *ngIf="!(pristine | async) && (datasetFamilyListIsLoaded | async) && (datasetListIsLoaded | async)" class="row mt-4">
     <div class="col-12 col-md-8 col-lg-9">
         <div class="border rounded my-2">
             <p class="border-bottom bg-light text-primary mb-0 py-4 pl-4">Cone Search</p>
diff --git a/client/src/app/instance/search-multiple/containers/result-multiple.component.html b/client/src/app/instance/search-multiple/containers/result-multiple.component.html
index 84f8d63b..258f1567 100644
--- a/client/src/app/instance/search-multiple/containers/result-multiple.component.html
+++ b/client/src/app/instance/search-multiple/containers/result-multiple.component.html
@@ -4,6 +4,7 @@
 <div *ngIf="(datasetFamilyListIsLoaded | async) && (datasetListIsLoaded | async) || (dataLengthIsLoaded | async)" class="row mt-4">
     <div class="col-12">
         <app-overview
+            [instanceSelected]="instanceSelected | async"
             [datasetFamilyList]="datasetFamilyList | async"
             [datasetList]="datasetList | async"
             [coneSearch]="coneSearch | async"
diff --git a/client/src/app/instance/search-multiple/containers/result-multiple.component.ts b/client/src/app/instance/search-multiple/containers/result-multiple.component.ts
index d6118271..3e4d66b4 100644
--- a/client/src/app/instance/search-multiple/containers/result-multiple.component.ts
+++ b/client/src/app/instance/search-multiple/containers/result-multiple.component.ts
@@ -22,7 +22,6 @@ import * as searchMultipleSelector from 'src/app/instance/store/selectors/search
     templateUrl: 'result-multiple.component.html'
 })
 export class ResultMultipleComponent extends AbstractSearchMultipleComponent {
-    public pristine: Observable<boolean>;
     public dataLength: Observable<SearchMultipleDatasetLength[]>;
     public dataLengthIsLoading: Observable<boolean>;
     public dataLengthIsLoaded: Observable<boolean>;
@@ -34,7 +33,6 @@ export class ResultMultipleComponent extends AbstractSearchMultipleComponent {
 
     constructor(protected store: Store<{ }>) {
         super(store);
-        this.pristine = this.store.select(searchMultipleSelector.selectPristine);
         this.dataLength = this.store.select(searchMultipleSelector.selectDataLength);
         this.dataLengthIsLoading = this.store.select(searchMultipleSelector.selectDataLengthIsLoading);
         this.dataLengthIsLoaded = this.store.select(searchMultipleSelector.selectDataLengthIsLoaded);
diff --git a/client/src/app/instance/store/actions/search-multiple.actions.ts b/client/src/app/instance/store/actions/search-multiple.actions.ts
index 173a56ec..87d20074 100644
--- a/client/src/app/instance/store/actions/search-multiple.actions.ts
+++ b/client/src/app/instance/store/actions/search-multiple.actions.ts
@@ -12,6 +12,7 @@ import { createAction, props } from '@ngrx/store';
 import { SearchMultipleDatasetLength, SearchMultipleDatasetData } from '../models';
 
 export const initSearch = createAction('[Search Multiple] Init Search');
+export const restartSearch = createAction('[Search Multiple] Restart Search');
 export const markAsDirty = createAction('[Search Multiple] Mark As Dirty');
 export const changeStep = createAction('[Search Multiple] Change Step', props<{ step: string }>());
 export const checkDatasets = createAction('[Search Multiple] Check Datasets');
diff --git a/client/src/app/instance/store/effects/search-multiple.effects.ts b/client/src/app/instance/store/effects/search-multiple.effects.ts
index 27078901..84382d44 100644
--- a/client/src/app/instance/store/effects/search-multiple.effects.ts
+++ b/client/src/app/instance/store/effects/search-multiple.effects.ts
@@ -17,6 +17,8 @@ import { ToastrService } from 'ngx-toastr';
 
 import { SearchMultipleDatasetLength } from '../models';
 import { SearchService } from '../services/search.service';
+import * as instanceSelector from 'src/app/metamodel/selectors/instance.selector';
+import * as datasetSelector from 'src/app/metamodel/selectors/dataset.selector';
 import * as searchMultipleActions from '../actions/search-multiple.actions';
 import * as searchMultipleSelector from '../selectors/search-multiple.selector';
 import * as coneSearchActions from '../actions/cone-search.actions';
@@ -30,9 +32,19 @@ export class SearchMultipleEffects {
             concatLatestFrom(() => [
                 this.store.select(searchMultipleSelector.selectPristine),
                 this.store.select(coneSearchSelector.selectConeSearchByRoute),
-                this.store.select(searchMultipleSelector.selectSelectedDatasetsByRoute)
+                this.store.select(searchMultipleSelector.selectSelectedDatasetsByRoute),
+                this.store.select(instanceSelector.selectInstanceByRouteName),
+                this.store.select(datasetSelector.selectAllConeSearchDatasets)
             ]),
-            mergeMap(([action, pristine, coneSearchByRoute, selectedDatasetsByRoute]) => {
+            mergeMap(([action, pristine, coneSearchByRoute, selectedDatasetsByRoute, instance, datasetList]) => {
+                if (!pristine && !coneSearchByRoute) {
+                    // Restart search
+                    return [
+                        coneSearchActions.deleteConeSearch(),
+                        searchMultipleActions.restartSearch()
+                    ];
+                }
+
                 if (!pristine) {
                     // Default form parameters already loaded or no dataset selected
                     return of({ type: '[No Action] Load Default Form Parameters' });
@@ -61,6 +73,11 @@ export class SearchMultipleEffects {
                         searchMultipleActions.updateSelectedDatasets({ selectedDatasets }),
                         searchMultipleActions.checkDatasets()
                     );
+                } else if (instance.config.search.search_multiple_all_datasets_selected) {
+                    const selectedDatasets = datasetList.map(dataset => dataset.name);
+                    actions.push(
+                        searchMultipleActions.updateSelectedDatasets({ selectedDatasets })
+                    );
                 }
 
                 // Returns actions and mark the form as dirty
@@ -69,6 +86,13 @@ export class SearchMultipleEffects {
         )
     );
 
+    restartSearch$ = createEffect(() => 
+        this.actions$.pipe(
+            ofType(searchMultipleActions.restartSearch),
+            map(() => searchMultipleActions.initSearch())
+        )
+    );
+
     retrieveDataLength$ = createEffect(() =>
         this.actions$.pipe(
             ofType(searchMultipleActions.retrieveDataLength),
diff --git a/client/src/app/instance/store/reducers/search-multiple.reducer.ts b/client/src/app/instance/store/reducers/search-multiple.reducer.ts
index af05dbda..bd73fbba 100644
--- a/client/src/app/instance/store/reducers/search-multiple.reducer.ts
+++ b/client/src/app/instance/store/reducers/search-multiple.reducer.ts
@@ -44,6 +44,10 @@ export const initialState: State = {
 
 export const searchMultipleReducer = createReducer(
     initialState,
+    on(searchMultipleActions.restartSearch, () => ({
+        ...initialState,
+        currentStep: 'position'
+    })),
     on(searchMultipleActions.changeStep, (state, { step }) => ({
         ...state,
         currentStep: step
diff --git a/client/src/app/metamodel/selectors/dataset.selector.ts b/client/src/app/metamodel/selectors/dataset.selector.ts
index 71294e91..d456b9e1 100644
--- a/client/src/app/metamodel/selectors/dataset.selector.ts
+++ b/client/src/app/metamodel/selectors/dataset.selector.ts
@@ -57,3 +57,8 @@ export const selectDatasetNameByRoute = createSelector(
     reducer.selectRouterState,
     router => router.state.params.dname as string
 );
+
+export const selectAllConeSearchDatasets = createSelector(
+    selectAllDatasets,
+    datasetList => datasetList.filter(dataset => dataset.config.cone_search.cone_search_enabled)
+);
\ No newline at end of file
-- 
GitLab