@cumulus/es-client 15.0.3 → 16.0.2-alpha.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (3) hide show
  1. package/indexer.js +47 -13
  2. package/package.json +8 -8
  3. package/search.js +7 -78
package/indexer.js CHANGED
@@ -127,6 +127,14 @@ function updateAsyncOperation(esClient, id, updates, index = defaultIndexAlias,
127
127
  return updateExistingRecord(esClient, id, updates, index, type);
128
128
  }
129
129
 
130
+ const executionInvalidNullFields = [
131
+ 'arn',
132
+ 'name',
133
+ 'status',
134
+ 'updatedAt',
135
+ 'createdAt',
136
+ ];
137
+
130
138
  /**
131
139
  * Upsert an execution record in Elasticsearch
132
140
  *
@@ -136,6 +144,8 @@ function updateAsyncOperation(esClient, id, updates, index = defaultIndexAlias,
136
144
  * @param {string} params.index - Elasticsearch index alias (default defined in search.js)
137
145
  * @param {string} params.type - Elasticsearch type (default: execution)
138
146
  * @param {string} [params.refresh] - whether to refresh the index on update or not
147
+ * @param {boolean} writeConstraints - boolean toggle restricting if conditionals should
148
+ * be used to determine write eligibility
139
149
  * @returns {Promise} elasticsearch update response
140
150
  */
