@@ -10,7 +10,7 @@ including this file, may be copied, modified, propagated, or distributed
10
10
except according to the terms contained in the LICENSE file.
11
11
-->
12
12
<template >
13
- <div >
13
+ <div id = " dataset-entities " >
14
14
<page-section >
15
15
<template #heading >
16
16
<span >{{ $t('resource.entities') }}</span >
@@ -19,10 +19,22 @@ except according to the terms contained in the LICENSE file.
19
19
class =" btn btn-primary" @click =" upload.show()" >
20
20
<span class =" icon-upload" ></span >{{ $t('action.upload') }}
21
21
</button >
22
- <odata-data-access @analyze =" analyze.show()" />
22
+ <template v-if =" deletedEntityCount .dataExists " >
23
+ <button v-if =" canDelete && (deletedEntityCount.value > 0 || deleted)" type =" button"
24
+ class =" btn toggle-deleted-entities" :class =" { 'btn-danger': deleted, 'btn-link': !deleted }"
25
+ @click =" toggleDeleted" >
26
+ <span class =" icon-trash" ></span >{{ $tcn('action.toggleDeletedEntities', deletedEntityCount.value) }}
27
+ <span v-show =" deleted" class =" icon-close" ></span >
28
+ </button >
29
+ </template >
30
+ <odata-data-access :analyze-disabled =" deleted"
31
+ :analyze-disabled-message =" $t('analyzeDisabledDeletedData')"
32
+ @analyze =" analyze.show()" />
23
33
</template >
24
34
<template #body >
25
- <entity-list ref =" list" :project-id =" projectId" :dataset-name =" datasetName" />
35
+ <entity-list ref =" list" :project-id =" projectId"
36
+ :dataset-name =" datasetName" :deleted =" deleted"
37
+ @fetch-deleted-count =" fetchDeletedCount" />
26
38
</template >
27
39
</page-section >
28
40
@@ -33,17 +45,21 @@ except according to the terms contained in the LICENSE file.
33
45
</template >
34
46
35
47
<script >
36
- import { defineAsyncComponent } from ' vue' ;
48
+ import { defineAsyncComponent , watchEffect , computed } from ' vue' ;
49
+ import { useRouter } from ' vue-router' ;
37
50
38
51
import EntityList from ' ../entity/list.vue' ;
39
52
import OdataAnalyze from ' ../odata/analyze.vue' ;
40
53
import OdataDataAccess from ' ../odata/data-access.vue' ;
41
54
import PageSection from ' ../page/section.vue' ;
55
+ import useEntities from ' ../../request-data/entities' ;
56
+ import useQueryRef from ' ../../composables/query-ref' ;
42
57
43
58
import { apiPaths } from ' ../../util/request' ;
44
59
import { loadAsync } from ' ../../util/load-async' ;
45
60
import { modalData } from ' ../../util/reactivity' ;
46
61
import { useRequestData } from ' ../../request-data' ;
62
+ import { noop } from ' ../../util/util' ;
47
63
48
64
export default {
49
65
name: ' DatasetEntities' ,
@@ -67,7 +83,28 @@ export default {
67
83
},
68
84
setup () {
69
85
const { project , dataset } = useRequestData ();
70
- return { project, dataset };
86
+ const { deletedEntityCount } = useEntities ();
87
+ const router = useRouter ();
88
+
89
+ const deleted = useQueryRef ({
90
+ fromQuery : (query ) => {
91
+ if (typeof query .deleted === ' string' && query .deleted === ' true' ) {
92
+ return true ;
93
+ }
94
+ return false ;
95
+ },
96
+ toQuery : (value ) => ({
97
+ deleted: value === true ? ' true' : null
98
+ })
99
+ });
100
+
101
+ const canDelete = computed (() => project .dataExists && project .permits (' entity.delete' ));
102
+
103
+ watchEffect (() => {
104
+ if (deleted .value && project .dataExists && ! canDelete .value ) router .push (' /' );
105
+ });
106
+
107
+ return { project, dataset, deletedEntityCount, deleted, canDelete };
71
108
},
72
109
data () {
73
110
return {
@@ -81,6 +118,9 @@ export default {
81
118
return ` ${ window .location .origin }${ path} ` ;
82
119
}
83
120
},
121
+ created () {
122
+ if (! this .deleted ) this .fetchDeletedCount ();
123
+ },
84
124
methods: {
85
125
afterUpload (count ) {
86
126
this .upload .hide ();
@@ -89,21 +129,66 @@ export default {
89
129
// Update dataset.entities so that the count in the OData loading message
90
130
// reflects the new entities.
91
131
this .dataset .entities += count;
132
+ },
133
+ fetchDeletedCount () {
134
+ this .deletedEntityCount .request ({
135
+ method: ' GET' ,
136
+ url: apiPaths .odataEntities (
137
+ this .projectId ,
138
+ this .datasetName ,
139
+ {
140
+ $top: 0 ,
141
+ $count: true ,
142
+ $filter: ' __system/deletedAt ne null' ,
143
+ }
144
+ ),
145
+ }).catch (noop);
146
+ },
147
+ toggleDeleted () {
148
+ const { path } = this .$route ;
149
+ this .$router .push (this .deleted ? path : ` ${ path} ?deleted=true` );
92
150
}
93
151
}
94
152
};
95
153
</script >
96
154
97
155
<style lang="scss">
156
+ @import ' ../../assets/scss/variables' ;
157
+
98
158
#odata-data-access { float : right ; }
159
+
160
+ #dataset-entities {
161
+ .toggle-deleted-entities {
162
+ margin-left : 8px ;
163
+
164
+ & .btn-link {
165
+ color : $color-danger ;
166
+ }
167
+
168
+ .icon-close { margin-left : 3px ; }
169
+ }
170
+
171
+ .purge-description {
172
+ display : inline ;
173
+ position : relative ;
174
+ top : -5px ;
175
+ left : 12px ;
176
+ font-size : 14px ;
177
+ }
178
+ }
99
179
</style >
100
180
101
181
<i18n lang="json5">
102
182
{
103
183
"en": {
104
184
"alert": {
105
185
"upload": "Success! Your Entities have been uploaded."
106
- }
186
+ },
187
+ "purgeDescription": "Entities are deleted after 30 days in the Trash",
188
+ "action": {
189
+ "toggleDeletedEntities": "{count} deleted Entity | {count} deleted Entities"
190
+ },
191
+ "analyzeDisabledDeletedData": "OData access is unavailable for deleted Entities",
107
192
}
108
193
}
109
194
</i18n >
0 commit comments