diff --git a/services/static-webserver/client/source/class/osparc/dashboard/ResourceDetails.js b/services/static-webserver/client/source/class/osparc/dashboard/ResourceDetails.js index 6677e485689a..8fbf22b7c31f 100644 --- a/services/static-webserver/client/source/class/osparc/dashboard/ResourceDetails.js +++ b/services/static-webserver/client/source/class/osparc/dashboard/ResourceDetails.js @@ -341,7 +341,8 @@ qx.Class.define("osparc.dashboard.ResourceDetails", { this.__getServicesBootOptionsPage, this.__getConversationsPage, this.__getPermissionsPage, - this.__getSaveAsTemplatePage, + this.__getPublishPage, + this.__getCreateTemplatePage, this.__getCreateFunctionsPage, this.__getTagsPage, this.__getQualityPage, @@ -738,7 +739,7 @@ qx.Class.define("osparc.dashboard.ResourceDetails", { return page; }, - __getSaveAsTemplatePage: function() { + __getPublishPage: function() { if (!osparc.utils.Resources.isStudy(this.__resourceData)) { return null; } @@ -746,9 +747,9 @@ qx.Class.define("osparc.dashboard.ResourceDetails", { const canIWrite = osparc.data.model.Study.canIWrite(this.__resourceData["accessRights"]); const canCreateTemplate = osparc.data.Permissions.getInstance().canDo("studies.template.create"); if (canIWrite && canCreateTemplate) { - const id = "SaveAsTemplate"; - const iconSrc = "@FontAwesome5Solid/copy/22"; - const title = this.tr("Publish ") + osparc.product.Utils.getTemplateAlias({firstUpperCase: true}); + const id = "Publish"; + const iconSrc = "@FontAwesome5Solid/globe/22"; + const title = this.tr("Publish"); const page = new osparc.dashboard.resources.pages.BasePage(title, iconSrc, id); if (this.__resourceData["resourceType"] === "study") { @@ -758,10 +759,11 @@ qx.Class.define("osparc.dashboard.ResourceDetails", { } const lazyLoadContent = () => { - const saveAsTemplate = new osparc.study.SaveAsTemplate(this.__resourceData); + const makeItPublic = true; + const saveAsTemplate = new osparc.study.SaveAsTemplate(this.__resourceData, makeItPublic); saveAsTemplate.addListener("publishTemplate", e => this.fireDataEvent("publishTemplate", e.getData())); - const publishTemplateButton = saveAsTemplate.getPublishTemplateButton(); + const publishTemplateButton = saveAsTemplate.getCreateTemplateButton(); osparc.dashboard.resources.pages.BasePage.decorateHeaderButton(publishTemplateButton); const toolbar = this.self().createToolbar(); toolbar.add(publishTemplateButton); @@ -775,6 +777,44 @@ qx.Class.define("osparc.dashboard.ResourceDetails", { return null; }, + __getCreateTemplatePage: function() { + if (!osparc.utils.Resources.isStudy(this.__resourceData)) { + return null; + } + + const canIWrite = osparc.data.model.Study.canIWrite(this.__resourceData["accessRights"]); + const canCreateTemplate = osparc.data.Permissions.getInstance().canDo("studies.template.create"); + if (canIWrite && canCreateTemplate) { + const id = "Template"; + const iconSrc = "@FontAwesome5Solid/copy/22"; + const title = this.tr("Template"); + const page = new osparc.dashboard.resources.pages.BasePage(title, iconSrc, id); + + if (this.__resourceData["resourceType"] === "study") { + const studyData = this.__resourceData; + const canBeOpened = osparc.study.Utils.canBeDuplicated(studyData); + page.setEnabled(canBeOpened); + } + + const lazyLoadContent = () => { + const makeItPublic = false; + const saveAsTemplate = new osparc.study.SaveAsTemplate(this.__resourceData, makeItPublic); + saveAsTemplate.addListener("publishTemplate", e => this.fireDataEvent("publishTemplate", e.getData())); + + const createTemplateButton = saveAsTemplate.getCreateTemplateButton(); + osparc.dashboard.resources.pages.BasePage.decorateHeaderButton(createTemplateButton); + const toolbar = this.self().createToolbar(); + toolbar.add(createTemplateButton); + page.addToHeader(toolbar); + page.addToContent(saveAsTemplate); + } + page.addListenerOnce("appear", lazyLoadContent, this); + + return page; + } + return null; + }, + __getCreateFunctionsPage: function() { if (!osparc.utils.Resources.isStudy(this.__resourceData)) { return null; diff --git a/services/static-webserver/client/source/class/osparc/share/ShareTemplateWith.js b/services/static-webserver/client/source/class/osparc/share/ShareTemplateWith.js index f20aa968f584..5a26282b57d8 100644 --- a/services/static-webserver/client/source/class/osparc/share/ShareTemplateWith.js +++ b/services/static-webserver/client/source/class/osparc/share/ShareTemplateWith.js @@ -50,10 +50,10 @@ qx.Class.define("osparc.share.ShareTemplateWith", { this.__potentialTemplateData["resourceType"] = "template"; const addCollaborators = new osparc.share.AddCollaborators(this.__potentialTemplateData, true); addCollaborators.getChildControl("intro-text").set({ - value: this.tr("Make the ") + osparc.product.Utils.getTemplateAlias() + this.tr(" also accessible to:"), - font: "text-14" + value: this.tr("Make the template accessible to:"), + font: "text-14", }); - addCollaborators.getChildControl("share-with").setLabel(this.tr("Publish for...")); + addCollaborators.getChildControl("share-with").setLabel(this.tr("Share with...")); this._add(addCollaborators); this._add(this.__selectedCollabs); diff --git a/services/static-webserver/client/source/class/osparc/study/SaveAsTemplate.js b/services/static-webserver/client/source/class/osparc/study/SaveAsTemplate.js index c29755d08a1c..20acb09ff222 100644 --- a/services/static-webserver/client/source/class/osparc/study/SaveAsTemplate.js +++ b/services/static-webserver/client/source/class/osparc/study/SaveAsTemplate.js @@ -27,12 +27,13 @@ qx.Class.define("osparc.study.SaveAsTemplate", { /** * @param studyData {Object} Object containing part or the entire serialized Study Data */ - construct: function(studyData) { + construct: function(studyData, makeItPublic = false) { this.base(arguments); this._setLayout(new qx.ui.layout.VBox(20)); this.__studyDataClone = osparc.data.model.Study.deepCloneStudyObject(studyData); + this.__makeItPublic = makeItPublic; this.__buildLayout(); }, @@ -43,10 +44,26 @@ qx.Class.define("osparc.study.SaveAsTemplate", { members: { __studyDataClone: null, + __makeItPublic: null, __form: null, - __publishTemplateBtn: null, + __createTemplateBtn: null, __buildLayout: function() { + let introText = ""; + if (this.__makeItPublic) { + introText += this.tr("This project will be published and accessible to everyone."); + introText += "
"; + introText += this.tr("All users will see it and can copy it."); + } else { + introText += this.tr("This project will be saved as a template."); + introText += "
"; + introText += this.tr("The users you select will be able to see it and copy it."); + } + this._add(new qx.ui.basic.Label(introText).set({ + font: "text-14", + rich: true, + })); + const form = this.__form = new qx.ui.form.Form(); this._add(new qx.ui.form.renderer.Single(form)); @@ -56,11 +73,14 @@ qx.Class.define("osparc.study.SaveAsTemplate", { }); form.add(publishWithData, this.tr("Publish with data"), null, "publishWithData"); - if (osparc.product.Utils.isS4LProduct()) { + if (osparc.data.Permissions.getInstance().isTester()) { const templateTypeSB = new qx.ui.form.SelectBox().set({ allowGrowX: false, }); const templateTypes = [{ + label: "Template", + id: null, + }, { label: "Tutorial", id: null, }, { @@ -74,33 +94,42 @@ qx.Class.define("osparc.study.SaveAsTemplate", { form.add(templateTypeSB, this.tr("Template Type"), null, "templateType"); } - const shareWith = this.__shareWith = new osparc.share.ShareTemplateWith(this.__studyDataClone); - this._add(shareWith); + if (!this.__makeItPublic) { + const shareWith = this.__shareWith = new osparc.share.ShareTemplateWith(this.__studyDataClone); + this._add(shareWith); + } - const publishTemplateBtn = this.__publishTemplateBtn = new qx.ui.form.Button().set({ + const createTemplateBtn = this.__createTemplateBtn = new qx.ui.form.Button().set({ appearance: "strong-button", - label: this.tr("Publish"), + label: this.__makeItPublic ? this.tr("Publish") : this.tr("Create Template"), allowGrowX: false, alignX: "right" }); - publishTemplateBtn.addListener("execute", () => this.__publishTemplate(), this); - this._add(publishTemplateBtn); + createTemplateBtn.addListener("execute", () => this.__createTemplate(), this); + this._add(createTemplateBtn); }, - __publishTemplate: function() { + __createTemplate: function() { const publishWithDataCB = this.__form.getItem("publishWithData"); const templateTypeSB = this.__form.getItem("templateType"); const templateType = templateTypeSB ? templateTypeSB.getSelection()[0].getModel() : null; - const readAccessRole = osparc.data.Roles.STUDY["read"]; // AccessRights will be POSTed after the template is created. // No need to add myself, backend will automatically do it const accessRights = {}; this.__studyDataClone["accessRights"] = {}; - const selectedGroupIDs = this.__shareWith.getSelectedGroups(); - selectedGroupIDs.forEach(gid => { - accessRights[gid] = readAccessRole.accessRights; - }); + if (this.__makeItPublic) { + // share the template with the everyone group + const groupsStore = osparc.store.Groups.getInstance(); + const groupProductEveryone = groupsStore.getEveryoneProductGroup(); + accessRights[groupProductEveryone.getGroupId()] = osparc.data.Roles.STUDY["read"].accessRights; + } else { + const selectedGroupIDs = this.__shareWith.getSelectedGroups(); + const readAccessRole = osparc.data.Roles.STUDY["read"]; + selectedGroupIDs.forEach(gid => { + accessRights[gid] = readAccessRole.accessRights; + }); + } this.fireDataEvent("publishTemplate", { "studyData": this.__studyDataClone, @@ -110,8 +139,8 @@ qx.Class.define("osparc.study.SaveAsTemplate", { }); }, - getPublishTemplateButton: function() { - return this.__publishTemplateBtn; + getCreateTemplateButton: function() { + return this.__createTemplateBtn; } } });