@webiny/api-headless-cms-ddb-es 5.41.0-dbt.0 → 5.41.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.
package/configurations.js CHANGED
@@ -21,9 +21,9 @@ const configurations = exports.configurations = {
21
21
  } else if (!locale) {
22
22
  throw new _error.default(`Missing "locale" parameter when trying to create Elasticsearch index name.`, "LOCALE_ERROR");
23
23
  }
24
- const sharedIndex = process.env.ELASTICSEARCH_SHARED_INDEXES === "true";
24
+ const sharedIndex = (0, _apiElasticsearch.isSharedElasticsearchIndex)();
25
25
  const index = [sharedIndex ? "root" : tenant, "headless-cms", locale, model.modelId].join("-").toLowerCase();
26
- const prefix = process.env.ELASTIC_SEARCH_INDEX_PREFIX || "";
26
+ const prefix = (0, _apiElasticsearch.getElasticsearchIndexPrefix)();
27
27
  if (!prefix) {
28
28
  return {
29
29
  index
@@ -1 +1 @@
1
- {"version":3,"names":["_error","_interopRequireDefault","require","_apiElasticsearch","_plugins","configurations","exports","es","model","tenant","locale","WebinyError","sharedIndex","process","env","ELASTICSEARCH_SHARED_INDEXES","index","modelId","join","toLowerCase","prefix","ELASTIC_SEARCH_INDEX_PREFIX","indexSettings","context","plugin","getLastAddedIndexPlugin","container","plugins","type","CmsEntryElasticsearchIndexPlugin","body"],"sources":["configurations.ts"],"sourcesContent":["import { CmsModel } from \"@webiny/api-headless-cms/types\";\nimport WebinyError from \"@webiny/error\";\nimport { CmsContext } from \"~/types\";\nimport { getLastAddedIndexPlugin } from \"@webiny/api-elasticsearch\";\nimport { ElasticsearchIndexRequestBody } from \"@webiny/api-elasticsearch/types\";\nimport { CmsEntryElasticsearchIndexPlugin } from \"~/plugins\";\n\ninterface ConfigurationsElasticsearch {\n index: string;\n}\n\nexport interface CmsElasticsearchParams {\n model: Pick<CmsModel, \"tenant\" | \"locale\" | \"modelId\">;\n}\n\nexport interface ConfigurationsIndexSettingsParams {\n context: CmsContext;\n model: Pick<CmsModel, \"locale\">;\n}\n\nexport interface Configurations {\n es: (params: CmsElasticsearchParams) => ConfigurationsElasticsearch;\n indexSettings: (\n params: ConfigurationsIndexSettingsParams\n ) => Partial<ElasticsearchIndexRequestBody>;\n}\n\nexport const configurations: Configurations = {\n es({ model }) {\n const { tenant, locale } = model;\n\n if (!tenant) {\n throw new WebinyError(\n `Missing \"tenant\" parameter when trying to create Elasticsearch index name.`,\n \"TENANT_ERROR\"\n );\n } else if (!locale) {\n throw new WebinyError(\n `Missing \"locale\" parameter when trying to create Elasticsearch index name.`,\n \"LOCALE_ERROR\"\n );\n }\n\n const sharedIndex = process.env.ELASTICSEARCH_SHARED_INDEXES === \"true\";\n const index = [sharedIndex ? \"root\" : tenant, \"headless-cms\", locale, model.modelId]\n .join(\"-\")\n .toLowerCase();\n\n const prefix = process.env.ELASTIC_SEARCH_INDEX_PREFIX || \"\";\n if (!prefix) {\n return {\n index\n };\n }\n return {\n index: prefix + index\n };\n },\n indexSettings: ({ context, model }) => {\n const plugin = getLastAddedIndexPlugin<CmsEntryElasticsearchIndexPlugin>({\n container: context.plugins,\n type: CmsEntryElasticsearchIndexPlugin.type,\n locale: model.locale\n });\n\n return plugin ? plugin.body : {};\n }\n};\n"],"mappings":";;;;;;;AACA,IAAAA,MAAA,GAAAC,sBAAA,CAAAC,OAAA;AAEA,IAAAC,iBAAA,GAAAD,OAAA;AAEA,IAAAE,QAAA,GAAAF,OAAA;AAsBO,MAAMG,cAA8B,GAAAC,OAAA,CAAAD,cAAA,GAAG;EAC1CE,EAAEA,CAAC;IAAEC;EAAM,CAAC,EAAE;IACV,MAAM;MAAEC,MAAM;MAAEC;IAAO,CAAC,GAAGF,KAAK;IAEhC,IAAI,CAACC,MAAM,EAAE;MACT,MAAM,IAAIE,cAAW,CAChB,4EAA2E,EAC5E,cACJ,CAAC;IACL,CAAC,MAAM,IAAI,CAACD,MAAM,EAAE;MAChB,MAAM,IAAIC,cAAW,CAChB,4EAA2E,EAC5E,cACJ,CAAC;IACL;IAEA,MAAMC,WAAW,GAAGC,OAAO,CAACC,GAAG,CAACC,4BAA4B,KAAK,MAAM;IACvE,MAAMC,KAAK,GAAG,CAACJ,WAAW,GAAG,MAAM,GAAGH,MAAM,EAAE,cAAc,EAAEC,MAAM,EAAEF,KAAK,CAACS,OAAO,CAAC,CAC/EC,IAAI,CAAC,GAAG,CAAC,CACTC,WAAW,CAAC,CAAC;IAElB,MAAMC,MAAM,GAAGP,OAAO,CAACC,GAAG,CAACO,2BAA2B,IAAI,EAAE;IAC5D,IAAI,CAACD,MAAM,EAAE;MACT,OAAO;QACHJ;MACJ,CAAC;IACL;IACA,OAAO;MACHA,KAAK,EAAEI,MAAM,GAAGJ;IACpB,CAAC;EACL,CAAC;EACDM,aAAa,EAAEA,CAAC;IAAEC,OAAO;IAAEf;EAAM,CAAC,KAAK;IACnC,MAAMgB,MAAM,GAAG,IAAAC,yCAAuB,EAAmC;MACrEC,SAAS,EAAEH,OAAO,CAACI,OAAO;MAC1BC,IAAI,EAAEC,yCAAgC,CAACD,IAAI;MAC3ClB,MAAM,EAAEF,KAAK,CAACE;IAClB,CAAC,CAAC;IAEF,OAAOc,MAAM,GAAGA,MAAM,CAACM,IAAI,GAAG,CAAC,CAAC;EACpC;AACJ,CAAC","ignoreList":[]}
1
+ {"version":3,"names":["_error","_interopRequireDefault","require","_apiElasticsearch","_plugins","configurations","exports","es","model","tenant","locale","WebinyError","sharedIndex","isSharedElasticsearchIndex","index","modelId","join","toLowerCase","prefix","getElasticsearchIndexPrefix","indexSettings","context","plugin","getLastAddedIndexPlugin","container","plugins","type","CmsEntryElasticsearchIndexPlugin","body"],"sources":["configurations.ts"],"sourcesContent":["import { CmsModel } from \"@webiny/api-headless-cms/types\";\nimport WebinyError from \"@webiny/error\";\nimport { CmsContext } from \"~/types\";\nimport {\n getElasticsearchIndexPrefix,\n getLastAddedIndexPlugin,\n isSharedElasticsearchIndex\n} from \"@webiny/api-elasticsearch\";\nimport { ElasticsearchIndexRequestBody } from \"@webiny/api-elasticsearch/types\";\nimport { CmsEntryElasticsearchIndexPlugin } from \"~/plugins\";\n\ninterface ConfigurationsElasticsearch {\n index: string;\n}\n\nexport interface CmsElasticsearchParams {\n model: Pick<CmsModel, \"tenant\" | \"locale\" | \"modelId\">;\n}\n\nexport interface ConfigurationsIndexSettingsParams {\n context: CmsContext;\n model: Pick<CmsModel, \"locale\">;\n}\n\nexport interface Configurations {\n es: (params: CmsElasticsearchParams) => ConfigurationsElasticsearch;\n indexSettings: (\n params: ConfigurationsIndexSettingsParams\n ) => Partial<ElasticsearchIndexRequestBody>;\n}\n\nexport const configurations: Configurations = {\n es({ model }) {\n const { tenant, locale } = model;\n\n if (!tenant) {\n throw new WebinyError(\n `Missing \"tenant\" parameter when trying to create Elasticsearch index name.`,\n \"TENANT_ERROR\"\n );\n } else if (!locale) {\n throw new WebinyError(\n `Missing \"locale\" parameter when trying to create Elasticsearch index name.`,\n \"LOCALE_ERROR\"\n );\n }\n\n const sharedIndex = isSharedElasticsearchIndex();\n const index = [sharedIndex ? \"root\" : tenant, \"headless-cms\", locale, model.modelId]\n .join(\"-\")\n .toLowerCase();\n\n const prefix = getElasticsearchIndexPrefix();\n\n if (!prefix) {\n return {\n index\n };\n }\n return {\n index: prefix + index\n };\n },\n indexSettings: ({ context, model }) => {\n const plugin = getLastAddedIndexPlugin<CmsEntryElasticsearchIndexPlugin>({\n container: context.plugins,\n type: CmsEntryElasticsearchIndexPlugin.type,\n locale: model.locale\n });\n\n return plugin ? plugin.body : {};\n }\n};\n"],"mappings":";;;;;;;AACA,IAAAA,MAAA,GAAAC,sBAAA,CAAAC,OAAA;AAEA,IAAAC,iBAAA,GAAAD,OAAA;AAMA,IAAAE,QAAA,GAAAF,OAAA;AAsBO,MAAMG,cAA8B,GAAAC,OAAA,CAAAD,cAAA,GAAG;EAC1CE,EAAEA,CAAC;IAAEC;EAAM,CAAC,EAAE;IACV,MAAM;MAAEC,MAAM;MAAEC;IAAO,CAAC,GAAGF,KAAK;IAEhC,IAAI,CAACC,MAAM,EAAE;MACT,MAAM,IAAIE,cAAW,CAChB,4EAA2E,EAC5E,cACJ,CAAC;IACL,CAAC,MAAM,IAAI,CAACD,MAAM,EAAE;MAChB,MAAM,IAAIC,cAAW,CAChB,4EAA2E,EAC5E,cACJ,CAAC;IACL;IAEA,MAAMC,WAAW,GAAG,IAAAC,4CAA0B,EAAC,CAAC;IAChD,MAAMC,KAAK,GAAG,CAACF,WAAW,GAAG,MAAM,GAAGH,MAAM,EAAE,cAAc,EAAEC,MAAM,EAAEF,KAAK,CAACO,OAAO,CAAC,CAC/EC,IAAI,CAAC,GAAG,CAAC,CACTC,WAAW,CAAC,CAAC;IAElB,MAAMC,MAAM,GAAG,IAAAC,6CAA2B,EAAC,CAAC;IAE5C,IAAI,CAACD,MAAM,EAAE;MACT,OAAO;QACHJ;MACJ,CAAC;IACL;IACA,OAAO;MACHA,KAAK,EAAEI,MAAM,GAAGJ;IACpB,CAAC;EACL,CAAC;EACDM,aAAa,EAAEA,CAAC;IAAEC,OAAO;IAAEb;EAAM,CAAC,KAAK;IACnC,MAAMc,MAAM,GAAG,IAAAC,yCAAuB,EAAmC;MACrEC,SAAS,EAAEH,OAAO,CAACI,OAAO;MAC1BC,IAAI,EAAEC,yCAAgC,CAACD,IAAI;MAC3ChB,MAAM,EAAEF,KAAK,CAACE;IAClB,CAAC,CAAC;IAEF,OAAOY,MAAM,GAAGA,MAAM,CAACM,IAAI,GAAG,CAAC,CAAC;EACpC;AACJ,CAAC","ignoreList":[]}
@@ -9,15 +9,15 @@ var _error = _interopRequireDefault(require("@webiny/error"));
9
9
  var _CmsEntryFilterPlugin = require("../../../../../plugins/CmsEntryFilterPlugin");
10
10
  var _apiElasticsearch = require("@webiny/api-elasticsearch");
11
11
  const createRefFilterPlugin = () => {
12
- return new _CmsEntryFilterPlugin.CmsEntryFilterPlugin({
12
+ const plugin = new _CmsEntryFilterPlugin.CmsEntryFilterPlugin({
13
13
  fieldType: "ref",
14
14
  exec: params => {
15
15
  const {
16
16
  applyFiltering,
17
- value: values,
18
17
  query,
19
18
  field
20
19
  } = params;
20
+ let values = params.value;
21
21
  /**
22
22
  * We must have an object when querying in the ref field.
23
23
  */
@@ -26,6 +26,11 @@ const createRefFilterPlugin = () => {
26
26
  value: values
27
27
  });
28
28
  }
29
+ if (values === null || values === undefined) {
30
+ values = {
31
+ entryId: null
32
+ };
33
+ }
29
34
  for (const key in values) {
30
35
  const {
31
36
  operator
@@ -44,6 +49,8 @@ const createRefFilterPlugin = () => {
44
49
  }
45
50
  }
46
51
  });
52
+ plugin.name = `${plugin.type}.default.ref`;
53
+ return plugin;
47
54
  };
48
55
  exports.createRefFilterPlugin = createRefFilterPlugin;
49
56
 
@@ -1 +1 @@
1
- {"version":3,"names":["_error","_interopRequireDefault","require","_CmsEntryFilterPlugin","_apiElasticsearch","createRefFilterPlugin","CmsEntryFilterPlugin","fieldType","exec","params","applyFiltering","value","values","query","field","WebinyError","key","operator","parseWhereKey","undefined","exports"],"sources":["refFilterPlugin.ts"],"sourcesContent":["import WebinyError from \"@webiny/error\";\nimport { CmsEntryFilterPlugin } from \"~/plugins/CmsEntryFilterPlugin\";\nimport { parseWhereKey } from \"@webiny/api-elasticsearch\";\n\nexport const createRefFilterPlugin = () => {\n return new CmsEntryFilterPlugin({\n fieldType: \"ref\",\n exec: params => {\n const { applyFiltering, value: values, query, field } = params;\n /**\n * We must have an object when querying in the ref field.\n */\n if (typeof values !== \"object\") {\n throw new WebinyError(\n `When querying by ref field, value of the field must be an object.`,\n \"OBJECT_REQUIRED\",\n {\n value: values\n }\n );\n }\n\n for (const key in values) {\n const { operator } = parseWhereKey(key);\n const value = values[key];\n if (value === undefined) {\n continue;\n }\n\n applyFiltering({\n query,\n field,\n operator,\n key,\n value\n });\n }\n }\n });\n};\n"],"mappings":";;;;;;;AAAA,IAAAA,MAAA,GAAAC,sBAAA,CAAAC,OAAA;AACA,IAAAC,qBAAA,GAAAD,OAAA;AACA,IAAAE,iBAAA,GAAAF,OAAA;AAEO,MAAMG,qBAAqB,GAAGA,CAAA,KAAM;EACvC,OAAO,IAAIC,0CAAoB,CAAC;IAC5BC,SAAS,EAAE,KAAK;IAChBC,IAAI,EAAEC,MAAM,IAAI;MACZ,MAAM;QAAEC,cAAc;QAAEC,KAAK,EAAEC,MAAM;QAAEC,KAAK;QAAEC;MAAM,CAAC,GAAGL,MAAM;MAC9D;AACZ;AACA;MACY,IAAI,OAAOG,MAAM,KAAK,QAAQ,EAAE;QAC5B,MAAM,IAAIG,cAAW,CAChB,mEAAkE,EACnE,iBAAiB,EACjB;UACIJ,KAAK,EAAEC;QACX,CACJ,CAAC;MACL;MAEA,KAAK,MAAMI,GAAG,IAAIJ,MAAM,EAAE;QACtB,MAAM;UAAEK;QAAS,CAAC,GAAG,IAAAC,+BAAa,EAACF,GAAG,CAAC;QACvC,MAAML,KAAK,GAAGC,MAAM,CAACI,GAAG,CAAC;QACzB,IAAIL,KAAK,KAAKQ,SAAS,EAAE;UACrB;QACJ;QAEAT,cAAc,CAAC;UACXG,KAAK;UACLC,KAAK;UACLG,QAAQ;UACRD,GAAG;UACHL;QACJ,CAAC,CAAC;MACN;IACJ;EACJ,CAAC,CAAC;AACN,CAAC;AAACS,OAAA,CAAAf,qBAAA,GAAAA,qBAAA","ignoreList":[]}
1
+ {"version":3,"names":["_error","_interopRequireDefault","require","_CmsEntryFilterPlugin","_apiElasticsearch","createRefFilterPlugin","plugin","CmsEntryFilterPlugin","fieldType","exec","params","applyFiltering","query","field","values","value","WebinyError","undefined","entryId","key","operator","parseWhereKey","name","type","exports"],"sources":["refFilterPlugin.ts"],"sourcesContent":["import WebinyError from \"@webiny/error\";\nimport { CmsEntryFilterPlugin } from \"~/plugins/CmsEntryFilterPlugin\";\nimport { parseWhereKey } from \"@webiny/api-elasticsearch\";\n\nexport const createRefFilterPlugin = () => {\n const plugin = new CmsEntryFilterPlugin({\n fieldType: \"ref\",\n exec: params => {\n const { applyFiltering, query, field } = params;\n\n let values = params.value;\n /**\n * We must have an object when querying in the ref field.\n */\n if (typeof values !== \"object\") {\n throw new WebinyError(\n `When querying by ref field, value of the field must be an object.`,\n \"OBJECT_REQUIRED\",\n {\n value: values\n }\n );\n }\n\n if (values === null || values === undefined) {\n values = {\n entryId: null\n };\n }\n\n for (const key in values) {\n const { operator } = parseWhereKey(key);\n const value = values[key];\n if (value === undefined) {\n continue;\n }\n\n applyFiltering({\n query,\n field,\n operator,\n key,\n value\n });\n }\n }\n });\n\n plugin.name = `${plugin.type}.default.ref`;\n\n return plugin;\n};\n"],"mappings":";;;;;;;AAAA,IAAAA,MAAA,GAAAC,sBAAA,CAAAC,OAAA;AACA,IAAAC,qBAAA,GAAAD,OAAA;AACA,IAAAE,iBAAA,GAAAF,OAAA;AAEO,MAAMG,qBAAqB,GAAGA,CAAA,KAAM;EACvC,MAAMC,MAAM,GAAG,IAAIC,0CAAoB,CAAC;IACpCC,SAAS,EAAE,KAAK;IAChBC,IAAI,EAAEC,MAAM,IAAI;MACZ,MAAM;QAAEC,cAAc;QAAEC,KAAK;QAAEC;MAAM,CAAC,GAAGH,MAAM;MAE/C,IAAII,MAAM,GAAGJ,MAAM,CAACK,KAAK;MACzB;AACZ;AACA;MACY,IAAI,OAAOD,MAAM,KAAK,QAAQ,EAAE;QAC5B,MAAM,IAAIE,cAAW,CAChB,mEAAkE,EACnE,iBAAiB,EACjB;UACID,KAAK,EAAED;QACX,CACJ,CAAC;MACL;MAEA,IAAIA,MAAM,KAAK,IAAI,IAAIA,MAAM,KAAKG,SAAS,EAAE;QACzCH,MAAM,GAAG;UACLI,OAAO,EAAE;QACb,CAAC;MACL;MAEA,KAAK,MAAMC,GAAG,IAAIL,MAAM,EAAE;QACtB,MAAM;UAAEM;QAAS,CAAC,GAAG,IAAAC,+BAAa,EAACF,GAAG,CAAC;QACvC,MAAMJ,KAAK,GAAGD,MAAM,CAACK,GAAG,CAAC;QACzB,IAAIJ,KAAK,KAAKE,SAAS,EAAE;UACrB;QACJ;QAEAN,cAAc,CAAC;UACXC,KAAK;UACLC,KAAK;UACLO,QAAQ;UACRD,GAAG;UACHJ;QACJ,CAAC,CAAC;MACN;IACJ;EACJ,CAAC,CAAC;EAEFT,MAAM,CAACgB,IAAI,GAAI,GAAEhB,MAAM,CAACiB,IAAK,cAAa;EAE1C,OAAOjB,MAAM;AACjB,CAAC;AAACkB,OAAA,CAAAnB,qBAAA,GAAAA,qBAAA","ignoreList":[]}
@@ -7,6 +7,7 @@ Object.defineProperty(exports, "__esModule", {
7
7
  exports.createInitialQuery = exports.createBaseQuery = void 0;
8
8
  var _error = _interopRequireDefault(require("@webiny/error"));
9
9
  var _recordType = require("../recordType");
10
+ var _apiElasticsearch = require("@webiny/api-elasticsearch");
10
11
  const createBaseQuery = () => {
11
12
  return {
12
13
  must: [],
@@ -36,7 +37,7 @@ const createInitialQuery = params => {
36
37
  *
37
38
  * TODO determine if we want to search across tenants in shared index?
38
39
  */
39
- const sharedIndex = process.env.ELASTICSEARCH_SHARED_INDEXES === "true";
40
+ const sharedIndex = (0, _apiElasticsearch.isSharedElasticsearchIndex)();
40
41
  if (sharedIndex) {
41
42
  /**
42
43
  * Tenant for the filtering is taken from the model.
@@ -1 +1 @@
1
- {"version":3,"names":["_error","_interopRequireDefault","require","_recordType","createBaseQuery","must","must_not","should","filter","exports","createInitialQuery","params","model","where","query","sharedIndex","process","env","ELASTICSEARCH_SHARED_INDEXES","push","term","tenant","modelId","locale","published","createPublishedRecordType","latest","createLatestRecordType","WebinyError"],"sources":["initialQuery.ts"],"sourcesContent":["import WebinyError from \"@webiny/error\";\nimport { ElasticsearchBoolQueryConfig } from \"@webiny/api-elasticsearch/types\";\nimport { CmsEntryListWhere, CmsModel } from \"@webiny/api-headless-cms/types\";\nimport { createLatestRecordType, createPublishedRecordType } from \"../recordType\";\n\nexport const createBaseQuery = (): ElasticsearchBoolQueryConfig => {\n return {\n must: [],\n must_not: [],\n should: [],\n filter: []\n };\n};\n\ninterface Params {\n model: CmsModel;\n where: CmsEntryListWhere;\n}\n/**\n * Latest and published are specific in Elasticsearch to that extend that they are tagged in the __type property.\n * We allow either published or either latest.\n * Latest is used in the manage API and published in the read API.\n *\n *\n * We add the query.filter terms because we do not need scored search here and it is a bit faster.\n */\nexport const createInitialQuery = (params: Params): ElasticsearchBoolQueryConfig => {\n const { model, where } = params;\n\n const query = createBaseQuery();\n\n /**\n * When ES index is shared between tenants, we need to filter records by tenant ID\n *\n * TODO determine if we want to search across tenants in shared index?\n */\n const sharedIndex = process.env.ELASTICSEARCH_SHARED_INDEXES === \"true\";\n if (sharedIndex) {\n /**\n * Tenant for the filtering is taken from the model.\n *\n * TODO determine if we want to send it in the \"where\" parameter?\n */\n query.filter.push({\n term: {\n \"tenant.keyword\": model.tenant\n }\n });\n /**\n * Also, we must search only in selected model.\n */\n query.filter.push({\n term: {\n \"modelId.keyword\": model.modelId\n }\n });\n /**\n * TODO determine if we want to search across locales?\n * This search would anyway work for a single model and when sharing index.\n */\n query.filter.push({\n term: {\n \"locale.keyword\": model.locale\n }\n });\n }\n\n /**\n * We must transform published and latest where args into something that is understandable by our Elasticsearch\n */\n if (where.published === true) {\n query.filter.push({\n term: {\n \"__type.keyword\": createPublishedRecordType()\n }\n });\n } else if (where.latest === true) {\n query.filter.push({\n term: {\n \"__type.keyword\": createLatestRecordType()\n }\n });\n }\n //\n /**\n * We do not allow filtering without the published or latest parameter.\n * Also, we do not want to set the default one, as there is a large possibility for user error when filtering.\n */\n else {\n throw new WebinyError(\n `Cannot call Elasticsearch query when not setting \"published\" or \"latest\".`,\n \"ELASTICSEARCH_UNSUPPORTED_QUERY\",\n {\n where\n }\n );\n }\n /**\n * We need to remove fields that actually do not exist on the record - it will break otherwise.\n * This will modify the original object, which is what we want.\n */\n delete where.published;\n delete where.latest;\n\n return query;\n};\n"],"mappings":";;;;;;;AAAA,IAAAA,MAAA,GAAAC,sBAAA,CAAAC,OAAA;AAGA,IAAAC,WAAA,GAAAD,OAAA;AAEO,MAAME,eAAe,GAAGA,CAAA,KAAoC;EAC/D,OAAO;IACHC,IAAI,EAAE,EAAE;IACRC,QAAQ,EAAE,EAAE;IACZC,MAAM,EAAE,EAAE;IACVC,MAAM,EAAE;EACZ,CAAC;AACL,CAAC;AAACC,OAAA,CAAAL,eAAA,GAAAA,eAAA;AAMF;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACO,MAAMM,kBAAkB,GAAIC,MAAc,IAAmC;EAChF,MAAM;IAAEC,KAAK;IAAEC;EAAM,CAAC,GAAGF,MAAM;EAE/B,MAAMG,KAAK,GAAGV,eAAe,CAAC,CAAC;;EAE/B;AACJ;AACA;AACA;AACA;EACI,MAAMW,WAAW,GAAGC,OAAO,CAACC,GAAG,CAACC,4BAA4B,KAAK,MAAM;EACvE,IAAIH,WAAW,EAAE;IACb;AACR;AACA;AACA;AACA;IACQD,KAAK,CAACN,MAAM,CAACW,IAAI,CAAC;MACdC,IAAI,EAAE;QACF,gBAAgB,EAAER,KAAK,CAACS;MAC5B;IACJ,CAAC,CAAC;IACF;AACR;AACA;IACQP,KAAK,CAACN,MAAM,CAACW,IAAI,CAAC;MACdC,IAAI,EAAE;QACF,iBAAiB,EAAER,KAAK,CAACU;MAC7B;IACJ,CAAC,CAAC;IACF;AACR;AACA;AACA;IACQR,KAAK,CAACN,MAAM,CAACW,IAAI,CAAC;MACdC,IAAI,EAAE;QACF,gBAAgB,EAAER,KAAK,CAACW;MAC5B;IACJ,CAAC,CAAC;EACN;;EAEA;AACJ;AACA;EACI,IAAIV,KAAK,CAACW,SAAS,KAAK,IAAI,EAAE;IAC1BV,KAAK,CAACN,MAAM,CAACW,IAAI,CAAC;MACdC,IAAI,EAAE;QACF,gBAAgB,EAAE,IAAAK,qCAAyB,EAAC;MAChD;IACJ,CAAC,CAAC;EACN,CAAC,MAAM,IAAIZ,KAAK,CAACa,MAAM,KAAK,IAAI,EAAE;IAC9BZ,KAAK,CAACN,MAAM,CAACW,IAAI,CAAC;MACdC,IAAI,EAAE;QACF,gBAAgB,EAAE,IAAAO,kCAAsB,EAAC;MAC7C;IACJ,CAAC,CAAC;EACN;EACA;EACA;AACJ;AACA;AACA,KAHI,KAIK;IACD,MAAM,IAAIC,cAAW,CAChB,2EAA0E,EAC3E,iCAAiC,EACjC;MACIf;IACJ,CACJ,CAAC;EACL;EACA;AACJ;AACA;AACA;EACI,OAAOA,KAAK,CAACW,SAAS;EACtB,OAAOX,KAAK,CAACa,MAAM;EAEnB,OAAOZ,KAAK;AAChB,CAAC;AAACL,OAAA,CAAAC,kBAAA,GAAAA,kBAAA","ignoreList":[]}
1
+ {"version":3,"names":["_error","_interopRequireDefault","require","_recordType","_apiElasticsearch","createBaseQuery","must","must_not","should","filter","exports","createInitialQuery","params","model","where","query","sharedIndex","isSharedElasticsearchIndex","push","term","tenant","modelId","locale","published","createPublishedRecordType","latest","createLatestRecordType","WebinyError"],"sources":["initialQuery.ts"],"sourcesContent":["import WebinyError from \"@webiny/error\";\nimport { ElasticsearchBoolQueryConfig } from \"@webiny/api-elasticsearch/types\";\nimport { CmsEntryListWhere, CmsModel } from \"@webiny/api-headless-cms/types\";\nimport { createLatestRecordType, createPublishedRecordType } from \"../recordType\";\nimport { isSharedElasticsearchIndex } from \"@webiny/api-elasticsearch\";\n\nexport const createBaseQuery = (): ElasticsearchBoolQueryConfig => {\n return {\n must: [],\n must_not: [],\n should: [],\n filter: []\n };\n};\n\ninterface Params {\n model: CmsModel;\n where: CmsEntryListWhere;\n}\n/**\n * Latest and published are specific in Elasticsearch to that extend that they are tagged in the __type property.\n * We allow either published or either latest.\n * Latest is used in the manage API and published in the read API.\n *\n *\n * We add the query.filter terms because we do not need scored search here and it is a bit faster.\n */\nexport const createInitialQuery = (params: Params): ElasticsearchBoolQueryConfig => {\n const { model, where } = params;\n\n const query = createBaseQuery();\n\n /**\n * When ES index is shared between tenants, we need to filter records by tenant ID\n *\n * TODO determine if we want to search across tenants in shared index?\n */\n const sharedIndex = isSharedElasticsearchIndex();\n if (sharedIndex) {\n /**\n * Tenant for the filtering is taken from the model.\n *\n * TODO determine if we want to send it in the \"where\" parameter?\n */\n query.filter.push({\n term: {\n \"tenant.keyword\": model.tenant\n }\n });\n /**\n * Also, we must search only in selected model.\n */\n query.filter.push({\n term: {\n \"modelId.keyword\": model.modelId\n }\n });\n /**\n * TODO determine if we want to search across locales?\n * This search would anyway work for a single model and when sharing index.\n */\n query.filter.push({\n term: {\n \"locale.keyword\": model.locale\n }\n });\n }\n\n /**\n * We must transform published and latest where args into something that is understandable by our Elasticsearch\n */\n if (where.published === true) {\n query.filter.push({\n term: {\n \"__type.keyword\": createPublishedRecordType()\n }\n });\n } else if (where.latest === true) {\n query.filter.push({\n term: {\n \"__type.keyword\": createLatestRecordType()\n }\n });\n }\n //\n /**\n * We do not allow filtering without the published or latest parameter.\n * Also, we do not want to set the default one, as there is a large possibility for user error when filtering.\n */\n else {\n throw new WebinyError(\n `Cannot call Elasticsearch query when not setting \"published\" or \"latest\".`,\n \"ELASTICSEARCH_UNSUPPORTED_QUERY\",\n {\n where\n }\n );\n }\n /**\n * We need to remove fields that actually do not exist on the record - it will break otherwise.\n * This will modify the original object, which is what we want.\n */\n delete where.published;\n delete where.latest;\n\n return query;\n};\n"],"mappings":";;;;;;;AAAA,IAAAA,MAAA,GAAAC,sBAAA,CAAAC,OAAA;AAGA,IAAAC,WAAA,GAAAD,OAAA;AACA,IAAAE,iBAAA,GAAAF,OAAA;AAEO,MAAMG,eAAe,GAAGA,CAAA,KAAoC;EAC/D,OAAO;IACHC,IAAI,EAAE,EAAE;IACRC,QAAQ,EAAE,EAAE;IACZC,MAAM,EAAE,EAAE;IACVC,MAAM,EAAE;EACZ,CAAC;AACL,CAAC;AAACC,OAAA,CAAAL,eAAA,GAAAA,eAAA;AAMF;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACO,MAAMM,kBAAkB,GAAIC,MAAc,IAAmC;EAChF,MAAM;IAAEC,KAAK;IAAEC;EAAM,CAAC,GAAGF,MAAM;EAE/B,MAAMG,KAAK,GAAGV,eAAe,CAAC,CAAC;;EAE/B;AACJ;AACA;AACA;AACA;EACI,MAAMW,WAAW,GAAG,IAAAC,4CAA0B,EAAC,CAAC;EAChD,IAAID,WAAW,EAAE;IACb;AACR;AACA;AACA;AACA;IACQD,KAAK,CAACN,MAAM,CAACS,IAAI,CAAC;MACdC,IAAI,EAAE;QACF,gBAAgB,EAAEN,KAAK,CAACO;MAC5B;IACJ,CAAC,CAAC;IACF;AACR;AACA;IACQL,KAAK,CAACN,MAAM,CAACS,IAAI,CAAC;MACdC,IAAI,EAAE;QACF,iBAAiB,EAAEN,KAAK,CAACQ;MAC7B;IACJ,CAAC,CAAC;IACF;AACR;AACA;AACA;IACQN,KAAK,CAACN,MAAM,CAACS,IAAI,CAAC;MACdC,IAAI,EAAE;QACF,gBAAgB,EAAEN,KAAK,CAACS;MAC5B;IACJ,CAAC,CAAC;EACN;;EAEA;AACJ;AACA;EACI,IAAIR,KAAK,CAACS,SAAS,KAAK,IAAI,EAAE;IAC1BR,KAAK,CAACN,MAAM,CAACS,IAAI,CAAC;MACdC,IAAI,EAAE;QACF,gBAAgB,EAAE,IAAAK,qCAAyB,EAAC;MAChD;IACJ,CAAC,CAAC;EACN,CAAC,MAAM,IAAIV,KAAK,CAACW,MAAM,KAAK,IAAI,EAAE;IAC9BV,KAAK,CAACN,MAAM,CAACS,IAAI,CAAC;MACdC,IAAI,EAAE;QACF,gBAAgB,EAAE,IAAAO,kCAAsB,EAAC;MAC7C;IACJ,CAAC,CAAC;EACN;EACA;EACA;AACJ;AACA;AACA,KAHI,KAIK;IACD,MAAM,IAAIC,cAAW,CAChB,2EAA0E,EAC3E,iCAAiC,EACjC;MACIb;IACJ,CACJ,CAAC;EACL;EACA;AACJ;AACA;AACA;EACI,OAAOA,KAAK,CAACS,SAAS;EACtB,OAAOT,KAAK,CAACW,MAAM;EAEnB,OAAOV,KAAK;AAChB,CAAC;AAACL,OAAA,CAAAC,kBAAA,GAAAA,kBAAA","ignoreList":[]}
@@ -15,7 +15,11 @@ const createElasticsearchSort = params => {
15
15
  plugins
16
16
  } = params;
17
17
  if (!sort || sort.length === 0) {
18
- return [];
18
+ return [{
19
+ ["id.keyword"]: {
20
+ order: "asc"
21
+ }
22
+ }];
19
23
  }
20
24
  const searchPlugins = (0, _search.createSearchPluginList)({
21
25
  plugins
@@ -1 +1 @@
1
- {"version":3,"names":["_apiElasticsearch","require","_keyword","_search","_path","createElasticsearchSort","params","sort","modelFields","plugins","length","searchPlugins","createSearchPluginList","createFieldPath","createFieldPathFactory","fieldIdToStorageIdIdMap","sortPlugins","Object","values","reduce","field","parents","fieldId","storageId","path","key","value","keyword","ElasticsearchFieldPlugin","unmappedType","hasKeyword","sortable","searchable","ALL","transformedSort","map","matched","match","order","filter","Boolean","createSort","fieldPlugins","exports"],"sources":["sort.ts"],"sourcesContent":["import { Sort as esSort } from \"@webiny/api-elasticsearch/types\";\nimport { createSort, ElasticsearchFieldPlugin } from \"@webiny/api-elasticsearch\";\nimport { PluginsContainer } from \"@webiny/plugins\";\nimport { CmsEntryListSort, CmsModel } from \"@webiny/api-headless-cms/types\";\nimport { ModelFields } from \"./types\";\nimport { hasKeyword } from \"~/operations/entry/elasticsearch/keyword\";\nimport { createSearchPluginList } from \"~/operations/entry/elasticsearch/plugins/search\";\nimport { createFieldPathFactory } from \"~/operations/entry/elasticsearch/filtering/path\";\n\ninterface Params {\n plugins: PluginsContainer;\n sort?: CmsEntryListSort;\n modelFields: ModelFields;\n model: CmsModel;\n}\nexport const createElasticsearchSort = (params: Params): esSort => {\n const { sort, modelFields, plugins } = params;\n\n if (!sort || sort.length === 0) {\n return [];\n }\n\n const searchPlugins = createSearchPluginList({\n plugins\n });\n\n const createFieldPath = createFieldPathFactory({\n plugins: searchPlugins\n });\n\n const fieldIdToStorageIdIdMap: Record<string, string> = {};\n\n const sortPlugins = Object.values(modelFields).reduce<Record<string, ElasticsearchFieldPlugin>>(\n (plugins, field) => {\n /**\n * We do not support sorting by nested fields.\n */\n if (field.parents.length > 0) {\n return plugins;\n }\n const { fieldId, storageId } = field.field;\n\n fieldIdToStorageIdIdMap[fieldId] = fieldId;\n\n const { path } = createFieldPath({\n key: storageId,\n field,\n value: \"\",\n keyword: false\n });\n /**\n * Plugins must be stored with fieldId as key because it is later used to find the sorting plugin.\n */\n plugins[fieldId] = new ElasticsearchFieldPlugin({\n unmappedType: field.unmappedType,\n keyword: hasKeyword(field),\n sortable: field.sortable,\n searchable: field.searchable,\n field: fieldId,\n path\n });\n return plugins;\n },\n {\n [\"*\"]: new ElasticsearchFieldPlugin({\n field: ElasticsearchFieldPlugin.ALL,\n keyword: false\n })\n }\n );\n\n const transformedSort = sort\n .map(value => {\n const matched = value.match(/^([a-zA-Z-0-9_]+)_(ASC|DESC)$/);\n if (!matched) {\n return null;\n }\n const [, fieldId, order] = matched;\n if (fieldIdToStorageIdIdMap[fieldId]) {\n return `${fieldIdToStorageIdIdMap[fieldId]}_${order}`;\n }\n\n return value;\n })\n .filter(Boolean) as string[];\n return createSort({\n fieldPlugins: sortPlugins,\n sort: transformedSort\n });\n};\n"],"mappings":";;;;;;AACA,IAAAA,iBAAA,GAAAC,OAAA;AAIA,IAAAC,QAAA,GAAAD,OAAA;AACA,IAAAE,OAAA,GAAAF,OAAA;AACA,IAAAG,KAAA,GAAAH,OAAA;AAQO,MAAMI,uBAAuB,GAAIC,MAAc,IAAa;EAC/D,MAAM;IAAEC,IAAI;IAAEC,WAAW;IAAEC;EAAQ,CAAC,GAAGH,MAAM;EAE7C,IAAI,CAACC,IAAI,IAAIA,IAAI,CAACG,MAAM,KAAK,CAAC,EAAE;IAC5B,OAAO,EAAE;EACb;EAEA,MAAMC,aAAa,GAAG,IAAAC,8BAAsB,EAAC;IACzCH;EACJ,CAAC,CAAC;EAEF,MAAMI,eAAe,GAAG,IAAAC,4BAAsB,EAAC;IAC3CL,OAAO,EAAEE;EACb,CAAC,CAAC;EAEF,MAAMI,uBAA+C,GAAG,CAAC,CAAC;EAE1D,MAAMC,WAAW,GAAGC,MAAM,CAACC,MAAM,CAACV,WAAW,CAAC,CAACW,MAAM,CACjD,CAACV,OAAO,EAAEW,KAAK,KAAK;IAChB;AACZ;AACA;IACY,IAAIA,KAAK,CAACC,OAAO,CAACX,MAAM,GAAG,CAAC,EAAE;MAC1B,OAAOD,OAAO;IAClB;IACA,MAAM;MAAEa,OAAO;MAAEC;IAAU,CAAC,GAAGH,KAAK,CAACA,KAAK;IAE1CL,uBAAuB,CAACO,OAAO,CAAC,GAAGA,OAAO;IAE1C,MAAM;MAAEE;IAAK,CAAC,GAAGX,eAAe,CAAC;MAC7BY,GAAG,EAAEF,SAAS;MACdH,KAAK;MACLM,KAAK,EAAE,EAAE;MACTC,OAAO,EAAE;IACb,CAAC,CAAC;IACF;AACZ;AACA;IACYlB,OAAO,CAACa,OAAO,CAAC,GAAG,IAAIM,0CAAwB,CAAC;MAC5CC,YAAY,EAAET,KAAK,CAACS,YAAY;MAChCF,OAAO,EAAE,IAAAG,mBAAU,EAACV,KAAK,CAAC;MAC1BW,QAAQ,EAAEX,KAAK,CAACW,QAAQ;MACxBC,UAAU,EAAEZ,KAAK,CAACY,UAAU;MAC5BZ,KAAK,EAAEE,OAAO;MACdE;IACJ,CAAC,CAAC;IACF,OAAOf,OAAO;EAClB,CAAC,EACD;IACI,CAAC,GAAG,GAAG,IAAImB,0CAAwB,CAAC;MAChCR,KAAK,EAAEQ,0CAAwB,CAACK,GAAG;MACnCN,OAAO,EAAE;IACb,CAAC;EACL,CACJ,CAAC;EAED,MAAMO,eAAe,GAAG3B,IAAI,CACvB4B,GAAG,CAACT,KAAK,IAAI;IACV,MAAMU,OAAO,GAAGV,KAAK,CAACW,KAAK,CAAC,+BAA+B,CAAC;IAC5D,IAAI,CAACD,OAAO,EAAE;MACV,OAAO,IAAI;IACf;IACA,MAAM,GAAGd,OAAO,EAAEgB,KAAK,CAAC,GAAGF,OAAO;IAClC,IAAIrB,uBAAuB,CAACO,OAAO,CAAC,EAAE;MAClC,OAAQ,GAAEP,uBAAuB,CAACO,OAAO,CAAE,IAAGgB,KAAM,EAAC;IACzD;IAEA,OAAOZ,KAAK;EAChB,CAAC,CAAC,CACDa,MAAM,CAACC,OAAO,CAAa;EAChC,OAAO,IAAAC,4BAAU,EAAC;IACdC,YAAY,EAAE1B,WAAW;IACzBT,IAAI,EAAE2B;EACV,CAAC,CAAC;AACN,CAAC;AAACS,OAAA,CAAAtC,uBAAA,GAAAA,uBAAA","ignoreList":[]}
1
+ {"version":3,"names":["_apiElasticsearch","require","_keyword","_search","_path","createElasticsearchSort","params","sort","modelFields","plugins","length","order","searchPlugins","createSearchPluginList","createFieldPath","createFieldPathFactory","fieldIdToStorageIdIdMap","sortPlugins","Object","values","reduce","field","parents","fieldId","storageId","path","key","value","keyword","ElasticsearchFieldPlugin","unmappedType","hasKeyword","sortable","searchable","ALL","transformedSort","map","matched","match","filter","Boolean","createSort","fieldPlugins","exports"],"sources":["sort.ts"],"sourcesContent":["import { Sort as esSort } from \"@webiny/api-elasticsearch/types\";\nimport { createSort, ElasticsearchFieldPlugin } from \"@webiny/api-elasticsearch\";\nimport { PluginsContainer } from \"@webiny/plugins\";\nimport { CmsEntryListSort, CmsModel } from \"@webiny/api-headless-cms/types\";\nimport { ModelFields } from \"./types\";\nimport { hasKeyword } from \"~/operations/entry/elasticsearch/keyword\";\nimport { createSearchPluginList } from \"~/operations/entry/elasticsearch/plugins/search\";\nimport { createFieldPathFactory } from \"~/operations/entry/elasticsearch/filtering/path\";\n\ninterface Params {\n plugins: PluginsContainer;\n sort?: CmsEntryListSort;\n modelFields: ModelFields;\n model: CmsModel;\n}\nexport const createElasticsearchSort = (params: Params): esSort => {\n const { sort, modelFields, plugins } = params;\n\n if (!sort || sort.length === 0) {\n return [\n {\n [\"id.keyword\"]: {\n order: \"asc\"\n }\n }\n ];\n }\n\n const searchPlugins = createSearchPluginList({\n plugins\n });\n\n const createFieldPath = createFieldPathFactory({\n plugins: searchPlugins\n });\n\n const fieldIdToStorageIdIdMap: Record<string, string> = {};\n\n const sortPlugins = Object.values(modelFields).reduce<Record<string, ElasticsearchFieldPlugin>>(\n (plugins, field) => {\n /**\n * We do not support sorting by nested fields.\n */\n if (field.parents.length > 0) {\n return plugins;\n }\n const { fieldId, storageId } = field.field;\n\n fieldIdToStorageIdIdMap[fieldId] = fieldId;\n\n const { path } = createFieldPath({\n key: storageId,\n field,\n value: \"\",\n keyword: false\n });\n /**\n * Plugins must be stored with fieldId as key because it is later used to find the sorting plugin.\n */\n plugins[fieldId] = new ElasticsearchFieldPlugin({\n unmappedType: field.unmappedType,\n keyword: hasKeyword(field),\n sortable: field.sortable,\n searchable: field.searchable,\n field: fieldId,\n path\n });\n return plugins;\n },\n {\n [\"*\"]: new ElasticsearchFieldPlugin({\n field: ElasticsearchFieldPlugin.ALL,\n keyword: false\n })\n }\n );\n\n const transformedSort = sort\n .map(value => {\n const matched = value.match(/^([a-zA-Z-0-9_]+)_(ASC|DESC)$/);\n if (!matched) {\n return null;\n }\n const [, fieldId, order] = matched;\n if (fieldIdToStorageIdIdMap[fieldId]) {\n return `${fieldIdToStorageIdIdMap[fieldId]}_${order}`;\n }\n\n return value;\n })\n .filter(Boolean) as string[];\n return createSort({\n fieldPlugins: sortPlugins,\n sort: transformedSort\n });\n};\n"],"mappings":";;;;;;AACA,IAAAA,iBAAA,GAAAC,OAAA;AAIA,IAAAC,QAAA,GAAAD,OAAA;AACA,IAAAE,OAAA,GAAAF,OAAA;AACA,IAAAG,KAAA,GAAAH,OAAA;AAQO,MAAMI,uBAAuB,GAAIC,MAAc,IAAa;EAC/D,MAAM;IAAEC,IAAI;IAAEC,WAAW;IAAEC;EAAQ,CAAC,GAAGH,MAAM;EAE7C,IAAI,CAACC,IAAI,IAAIA,IAAI,CAACG,MAAM,KAAK,CAAC,EAAE;IAC5B,OAAO,CACH;MACI,CAAC,YAAY,GAAG;QACZC,KAAK,EAAE;MACX;IACJ,CAAC,CACJ;EACL;EAEA,MAAMC,aAAa,GAAG,IAAAC,8BAAsB,EAAC;IACzCJ;EACJ,CAAC,CAAC;EAEF,MAAMK,eAAe,GAAG,IAAAC,4BAAsB,EAAC;IAC3CN,OAAO,EAAEG;EACb,CAAC,CAAC;EAEF,MAAMI,uBAA+C,GAAG,CAAC,CAAC;EAE1D,MAAMC,WAAW,GAAGC,MAAM,CAACC,MAAM,CAACX,WAAW,CAAC,CAACY,MAAM,CACjD,CAACX,OAAO,EAAEY,KAAK,KAAK;IAChB;AACZ;AACA;IACY,IAAIA,KAAK,CAACC,OAAO,CAACZ,MAAM,GAAG,CAAC,EAAE;MAC1B,OAAOD,OAAO;IAClB;IACA,MAAM;MAAEc,OAAO;MAAEC;IAAU,CAAC,GAAGH,KAAK,CAACA,KAAK;IAE1CL,uBAAuB,CAACO,OAAO,CAAC,GAAGA,OAAO;IAE1C,MAAM;MAAEE;IAAK,CAAC,GAAGX,eAAe,CAAC;MAC7BY,GAAG,EAAEF,SAAS;MACdH,KAAK;MACLM,KAAK,EAAE,EAAE;MACTC,OAAO,EAAE;IACb,CAAC,CAAC;IACF;AACZ;AACA;IACYnB,OAAO,CAACc,OAAO,CAAC,GAAG,IAAIM,0CAAwB,CAAC;MAC5CC,YAAY,EAAET,KAAK,CAACS,YAAY;MAChCF,OAAO,EAAE,IAAAG,mBAAU,EAACV,KAAK,CAAC;MAC1BW,QAAQ,EAAEX,KAAK,CAACW,QAAQ;MACxBC,UAAU,EAAEZ,KAAK,CAACY,UAAU;MAC5BZ,KAAK,EAAEE,OAAO;MACdE;IACJ,CAAC,CAAC;IACF,OAAOhB,OAAO;EAClB,CAAC,EACD;IACI,CAAC,GAAG,GAAG,IAAIoB,0CAAwB,CAAC;MAChCR,KAAK,EAAEQ,0CAAwB,CAACK,GAAG;MACnCN,OAAO,EAAE;IACb,CAAC;EACL,CACJ,CAAC;EAED,MAAMO,eAAe,GAAG5B,IAAI,CACvB6B,GAAG,CAACT,KAAK,IAAI;IACV,MAAMU,OAAO,GAAGV,KAAK,CAACW,KAAK,CAAC,+BAA+B,CAAC;IAC5D,IAAI,CAACD,OAAO,EAAE;MACV,OAAO,IAAI;IACf;IACA,MAAM,GAAGd,OAAO,EAAEZ,KAAK,CAAC,GAAG0B,OAAO;IAClC,IAAIrB,uBAAuB,CAACO,OAAO,CAAC,EAAE;MAClC,OAAQ,GAAEP,uBAAuB,CAACO,OAAO,CAAE,IAAGZ,KAAM,EAAC;IACzD;IAEA,OAAOgB,KAAK;EAChB,CAAC,CAAC,CACDY,MAAM,CAACC,OAAO,CAAa;EAChC,OAAO,IAAAC,4BAAU,EAAC;IACdC,YAAY,EAAEzB,WAAW;IACzBV,IAAI,EAAE4B;EACV,CAAC,CAAC;AACN,CAAC;AAACQ,OAAA,CAAAtC,uBAAA,GAAAA,uBAAA","ignoreList":[]}
@@ -26,6 +26,20 @@ var _dbDynamodb = require("@webiny/db-dynamodb");
26
26
  var _transformations = require("./transformations");
27
27
  var _convertEntryKeys = require("./transformations/convertEntryKeys");
28
28
  var _constants = require("@webiny/api-headless-cms/constants");
29
+ const convertToStorageEntry = params => {
30
+ const {
31
+ model,
32
+ storageEntry
33
+ } = params;
34
+ const values = model.convertValueKeyToStorage({
35
+ fields: model.fields,
36
+ values: storageEntry.values
37
+ });
38
+ return {
39
+ ...storageEntry,
40
+ values
41
+ };
42
+ };
29
43
  const createEntriesStorageOperations = params => {
30
44
  const {
31
45
  entity,
@@ -219,6 +233,25 @@ const createEntriesStorageOperations = params => {
219
233
  TYPE: (0, _recordType.createPublishedRecordType)(),
220
234
  ...publishedKeys
221
235
  }));
236
+
237
+ // Unpublish previously published revision (if any).
238
+ const [publishedRevisionStorageEntry] = await dataLoaders.getPublishedRevisionByEntryId({
239
+ model,
240
+ ids: [entry.id]
241
+ });
242
+ if (publishedRevisionStorageEntry) {
243
+ items.push(entity.putBatch({
244
+ ...publishedRevisionStorageEntry,
245
+ PK: (0, _keys.createPartitionKey)({
246
+ id: publishedRevisionStorageEntry.id,
247
+ locale: model.locale,
248
+ tenant: model.tenant
249
+ }),
250
+ SK: (0, _keys.createRevisionSortKey)(publishedRevisionStorageEntry),
251
+ TYPE: (0, _recordType.createRecordType)(),
252
+ status: _types.CONTENT_ENTRY_STATUS.UNPUBLISHED
253
+ }));
254
+ }
222
255
  }
223
256
  try {
224
257
  await (0, _batchWrite.batchWriteAll)({
@@ -945,7 +978,7 @@ const createEntriesStorageOperations = params => {
945
978
  const {
946
979
  entry,
947
980
  latestEntry,
948
- latestStorageEntry
981
+ latestStorageEntry: initialLatestStorageEntry
949
982
  } = params;
950
983
  const model = getStorageOperationsModel(initialModel);
951
984
  const partitionKey = (0, _keys.createPartitionKey)({
@@ -986,12 +1019,17 @@ const createEntriesStorageOperations = params => {
986
1019
  PK: partitionKey,
987
1020
  SK: (0, _keys.createPublishedSortKey)()
988
1021
  }));
989
- esItems.push(entity.deleteBatch({
1022
+ esItems.push(esEntity.deleteBatch({
990
1023
  PK: partitionKey,
991
1024
  SK: (0, _keys.createPublishedSortKey)()
992
1025
  }));
993
1026
  }
994
- if (latestEntry && latestStorageEntry) {
1027
+ if (latestEntry && initialLatestStorageEntry) {
1028
+ const latestStorageEntry = convertToStorageEntry({
1029
+ storageEntry: initialLatestStorageEntry,
1030
+ model
1031
+ });
1032
+
995
1033
  /**
996
1034
  * In the end we need to set the new latest entry.
997
1035
  */
@@ -1009,18 +1047,18 @@ const createEntriesStorageOperations = params => {
1009
1047
  items.push(entity.putBatch({
1010
1048
  ...latestStorageEntry,
1011
1049
  PK: (0, _keys.createPartitionKey)({
1012
- id: latestStorageEntry.id,
1050
+ id: initialLatestStorageEntry.id,
1013
1051
  locale: model.locale,
1014
1052
  tenant: model.tenant
1015
1053
  }),
1016
- SK: (0, _keys.createRevisionSortKey)(latestStorageEntry),
1054
+ SK: (0, _keys.createRevisionSortKey)(initialLatestStorageEntry),
1017
1055
  TYPE: (0, _recordType.createRecordType)()
1018
1056
  }));
1019
1057
  const latestTransformer = (0, _transformations.createTransformer)({
1020
1058
  plugins,
1021
1059
  model,
1022
1060
  entry: latestEntry,
1023
- storageEntry: latestStorageEntry
1061
+ storageEntry: initialLatestStorageEntry
1024
1062
  });
1025
1063
  const esLatestData = await latestTransformer.getElasticsearchLatestEntryData();
1026
1064
  esItems.push(esEntity.putBatch({
@@ -1043,7 +1081,7 @@ const createEntriesStorageOperations = params => {
1043
1081
  error: ex,
1044
1082
  entry,
1045
1083
  latestEntry,
1046
- latestStorageEntry
1084
+ initialLatestStorageEntry
1047
1085
  });
1048
1086
  }
1049
1087
  if (esItems.length === 0) {
@@ -1059,7 +1097,7 @@ const createEntriesStorageOperations = params => {
1059
1097
  error: ex,
1060
1098
  entry,
1061
1099
  latestEntry,
1062
- latestStorageEntry
1100
+ initialLatestStorageEntry
1063
1101
  });
1064
1102
  }
1065
1103
  };
@@ -1251,14 +1289,6 @@ const createEntriesStorageOperations = params => {
1251
1289
  entry,
1252
1290
  storageEntry
1253
1291
  } = transformer.transformEntryKeys();
1254
-
1255
- /**
1256
- * We need currently published entry to check if need to remove it.
1257
- */
1258
- const [publishedStorageEntry] = await dataLoaders.getPublishedRevisionByEntryId({
1259
- model,
1260
- ids: [entry.id]
1261
- });
1262
1292
  const revisionKeys = {
1263
1293
  PK: (0, _keys.createPartitionKey)({
1264
1294
  id: entry.id,
@@ -1296,10 +1326,42 @@ const createEntriesStorageOperations = params => {
1296
1326
  publishedKeys: publishedKeys
1297
1327
  });
1298
1328
  }
1329
+ if (!latestEsEntry) {
1330
+ throw new _error.default(`Could not publish entry. Could not load latest ("L") record (ES table).`, "PUBLISH_ERROR", {
1331
+ entry
1332
+ });
1333
+ }
1334
+
1335
+ /**
1336
+ * We need the latest entry to check if it needs to be updated as well in the Elasticsearch.
1337
+ */
1338
+ const [latestStorageEntry] = await dataLoaders.getLatestRevisionByEntryId({
1339
+ model,
1340
+ ids: [entry.id]
1341
+ });
1342
+ if (!latestStorageEntry) {
1343
+ throw new _error.default(`Could not publish entry. Could not load latest ("L") record.`, "PUBLISH_ERROR", {
1344
+ entry
1345
+ });
1346
+ }
1347
+
1348
+ /**
1349
+ * We need currently published entry to check if need to remove it.
1350
+ */
1351
+ const [publishedStorageEntry] = await dataLoaders.getPublishedRevisionByEntryId({
1352
+ model,
1353
+ ids: [entry.id]
1354
+ });
1355
+
1356
+ // 1. Update REV# and P records with new data.
1299
1357
  const items = [entity.putBatch({
1300
1358
  ...storageEntry,
1301
1359
  ...revisionKeys,
1302
1360
  TYPE: (0, _recordType.createRecordType)()
1361
+ }), entity.putBatch({
1362
+ ...storageEntry,
1363
+ ...publishedKeys,
1364
+ TYPE: (0, _recordType.createPublishedRecordType)()
1303
1365
  })];
1304
1366
  const esItems = [];
1305
1367
  const {
@@ -1307,130 +1369,91 @@ const createEntriesStorageOperations = params => {
1307
1369
  } = _configurations.configurations.es({
1308
1370
  model
1309
1371
  });
1310
- if (publishedStorageEntry && publishedStorageEntry.id !== entry.id) {
1311
- /**
1312
- * If there is a `published` entry already, we need to set it to `unpublished`. We need to
1313
- * execute two updates: update the previously published entry's status and the published entry record.
1314
- * DynamoDB does not support `batchUpdate` - so here we load the previously published
1315
- * entry's data to update its status within a batch operation. If, hopefully,
1316
- * they introduce a true update batch operation, remove this `read` call.
1317
- */
1318
- const [previouslyPublishedEntry] = await dataLoaders.getRevisionById({
1319
- model,
1320
- ids: [publishedStorageEntry.id]
1321
- });
1322
- items.push(
1323
- /**
1324
- * Update currently published entry (unpublish it)
1325
- */
1326
- entity.putBatch({
1327
- ...previouslyPublishedEntry,
1328
- status: _types.CONTENT_ENTRY_STATUS.UNPUBLISHED,
1329
- TYPE: (0, _recordType.createRecordType)(),
1330
- PK: (0, _keys.createPartitionKey)(publishedStorageEntry),
1331
- SK: (0, _keys.createRevisionSortKey)(publishedStorageEntry)
1332
- }));
1333
- }
1334
- /**
1335
- * Update the helper item in DB with the new published entry
1336
- */
1337
- items.push(entity.putBatch({
1338
- ...storageEntry,
1339
- ...publishedKeys,
1340
- TYPE: (0, _recordType.createPublishedRecordType)()
1341
- }));
1342
1372
 
1343
- /**
1344
- * We need the latest entry to check if it needs to be updated as well in the Elasticsearch.
1345
- */
1346
- const [latestStorageEntry] = await dataLoaders.getLatestRevisionByEntryId({
1347
- model,
1348
- ids: [entry.id]
1349
- });
1350
- if (latestStorageEntry?.id === entry.id) {
1373
+ // 2. When it comes to the latest record, we need to perform a couple of different
1374
+ // updates, based on whether the entry being published is the latest revision or not.
1375
+ const publishedRevisionId = publishedStorageEntry?.id;
1376
+ const publishingLatestRevision = latestStorageEntry?.id === entry.id;
1377
+ if (publishingLatestRevision) {
1378
+ // 2.1 If we're publishing the latest revision, we first need to update the L record.
1351
1379
  items.push(entity.putBatch({
1352
1380
  ...storageEntry,
1353
1381
  ...latestKeys
1354
1382
  }));
1355
- }
1356
- if (latestEsEntry) {
1357
- const publishingLatestRevision = latestStorageEntry?.id === entry.id;
1358
1383
 
1359
- /**
1360
- * Need to decompress the data from Elasticsearch DynamoDB table.
1361
- *
1362
- * No need to transform it for the storage because it was fetched
1363
- * directly from the Elasticsearch table, where it sits transformed.
1364
- */
1365
- const latestEsEntryDataDecompressed = await (0, _apiElasticsearch.decompress)(plugins, latestEsEntry.data);
1366
- if (publishingLatestRevision) {
1367
- const updatedMetaFields = (0, _constants.pickEntryMetaFields)(entry);
1368
- const latestTransformer = (0, _transformations.createTransformer)({
1369
- plugins,
1370
- model,
1371
- transformedToIndex: {
1372
- ...latestEsEntryDataDecompressed,
1373
- status: _types.CONTENT_ENTRY_STATUS.PUBLISHED,
1374
- locked: true,
1375
- ...updatedMetaFields
1376
- }
1377
- });
1378
- esItems.push(esEntity.putBatch({
1379
- index: esIndex,
1380
- PK: (0, _keys.createPartitionKey)(latestEsEntryDataDecompressed),
1381
- SK: (0, _keys.createLatestSortKey)(),
1382
- data: await latestTransformer.getElasticsearchLatestEntryData()
1383
- }));
1384
- } else {
1385
- const updatedEntryLevelMetaFields = (0, _constants.pickEntryMetaFields)(entry, _constants.isEntryLevelEntryMetaField);
1386
- const updatedLatestStorageEntry = {
1387
- ...latestStorageEntry,
1388
- ...latestKeys,
1389
- ...updatedEntryLevelMetaFields
1390
- };
1384
+ // 2.2 Additionally, if we have a previously published entry, we need to mark it as unpublished.
1385
+ // Note that we need to take re-publishing into account (same published revision being
1386
+ // published again), in which case the below code does not apply. This is because the
1387
+ // required updates were already applied above.
1388
+ if (publishedStorageEntry) {
1389
+ const isRepublishing = publishedStorageEntry.id === entry.id;
1390
+ if (!isRepublishing) {
1391
+ items.push(
1392
+ /**
1393
+ * Update currently published entry (unpublish it)
1394
+ */
1395
+ entity.putBatch({
1396
+ ...publishedStorageEntry,
1397
+ status: _types.CONTENT_ENTRY_STATUS.UNPUBLISHED,
1398
+ TYPE: (0, _recordType.createRecordType)(),
1399
+ PK: (0, _keys.createPartitionKey)(publishedStorageEntry),
1400
+ SK: (0, _keys.createRevisionSortKey)(publishedStorageEntry)
1401
+ }));
1402
+ }
1403
+ }
1404
+ } else {
1405
+ // 2.3 If the published revision is not the latest one, the situation is a bit
1406
+ // more complex. We first need to update the L and REV# records with the new
1407
+ // values of *only entry-level* meta fields.
1408
+ const updatedEntryLevelMetaFields = (0, _constants.pickEntryMetaFields)(entry, _constants.isEntryLevelEntryMetaField);
1391
1409
 
1392
- /**
1393
- * First we update the regular DynamoDB table. Two updates are needed:
1394
- * - one for the actual revision record
1395
- * - one for the latest record
1396
- */
1397
- items.push(entity.putBatch({
1398
- ...updatedLatestStorageEntry,
1399
- PK: (0, _keys.createPartitionKey)({
1400
- id: latestStorageEntry.id,
1401
- locale: model.locale,
1402
- tenant: model.tenant
1403
- }),
1404
- SK: (0, _keys.createRevisionSortKey)(latestStorageEntry),
1405
- TYPE: (0, _recordType.createRecordType)()
1406
- }));
1407
- items.push(entity.putBatch({
1408
- ...updatedLatestStorageEntry,
1409
- TYPE: (0, _recordType.createLatestRecordType)()
1410
- }));
1410
+ // 2.4 Update L record. Apart from updating the entry-level meta fields, we also need
1411
+ // to change the status from "published" to "unpublished" (if the status is set to "published").
1412
+ let latestRevisionStatus = latestStorageEntry.status;
1413
+ if (latestRevisionStatus === _types.CONTENT_ENTRY_STATUS.PUBLISHED) {
1414
+ latestRevisionStatus = _types.CONTENT_ENTRY_STATUS.UNPUBLISHED;
1415
+ }
1416
+ const latestStorageEntryFields = {
1417
+ ...latestStorageEntry,
1418
+ ...updatedEntryLevelMetaFields,
1419
+ status: latestRevisionStatus
1420
+ };
1421
+ items.push(entity.putBatch({
1422
+ ...latestStorageEntryFields,
1423
+ PK: (0, _keys.createPartitionKey)(latestStorageEntry),
1424
+ SK: (0, _keys.createLatestSortKey)(),
1425
+ TYPE: (0, _recordType.createLatestRecordType)()
1426
+ }));
1411
1427
 
1412
- /**
1413
- * Update the Elasticsearch table to propagate changes to the Elasticsearch.
1414
- */
1415
- const latestEsEntry = await (0, _get.getClean)({
1416
- entity: esEntity,
1417
- keys: latestKeys
1418
- });
1419
- if (latestEsEntry) {
1420
- const latestEsEntryDataDecompressed = await (0, _apiElasticsearch.decompress)(plugins, latestEsEntry.data);
1421
- const updatedLatestEntry = await (0, _apiElasticsearch.compress)(plugins, {
1422
- ...latestEsEntryDataDecompressed,
1423
- ...updatedEntryLevelMetaFields
1424
- });
1425
- esItems.push(esEntity.putBatch({
1426
- ...latestKeys,
1427
- index: esIndex,
1428
- data: updatedLatestEntry
1428
+ // 2.5 Update REV# record.
1429
+ items.push(entity.putBatch({
1430
+ ...latestStorageEntryFields,
1431
+ PK: (0, _keys.createPartitionKey)(latestStorageEntry),
1432
+ SK: (0, _keys.createRevisionSortKey)(latestStorageEntry),
1433
+ TYPE: (0, _recordType.createRecordType)()
1434
+ }));
1435
+
1436
+ // 2.6 Additionally, if we have a previously published entry, we need to mark it as unpublished.
1437
+ // Note that we need to take re-publishing into account (same published revision being
1438
+ // published again), in which case the below code does not apply. This is because the
1439
+ // required updates were already applied above.
1440
+ if (publishedStorageEntry) {
1441
+ const isRepublishing = publishedStorageEntry.id === entry.id;
1442
+ const publishedRevisionDifferentFromLatest = publishedRevisionId !== latestStorageEntry.id;
1443
+ if (!isRepublishing && publishedRevisionDifferentFromLatest) {
1444
+ items.push(entity.putBatch({
1445
+ ...publishedStorageEntry,
1446
+ PK: (0, _keys.createPartitionKey)(publishedStorageEntry),
1447
+ SK: (0, _keys.createRevisionSortKey)(publishedStorageEntry),
1448
+ TYPE: (0, _recordType.createRecordType)(),
1449
+ status: _types.CONTENT_ENTRY_STATUS.UNPUBLISHED
1429
1450
  }));
1430
1451
  }
1431
1452
  }
1432
1453
  }
1433
1454
 
1455
+ // 3. Update records in ES -> DDB table.
1456
+
1434
1457
  /**
1435
1458
  * Update the published revision entry in ES.
1436
1459
  */
@@ -1441,6 +1464,60 @@ const createEntriesStorageOperations = params => {
1441
1464
  data: esPublishedData
1442
1465
  }));
1443
1466
 
1467
+ /**
1468
+ * Need to decompress the data from Elasticsearch DynamoDB table.
1469
+ *
1470
+ * No need to transform it for the storage because it was fetched
1471
+ * directly from the Elasticsearch table, where it sits transformed.
1472
+ */
1473
+ const latestEsEntryDataDecompressed = await (0, _apiElasticsearch.decompress)(plugins, latestEsEntry.data);
1474
+ if (publishingLatestRevision) {
1475
+ const updatedMetaFields = (0, _constants.pickEntryMetaFields)(entry);
1476
+ const latestTransformer = (0, _transformations.createTransformer)({
1477
+ plugins,
1478
+ model,
1479
+ transformedToIndex: {
1480
+ ...latestEsEntryDataDecompressed,
1481
+ status: _types.CONTENT_ENTRY_STATUS.PUBLISHED,
1482
+ locked: true,
1483
+ ...updatedMetaFields
1484
+ }
1485
+ });
1486
+ esItems.push(esEntity.putBatch({
1487
+ index: esIndex,
1488
+ PK: (0, _keys.createPartitionKey)(latestEsEntryDataDecompressed),
1489
+ SK: (0, _keys.createLatestSortKey)(),
1490
+ data: await latestTransformer.getElasticsearchLatestEntryData()
1491
+ }));
1492
+ } else {
1493
+ const updatedEntryLevelMetaFields = (0, _constants.pickEntryMetaFields)(entry, _constants.isEntryLevelEntryMetaField);
1494
+
1495
+ /**
1496
+ * Update the Elasticsearch table to propagate changes to the Elasticsearch.
1497
+ */
1498
+ const latestEsEntry = await (0, _get.getClean)({
1499
+ entity: esEntity,
1500
+ keys: latestKeys
1501
+ });
1502
+ if (latestEsEntry) {
1503
+ const latestEsEntryDataDecompressed = await (0, _apiElasticsearch.decompress)(plugins, latestEsEntry.data);
1504
+ let latestRevisionStatus = latestEsEntryDataDecompressed.status;
1505
+ if (latestRevisionStatus === _types.CONTENT_ENTRY_STATUS.PUBLISHED) {
1506
+ latestRevisionStatus = _types.CONTENT_ENTRY_STATUS.UNPUBLISHED;
1507
+ }
1508
+ const updatedLatestEntry = await (0, _apiElasticsearch.compress)(plugins, {
1509
+ ...latestEsEntryDataDecompressed,
1510
+ ...updatedEntryLevelMetaFields,
1511
+ status: latestRevisionStatus
1512
+ });
1513
+ esItems.push(esEntity.putBatch({
1514
+ ...latestKeys,
1515
+ index: esIndex,
1516
+ data: updatedLatestEntry
1517
+ }));
1518
+ }
1519
+ }
1520
+
1444
1521
  /**
1445
1522
  * Finally, execute regular table batch.
1446
1523
  */