141
151
  async function upsertExecution({
@@ -144,11 +154,42 @@ async function upsertExecution({
144
154
  index = defaultIndexAlias,
145
155
  type = 'execution',
146
156
  refresh,
147
- }) {
157
+ }, writeConstraints = true) {
158
+ Object.keys(updates).forEach((key) => {
159
+ if (updates[key] === null && executionInvalidNullFields.includes(key)) {
160
+ throw new ValidationError(`Attempted Elasticsearch write with invalid key ${key} set to null. Please remove or change this field and retry`);
161
+ }
162
+ });
163
+
148
164
  const upsertDoc = {
149
- ...updates,
150
- timestamp: Date.now(),
165
+ ...removeNilProperties(updates),
166
+ timestamp: updates.timestamp || Date.now(),
151
167
  };
168
+
169
+ let removeString = '';
170
+ // Set field removal for null values
171
+ Object.entries(updates).forEach(([fieldName, value]) => {
172
+ if (value === null) {
173
+ removeString += `ctx._source.remove('${fieldName}'); `;
174
+ }
175
+ });
176
+
177
+ let inlineDocWriteString = 'ctx._source.putAll(params.doc);';
178
+ if (removeString !== '') {
179
+ inlineDocWriteString += removeString;
180
+ }
181
+ let inline = inlineDocWriteString;
182
+ if (writeConstraints === true) {
183
+ inline = `
184
+ if (params.doc.status == "running") {
185
+ ctx._source.updatedAt = params.doc.updatedAt;
186
+ ctx._source.timestamp = params.doc.timestamp;
187
+ ctx._source.originalPayload = params.doc.originalPayload;
188
+ } else {
189
+ ${inlineDocWriteString}
190
+ }
191
+ `;
192
+ }
152
193
  return await esClient.update({
153
194
  index,
154
195
  type,
@@ -156,15 +197,7 @@ async function upsertExecution({
156
197
  body: {
157
198
  script: {
158
199
  lang: 'painless',
159
- inline: `
160
- if (params.doc.status == "running") {
161
- ctx._source.updatedAt = params.doc.updatedAt;
162
- ctx._source.timestamp = params.doc.timestamp;
163
- ctx._source.originalPayload = params.doc.originalPayload;
164
- } else {
165
- ctx._source.putAll(params.doc)
166
- }
167
- `,
200
+ inline,
168
201
  params: {
169
202
  doc: upsertDoc,
170
203
  },
@@ -320,7 +353,7 @@ async function upsertGranule({
320
353
  }, writeConstraints = true) {
321
354
  Object.keys(updates).forEach((key) => {
322
355
  if (updates[key] === null && granuleInvalidNullFields.includes(key)) {
323
- throw new ValidationError(`Attempted DynamoDb write with invalid key ${key} set to null. Please remove or change this field and retry`);
356
+ throw new ValidationError(`Attempted Elasticsearch write with invalid key ${key} set to null. Please remove or change this field and retry`);
324
357
  }
325
358
  });
326
359
  // If the granule exists in 'deletedgranule', delete it first before inserting the granule
@@ -766,5 +799,6 @@ module.exports = {
766
799
  deleteGranule,
767
800
  deleteExecution,
768
801
  deleteReconciliationReport,
802
+ executionInvalidNullFields,
769
803
  granuleInvalidNullFields,
770
804
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@cumulus/es-client",
3
- "version": "15.0.3",
3
+ "version": "16.0.2-alpha.0",
4
4
  "description": "Utilities for working with Elasticsearch",
5
5
  "keywords": [
6
6
  "CUMULUS",
@@ -30,10 +30,10 @@
30
30
  "author": "Cumulus Authors",
31
31
  "license": "Apache-2.0",
32
32
  "dependencies": {
33
- "@cumulus/common": "15.0.3",
34
- "@cumulus/errors": "15.0.3",
35
- "@cumulus/logger": "15.0.3",
36
- "@cumulus/message": "15.0.3",
33
+ "@cumulus/common": "16.0.2-alpha.0",
34
+ "@cumulus/errors": "16.0.2-alpha.0",
35
+ "@cumulus/logger": "16.0.2-alpha.0",
36
+ "@cumulus/message": "16.0.2-alpha.0",
37
37
  "@elastic/elasticsearch": "^5.6.20",
38
38
  "aws-elasticsearch-connector": "8.2.0",
39
39
  "aws-sdk": "^2.585.0",
@@ -42,9 +42,9 @@
42
42
  "p-limit": "^1.2.0"
43
43
  },
44
44
  "devDependencies": {
45
- "@cumulus/aws-client": "15.0.3",
46
- "@cumulus/test-data": "15.0.3",
45
+ "@cumulus/aws-client": "16.0.2-alpha.0",
46
+ "@cumulus/test-data": "16.0.2-alpha.0",
47
47
  "p-each-series": "^2.1.0"
48
48
  },
49
- "gitHead": "5fd5febe740ef96f365d1defc7b9f76ae64c9cc0"
49
+ "gitHead": "215833a8dbf46eff436099c9d056cf697df9903f"
50
50
  }
package/search.js CHANGED
@@ -23,6 +23,8 @@ const logDetails = {
23
23
  };
24
24
 
25
25
  const defaultIndexAlias = 'cumulus-alias';
26
+ const multipleRecordFoundString = 'More than one record was found!';
27
+ const recordNotFoundString = 'Record not found';
26
28
 
27
29
  const getCredentials = () =>
28
30
  new Promise((resolve, reject) => aws.config.getCredentials((err) => {
@@ -135,12 +137,6 @@ class BaseSearch {
135
137
  this.frm = (page - 1) * this.size;
136
138
  this.page = Number.parseInt((params.skip) ? params.skip : page, 10);
137
139
  this.index = index || defaultIndexAlias;
138
-
139
- if (this.type === process.env.CollectionsTable) {
140
- this.hash = 'collectionName';
141
- } else if (this.type === process.env.PdrsTable) {
142
- this.hash = 'pdrName';
143
- }
144
140
  }
145
141
 
146
142
  _buildSearch() {
@@ -234,10 +230,10 @@ class BaseSearch {
234
230
  }).then((response) => response.body);
235
231
 
236
232
  if (result.hits.total > 1) {
237
- return { detail: 'More than one record was found!' };
233
+ return { detail: multipleRecordFoundString };
238
234
  }
239
235
  if (result.hits.total === 0) {
240
- return { detail: 'Record not found' };
236
+ return { detail: recordNotFoundString };
241
237
  }
242
238
 
243
239
  const resp = result.hits.hits[0]._source;
@@ -247,76 +243,7 @@ class BaseSearch {
247
243
 
248
244
  async exists(id, parentId) {
249
245
  const response = await this.get(id, parentId);
250
- return response.detail !== 'Record not found';
251
- }
252
-
253
- async granulesStats(key, value) {
254
- const body = {
255
- query: {
256
- term: {
257
- [`${key}.keyword`]: value,
258
- },
259
- },
260
- aggs: {
261
- statusCount: {
262
- terms: {
263
- field: 'status.keyword',
264
- },
265
- },
266
- averageDuration: {
267
- avg: {
268
- field: 'duration',
269
- },
270
- },
271
- granulesCount: {
272
- value_count: {
273
- field: 'granuleId.keyword',
274
- },
275
- },
276
- },
277
- };
278
-
279
- const ag = await this.client.search({
280
- index: this.index,
281
- type: process.env.GranulesTable,
282
- body: body,
283
- size: 0,
284
- });
285
-
286
- const status = {
287
- failed: 0,
288
- ingesting: 0,
289
- processing: 0,
290
- archiving: 0,
291
- cmr: 0,
292
- completed: 0,
293
- };
294
-
295
- const item = ag.body.aggregations;
296
-
297
- const newObj = {
298
- averageDuration: item.averageDuration.value,
299
- granules: item.granulesCount.value,
300
- granulesStatus: { ...status },
301
- };
302
-
303
- item.statusCount.buckets.forEach((b) => {
304
- newObj.granulesStatus[b.key] = b.doc_count;
305
- });
306
-
307
- if (newObj.granules > 0) {
308
- newObj.progress = (
309
- (
310
- (newObj.granulesStatus.completed + newObj.granulesStatus.failed)
311
- / newObj.granules
312
- )
313
- * 100
314
- );
315
- } else {
316
- newObj.progress = 0;
317
- }
318
-
319
- return newObj;
246
+ return response.detail !== recordNotFoundString;
320
247
  }
321
248
 
322
249
  async query(searchParamsOverride) {
@@ -378,5 +305,7 @@ module.exports = {
378
305
  BaseSearch,
379
306
  Search,
380
307
  defaultIndexAlias,
308
+ multipleRecordFoundString,
309
+ recordNotFoundString,
381
310
  getLocalEsHost,
382
311
  };