diff --git a/designer-base/src/main/java/com/fr/design/mainframe/DesignerFrameFileDealerPane.java b/designer-base/src/main/java/com/fr/design/mainframe/DesignerFrameFileDealerPane.java
index 747cf6aef5..16c8ef46ca 100644
--- a/designer-base/src/main/java/com/fr/design/mainframe/DesignerFrameFileDealerPane.java
+++ b/designer-base/src/main/java/com/fr/design/mainframe/DesignerFrameFileDealerPane.java
@@ -36,9 +36,9 @@ import com.fr.design.layout.TableLayoutHelper;
import com.fr.design.mainframe.manager.search.TemplateTreeSearchManager;
import com.fr.design.mainframe.manager.search.searcher.control.pane.TemplateTreeSearchToolbarPane;
import com.fr.design.mainframe.vcs.RecycleAction;
+import com.fr.design.mainframe.vcs.common.VcsCloseTemplateHelper;
import com.fr.design.mainframe.vcs.common.VcsHelper;
import com.fr.design.mainframe.vcs.ui.FileVersionsPanel;
-import com.fr.design.mainframe.vcs.ui.VcsNewPane;
import com.fr.design.menu.KeySetUtils;
import com.fr.design.menu.ShortCut;
import com.fr.design.menu.ToolBarDef;
@@ -46,7 +46,6 @@ import com.fr.design.roleAuthority.RolesAlreadyEditedPane;
import com.fr.design.ui.util.UIUtil;
import com.fr.design.utils.DesignUtils;
import com.fr.design.utils.gui.GUICoreUtils;
-import com.fr.design.worker.save.CallbackSaveWorker;
import com.fr.event.Event;
import com.fr.file.filetree.FileNode;
import com.fr.general.ComparatorUtils;
@@ -392,15 +391,6 @@ public class DesignerFrameFileDealerPane extends JPanel implements FileToolbarSt
}
}
- private boolean isCurrentEditing(String path) {
- JTemplate, ?> jt = HistoryTemplateListCache.getInstance().getCurrentEditingTemplate();
- if (JTemplate.isValid(jt)) {
- String editing = jt.getEditingFILE().getPath();
- return ComparatorUtils.equals(editing, path);
- }
- return false;
- }
-
/**
* 按钮状态改变
*/
@@ -505,7 +495,7 @@ public class DesignerFrameFileDealerPane extends JPanel implements FileToolbarSt
public void actionPerformed(ActionEvent e) {
String path = DesignerFrameFileDealerPane.getInstance().getSelectedOperation().getFilePath();
path = StableUtils.pathJoin(ProjectConstants.REPORTLETS_NAME, path);
- boolean currentEditing = isCurrentEditing(path);
+ boolean currentEditing = VcsCloseTemplateHelper.isCurrentEditing(path);
if (VcsHelper.getInstance().isLegacyMode()) {
// 如果模板已经打开了,关掉,避免出现2个同名tab(1个是模板,1个是版本)
closeOpenedTemplate(path, currentEditing);
@@ -513,16 +503,10 @@ public class DesignerFrameFileDealerPane extends JPanel implements FileToolbarSt
fileVersionTablePanel.showFileVersionsPane();
stateChange();
} else {
- checkTemplateSavedAndShowVcsNewPane(path, currentEditing);
+ VcsCloseTemplateHelper.checkTemplateSavedAndShowVcsNewPane(path, currentEditing);
}
-
-
}
- private void showVcsNewPane(String path) {
- VcsNewPane panel = new VcsNewPane(path);
- panel.showDialog();
- }
/**
* 版本管理可用状态的监控
@@ -577,61 +561,6 @@ public class DesignerFrameFileDealerPane extends JPanel implements FileToolbarSt
}
}
- /**
- * 如果指定模板已经打开:
- *
1.如果该模板已保存,则正常打开新版本管理弹窗
- *
2.如果该模板未保存,触发保存逻辑
- *
a.如果用户选择保存,则保存并不关闭模板,弹出新版本管理弹窗
- * b.如果用户选择不保存,则关闭当前模板,弹出新版本管理弹窗
- * c.如果用户选择取消, 则啥操作都不做
- *
- * @param path
- * @param isCurrentEditing
- */
- private void checkTemplateSavedAndShowVcsNewPane(String path, boolean isCurrentEditing) {
- for (JTemplate jTemplate : HistoryTemplateListCache.getInstance().getHistoryList()) {
- if (ComparatorUtils.equals(jTemplate.getEditingFILE().getPath(), path)) {
- if (!jTemplate.isALLSaved()) {
- MultiTemplateTabPane.getInstance().setIsCloseCurrent(isCurrentEditing);
- MultiTemplateTabPane.getInstance().closeFormat(jTemplate);
- confirmCloseAndShowVcsNewPane(jTemplate, path);
- return;
- }
- }
- }
- showVcsNewPane(path);
- }
-
- private void confirmCloseAndShowVcsNewPane(JTemplate, ?> specifiedTemplate, String path) {
- if (specifiedTemplate == null) {
- return;
- }
- if (!specifiedTemplate.isALLSaved() && !DesignerMode.isVcsMode()) {
- specifiedTemplate.stopEditing();
- int returnVal = FineJOptionPane.showConfirmDialog(DesignerContext.getDesignerFrame(), Toolkit.i18nText("Fine-Design_Basic_Utils_Would_You_Like_To_Save") + " \"" + specifiedTemplate.getEditingFILE() + "\" ?",
- Toolkit.i18nText("Fine-Design_Basic_Confirm"), JOptionPane.YES_NO_CANCEL_OPTION, JOptionPane.QUESTION_MESSAGE);
- if (returnVal == JOptionPane.YES_OPTION) {
- CallbackSaveWorker worker = specifiedTemplate.save();
- worker.addSuccessCallback(() -> {
- FineLoggerFactory.getLogger().info(Toolkit.i18nText("Fine-Design_Basic_Template_Already_Saved", specifiedTemplate.getEditingFILE().getName()));
- showVcsNewPane(path);
- });
- worker.start(specifiedTemplate.getRuntimeId());
- } else if (returnVal == JOptionPane.NO_OPTION) {
- closeTpl(specifiedTemplate);
- showVcsNewPane(path);
- }
- } else {
- showVcsNewPane(path);
- }
- }
-
- private void closeTpl(JTemplate, ?> specifiedTemplate) {
- HistoryTemplateListCache.getInstance().closeSelectedReport(specifiedTemplate);
- MultiTemplateTabPane.getInstance().closeAndFreeLock(specifiedTemplate);
- MultiTemplateTabPane.getInstance().activePrevTemplateAfterClose();
- }
-
}
/**
diff --git a/designer-base/src/main/java/com/fr/design/mainframe/vcs/VcsOperatorWorker.java b/designer-base/src/main/java/com/fr/design/mainframe/vcs/VcsOperatorWorker.java
index b59ac3c128..799abcf17c 100644
--- a/designer-base/src/main/java/com/fr/design/mainframe/vcs/VcsOperatorWorker.java
+++ b/designer-base/src/main/java/com/fr/design/mainframe/vcs/VcsOperatorWorker.java
@@ -10,7 +10,9 @@ import com.fr.report.entity.VcsEntity;
import com.fr.stable.StringUtils;
import com.fr.workspace.WorkContext;
import com.fr.workspace.server.vcs.VcsOperator;
+import com.fr.workspace.server.vcs.v2.VcsTaskResult;
+import javax.swing.SwingUtilities;
import javax.swing.SwingWorker;
import java.util.ArrayList;
import java.util.List;
@@ -26,7 +28,7 @@ import java.util.concurrent.ExecutionException;
public class VcsOperatorWorker {
private int count = 0;
- private static final int FREQ = 5;
+ private static final int FREQ = 6;
private String successStr;
@@ -102,21 +104,16 @@ public class VcsOperatorWorker {
*
* @param vcsEntities 需要还原的版本
*/
- public void batchRestore(List vcsEntities) {
- List failedList = new ArrayList<>();
- startProcess(vcsEntities, failedList, (vcsEntity, operator) -> {
+ public void batchRestore(List vcsEntities, VcsTableOperatorListener listener) {
+ VcsProcessFailedWrapper wrapper = new VcsProcessFailedWrapper();
+ startProcess(vcsEntities, wrapper, (vcsEntity, operator) -> {
String fileName = vcsEntity.getFilename();
- boolean result = true;
- try {
- operator.restoreVersion(fileName);
- } catch (Exception e) {
- FineLoggerFactory.getLogger().error(e.getMessage(), e);
- result = false;
+ VcsTaskResult result = operator.restoreVersion(fileName);
+ if (!result.isSuccess()) {
+ wrapper.addFailedEntity(vcsEntity);
}
- if (!result) {
- failedList.add(fileName+PREFIX+vcsEntity.getVersion()+TAIL);
- }
- });
+ return result;
+ }, listener);
}
@@ -126,25 +123,21 @@ public class VcsOperatorWorker {
* @param vcsEntities 需要删除的版本
* @param all 是否需要删除所有版本
*/
- public void batchDelete(List vcsEntities, boolean all) {
- List failedList = new ArrayList<>();
- startProcess(vcsEntities, failedList, (vcsEntity, operator) -> {
+ public void batchDelete(List vcsEntities, boolean all, VcsTableOperatorListener listener) {
+ VcsProcessFailedWrapper wrapper = new VcsProcessFailedWrapper();
+ startProcess(vcsEntities, wrapper, (vcsEntity, operator) -> {
String fileName = vcsEntity.getFilename();
- boolean result = true;
- try {
- if (all) {
- operator.deleteVersionForRecycle(fileName);
- } else {
- operator.deleteVersion(fileName, vcsEntity.getVersion());
- }
- } catch (Exception e) {
- FineLoggerFactory.getLogger().error(e.getMessage(), e);
- result = false;
+ VcsTaskResult result;
+ if (all) {
+ result = operator.deleteVersionForRecycle(fileName);
+ } else {
+ result = operator.deleteVersion(fileName, vcsEntity.getVersion(), VcsEntity.CommitType.TYPE_DEFAULT);
}
- if (!result) {
- failedList.add(fileName+PREFIX+vcsEntity.getVersion()+TAIL);
+ if (!result.isSuccess()) {
+ wrapper.addFailedEntity(vcsEntity);
}
- });
+ return result;
+ }, listener);
}
@@ -153,9 +146,9 @@ public class VcsOperatorWorker {
*
* @param entity VcsEntity
*/
- public void doDelete(VcsEntity entity) {
+ public void doDelete(VcsEntity entity, VcsTableOperatorListener listener) {
String fileName = entity.getFilename();
- start4Single(entity, (vcsEntity, operator) -> operator.deleteVersionForRecycle(fileName), fileName + everyFailedStr);
+ start4Single(entity, (vcsEntity, operator) -> operator.deleteVersionForRecycle(fileName), fileName + everyFailedStr, listener);
}
/**
@@ -163,12 +156,11 @@ public class VcsOperatorWorker {
*
* @param entity 版本
*/
- public void deleteTargetVersion(VcsEntity entity) {
+ public void deleteTargetVersion(VcsEntity entity, VcsTableOperatorListener listener) {
String fileName = entity.getFilename();
int version = entity.getVersion();
- start4Single(entity, (vcsEntity, operator) -> {
- operator.deleteVersion(fileName, version);
- }, fileName + everyFailedStr);
+ VcsEntity.CommitType commitType = entity.getCommitType();
+ start4Single(entity, (vcsEntity, operator) -> operator.deleteVersion(fileName, version, commitType), fileName + everyFailedStr, listener);
}
@@ -177,16 +169,17 @@ public class VcsOperatorWorker {
*
* @param entity 版本
*/
- public void updateEntityAnnotation(VcsEntity entity) {
+ public void updateEntityAnnotation(VcsEntity entity, VcsTableOperatorListener listener) {
start4Single(entity, (vcsEntity, operator) -> {
operator.updateVersion(entity);
- }, everyFailedStr);
+ return new VcsTaskResult(true);
+ }, everyFailedStr, listener);
}
- private void startProcess(List vcsEntities, List failedList, VcsWorkerOperator workerOperator) {
+ private void startProcess(List vcsEntities, VcsProcessFailedWrapper wrapper, VcsWorkerOperator workerOperator, VcsTableOperatorListener listener) {
try {
dialog.getProgressBar().setMaximum(vcsEntities.size());
- start4Batch(vcsEntities, failedList, workerOperator);
+ start4Batch(vcsEntities, wrapper, workerOperator, listener);
dialog.showDialog();
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e.getMessage(), e);
@@ -202,13 +195,15 @@ public class VcsOperatorWorker {
return (count > FREQ && count % FREQ == 0) || count < FREQ;
}
- private void start4Single(VcsEntity entity, VcsWorkerOperator vcsWorkerOperator, String failedTip) {
+ private void start4Single(VcsEntity entity, VcsWorkerOperator vcsWorkerOperator, String failedTip, VcsTableOperatorListener listener) {
new SwingWorker() {
@Override
protected void done() {
try {
if (!get()) {
- FineJOptionPane.showMessageDialog(DesignerContext.getDesignerFrame(), failedTip);
+ FineJOptionPane.showMessageDialog(SwingUtilities.getWindowAncestor(DesignerContext.getDesignerFrame()), failedTip);
+ } else {
+ listener.updateUI();
}
} catch (InterruptedException | ExecutionException e) {
throw new RuntimeException(e);
@@ -218,16 +213,16 @@ public class VcsOperatorWorker {
protected Boolean doInBackground() throws Exception {
try {
VcsOperator operator = WorkContext.getCurrent().get(VcsOperator.class);
- vcsWorkerOperator.process(entity, operator);
+ VcsTaskResult result = vcsWorkerOperator.process(entity, operator);
+ return result.isSuccess();
} catch (Exception e) {
return false;
}
- return true;
}
}.execute();
}
- private void start4Batch(List vcsEntities, List failedList, VcsWorkerOperator workerOperator) {
+ private void start4Batch(List vcsEntities, VcsProcessFailedWrapper wrapper, VcsWorkerOperator workerOperator, VcsTableOperatorListener listener) {
new SwingWorker() {
@Override
protected Boolean doInBackground() throws Exception {
@@ -239,7 +234,7 @@ public class VcsOperatorWorker {
publish(count);
}
}
- return failedList.isEmpty();
+ return wrapper.isAllSuccess();
}
@Override
protected void process(List chunks) {
@@ -249,7 +244,9 @@ public class VcsOperatorWorker {
protected void done() {
dialog.closeDialog();
try {
+ List failedList = wrapper.getDetailFailedList();
showErrorDetailPane(get(), failedList, failedList.size(), vcsEntities.size() - failedList.size());
+ listener.updateUI(wrapper);
} catch (InterruptedException | ExecutionException e) {
throw new RuntimeException(e);
}
@@ -286,6 +283,6 @@ public class VcsOperatorWorker {
* @param vcsEntity 版本
* @param operator 操作类
*/
- void process(VcsEntity vcsEntity, VcsOperator operator) throws Exception;
+ VcsTaskResult process(VcsEntity vcsEntity, VcsOperator operator) throws Exception;
}
}
diff --git a/designer-base/src/main/java/com/fr/design/mainframe/vcs/VcsProcessFailedWrapper.java b/designer-base/src/main/java/com/fr/design/mainframe/vcs/VcsProcessFailedWrapper.java
new file mode 100644
index 0000000000..0a257ce2e4
--- /dev/null
+++ b/designer-base/src/main/java/com/fr/design/mainframe/vcs/VcsProcessFailedWrapper.java
@@ -0,0 +1,60 @@
+package com.fr.design.mainframe.vcs;
+
+import com.fr.report.entity.VcsEntity;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * 版本管理处理失败列表的包装类
+ *
+ * @author Destiny.Lin
+ * @since 11.0
+ * Created on 2023/7/28
+ */
+public class VcsProcessFailedWrapper {
+ private static final String PREFIX = "(v.";
+ private static final String TAIL = ")";
+
+ private List failedList = new ArrayList<>();
+
+
+ /**
+ * 添加处理失败的VcsEntity
+ *
+ * @param entity entity
+ */
+ public void addFailedEntity(VcsEntity entity) {
+ failedList.add(entity);
+ }
+
+
+ /**
+ * 获取用于展示的详细失败信息列表
+ */
+ public List getDetailFailedList() {
+ List detailList = new ArrayList<>();
+ for (VcsEntity entity : failedList) {
+ detailList.add(entity.getFilename()+PREFIX+entity.getVersion()+TAIL);
+ }
+ return detailList;
+ }
+
+ /**
+ * 获取处理失败的vcsEntity的名称列表
+ */
+ public List getFailedNameList() {
+ List detailList = new ArrayList<>();
+ for (VcsEntity entity : failedList) {
+ detailList.add(entity.getFilename());
+ }
+ return detailList;
+ }
+
+ /**
+ * 处理是否全部成功
+ */
+ public boolean isAllSuccess() {
+ return failedList.isEmpty();
+ }
+}
diff --git a/designer-base/src/main/java/com/fr/design/mainframe/vcs/VcsTableOperatorListener.java b/designer-base/src/main/java/com/fr/design/mainframe/vcs/VcsTableOperatorListener.java
new file mode 100644
index 0000000000..a6f19572ec
--- /dev/null
+++ b/designer-base/src/main/java/com/fr/design/mainframe/vcs/VcsTableOperatorListener.java
@@ -0,0 +1,32 @@
+package com.fr.design.mainframe.vcs;
+
+import java.util.List;
+
+/**
+ * 版本管理表格操作事件
+ *
+ * @author Destiny.Lin
+ * @since 11.0
+ * Created on 2023/7/27
+ */
+public interface VcsTableOperatorListener {
+
+
+ /**
+ * 处理操作
+ */
+ default void doOperator(List entityList){}
+
+ /**
+ * 更新界面
+ */
+ default void updateUI(){}
+
+
+ /**
+ * 根据处理失败的内容来更新界面
+ *
+ * @param wrapper 失败内容
+ */
+ default void updateUI(VcsProcessFailedWrapper wrapper){}
+}
diff --git a/designer-base/src/main/java/com/fr/design/mainframe/vcs/common/VcsCloseTemplateHelper.java b/designer-base/src/main/java/com/fr/design/mainframe/vcs/common/VcsCloseTemplateHelper.java
new file mode 100644
index 0000000000..5877795589
--- /dev/null
+++ b/designer-base/src/main/java/com/fr/design/mainframe/vcs/common/VcsCloseTemplateHelper.java
@@ -0,0 +1,113 @@
+package com.fr.design.mainframe.vcs.common;
+
+import com.fr.base.vcs.DesignerMode;
+import com.fr.design.dialog.BasicDialog;
+import com.fr.design.dialog.FineJOptionPane;
+import com.fr.design.file.HistoryTemplateListCache;
+import com.fr.design.file.MultiTemplateTabPane;
+import com.fr.design.i18n.Toolkit;
+import com.fr.design.mainframe.DesignerContext;
+import com.fr.design.mainframe.JTemplate;
+import com.fr.design.mainframe.vcs.ui.VcsNewPane;
+import com.fr.design.worker.save.CallbackSaveWorker;
+import com.fr.general.ComparatorUtils;
+import com.fr.log.FineLoggerFactory;
+
+import javax.swing.JOptionPane;
+import javax.swing.SwingUtilities;
+
+/**
+ * 版本管理关闭模板辅助类
+ *
+ * @author Destiny.Lin
+ * @since 11.0
+ * Created on 2023/7/27
+ */
+public class VcsCloseTemplateHelper {
+
+ /**
+ * 根据传入的pane与dialog生成指定面板的Vcs模板关闭的处理方法
+ * 如果指定模板已经打开:
+ * 1.如果该模板已保存,则正常打开新版本管理弹窗
+ *
2.如果该模板未保存,触发保存逻辑
+ *
a.如果用户选择保存,则保存并不关闭模板,弹出新版本管理弹窗
+ * b.如果用户选择不保存,则关闭当前模板,弹出新版本管理弹窗
+ * c.如果用户选择取消, 则啥操作都不做
+ *
+ * @param path 对应模板路径
+ * @param isCurrentEditing 是否是正在编辑的模板
+ * @param parent 生成的新版本管理的详情面板的父面板
+ */
+ public static void checkTemplateSavedAndShowVcsNewPane(String path, boolean isCurrentEditing, BasicDialog parent, VcsNewPane pane) {
+ VcsNewPaneWrapper wrapper = new VcsNewPaneWrapper(path, parent, pane);
+ for (JTemplate jTemplate : HistoryTemplateListCache.getInstance().getHistoryList()) {
+ if (ComparatorUtils.equals(jTemplate.getEditingFILE().getPath(), path)) {
+ if (!jTemplate.isALLSaved()) {
+ MultiTemplateTabPane.getInstance().setIsCloseCurrent(isCurrentEditing);
+ MultiTemplateTabPane.getInstance().closeFormat(jTemplate);
+ confirmCloseAndShowVcsNewPane(jTemplate, wrapper);
+ return;
+ }
+ }
+ }
+ wrapper.show();
+ }
+
+
+ /**
+ * 自己生成新的VcsNewPane的Vcs模板关闭的处理方法
+ */
+ public static void checkTemplateSavedAndShowVcsNewPane(String path, boolean isCurrentEditing) {
+ checkTemplateSavedAndShowVcsNewPane(path, isCurrentEditing, null, null);
+ }
+
+
+ /**
+ * 是否是当前编辑的模板
+ *
+ * @param path 对应模板路径
+ * @return 是则返回true
+ */
+ public static boolean isCurrentEditing(String path) {
+ JTemplate, ?> jt = HistoryTemplateListCache.getInstance().getCurrentEditingTemplate();
+ if (JTemplate.isValid(jt)) {
+ String editing = jt.getEditingFILE().getPath();
+ return ComparatorUtils.equals(editing, path);
+ }
+ return false;
+ }
+
+
+
+
+ private static void confirmCloseAndShowVcsNewPane(JTemplate, ?> specifiedTemplate, VcsNewPaneWrapper wrapper) {
+ if (specifiedTemplate == null) {
+ return;
+ }
+ if (!specifiedTemplate.isALLSaved() && !DesignerMode.isVcsMode()) {
+ specifiedTemplate.stopEditing();
+ int returnVal = FineJOptionPane.showConfirmDialog(DesignerContext.getDesignerFrame(),
+ String.format("%s\"%s\" ?",Toolkit.i18nText("Fine-Design_Basic_Utils_Would_You_Like_To_Save"), specifiedTemplate.getEditingFILE()),
+ Toolkit.i18nText("Fine-Design_Basic_Confirm"), JOptionPane.YES_NO_CANCEL_OPTION, JOptionPane.QUESTION_MESSAGE);
+ if (returnVal == JOptionPane.YES_OPTION) {
+ CallbackSaveWorker worker = specifiedTemplate.save();
+ worker.addSuccessCallback(() -> {
+ FineLoggerFactory.getLogger().info(Toolkit.i18nText("Fine-Design_Basic_Template_Already_Saved", specifiedTemplate.getEditingFILE().getName()));
+ SwingUtilities.invokeLater(wrapper::show);
+ });
+ worker.start(specifiedTemplate.getRuntimeId());
+ } else if (returnVal == JOptionPane.NO_OPTION) {
+ closeTpl(specifiedTemplate);
+ wrapper.show();
+ }
+ } else {
+ wrapper.show();
+ }
+ }
+
+ private static void closeTpl(JTemplate, ?> specifiedTemplate) {
+ HistoryTemplateListCache.getInstance().closeSelectedReport(specifiedTemplate);
+ MultiTemplateTabPane.getInstance().closeAndFreeLock(specifiedTemplate);
+ MultiTemplateTabPane.getInstance().activePrevTemplateAfterClose();
+ }
+}
diff --git a/designer-base/src/main/java/com/fr/design/mainframe/vcs/common/VcsHelper.java b/designer-base/src/main/java/com/fr/design/mainframe/vcs/common/VcsHelper.java
index 49054f651b..07007604d0 100644
--- a/designer-base/src/main/java/com/fr/design/mainframe/vcs/common/VcsHelper.java
+++ b/designer-base/src/main/java/com/fr/design/mainframe/vcs/common/VcsHelper.java
@@ -22,6 +22,7 @@ import com.fr.log.FineLoggerFactory;
import com.fr.plugin.context.PluginContext;
import com.fr.plugin.manage.PluginManager;
import com.fr.report.entity.VcsEntity;
+import com.fr.stable.StableUtils;
import com.fr.stable.StringUtils;
import com.fr.stable.project.ProjectConstants;
import com.fr.workspace.WorkContext;
@@ -64,6 +65,8 @@ public class VcsHelper implements JTemplateActionListener {
private final static String VCS_PLUGIN_ID = "com.fr.plugin.vcs.v10";
private final static String VCS_FILE_SLASH = "/";
private final static String SERVICE_NAME_MOVE = "moveVcs";
+ private static final String VCS_VERSIONS = "reportlets_versions";
+ private static final String VERSION_MARK = ".v";
private static final VcsHelper INSTANCE = new VcsHelper();
private static ScheduledExecutorService saveSchedule;
@@ -398,4 +401,14 @@ public class VcsHelper implements JTemplateActionListener {
public boolean checkAutoSaveSupport() {
return VcsConfigManager.getInstance().isUseAutoSave() && !VcsHelper.getInstance().isLegacyMode();
}
+
+ /**
+ * 获取文件路径
+ *
+ * @param entity
+ * @return
+ */
+ public String getFilePath(VcsEntity entity) {
+ return StableUtils.pathJoin(VCS_VERSIONS, entity.getFilename() + VERSION_MARK + entity.getVersion());
+ }
}
diff --git a/designer-base/src/main/java/com/fr/design/mainframe/vcs/common/VcsNewPaneWrapper.java b/designer-base/src/main/java/com/fr/design/mainframe/vcs/common/VcsNewPaneWrapper.java
new file mode 100644
index 0000000000..179b7c9400
--- /dev/null
+++ b/designer-base/src/main/java/com/fr/design/mainframe/vcs/common/VcsNewPaneWrapper.java
@@ -0,0 +1,36 @@
+package com.fr.design.mainframe.vcs.common;
+
+import com.fr.design.dialog.BasicDialog;
+import com.fr.design.mainframe.vcs.ui.VcsNewPane;
+
+/**
+ * 构建VcsNewPane的包装类
+ *
+ * @author Destiny.Lin
+ * @since 11.0
+ * Created on 2023/7/27
+ */
+public class VcsNewPaneWrapper {
+
+ private String path;
+ private BasicDialog dialog;
+ private VcsNewPane pane;
+
+ public VcsNewPaneWrapper(String path, BasicDialog dialog, VcsNewPane pane) {
+ this.path = path;
+ this.dialog = dialog;
+ this.pane = pane;
+ }
+
+ /**
+ * 显示面板
+ */
+ public void show() {
+ if (pane != null) {
+ pane.showDialog(dialog);
+ } else {
+ VcsNewPane newPane = new VcsNewPane(path);
+ newPane.showDialog(dialog);
+ }
+ }
+}
diff --git a/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/RecyclePane.java b/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/RecyclePane.java
index 4b0f8e9763..98e7bae071 100644
--- a/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/RecyclePane.java
+++ b/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/RecyclePane.java
@@ -10,7 +10,9 @@ import com.fr.design.mainframe.DesignerContext;
import com.fr.design.mainframe.vcs.VcsOperatorWorker;
import com.fr.design.mainframe.vcs.TableEntity;
import com.fr.design.mainframe.vcs.TableValueOperator;
+import com.fr.design.mainframe.vcs.VcsProcessFailedWrapper;
import com.fr.design.mainframe.vcs.VcsTableEntity;
+import com.fr.design.mainframe.vcs.VcsTableOperatorListener;
import com.fr.report.entity.VcsEntity;
import com.fr.stable.StringUtils;
import com.fr.workspace.WorkContext;
@@ -25,7 +27,9 @@ import java.awt.event.ActionListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.util.ArrayList;
+import java.util.HashSet;
import java.util.List;
+import java.util.Set;
import java.util.stream.Collectors;
import static com.fr.design.i18n.Toolkit.i18nText;
@@ -44,6 +48,8 @@ public class RecyclePane extends AbstractSupportSelectTablePane
public static final Icon ICON_DELETE = IconUtils.readSVGIcon("/com/fr/design/standard/vcslist/vcs_recycle_delete", IconUtils.ICON_TYPE_NORMAL);
public static final Icon ICON_DELETE_DISABLE = IconUtils.readSVGIcon("/com/fr/design/standard/vcslist/vcs_recycle_delete", IconUtils.ICON_TYPE_DISABLED);
+ private Set listenerSet = new HashSet<>();
+
protected UITextField searchTextField;
protected UILabel deleteLabel;
@@ -160,7 +166,12 @@ public class RecyclePane extends AbstractSupportSelectTablePane
fireListener(new VcsResponseListener() {
@Override
public void doAfterChooseYes(List selectList) {
- VcsOperatorWorker.createDeleteWorker().batchDelete(selectList, isNeedDeleteAllVersion());
+ VcsOperatorWorker.createDeleteWorker(). batchDelete(selectList, isNeedDeleteAllVersion(), new VcsTableOperatorListener() {
+ @Override
+ public void updateUI(VcsProcessFailedWrapper wrapper) {
+ updateVcsUI(wrapper);
+ }
+ });
}
}, true);
}
@@ -177,7 +188,12 @@ public class RecyclePane extends AbstractSupportSelectTablePane
fireListener(new VcsResponseListener() {
@Override
public void doAfterChooseYes(List selectList) {
- VcsOperatorWorker.createRestoreWorker().batchRestore(selectList);
+ VcsOperatorWorker.createRestoreWorker().batchRestore(selectList, new VcsTableOperatorListener() {
+ @Override
+ public void updateUI(VcsProcessFailedWrapper wrapper) {
+ updateVcsUI(wrapper);
+ }
+ });
}
}, false);
}
@@ -210,14 +226,17 @@ public class RecyclePane extends AbstractSupportSelectTablePane
JOptionPane.OK_CANCEL_OPTION,
JOptionPane.QUESTION_MESSAGE);
if (selVal == JOptionPane.YES_OPTION) {
- tableEntities = model.getList().stream().filter(tableEntity -> !tableEntity.isSelect()).collect(Collectors.toList());
- model.setList(tableEntities);
- model.fireTableDataChanged();
listener.doAfterChooseYes(selectList);
}
}
}
+ private void updateVcsUI(VcsProcessFailedWrapper wrapper) {
+ tableEntities = model.getList().stream().filter(tableEntity -> !tableEntity.isSelect() || wrapper.getFailedNameList().contains(tableEntity.getFilename())).collect(Collectors.toList());
+ model.setList(new ArrayList<>(tableEntities));
+ model.fireTableDataChanged();
+ fireVcsListener(model.getList());
+ }
/**
* 显示弹窗
@@ -274,6 +293,25 @@ public class RecyclePane extends AbstractSupportSelectTablePane
this.parentDialog = parentDialog;
}
+
+ /**
+ * 添加版本管理表格操作事件
+ *
+ * @param listener 版本管理表格操作事件
+ */
+ public void addVcsListener(VcsTableOperatorListener listener) {
+ listenerSet.add(listener);
+ }
+
+ /**
+ * 触发版本管理表格操作事件
+ */
+ public void fireVcsListener(List tableEntities) {
+ for (VcsTableOperatorListener listener : listenerSet) {
+ listener.doOperator(tableEntities);
+ }
+ }
+
/**
* 删除范围
*
@@ -340,7 +378,7 @@ public class RecyclePane extends AbstractSupportSelectTablePane
* @param entities
*/
public void updateTableList(List entities) {
- tableEntities = entities;
+ tableEntities = new ArrayList<>(entities);
}
/**
diff --git a/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/VcsCenterPane.java b/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/VcsCenterPane.java
index 5a2f20cf15..9efb268a04 100644
--- a/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/VcsCenterPane.java
+++ b/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/VcsCenterPane.java
@@ -10,6 +10,8 @@ import com.fr.design.mainframe.DesignerContext;
import com.fr.design.mainframe.vcs.VcsOperatorWorker;
import com.fr.design.mainframe.vcs.VcsTableEntity;
+import com.fr.design.mainframe.vcs.VcsTableOperatorListener;
+import com.fr.design.mainframe.vcs.common.VcsCloseTemplateHelper;
import com.fr.file.FileNodeFILE;
import com.fr.file.filetree.FileNode;
import com.fr.report.entity.VcsEntity;
@@ -104,7 +106,8 @@ public class VcsCenterPane extends VcsNewPane {
@Override
public void mouseClicked(MouseEvent e) {
JTable table = tableContentPane.getEditTable();
- Object o = table.getValueAt(table.getEditingRow(), table.getEditingColumn());
+ int row = table.getEditingRow();
+ Object o = table.getValueAt(row, table.getEditingColumn());
if (o instanceof VcsTableEntity) {
VcsEntity entity = ((VcsTableEntity) o).getEntity();
String fileName = entity.getFilename();
@@ -115,10 +118,15 @@ public class VcsCenterPane extends VcsNewPane {
JOptionPane.OK_CANCEL_OPTION,
JOptionPane.QUESTION_MESSAGE);
if (selVal == JOptionPane.YES_OPTION) {
- VcsOperatorWorker.createDeleteWorker().doDelete(entity);
- removeTarget((VcsTableEntity) o);
- model.getList().remove(o);
- model.fireTableDataChanged();
+ VcsOperatorWorker.createDeleteWorker().doDelete(entity, new VcsTableOperatorListener() {
+ @Override
+ public void updateUI() {
+ removeTarget((VcsTableEntity) o);
+ model.fireTableRowsDeleted(row, row);
+ model.removeRow(row);
+ model.fireTableDataChanged();
+ }
+ });
}
}
}
@@ -154,13 +162,23 @@ public class VcsCenterPane extends VcsNewPane {
Object o = table.getValueAt(table.getEditingRow(), table.getEditingColumn());
if (o instanceof VcsTableEntity) {
VcsEntity entity = ((VcsTableEntity) o).getEntity();
- VcsNewPane pane = new VcsNewPane(getTemplateTruePath(entity.getFilename())) {
+ String path = getTemplateTruePath(entity.getFilename());
+ VcsNewPane pane = new VcsNewPane(path) {
@Override
protected String title4PopupWindow() {
return entity.getFilename()+Toolkit.i18nText("Fine-Design_Vcs_Version_Tips");
}
};
- pane.showDialog(getDialog());
+ pane.addVcsListener(new VcsTableOperatorListener() {
+ @Override
+ public void doOperator(List entityList) {
+ if (entities.size() == 0) {
+ model.getList().remove(o);
+ model.fireTableDataChanged();
+ }
+ }
+ });
+ VcsCloseTemplateHelper.checkTemplateSavedAndShowVcsNewPane(path, VcsCloseTemplateHelper.isCurrentEditing(path), getDialog(), pane);
}
}
});
@@ -182,8 +200,9 @@ public class VcsCenterPane extends VcsNewPane {
dialog.addDialogActionListener(new DialogActionAdapter() {
@Override
public void doOk() {
- getParentDialog().doOK();
- getParentDialog().dispose();
+ BasicDialog parent = getParentDialog();
+ parent.doOK();
+ parent.dispose();
}
});
}
diff --git a/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/VcsMovePanel.java b/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/VcsMovePanel.java
index 0479ee68e7..28cb3f2447 100644
--- a/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/VcsMovePanel.java
+++ b/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/VcsMovePanel.java
@@ -11,6 +11,7 @@ import com.fr.design.gui.ibutton.UIRadioButton;
import com.fr.design.gui.ilable.UILabel;
import com.fr.design.gui.iprogressbar.ModernUIProgressBarUI;
import com.fr.design.gui.ispinner.UISpinner;
+import com.fr.design.i18n.LocaleLinkProvider;
import com.fr.design.i18n.Toolkit;
import com.fr.design.layout.FRGUIPaneFactory;
import com.fr.design.layout.VerticalFlowLayout;
@@ -18,6 +19,7 @@ import com.fr.design.mainframe.DesignerContext;
import com.fr.design.mainframe.DesignerFrameFileDealerPane;
import com.fr.design.mainframe.vcs.VcsExceptionUtils;
import com.fr.design.mainframe.vcs.common.VcsHelper;
+import com.fr.design.utils.BrowseUtils;
import com.fr.design.utils.DesignUtils;
import com.fr.design.utils.ThemeUtils;
import com.fr.design.widget.FRWidgetFactory;
@@ -74,6 +76,12 @@ public class VcsMovePanel extends BasicPane {
private static final int DEFAULT_VALUE = 5;
+ private static final String HELP_KEY = "Fine-Design_Vcs_Move_Help_Link";
+
+ private static final String HELP_KEY_DEFAULT = "Fine-Design_Vcs_Move_Help_Link_Default";
+
+ private static final String HELP_URL = LocaleLinkProvider.getInstance().getLink(HELP_KEY, HELP_KEY_DEFAULT);
+
public static final String SETTING = "SETTING";
public static final String PROCESS = "PROCESS";
@@ -121,6 +129,8 @@ public class VcsMovePanel extends BasicPane {
private boolean visible = false;
+ private UILabel seeLabel;
+ private UILabel helpLabel;
public VcsMovePanel(CardLayout cardLayout, JPanel parentPane, MoveCallBack callBack, BasicDialog parentDialog) {
this.parentCard = cardLayout;
@@ -407,6 +417,9 @@ public class VcsMovePanel extends BasicPane {
body.add(new UILabel(StringUtils.BLANK));
body.add(tipLabel);
body.add(new UILabel(StringUtils.BLANK));
+ JPanel panel = createHelpPane();
+ body.add(panel);
+ body.add(new UILabel(StringUtils.BLANK));
body.add(button);
statusPane.add(body);
statusPane.setLayout(FRGUIPaneFactory.createCenterLayout(body, 0.5f, 0.5f));
@@ -417,6 +430,24 @@ public class VcsMovePanel extends BasicPane {
tipLabel.setAlignmentX(CENTER_ALIGNMENT);
}
+ private JPanel createHelpPane() {
+ JPanel panel = new JPanel();
+ seeLabel = new UILabel(Toolkit.i18nText("Fine-Design_Vcs_Move_See"));
+ seeLabel.setForeground(TIP_COLOR);
+ helpLabel = new UILabel(Toolkit.i18nText("Fine-Design_Vcs_Move_Help"));
+ helpLabel.setForeground(LABEL_COLOR);
+ helpLabel.setCursor(new Cursor(Cursor.HAND_CURSOR));
+ helpLabel.addMouseListener(new MouseAdapter() {
+ @Override
+ public void mouseClicked(MouseEvent e) {
+ BrowseUtils.browser(HELP_URL);
+ }
+ });
+ panel.add(seeLabel);
+ panel.add(helpLabel);
+ return panel;
+ }
+
private class MoveWorker extends SwingWorker {
diff --git a/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/VcsNewPane.java b/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/VcsNewPane.java
index baafe56868..b924228fd1 100644
--- a/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/VcsNewPane.java
+++ b/designer-base/src/main/java/com/fr/design/mainframe/vcs/ui/VcsNewPane.java
@@ -11,15 +11,18 @@ import com.fr.design.mainframe.JTemplate;
import com.fr.design.mainframe.vcs.TableValueOperator;
import com.fr.design.mainframe.vcs.VcsOperatorWorker;
import com.fr.design.mainframe.vcs.VcsTableEntity;
+import com.fr.design.mainframe.vcs.VcsTableOperatorListener;
import com.fr.design.mainframe.vcs.common.VcsCacheFileNodeFile;
import com.fr.design.mainframe.vcs.common.VcsHelper;
import com.fr.file.FileNodeFILE;
import com.fr.file.filetree.FileNode;
+import com.fr.io.utils.ResourceIOUtils;
import com.fr.report.entity.VcsEntity;
import com.fr.stable.StringUtils;
import com.fr.workspace.WorkContext;
import com.fr.workspace.server.vcs.VcsFileUtils;
import com.fr.workspace.server.vcs.VcsOperator;
+import com.fr.workspace.server.vcs.v2.VcsTaskResult;
import javax.swing.Icon;
import javax.swing.JComponent;
@@ -30,6 +33,7 @@ import java.awt.*;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.MouseMotionAdapter;
+import java.io.FileNotFoundException;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.ExecutionException;
@@ -51,6 +55,7 @@ public class VcsNewPane extends RecyclePane {
protected static int EDIT_COL = 4;
+ private static final String PATH = "path";
private static final int DOUBLE_CLICK_COUNT = 2;
protected VcsOperatorPane operatorPane;
@@ -170,28 +175,42 @@ public class VcsNewPane extends RecyclePane {
private void restoreEntity(VcsEntity entity) {
- new SwingWorker() {
+ new SwingWorker() {
@Override
- protected Void doInBackground() throws Exception {
+ protected VcsTaskResult doInBackground() throws Exception {
+ String path = VcsHelper.getInstance().getFilePath(entity);
+ if (!ResourceIOUtils.exist(path)) {
+ return new VcsTaskResult(false, new FileNotFoundException());
+ }
//step1.设置还原的用户名
entity.setUsername(VcsHelper.getInstance().getCurrentUsername());
//step2.rollback到指定版本
WorkContext.getCurrent().get(VcsOperator.class).rollbackTo(entity);
- return null;
+ //最里面的文件系统的write会吞异常,这边就一直默认成功吧,日志里会体现失败的情况
+ return new VcsTaskResult(true);
}
@Override
protected void done() {
- //step3.如果原来原模板已经打开则关闭原模板,打开rollback后的新模板
- List> templateList = HistoryTemplateListCache.getInstance().getHistoryList();
- for (JTemplate, ?> template : templateList) {
- if (StringUtils.equals(filePath, template.getPath())) {
- MultiTemplateTabPane.getInstance().setIsCloseCurrent(HistoryTemplateListCache.getInstance().isCurrentEditingFile(filePath));
- MultiTemplateTabPane.getInstance().closeFormat(template);
- MultiTemplateTabPane.getInstance().closeSpecifiedTemplate(template);
- break;
+ try {
+ VcsTaskResult result = get();
+ if (result.isSuccess()) {
+ //step3.如果原来原模板已经打开则关闭原模板,打开rollback后的新模板
+ List> templateList = HistoryTemplateListCache.getInstance().getHistoryList();
+ for (JTemplate, ?> template : templateList) {
+ if (StringUtils.equals(filePath, template.getPath())) {
+ MultiTemplateTabPane.getInstance().setIsCloseCurrent(HistoryTemplateListCache.getInstance().isCurrentEditingFile(filePath));
+ MultiTemplateTabPane.getInstance().closeFormat(template);
+ MultiTemplateTabPane.getInstance().closeSpecifiedTemplate(template);
+ break;
+ }
+ }
+ DesignerContext.getDesignerFrame().openTemplate(new FileNodeFILE(new FileNode(filePath, false)));
+ } else {
+ FineJOptionPane.showMessageDialog(DesignerContext.getDesignerFrame(), Toolkit.i18nText("Fine-Design_Basic_Warning_Template_Do_Not_Exsit"));
}
+ } catch (InterruptedException | ExecutionException e) {
+ throw new RuntimeException(e);
}
- DesignerContext.getDesignerFrame().openTemplate(new FileNodeFILE(new FileNode(filePath, false)));
}
}.execute();
}
@@ -202,8 +221,8 @@ public class VcsNewPane extends RecyclePane {
@Override
public void mouseClicked(MouseEvent e) {
JTable table = tableContentPane.getEditTable();
- int row = table.getEditingColumn();
- Object o = table.getValueAt(table.getEditingRow(), row);
+ int row = table.getEditingRow();
+ Object o = table.getValueAt(row, table.getEditingColumn());
if (o instanceof VcsTableEntity) {
VcsEntity entity = ((VcsTableEntity) o).getEntity();
int selVal = FineJOptionPane.showConfirmDialog(
@@ -213,9 +232,15 @@ public class VcsNewPane extends RecyclePane {
JOptionPane.OK_CANCEL_OPTION,
JOptionPane.QUESTION_MESSAGE);
if (selVal == JOptionPane.YES_OPTION) {
- model.getList().remove(o);
- model.fireTableDataChanged();
- VcsOperatorWorker.createDeleteWorker().deleteTargetVersion(entity);
+ VcsOperatorWorker.createDeleteWorker().deleteTargetVersion(entity, new VcsTableOperatorListener() {
+ @Override
+ public void updateUI() {
+ model.fireTableRowsDeleted(row, row);
+ model.removeRow(row);
+ model.fireTableDataChanged();
+ }
+ });
+ fireVcsListener(model.getList());
}
}
}
@@ -231,7 +256,6 @@ public class VcsNewPane extends RecyclePane {
if (o instanceof VcsTableEntity) {
VcsEntity entity = ((VcsTableEntity) o).getEntity();
previewEntity(entity);
- VcsNewPane.this.saveSettingAndCloseDialog();
}
}
});
@@ -336,9 +360,13 @@ public class VcsNewPane extends RecyclePane {
@Override
public void doOK() {
entity.setCommitMsg(getMsgTestArea().getText());
- VcsOperatorWorker.createUpdateWorker().updateEntityAnnotation(entity);
- setVisible(false);
- model.fireTableDataChanged();
+ VcsOperatorWorker.createUpdateWorker().updateEntityAnnotation(entity, new VcsTableOperatorListener() {
+ @Override
+ public void updateUI() {
+ setVisible(false);
+ model.fireTableDataChanged();
+ }
+ });
}
};
dialog.setVisible(true);
diff --git a/designer-realize/src/main/java/com/fr/design/sort/common/SortColumnRowPane.java b/designer-realize/src/main/java/com/fr/design/sort/common/SortColumnRowPane.java
index 19b8ad50ad..0db7af4a12 100644
--- a/designer-realize/src/main/java/com/fr/design/sort/common/SortColumnRowPane.java
+++ b/designer-realize/src/main/java/com/fr/design/sort/common/SortColumnRowPane.java
@@ -24,13 +24,16 @@ import com.fr.stable.ColumnRow;
import com.fr.stable.EssentialUtils;
import com.fr.stable.StringUtils;
-import javax.swing.*;
-import java.awt.*;
+import javax.swing.Icon;
+import javax.swing.JPanel;
+import javax.swing.JTextField;
+import java.awt.Color;
+import java.awt.Dimension;
+import java.awt.FlowLayout;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.util.ArrayList;
import java.util.HashMap;
-import java.util.Iterator;
import java.util.Map;
public class SortColumnRowPane extends JPanel implements UIObserver {
@@ -260,8 +263,10 @@ public class SortColumnRowPane extends JPanel implements UIObserver {
disableHeaderCellsStyleMap = new HashMap<>();
tempHeaderCells = new ArrayList<>();
for (ColumnRow columnRow : notSelectables) {
- TemplateCellElement templateCellElement
- = elementCase.getTemplateCellElement(columnRow.column, columnRow.row);
+ TemplateCellElement templateCellElement = null;
+ if (columnRow != ColumnRow.ERROR) {
+ templateCellElement = elementCase.getTemplateCellElement(columnRow.column, columnRow.row);
+ }
if (templateCellElement == null) {
templateCellElement = new DefaultTemplateCellElement(columnRow.column, columnRow.row);
elementCase.addCellElement(templateCellElement);
@@ -280,8 +285,11 @@ public class SortColumnRowPane extends JPanel implements UIObserver {
if (cellSelectionManager != null) {
try {
for (ColumnRow headerColumnRow : disableHeaderCellsStyleMap.keySet()) {
- TemplateCellElement headerTemplateCellElement
- = elementCase.getTemplateCellElement(headerColumnRow.column, headerColumnRow.row);
+ TemplateCellElement headerTemplateCellElement = null;
+ if (headerColumnRow != ColumnRow.ERROR) {
+ headerTemplateCellElement
+ = elementCase.getTemplateCellElement(headerColumnRow.column, headerColumnRow.row);
+ }
if (headerTemplateCellElement != null) {
headerTemplateCellElement.setStyle(disableHeaderCellsStyleMap.get(headerColumnRow));
}