@strapi/content-releases 0.0.0-next.a9d79bec775daaf0da4e506b2aebafdb4ca95b06 → 0.0.0-next.b4115cb216b8c27a4b97f78075a250e755fcabf2
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/dist/_chunks/{App-p8aKBitd.js → App-dLXY5ei3.js} +138 -131
- package/dist/_chunks/App-dLXY5ei3.js.map +1 -0
- package/dist/_chunks/{App-bpzO2Ljh.mjs → App-jrh58sXY.mjs} +141 -134
- package/dist/_chunks/App-jrh58sXY.mjs.map +1 -0
- package/dist/_chunks/{PurchaseContentReleases-Clm0iACO.mjs → PurchaseContentReleases-3tRbmbY3.mjs} +2 -2
- package/dist/_chunks/PurchaseContentReleases-3tRbmbY3.mjs.map +1 -0
- package/dist/_chunks/{PurchaseContentReleases-YhAPgpG9.js → PurchaseContentReleases-bpIYXOfu.js} +2 -2
- package/dist/_chunks/PurchaseContentReleases-bpIYXOfu.js.map +1 -0
- package/dist/_chunks/{en-gcJJ5htG.js → en-HrREghh3.js} +11 -3
- package/dist/_chunks/en-HrREghh3.js.map +1 -0
- package/dist/_chunks/{en-WuuhP6Bn.mjs → en-ltT1TlKQ.mjs} +11 -3
- package/dist/_chunks/en-ltT1TlKQ.mjs.map +1 -0
- package/dist/_chunks/{index-fP3qoWZ4.js → index-CVO0Rqdm.js} +320 -18
- package/dist/_chunks/index-CVO0Rqdm.js.map +1 -0
- package/dist/_chunks/{index-AECgcaDa.mjs → index-PiOGBETy.mjs} +325 -23
- package/dist/_chunks/index-PiOGBETy.mjs.map +1 -0
- package/dist/admin/index.js +1 -1
- package/dist/admin/index.mjs +1 -1
- package/dist/server/index.js +282 -158
- package/dist/server/index.js.map +1 -1
- package/dist/server/index.mjs +282 -158
- package/dist/server/index.mjs.map +1 -1
- package/package.json +12 -12
- package/dist/_chunks/App-bpzO2Ljh.mjs.map +0 -1
- package/dist/_chunks/App-p8aKBitd.js.map +0 -1
- package/dist/_chunks/PurchaseContentReleases-Clm0iACO.mjs.map +0 -1
- package/dist/_chunks/PurchaseContentReleases-YhAPgpG9.js.map +0 -1
- package/dist/_chunks/en-WuuhP6Bn.mjs.map +0 -1
- package/dist/_chunks/en-gcJJ5htG.js.map +0 -1
- package/dist/_chunks/index-AECgcaDa.mjs.map +0 -1
- package/dist/_chunks/index-fP3qoWZ4.js.map +0 -1
package/dist/server/index.mjs
CHANGED
|
@@ -211,13 +211,16 @@ async function disableContentTypeLocalized({ oldContentTypes, contentTypes: cont
|
|
|
211
211
|
if (!oldContentTypes) {
|
|
212
212
|
return;
|
|
213
213
|
}
|
|
214
|
+
const i18nPlugin = strapi.plugin("i18n");
|
|
215
|
+
if (!i18nPlugin) {
|
|
216
|
+
return;
|
|
217
|
+
}
|
|
214
218
|
for (const uid in contentTypes2) {
|
|
215
219
|
if (!oldContentTypes[uid]) {
|
|
216
220
|
continue;
|
|
217
221
|
}
|
|
218
222
|
const oldContentType = oldContentTypes[uid];
|
|
219
223
|
const contentType = contentTypes2[uid];
|
|
220
|
-
const i18nPlugin = strapi.plugin("i18n");
|
|
221
224
|
const { isLocalizedContentType } = i18nPlugin.service("content-types");
|
|
222
225
|
if (isLocalizedContentType(oldContentType) && !isLocalizedContentType(contentType)) {
|
|
223
226
|
await strapi.db.queryBuilder(RELEASE_ACTION_MODEL_UID).update({
|
|
@@ -230,13 +233,16 @@ async function enableContentTypeLocalized({ oldContentTypes, contentTypes: conte
|
|
|
230
233
|
if (!oldContentTypes) {
|
|
231
234
|
return;
|
|
232
235
|
}
|
|
236
|
+
const i18nPlugin = strapi.plugin("i18n");
|
|
237
|
+
if (!i18nPlugin) {
|
|
238
|
+
return;
|
|
239
|
+
}
|
|
233
240
|
for (const uid in contentTypes2) {
|
|
234
241
|
if (!oldContentTypes[uid]) {
|
|
235
242
|
continue;
|
|
236
243
|
}
|
|
237
244
|
const oldContentType = oldContentTypes[uid];
|
|
238
245
|
const contentType = contentTypes2[uid];
|
|
239
|
-
const i18nPlugin = strapi.plugin("i18n");
|
|
240
246
|
const { isLocalizedContentType } = i18nPlugin.service("content-types");
|
|
241
247
|
const { getDefaultLocale } = i18nPlugin.service("locales");
|
|
242
248
|
if (!isLocalizedContentType(oldContentType) && isLocalizedContentType(contentType)) {
|
|
@@ -383,27 +389,23 @@ const bootstrap = async ({ strapi: strapi2 }) => {
|
|
|
383
389
|
}
|
|
384
390
|
}
|
|
385
391
|
});
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
});
|
|
396
|
-
}
|
|
392
|
+
getService("scheduling", { strapi: strapi2 }).syncFromDatabase().catch((err) => {
|
|
393
|
+
strapi2.log.error(
|
|
394
|
+
"Error while syncing scheduled jobs from the database in the content-releases plugin. This could lead to errors in the releases scheduling."
|
|
395
|
+
);
|
|
396
|
+
throw err;
|
|
397
|
+
});
|
|
398
|
+
Object.entries(ALLOWED_WEBHOOK_EVENTS).forEach(([key, value]) => {
|
|
399
|
+
strapi2.webhookStore.addAllowedEvent(key, value);
|
|
400
|
+
});
|
|
397
401
|
}
|
|
398
402
|
};
|
|
399
403
|
const destroy = async ({ strapi: strapi2 }) => {
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
job.cancel();
|
|
406
|
-
}
|
|
404
|
+
const scheduledJobs = getService("scheduling", {
|
|
405
|
+
strapi: strapi2
|
|
406
|
+
}).getAll();
|
|
407
|
+
for (const [, job] of scheduledJobs) {
|
|
408
|
+
job.cancel();
|
|
407
409
|
}
|
|
408
410
|
};
|
|
409
411
|
const schema$1 = {
|
|
@@ -528,6 +530,94 @@ const createReleaseService = ({ strapi: strapi2 }) => {
|
|
|
528
530
|
release: release2
|
|
529
531
|
});
|
|
530
532
|
};
|
|
533
|
+
const publishSingleTypeAction = async (uid, actionType, entryId) => {
|
|
534
|
+
const entityManagerService = strapi2.plugin("content-manager").service("entity-manager");
|
|
535
|
+
const populateBuilderService = strapi2.plugin("content-manager").service("populate-builder");
|
|
536
|
+
const populate = await populateBuilderService(uid).populateDeep(Infinity).build();
|
|
537
|
+
const entry = await strapi2.entityService.findOne(uid, entryId, { populate });
|
|
538
|
+
try {
|
|
539
|
+
if (actionType === "publish") {
|
|
540
|
+
await entityManagerService.publish(entry, uid);
|
|
541
|
+
} else {
|
|
542
|
+
await entityManagerService.unpublish(entry, uid);
|
|
543
|
+
}
|
|
544
|
+
} catch (error) {
|
|
545
|
+
if (error instanceof errors.ApplicationError && (error.message === "already.published" || error.message === "already.draft"))
|
|
546
|
+
;
|
|
547
|
+
else {
|
|
548
|
+
throw error;
|
|
549
|
+
}
|
|
550
|
+
}
|
|
551
|
+
};
|
|
552
|
+
const publishCollectionTypeAction = async (uid, entriesToPublishIds, entriestoUnpublishIds) => {
|
|
553
|
+
const entityManagerService = strapi2.plugin("content-manager").service("entity-manager");
|
|
554
|
+
const populateBuilderService = strapi2.plugin("content-manager").service("populate-builder");
|
|
555
|
+
const populate = await populateBuilderService(uid).populateDeep(Infinity).build();
|
|
556
|
+
const entriesToPublish = await strapi2.entityService.findMany(uid, {
|
|
557
|
+
filters: {
|
|
558
|
+
id: {
|
|
559
|
+
$in: entriesToPublishIds
|
|
560
|
+
}
|
|
561
|
+
},
|
|
562
|
+
populate
|
|
563
|
+
});
|
|
564
|
+
const entriesToUnpublish = await strapi2.entityService.findMany(uid, {
|
|
565
|
+
filters: {
|
|
566
|
+
id: {
|
|
567
|
+
$in: entriestoUnpublishIds
|
|
568
|
+
}
|
|
569
|
+
},
|
|
570
|
+
populate
|
|
571
|
+
});
|
|
572
|
+
if (entriesToPublish.length > 0) {
|
|
573
|
+
await entityManagerService.publishMany(entriesToPublish, uid);
|
|
574
|
+
}
|
|
575
|
+
if (entriesToUnpublish.length > 0) {
|
|
576
|
+
await entityManagerService.unpublishMany(entriesToUnpublish, uid);
|
|
577
|
+
}
|
|
578
|
+
};
|
|
579
|
+
const getFormattedActions = async (releaseId) => {
|
|
580
|
+
const actions = await strapi2.db.query(RELEASE_ACTION_MODEL_UID).findMany({
|
|
581
|
+
where: {
|
|
582
|
+
release: {
|
|
583
|
+
id: releaseId
|
|
584
|
+
}
|
|
585
|
+
},
|
|
586
|
+
populate: {
|
|
587
|
+
entry: {
|
|
588
|
+
fields: ["id"]
|
|
589
|
+
}
|
|
590
|
+
}
|
|
591
|
+
});
|
|
592
|
+
if (actions.length === 0) {
|
|
593
|
+
throw new errors.ValidationError("No entries to publish");
|
|
594
|
+
}
|
|
595
|
+
const collectionTypeActions = {};
|
|
596
|
+
const singleTypeActions = [];
|
|
597
|
+
for (const action of actions) {
|
|
598
|
+
const contentTypeUid = action.contentType;
|
|
599
|
+
if (strapi2.contentTypes[contentTypeUid].kind === "collectionType") {
|
|
600
|
+
if (!collectionTypeActions[contentTypeUid]) {
|
|
601
|
+
collectionTypeActions[contentTypeUid] = {
|
|
602
|
+
entriesToPublishIds: [],
|
|
603
|
+
entriesToUnpublishIds: []
|
|
604
|
+
};
|
|
605
|
+
}
|
|
606
|
+
if (action.type === "publish") {
|
|
607
|
+
collectionTypeActions[contentTypeUid].entriesToPublishIds.push(action.entry.id);
|
|
608
|
+
} else {
|
|
609
|
+
collectionTypeActions[contentTypeUid].entriesToUnpublishIds.push(action.entry.id);
|
|
610
|
+
}
|
|
611
|
+
} else {
|
|
612
|
+
singleTypeActions.push({
|
|
613
|
+
uid: contentTypeUid,
|
|
614
|
+
action: action.type,
|
|
615
|
+
id: action.entry.id
|
|
616
|
+
});
|
|
617
|
+
}
|
|
618
|
+
}
|
|
619
|
+
return { collectionTypeActions, singleTypeActions };
|
|
620
|
+
};
|
|
531
621
|
return {
|
|
532
622
|
async create(releaseData, { user }) {
|
|
533
623
|
const releaseWithCreatorFields = await setCreatorFields({ user })(releaseData);
|
|
@@ -547,7 +637,7 @@ const createReleaseService = ({ strapi: strapi2 }) => {
|
|
|
547
637
|
status: "empty"
|
|
548
638
|
}
|
|
549
639
|
});
|
|
550
|
-
if (
|
|
640
|
+
if (releaseWithCreatorFields.scheduledAt) {
|
|
551
641
|
const schedulingService = getService("scheduling", { strapi: strapi2 });
|
|
552
642
|
await schedulingService.set(release2.id, release2.scheduledAt);
|
|
553
643
|
}
|
|
@@ -571,12 +661,18 @@ const createReleaseService = ({ strapi: strapi2 }) => {
|
|
|
571
661
|
}
|
|
572
662
|
});
|
|
573
663
|
},
|
|
574
|
-
async findManyWithContentTypeEntryAttached(contentTypeUid,
|
|
664
|
+
async findManyWithContentTypeEntryAttached(contentTypeUid, entriesIds) {
|
|
665
|
+
let entries = entriesIds;
|
|
666
|
+
if (!Array.isArray(entriesIds)) {
|
|
667
|
+
entries = [entriesIds];
|
|
668
|
+
}
|
|
575
669
|
const releases = await strapi2.db.query(RELEASE_MODEL_UID).findMany({
|
|
576
670
|
where: {
|
|
577
671
|
actions: {
|
|
578
672
|
target_type: contentTypeUid,
|
|
579
|
-
target_id:
|
|
673
|
+
target_id: {
|
|
674
|
+
$in: entries
|
|
675
|
+
}
|
|
580
676
|
},
|
|
581
677
|
releasedAt: {
|
|
582
678
|
$null: true
|
|
@@ -587,18 +683,25 @@ const createReleaseService = ({ strapi: strapi2 }) => {
|
|
|
587
683
|
actions: {
|
|
588
684
|
where: {
|
|
589
685
|
target_type: contentTypeUid,
|
|
590
|
-
target_id:
|
|
686
|
+
target_id: {
|
|
687
|
+
$in: entries
|
|
688
|
+
}
|
|
689
|
+
},
|
|
690
|
+
populate: {
|
|
691
|
+
entry: {
|
|
692
|
+
select: ["id"]
|
|
693
|
+
}
|
|
591
694
|
}
|
|
592
695
|
}
|
|
593
696
|
}
|
|
594
697
|
});
|
|
595
698
|
return releases.map((release2) => {
|
|
596
699
|
if (release2.actions?.length) {
|
|
597
|
-
const
|
|
700
|
+
const actionsForEntry = release2.actions;
|
|
598
701
|
delete release2.actions;
|
|
599
702
|
return {
|
|
600
703
|
...release2,
|
|
601
|
-
|
|
704
|
+
actions: actionsForEntry
|
|
602
705
|
};
|
|
603
706
|
}
|
|
604
707
|
return release2;
|
|
@@ -672,13 +775,11 @@ const createReleaseService = ({ strapi: strapi2 }) => {
|
|
|
672
775
|
// @ts-expect-error see above
|
|
673
776
|
data: releaseWithCreatorFields
|
|
674
777
|
});
|
|
675
|
-
|
|
676
|
-
|
|
677
|
-
|
|
678
|
-
|
|
679
|
-
|
|
680
|
-
schedulingService.cancel(id);
|
|
681
|
-
}
|
|
778
|
+
const schedulingService = getService("scheduling", { strapi: strapi2 });
|
|
779
|
+
if (releaseData.scheduledAt) {
|
|
780
|
+
await schedulingService.set(id, releaseData.scheduledAt);
|
|
781
|
+
} else if (release2.scheduledAt) {
|
|
782
|
+
schedulingService.cancel(id);
|
|
682
783
|
}
|
|
683
784
|
this.updateReleaseStatus(id);
|
|
684
785
|
strapi2.telemetry.send("didUpdateContentRelease");
|
|
@@ -844,7 +945,7 @@ const createReleaseService = ({ strapi: strapi2 }) => {
|
|
|
844
945
|
});
|
|
845
946
|
await strapi2.entityService.delete(RELEASE_MODEL_UID, releaseId);
|
|
846
947
|
});
|
|
847
|
-
if (
|
|
948
|
+
if (release2.scheduledAt) {
|
|
848
949
|
const schedulingService = getService("scheduling", { strapi: strapi2 });
|
|
849
950
|
await schedulingService.cancel(release2.id);
|
|
850
951
|
}
|
|
@@ -852,145 +953,71 @@ const createReleaseService = ({ strapi: strapi2 }) => {
|
|
|
852
953
|
return release2;
|
|
853
954
|
},
|
|
854
955
|
async publish(releaseId) {
|
|
855
|
-
|
|
856
|
-
|
|
857
|
-
|
|
858
|
-
|
|
859
|
-
|
|
860
|
-
|
|
861
|
-
actions: {
|
|
862
|
-
populate: {
|
|
863
|
-
entry: {
|
|
864
|
-
fields: ["id"]
|
|
865
|
-
}
|
|
866
|
-
}
|
|
867
|
-
}
|
|
868
|
-
}
|
|
869
|
-
}
|
|
870
|
-
);
|
|
871
|
-
if (!releaseWithPopulatedActionEntries) {
|
|
956
|
+
const {
|
|
957
|
+
release: release2,
|
|
958
|
+
error
|
|
959
|
+
} = await strapi2.db.transaction(async ({ trx }) => {
|
|
960
|
+
const lockedRelease = await strapi2.db?.queryBuilder(RELEASE_MODEL_UID).where({ id: releaseId }).select(["id", "name", "releasedAt", "status"]).first().transacting(trx).forUpdate().execute();
|
|
961
|
+
if (!lockedRelease) {
|
|
872
962
|
throw new errors.NotFoundError(`No release found for id ${releaseId}`);
|
|
873
963
|
}
|
|
874
|
-
if (
|
|
964
|
+
if (lockedRelease.releasedAt) {
|
|
875
965
|
throw new errors.ValidationError("Release already published");
|
|
876
966
|
}
|
|
877
|
-
if (
|
|
878
|
-
throw new errors.ValidationError("
|
|
967
|
+
if (lockedRelease.status === "failed") {
|
|
968
|
+
throw new errors.ValidationError("Release failed to publish");
|
|
879
969
|
}
|
|
880
|
-
|
|
881
|
-
|
|
882
|
-
|
|
883
|
-
|
|
884
|
-
|
|
885
|
-
|
|
886
|
-
|
|
887
|
-
|
|
888
|
-
entriesToUnpublishIds: []
|
|
889
|
-
};
|
|
890
|
-
}
|
|
891
|
-
if (action.type === "publish") {
|
|
892
|
-
collectionTypeActions[contentTypeUid].entriestoPublishIds.push(action.entry.id);
|
|
893
|
-
} else {
|
|
894
|
-
collectionTypeActions[contentTypeUid].entriesToUnpublishIds.push(action.entry.id);
|
|
895
|
-
}
|
|
896
|
-
} else {
|
|
897
|
-
singleTypeActions.push({
|
|
898
|
-
uid: contentTypeUid,
|
|
899
|
-
action: action.type,
|
|
900
|
-
id: action.entry.id
|
|
901
|
-
});
|
|
902
|
-
}
|
|
903
|
-
}
|
|
904
|
-
const entityManagerService = strapi2.plugin("content-manager").service("entity-manager");
|
|
905
|
-
const populateBuilderService = strapi2.plugin("content-manager").service("populate-builder");
|
|
906
|
-
await strapi2.db.transaction(async () => {
|
|
907
|
-
for (const { uid, action, id } of singleTypeActions) {
|
|
908
|
-
const populate = await populateBuilderService(uid).populateDeep(Infinity).build();
|
|
909
|
-
const entry = await strapi2.entityService.findOne(uid, id, { populate });
|
|
910
|
-
try {
|
|
911
|
-
if (action === "publish") {
|
|
912
|
-
await entityManagerService.publish(entry, uid);
|
|
913
|
-
} else {
|
|
914
|
-
await entityManagerService.unpublish(entry, uid);
|
|
915
|
-
}
|
|
916
|
-
} catch (error) {
|
|
917
|
-
if (error instanceof errors.ApplicationError && (error.message === "already.published" || error.message === "already.draft")) {
|
|
918
|
-
} else {
|
|
919
|
-
throw error;
|
|
920
|
-
}
|
|
921
|
-
}
|
|
922
|
-
}
|
|
923
|
-
for (const contentTypeUid of Object.keys(collectionTypeActions)) {
|
|
924
|
-
const populate = await populateBuilderService(contentTypeUid).populateDeep(Infinity).build();
|
|
925
|
-
const { entriestoPublishIds, entriesToUnpublishIds } = collectionTypeActions[contentTypeUid];
|
|
926
|
-
const entriesToPublish = await strapi2.entityService.findMany(
|
|
927
|
-
contentTypeUid,
|
|
928
|
-
{
|
|
929
|
-
filters: {
|
|
930
|
-
id: {
|
|
931
|
-
$in: entriestoPublishIds
|
|
932
|
-
}
|
|
933
|
-
},
|
|
934
|
-
populate
|
|
935
|
-
}
|
|
936
|
-
);
|
|
937
|
-
const entriesToUnpublish = await strapi2.entityService.findMany(
|
|
938
|
-
contentTypeUid,
|
|
939
|
-
{
|
|
940
|
-
filters: {
|
|
941
|
-
id: {
|
|
942
|
-
$in: entriesToUnpublishIds
|
|
943
|
-
}
|
|
944
|
-
},
|
|
945
|
-
populate
|
|
946
|
-
}
|
|
947
|
-
);
|
|
948
|
-
if (entriesToPublish.length > 0) {
|
|
949
|
-
await entityManagerService.publishMany(entriesToPublish, contentTypeUid);
|
|
970
|
+
try {
|
|
971
|
+
strapi2.log.info(`[Content Releases] Starting to publish release ${lockedRelease.name}`);
|
|
972
|
+
const { collectionTypeActions, singleTypeActions } = await getFormattedActions(
|
|
973
|
+
releaseId
|
|
974
|
+
);
|
|
975
|
+
await strapi2.db.transaction(async () => {
|
|
976
|
+
for (const { uid, action, id } of singleTypeActions) {
|
|
977
|
+
await publishSingleTypeAction(uid, action, id);
|
|
950
978
|
}
|
|
951
|
-
|
|
952
|
-
|
|
979
|
+
for (const contentTypeUid of Object.keys(collectionTypeActions)) {
|
|
980
|
+
const uid = contentTypeUid;
|
|
981
|
+
await publishCollectionTypeAction(
|
|
982
|
+
uid,
|
|
983
|
+
collectionTypeActions[uid].entriesToPublishIds,
|
|
984
|
+
collectionTypeActions[uid].entriesToUnpublishIds
|
|
985
|
+
);
|
|
953
986
|
}
|
|
954
|
-
}
|
|
955
|
-
|
|
956
|
-
|
|
957
|
-
|
|
958
|
-
|
|
959
|
-
|
|
960
|
-
|
|
961
|
-
|
|
962
|
-
releasedAt: /* @__PURE__ */ new Date()
|
|
963
|
-
},
|
|
964
|
-
populate: {
|
|
965
|
-
actions: {
|
|
966
|
-
// @ts-expect-error is not expecting count but it is working
|
|
967
|
-
count: true
|
|
987
|
+
});
|
|
988
|
+
const release22 = await strapi2.db.query(RELEASE_MODEL_UID).update({
|
|
989
|
+
where: {
|
|
990
|
+
id: releaseId
|
|
991
|
+
},
|
|
992
|
+
data: {
|
|
993
|
+
status: "done",
|
|
994
|
+
releasedAt: /* @__PURE__ */ new Date()
|
|
968
995
|
}
|
|
969
|
-
}
|
|
970
|
-
});
|
|
971
|
-
if (strapi2.features.future.isEnabled("contentReleasesScheduling")) {
|
|
996
|
+
});
|
|
972
997
|
dispatchWebhook(ALLOWED_WEBHOOK_EVENTS.RELEASES_PUBLISH, {
|
|
973
998
|
isPublished: true,
|
|
974
|
-
release:
|
|
999
|
+
release: release22
|
|
975
1000
|
});
|
|
976
|
-
|
|
977
|
-
|
|
978
|
-
|
|
979
|
-
} catch (error) {
|
|
980
|
-
if (strapi2.features.future.isEnabled("contentReleasesScheduling")) {
|
|
1001
|
+
strapi2.telemetry.send("didPublishContentRelease");
|
|
1002
|
+
return { release: release22, error: null };
|
|
1003
|
+
} catch (error2) {
|
|
981
1004
|
dispatchWebhook(ALLOWED_WEBHOOK_EVENTS.RELEASES_PUBLISH, {
|
|
982
1005
|
isPublished: false,
|
|
983
|
-
error
|
|
1006
|
+
error: error2
|
|
984
1007
|
});
|
|
985
|
-
|
|
986
|
-
strapi2.db.query(RELEASE_MODEL_UID).update({
|
|
987
|
-
where: { id: releaseId },
|
|
988
|
-
data: {
|
|
1008
|
+
await strapi2.db?.queryBuilder(RELEASE_MODEL_UID).where({ id: releaseId }).update({
|
|
989
1009
|
status: "failed"
|
|
990
|
-
}
|
|
991
|
-
|
|
1010
|
+
}).transacting(trx).execute();
|
|
1011
|
+
return {
|
|
1012
|
+
release: null,
|
|
1013
|
+
error: error2
|
|
1014
|
+
};
|
|
1015
|
+
}
|
|
1016
|
+
});
|
|
1017
|
+
if (error) {
|
|
992
1018
|
throw error;
|
|
993
1019
|
}
|
|
1020
|
+
return release2;
|
|
994
1021
|
},
|
|
995
1022
|
async updateAction(actionId, releaseId, update) {
|
|
996
1023
|
const updatedAction = await strapi2.db.query(RELEASE_ACTION_MODEL_UID).update({
|
|
@@ -1077,6 +1104,12 @@ const createReleaseService = ({ strapi: strapi2 }) => {
|
|
|
1077
1104
|
}
|
|
1078
1105
|
};
|
|
1079
1106
|
};
|
|
1107
|
+
class AlreadyOnReleaseError extends errors.ApplicationError {
|
|
1108
|
+
constructor(message) {
|
|
1109
|
+
super(message);
|
|
1110
|
+
this.name = "AlreadyOnReleaseError";
|
|
1111
|
+
}
|
|
1112
|
+
}
|
|
1080
1113
|
const createReleaseValidationService = ({ strapi: strapi2 }) => ({
|
|
1081
1114
|
async validateUniqueEntry(releaseId, releaseActionArgs) {
|
|
1082
1115
|
const release2 = await strapi2.entityService.findOne(RELEASE_MODEL_UID, releaseId, {
|
|
@@ -1089,7 +1122,7 @@ const createReleaseValidationService = ({ strapi: strapi2 }) => ({
|
|
|
1089
1122
|
(action) => Number(action.entry.id) === Number(releaseActionArgs.entry.id) && action.contentType === releaseActionArgs.entry.contentType
|
|
1090
1123
|
);
|
|
1091
1124
|
if (isEntryInRelease) {
|
|
1092
|
-
throw new
|
|
1125
|
+
throw new AlreadyOnReleaseError(
|
|
1093
1126
|
`Entry with id ${releaseActionArgs.entry.id} and contentType ${releaseActionArgs.entry.contentType} already exists in release with id ${releaseId}`
|
|
1094
1127
|
);
|
|
1095
1128
|
}
|
|
@@ -1197,7 +1230,7 @@ const createSchedulingService = ({ strapi: strapi2 }) => {
|
|
|
1197
1230
|
const services = {
|
|
1198
1231
|
release: createReleaseService,
|
|
1199
1232
|
"release-validation": createReleaseValidationService,
|
|
1200
|
-
|
|
1233
|
+
scheduling: createSchedulingService
|
|
1201
1234
|
};
|
|
1202
1235
|
const RELEASE_SCHEMA = yup.object().shape({
|
|
1203
1236
|
name: yup.string().trim().required(),
|
|
@@ -1284,6 +1317,33 @@ const releaseController = {
|
|
|
1284
1317
|
};
|
|
1285
1318
|
ctx.body = { data };
|
|
1286
1319
|
},
|
|
1320
|
+
async mapEntriesToReleases(ctx) {
|
|
1321
|
+
const { contentTypeUid, entriesIds } = ctx.query;
|
|
1322
|
+
if (!contentTypeUid || !entriesIds) {
|
|
1323
|
+
throw new errors.ValidationError("Missing required query parameters");
|
|
1324
|
+
}
|
|
1325
|
+
const releaseService = getService("release", { strapi });
|
|
1326
|
+
const releasesWithActions = await releaseService.findManyWithContentTypeEntryAttached(
|
|
1327
|
+
contentTypeUid,
|
|
1328
|
+
entriesIds
|
|
1329
|
+
);
|
|
1330
|
+
const mappedEntriesInReleases = releasesWithActions.reduce(
|
|
1331
|
+
(acc, release2) => {
|
|
1332
|
+
release2.actions.forEach((action) => {
|
|
1333
|
+
if (!acc[action.entry.id]) {
|
|
1334
|
+
acc[action.entry.id] = [{ id: release2.id, name: release2.name }];
|
|
1335
|
+
} else {
|
|
1336
|
+
acc[action.entry.id].push({ id: release2.id, name: release2.name });
|
|
1337
|
+
}
|
|
1338
|
+
});
|
|
1339
|
+
return acc;
|
|
1340
|
+
},
|
|
1341
|
+
{}
|
|
1342
|
+
);
|
|
1343
|
+
ctx.body = {
|
|
1344
|
+
data: mappedEntriesInReleases
|
|
1345
|
+
};
|
|
1346
|
+
},
|
|
1287
1347
|
async create(ctx) {
|
|
1288
1348
|
const user = ctx.state.user;
|
|
1289
1349
|
const releaseArgs = ctx.request.body;
|
|
@@ -1373,6 +1433,38 @@ const releaseActionController = {
|
|
|
1373
1433
|
data: releaseAction2
|
|
1374
1434
|
};
|
|
1375
1435
|
},
|
|
1436
|
+
async createMany(ctx) {
|
|
1437
|
+
const releaseId = ctx.params.releaseId;
|
|
1438
|
+
const releaseActionsArgs = ctx.request.body;
|
|
1439
|
+
await Promise.all(
|
|
1440
|
+
releaseActionsArgs.map((releaseActionArgs) => validateReleaseAction(releaseActionArgs))
|
|
1441
|
+
);
|
|
1442
|
+
const releaseService = getService("release", { strapi });
|
|
1443
|
+
const releaseActions = await strapi.db.transaction(async () => {
|
|
1444
|
+
const releaseActions2 = await Promise.all(
|
|
1445
|
+
releaseActionsArgs.map(async (releaseActionArgs) => {
|
|
1446
|
+
try {
|
|
1447
|
+
const action = await releaseService.createAction(releaseId, releaseActionArgs);
|
|
1448
|
+
return action;
|
|
1449
|
+
} catch (error) {
|
|
1450
|
+
if (error instanceof AlreadyOnReleaseError) {
|
|
1451
|
+
return null;
|
|
1452
|
+
}
|
|
1453
|
+
throw error;
|
|
1454
|
+
}
|
|
1455
|
+
})
|
|
1456
|
+
);
|
|
1457
|
+
return releaseActions2;
|
|
1458
|
+
});
|
|
1459
|
+
const newReleaseActions = releaseActions.filter((action) => action !== null);
|
|
1460
|
+
ctx.body = {
|
|
1461
|
+
data: newReleaseActions,
|
|
1462
|
+
meta: {
|
|
1463
|
+
entriesAlreadyInRelease: releaseActions.length - newReleaseActions.length,
|
|
1464
|
+
totalEntries: releaseActions.length
|
|
1465
|
+
}
|
|
1466
|
+
};
|
|
1467
|
+
},
|
|
1376
1468
|
async findMany(ctx) {
|
|
1377
1469
|
const releaseId = ctx.params.releaseId;
|
|
1378
1470
|
const permissionsManager = strapi.admin.services.permission.createPermissionsManager({
|
|
@@ -1441,6 +1533,22 @@ const controllers = { release: releaseController, "release-action": releaseActio
|
|
|
1441
1533
|
const release = {
|
|
1442
1534
|
type: "admin",
|
|
1443
1535
|
routes: [
|
|
1536
|
+
{
|
|
1537
|
+
method: "GET",
|
|
1538
|
+
path: "/mapEntriesToReleases",
|
|
1539
|
+
handler: "release.mapEntriesToReleases",
|
|
1540
|
+
config: {
|
|
1541
|
+
policies: [
|
|
1542
|
+
"admin::isAuthenticatedAdmin",
|
|
1543
|
+
{
|
|
1544
|
+
name: "admin::hasPermissions",
|
|
1545
|
+
config: {
|
|
1546
|
+
actions: ["plugin::content-releases.read"]
|
|
1547
|
+
}
|
|
1548
|
+
}
|
|
1549
|
+
]
|
|
1550
|
+
}
|
|
1551
|
+
},
|
|
1444
1552
|
{
|
|
1445
1553
|
method: "POST",
|
|
1446
1554
|
path: "/",
|
|
@@ -1558,6 +1666,22 @@ const releaseAction = {
|
|
|
1558
1666
|
]
|
|
1559
1667
|
}
|
|
1560
1668
|
},
|
|
1669
|
+
{
|
|
1670
|
+
method: "POST",
|
|
1671
|
+
path: "/:releaseId/actions/bulk",
|
|
1672
|
+
handler: "release-action.createMany",
|
|
1673
|
+
config: {
|
|
1674
|
+
policies: [
|
|
1675
|
+
"admin::isAuthenticatedAdmin",
|
|
1676
|
+
{
|
|
1677
|
+
name: "admin::hasPermissions",
|
|
1678
|
+
config: {
|
|
1679
|
+
actions: ["plugin::content-releases.create-action"]
|
|
1680
|
+
}
|
|
1681
|
+
}
|
|
1682
|
+
]
|
|
1683
|
+
}
|
|
1684
|
+
},
|
|
1561
1685
|
{
|
|
1562
1686
|
method: "GET",
|
|
1563
1687
|
path: "/:releaseId/actions",
|