Files
HaE/src/main/java/hae/component/board/Databoard.java

614 lines
24 KiB
Java
Raw Normal View History

2024-05-06 12:56:56 +08:00
package hae.component.board;
2023-10-12 21:38:27 +08:00
2024-05-06 12:56:56 +08:00
import burp.api.montoya.MontoyaApi;
import hae.Config;
2024-05-24 15:00:49 +08:00
import hae.component.board.message.MessageEntry;
2024-05-06 12:56:56 +08:00
import hae.component.board.message.MessageTableModel;
import hae.component.board.message.MessageTableModel.MessageTable;
2024-05-24 15:00:49 +08:00
import hae.instances.http.utils.RegularMatcher;
import hae.utils.ConfigLoader;
import hae.utils.project.ProjectProcessor;
import hae.utils.project.model.HaeFileContent;
2024-05-12 19:02:38 +08:00
import hae.utils.string.StringProcessor;
2023-10-18 00:44:50 +08:00
2024-05-12 19:02:38 +08:00
import javax.swing.*;
import javax.swing.event.DocumentEvent;
import javax.swing.event.DocumentListener;
2024-05-24 15:00:49 +08:00
import javax.swing.filechooser.FileNameExtensionFilter;
2023-10-12 21:38:27 +08:00
import javax.swing.table.TableColumnModel;
import javax.swing.table.TableModel;
import javax.swing.table.TableRowSorter;
import java.awt.*;
import java.awt.event.*;
2024-05-24 15:00:49 +08:00
import java.io.File;
2023-10-18 00:44:50 +08:00
import java.util.List;
2024-05-12 19:02:38 +08:00
import java.util.*;
2024-05-30 14:37:01 +08:00
import java.util.concurrent.*;
import java.util.function.Function;
2024-05-24 15:00:49 +08:00
import java.util.stream.Collectors;
2023-10-12 21:38:27 +08:00
public class Databoard extends JPanel {
2024-05-06 12:56:56 +08:00
private final MontoyaApi api;
private final ConfigLoader configLoader;
2024-05-24 15:00:49 +08:00
private final ProjectProcessor projectProcessor;
2024-05-06 12:56:56 +08:00
private final MessageTableModel messageTableModel;
2024-05-30 14:37:01 +08:00
2023-10-12 21:38:27 +08:00
private JTextField hostTextField;
2023-11-07 11:15:20 +08:00
private JTabbedPane dataTabbedPane;
2023-10-12 21:38:27 +08:00
private JSplitPane splitPane;
2024-05-06 12:56:56 +08:00
private MessageTable messageTable;
2024-05-30 14:37:01 +08:00
private JProgressBar progressBar;
2024-05-06 12:56:56 +08:00
private static Boolean isMatchHost = false;
2024-05-12 19:02:38 +08:00
private final DefaultComboBoxModel comboBoxModel = new DefaultComboBoxModel();
private final JComboBox hostComboBox = new JComboBox(comboBoxModel);
2023-11-07 11:15:20 +08:00
2024-05-30 14:37:01 +08:00
private SwingWorker<Boolean, Void> currentWorker;
2024-05-06 12:56:56 +08:00
public Databoard(MontoyaApi api, ConfigLoader configLoader, MessageTableModel messageTableModel) {
this.api = api;
this.configLoader = configLoader;
2024-05-24 15:00:49 +08:00
this.projectProcessor = new ProjectProcessor(api);
2024-05-06 12:56:56 +08:00
this.messageTableModel = messageTableModel;
2023-11-07 11:15:20 +08:00
2023-10-12 21:38:27 +08:00
initComponents();
}
private void initComponents() {
setLayout(new GridBagLayout());
2024-05-12 19:02:38 +08:00
((GridBagLayout) getLayout()).columnWidths = new int[]{25, 0, 0, 0, 20, 0};
2024-05-30 14:37:01 +08:00
((GridBagLayout) getLayout()).rowHeights = new int[]{0, 65, 20, 25, 0};
2024-05-12 19:02:38 +08:00
((GridBagLayout) getLayout()).columnWeights = new double[]{0.0, 0.0, 1.0, 0.0, 0.0, 1.0E-4};
2024-05-30 14:37:01 +08:00
((GridBagLayout) getLayout()).rowWeights = new double[]{0.0, 1.0, 0.0, 0.0, 1.0E-4};
2023-10-12 21:38:27 +08:00
2024-05-06 12:56:56 +08:00
JLabel hostLabel = new JLabel("Host:");
2023-11-27 14:55:28 +08:00
2024-05-06 12:56:56 +08:00
JButton clearButton = new JButton("Clear");
2024-05-24 15:00:49 +08:00
JButton exportButton = new JButton("Export");
JButton importButton = new JButton("Import");
2024-05-06 12:56:56 +08:00
JButton actionButton = new JButton("Action");
2024-05-24 15:00:49 +08:00
JPanel menuPanel = new JPanel(new GridLayout(3, 1, 0, 5));
2024-05-06 12:56:56 +08:00
menuPanel.setBorder(BorderFactory.createEmptyBorder(3, 3, 3, 3));
JPopupMenu menu = new JPopupMenu();
menuPanel.add(clearButton);
2024-05-24 15:00:49 +08:00
menuPanel.add(exportButton);
menuPanel.add(importButton);
2024-05-06 12:56:56 +08:00
menu.add(menuPanel);
2023-10-12 21:38:27 +08:00
2024-05-06 12:56:56 +08:00
hostTextField = new JTextField();
2023-10-12 21:38:27 +08:00
splitPane = new JSplitPane(JSplitPane.HORIZONTAL_SPLIT);
2024-05-06 12:56:56 +08:00
dataTabbedPane = new JTabbedPane(JTabbedPane.TOP);
2024-05-30 14:37:01 +08:00
dataTabbedPane.setPreferredSize(new Dimension(500, 0));
dataTabbedPane.setTabLayoutPolicy(JTabbedPane.SCROLL_TAB_LAYOUT);
splitPane.setLeftComponent(dataTabbedPane);
2024-05-06 12:56:56 +08:00
actionButton.addActionListener(e -> {
int x = 0;
int y = actionButton.getHeight();
menu.show(actionButton, x, y);
});
clearButton.addActionListener(this::clearActionPerformed);
2024-05-24 15:00:49 +08:00
exportButton.addActionListener(this::exportActionPerformed);
importButton.addActionListener(this::importActionPerformed);
2023-10-12 21:38:27 +08:00
2024-05-30 14:37:01 +08:00
progressBar = new JProgressBar();
2024-02-02 19:07:03 +08:00
splitPane.addComponentListener(new ComponentAdapter() {
@Override
public void componentResized(ComponentEvent e) {
resizePanel();
}
});
2024-05-06 12:56:56 +08:00
splitPane.setVisible(false);
2024-05-30 14:37:01 +08:00
progressBar.setVisible(false);
2024-05-06 12:56:56 +08:00
add(hostLabel, new GridBagConstraints(1, 0, 1, 1, 0.0, 0.0, GridBagConstraints.CENTER, GridBagConstraints.BOTH,
new Insets(8, 0, 5, 5), 0, 0));
add(hostTextField, new GridBagConstraints(2, 0, 1, 1, 0.0, 0.0, GridBagConstraints.CENTER, GridBagConstraints.BOTH,
new Insets(8, 0, 5, 5), 0, 0));
2024-05-12 19:02:38 +08:00
add(actionButton, new GridBagConstraints(3, 0, 1, 1, 0.0, 0.0, GridBagConstraints.CENTER, GridBagConstraints.BOTH,
2024-05-06 12:56:56 +08:00
new Insets(8, 0, 5, 5), 0, 0));
2024-05-30 14:37:01 +08:00
add(splitPane, new GridBagConstraints(1, 1, 3, 1, 0.0, 1.0,
2024-05-06 12:56:56 +08:00
GridBagConstraints.CENTER, GridBagConstraints.BOTH,
2024-05-30 14:37:01 +08:00
new Insets(0, 5, 0, 5), 0, 0));
add(progressBar, new GridBagConstraints(1, 3, 3, 1, 1.0, 0.0,
GridBagConstraints.CENTER, GridBagConstraints.HORIZONTAL,
new Insets(0, 5, 0, 5), 0, 0));
2024-05-06 12:56:56 +08:00
hostComboBox.setMaximumRowCount(5);
add(hostComboBox, new GridBagConstraints(2, 0, 1, 1, 0.0, 0.0, GridBagConstraints.CENTER, GridBagConstraints.BOTH,
new Insets(8, 0, 5, 5), 0, 0));
2023-10-12 21:38:27 +08:00
setAutoMatch();
}
2024-02-02 19:07:03 +08:00
private void resizePanel() {
splitPane.setDividerLocation(0.4);
2024-05-06 12:56:56 +08:00
TableColumnModel columnModel = messageTable.getColumnModel();
2024-02-02 19:07:03 +08:00
int totalWidth = (int) (getWidth() * 0.6);
columnModel.getColumn(0).setPreferredWidth((int) (totalWidth * 0.1));
columnModel.getColumn(1).setPreferredWidth((int) (totalWidth * 0.3));
columnModel.getColumn(2).setPreferredWidth((int) (totalWidth * 0.3));
columnModel.getColumn(3).setPreferredWidth((int) (totalWidth * 0.1));
columnModel.getColumn(4).setPreferredWidth((int) (totalWidth * 0.1));
columnModel.getColumn(5).setPreferredWidth((int) (totalWidth * 0.1));
}
2024-05-30 14:37:01 +08:00
private void setProgressBar(boolean status) {
progressBar.setIndeterminate(status);
if (!status) {
progressBar.setMaximum(100);
progressBar.setString("OK");
progressBar.setStringPainted(true);
progressBar.setValue(progressBar.getMaximum());
} else {
progressBar.setString("Loading...");
progressBar.setStringPainted(true);
}
}
2023-10-12 21:38:27 +08:00
private void setAutoMatch() {
hostComboBox.setSelectedItem(null);
2023-11-07 11:15:20 +08:00
hostComboBox.addActionListener(this::handleComboBoxAction);
2023-10-12 21:38:27 +08:00
hostTextField.addKeyListener(new KeyAdapter() {
@Override
public void keyPressed(KeyEvent e) {
2023-11-07 11:15:20 +08:00
handleKeyEvents(e);
2023-10-12 21:38:27 +08:00
}
});
hostTextField.getDocument().addDocumentListener(new DocumentListener() {
@Override
public void insertUpdate(DocumentEvent e) {
2023-11-27 14:55:28 +08:00
filterComboBoxList();
2023-10-12 21:38:27 +08:00
}
@Override
public void removeUpdate(DocumentEvent e) {
2023-11-27 14:55:28 +08:00
filterComboBoxList();
2023-10-12 21:38:27 +08:00
}
@Override
public void changedUpdate(DocumentEvent e) {
2023-11-07 11:15:20 +08:00
filterComboBoxList();
}
2023-11-27 14:55:28 +08:00
2023-11-07 11:15:20 +08:00
});
}
private void handleComboBoxAction(ActionEvent e) {
if (!isMatchHost && hostComboBox.getSelectedItem() != null) {
2024-05-30 14:37:01 +08:00
progressBar.setVisible(true);
setProgressBar(true);
2023-11-07 11:15:20 +08:00
String selectedHost = hostComboBox.getSelectedItem().toString();
hostTextField.setText(selectedHost);
2024-05-30 14:37:01 +08:00
if (currentWorker != null && !currentWorker.isDone()) {
currentWorker.cancel(true);
}
currentWorker = new SwingWorker<Boolean, Void>() {
@Override
protected Boolean doInBackground() {
return populateTabbedPaneByHost(selectedHost);
}
@Override
protected void done() {
if (!isCancelled()) {
try {
boolean status = get();
if (status) {
JSplitPane messageSplitPane = messageTableModel.getSplitPane();
splitPane.setRightComponent(messageSplitPane);
messageTable = messageTableModel.getMessageTable();
resizePanel();
splitPane.setVisible(true);
hostTextField.setText(selectedHost);
hostComboBox.setPopupVisible(false);
applyHostFilter(selectedHost);
}
} catch (Exception ignored) {
}
}
}
};
currentWorker.execute();
2023-11-07 11:15:20 +08:00
}
}
2024-05-06 12:56:56 +08:00
2023-11-07 11:15:20 +08:00
private void handleKeyEvents(KeyEvent e) {
isMatchHost = true;
int keyCode = e.getKeyCode();
if (keyCode == KeyEvent.VK_SPACE && hostComboBox.isPopupVisible()) {
e.setKeyCode(KeyEvent.VK_ENTER);
}
2023-11-27 14:55:28 +08:00
if (Arrays.asList(KeyEvent.VK_DOWN, KeyEvent.VK_UP).contains(keyCode)) {
2023-11-07 11:15:20 +08:00
hostComboBox.dispatchEvent(e);
2023-11-27 14:55:28 +08:00
}
if (keyCode == KeyEvent.VK_ENTER) {
isMatchHost = false;
handleComboBoxAction(null);
2023-11-07 11:15:20 +08:00
}
if (keyCode == KeyEvent.VK_ESCAPE) {
hostComboBox.setPopupVisible(false);
}
isMatchHost = false;
}
2024-05-30 14:37:01 +08:00
private boolean populateTabbedPaneByHost(String selectedHost) {
ConcurrentHashMap<String, Map<String, List<String>>> dataMap = Config.globalDataMap;
Map<String, List<String>> selectedDataMap;
if (selectedHost.contains("*")) {
selectedDataMap = new HashMap<>();
dataMap.keySet().parallelStream().forEach(key -> {
if ((StringProcessor.matchesHostPattern(key, selectedHost) || selectedHost.equals("*")) && !key.contains("*")) {
Map<String, List<String>> ruleMap = dataMap.get(key);
for (String ruleKey : ruleMap.keySet()) {
List<String> dataList = ruleMap.get(ruleKey);
if (selectedDataMap.containsKey(ruleKey)) {
List<String> mergedList = new ArrayList<>(selectedDataMap.get(ruleKey));
mergedList.addAll(dataList);
HashSet<String> uniqueSet = new HashSet<>(mergedList);
selectedDataMap.put(ruleKey, new ArrayList<>(uniqueSet));
} else {
selectedDataMap.put(ruleKey, dataList);
}
}
}
});
} else {
selectedDataMap = dataMap.get(selectedHost);
}
if (!selectedDataMap.isEmpty()) {
dataTabbedPane.removeAll();
for (Map.Entry<String, List<String>> entry : selectedDataMap.entrySet()) {
String tabTitle = String.format("%s (%s)", entry.getKey(), entry.getValue().size());
Datatable datatablePanel = new Datatable(api, entry.getKey(), entry.getValue());
datatablePanel.setTableListener(messageTableModel);
dataTabbedPane.addTab(tabTitle, datatablePanel);
}
return true;
}
return false;
}
2023-11-07 11:15:20 +08:00
private void filterComboBoxList() {
isMatchHost = true;
comboBoxModel.removeAllElements();
String input = hostTextField.getText().toLowerCase();
2024-05-30 14:37:01 +08:00
2023-11-07 11:15:20 +08:00
if (!input.isEmpty()) {
for (String host : getHostByList()) {
String lowerCaseHost = host.toLowerCase();
if (lowerCaseHost.contains(input)) {
if (lowerCaseHost.equals(input)) {
comboBoxModel.insertElementAt(lowerCaseHost, 0);
comboBoxModel.setSelectedItem(lowerCaseHost);
} else {
comboBoxModel.addElement(host);
2023-10-12 21:38:27 +08:00
}
}
}
2023-11-07 11:15:20 +08:00
}
hostComboBox.setPopupVisible(comboBoxModel.getSize() > 0);
isMatchHost = false;
2023-10-12 21:38:27 +08:00
}
2024-05-06 12:56:56 +08:00
private void applyHostFilter(String filterText) {
TableRowSorter<TableModel> sorter = (TableRowSorter<TableModel>) messageTable.getRowSorter();
String cleanedText = StringProcessor.replaceFirstOccurrence(filterText, "*.", "");
2024-05-30 14:37:01 +08:00
new SwingWorker<Void, Void>() {
@Override
protected Void doInBackground() throws Exception {
RowFilter<Object, Object> rowFilter = new RowFilter<Object, Object>() {
public boolean include(Entry<?, ?> entry) {
if (cleanedText.equals("*")) {
return true;
} else {
String host = StringProcessor.getHostByUrl((String) entry.getValue(1));
return StringProcessor.matchesHostPattern(host, filterText);
}
}
};
2024-05-24 15:00:49 +08:00
2024-05-30 14:37:01 +08:00
sorter.setRowFilter(rowFilter);
messageTableModel.applyHostFilter(filterText);
return null;
2024-05-23 12:00:13 +08:00
}
2024-05-06 12:56:56 +08:00
2024-05-30 14:37:01 +08:00
@Override
protected void done() {
setProgressBar(false);
}
}.execute();
2024-05-06 12:56:56 +08:00
}
private List<String> getHostByList() {
2024-05-30 14:37:01 +08:00
if (!Config.globalDataMap.keySet().isEmpty()) {
2024-05-24 15:00:49 +08:00
return new ArrayList<>(Config.globalDataMap.keySet());
}
return new ArrayList<>();
}
private void exportActionPerformed(ActionEvent e) {
String selectedHost = hostTextField.getText().trim();
if (selectedHost.isEmpty()) {
return;
}
String exportDir = selectDirectory(true);
if (exportDir.isEmpty()) {
return;
}
2024-05-30 14:37:01 +08:00
new SwingWorker<List<String>, Void>() {
@Override
protected List<String> doInBackground() {
ConcurrentHashMap<String, Map<String, List<String>>> dataMap = Config.globalDataMap;
return exportData(selectedHost, exportDir, dataMap);
}
2024-05-24 15:00:49 +08:00
2024-05-30 14:37:01 +08:00
@Override
protected void done() {
try {
List<String> taskStatusList = get();
if (!taskStatusList.isEmpty()) {
String exportStatusMessage = String.format("Exported File List Status:\n%s", String.join("\n", taskStatusList));
JOptionPane.showConfirmDialog(Databoard.this, exportStatusMessage, "Info", JOptionPane.YES_OPTION);
}
} catch (Exception ignored) {
}
}
}.execute();
2024-05-24 15:00:49 +08:00
}
private List<String> exportData(String selectedHost, String exportDir, Map<String, Map<String, List<String>>> dataMap) {
return dataMap.entrySet().stream()
.filter(entry -> selectedHost.equals("*") || StringProcessor.matchesHostPattern(entry.getKey(), selectedHost))
.filter(entry -> !entry.getKey().contains("*"))
.map(entry -> exportEntry(entry, exportDir))
.filter(Objects::nonNull)
.collect(Collectors.toList());
}
private String exportEntry(Map.Entry<String, Map<String, List<String>>> entry, String exportDir) {
String key = entry.getKey();
Map<String, List<String>> ruleMap = entry.getValue();
if (ruleMap == null || ruleMap.isEmpty()) {
return null;
}
List<MessageEntry> messageEntryList = messageTableModel.getLogs();
2024-05-30 14:37:01 +08:00
Map<MessageEntry, String> entryUUIDMap = messageEntryList.stream()
2024-05-24 15:00:49 +08:00
.collect(Collectors.toMap(
2024-05-30 14:37:01 +08:00
messageEntry -> messageEntry,
messageEntry -> StringProcessor.getRandomUUID(),
(existing, replacement) -> existing // 在冲突时保留现有的映射
2024-05-24 15:00:49 +08:00
));
2024-05-30 14:37:01 +08:00
Map<String, Map<String, Object>> httpMap = processEntries(
messageEntryList,
key,
entryUUIDMap,
this::createHttpItemMap
);
Map<String, Map<String, Object>> urlMap = processEntries(
messageEntryList,
key,
entryUUIDMap,
this::creteUrlItemMap
);
2024-05-24 15:00:49 +08:00
String hostName = key.replace(":", "_");
2024-05-30 14:37:01 +08:00
String filename = String.format("%s/%s-%s.hae", exportDir, StringProcessor.getCurrentTime(), hostName);
boolean createdStatus = projectProcessor.createHaeFile(filename, key, ruleMap, urlMap, httpMap);
2024-05-24 15:00:49 +08:00
return String.format("Filename: %s, Status: %s", filename, createdStatus);
}
2024-05-30 14:37:01 +08:00
private Map<String, Map<String, Object>> processEntries(List<MessageEntry> messageEntryList, String key, Map<MessageEntry, String> entryUUIDMap, Function<MessageEntry, Map<String, Object>> mapFunction) {
return messageEntryList.stream()
.filter(messageEntry -> !StringProcessor.getHostByUrl(messageEntry.getUrl()).isEmpty())
.filter(messageEntry -> StringProcessor.getHostByUrl(messageEntry.getUrl()).equals(key))
.collect(Collectors.toMap(
entryUUIDMap::get,
mapFunction,
(existing, replacement) -> existing
));
}
private Map<String, Object> creteUrlItemMap(MessageEntry entry) {
Map<String, Object> urlItemMap = new LinkedHashMap<>();
urlItemMap.put("url", entry.getUrl());
urlItemMap.put("method", entry.getMethod());
urlItemMap.put("status", entry.getStatus());
urlItemMap.put("length", entry.getLength());
urlItemMap.put("comment", entry.getComment());
urlItemMap.put("color", entry.getColor());
urlItemMap.put("size", String.valueOf(entry.getRequestResponse().request().toByteArray().length()));
return urlItemMap;
}
private Map<String, Object> createHttpItemMap(MessageEntry entry) {
Map<String, Object> httpItemMap = new LinkedHashMap<>();
httpItemMap.put("request", entry.getRequestResponse().request().toByteArray().getBytes());
httpItemMap.put("response", entry.getRequestResponse().response().toByteArray().getBytes());
2024-05-24 15:00:49 +08:00
return httpItemMap;
}
private void importActionPerformed(ActionEvent e) {
String exportDir = selectDirectory(false);
if (exportDir.isEmpty()) {
return;
}
2024-05-30 14:37:01 +08:00
new SwingWorker<List<String>, Void>() {
@Override
protected List<String> doInBackground() {
List<String> filesWithExtension = findFilesWithExtension(new File(exportDir), ".hae");
return filesWithExtension.stream()
.map(Databoard.this::importData)
.collect(Collectors.toList());
}
2024-05-24 15:00:49 +08:00
2024-05-30 14:37:01 +08:00
@Override
protected void done() {
try {
List<String> taskStatusList = get();
if (!taskStatusList.isEmpty()) {
String importStatusMessage = "Imported File List Status:\n" + String.join("\n", taskStatusList);
JOptionPane.showConfirmDialog(Databoard.this, importStatusMessage, "Info", JOptionPane.YES_OPTION);
}
} catch (Exception ignored) {
}
}
}.execute();
2024-05-24 15:00:49 +08:00
}
private String importData(String filename) {
HaeFileContent haeFileContent = projectProcessor.readHaeFile(filename);
boolean readStatus = haeFileContent != null;
2024-05-30 14:37:01 +08:00
ExecutorService executor = Executors.newFixedThreadPool(Runtime.getRuntime().availableProcessors() * 2);
List<Future<?>> futures = new ArrayList<>();
2024-05-24 15:00:49 +08:00
if (readStatus) {
2024-05-30 14:37:01 +08:00
try {
String host = haeFileContent.getHost();
haeFileContent.getDataMap().forEach((key, value) -> RegularMatcher.putDataToGlobalMap(host, key, value));
haeFileContent.getUrlMap().forEach((key, urlItemMap) -> {
Future<?> future = executor.submit(() -> {
String url = urlItemMap.get("url");
String comment = urlItemMap.get("comment");
String color = urlItemMap.get("color");
String length = urlItemMap.get("length");
String method = urlItemMap.get("method");
String status = urlItemMap.get("status");
String path = haeFileContent.getHttpPath();
messageTableModel.add(null, url, method, status, length, comment, color, key, path);
});
futures.add(future);
});
for (Future<?> future : futures) {
try {
future.get();
} catch (InterruptedException | ExecutionException e) {
Thread.currentThread().interrupt();
}
}
} catch (Exception e) {
api.logging().logToError("importData: " + e.getMessage());
} finally {
executor.shutdown();
}
2024-05-24 15:00:49 +08:00
}
return String.format("Filename: %s, Status: %s", filename, readStatus);
}
private List<String> findFilesWithExtension(File directory, String extension) {
List<String> filePaths = new ArrayList<>();
if (directory.isDirectory()) {
File[] files = directory.listFiles();
if (files != null) {
for (File file : files) {
if (file.isDirectory()) {
filePaths.addAll(findFilesWithExtension(file, extension));
} else if (file.isFile() && file.getName().toLowerCase().endsWith(extension)) {
filePaths.add(file.getAbsolutePath());
}
}
}
2024-05-30 14:37:01 +08:00
} else {
filePaths.add(directory.getAbsolutePath());
2024-05-24 15:00:49 +08:00
}
return filePaths;
}
private String selectDirectory(boolean forDirectories) {
JFileChooser chooser = new JFileChooser();
chooser.setCurrentDirectory(new java.io.File(configLoader.getRulesFilePath()));
chooser.setDialogTitle(String.format("Select a Directory%s", forDirectories ? "" : " or File"));
FileNameExtensionFilter filter = new FileNameExtensionFilter(".hae Files", "hae");
chooser.addChoosableFileFilter(filter);
chooser.setFileFilter(filter);
chooser.setFileSelectionMode(forDirectories ? JFileChooser.DIRECTORIES_ONLY : JFileChooser.FILES_AND_DIRECTORIES);
chooser.setAcceptAllFileFilterUsed(!forDirectories);
if (chooser.showOpenDialog(this) == JFileChooser.APPROVE_OPTION) {
File selectedDirectory = chooser.getSelectedFile();
return selectedDirectory.getAbsolutePath();
}
return "";
2024-05-06 12:56:56 +08:00
}
private void clearActionPerformed(ActionEvent e) {
2024-05-30 14:37:01 +08:00
int retCode = JOptionPane.showConfirmDialog(this, "Do you want to clear data?", "Info",
2024-05-06 12:56:56 +08:00
JOptionPane.YES_NO_OPTION);
String host = hostTextField.getText();
if (retCode == JOptionPane.YES_OPTION && !host.isEmpty()) {
dataTabbedPane.removeAll();
splitPane.setVisible(false);
2024-05-30 14:37:01 +08:00
progressBar.setVisible(false);
2024-05-06 12:56:56 +08:00
2024-05-30 14:37:01 +08:00
Config.globalDataMap.keySet().parallelStream().forEach(key -> {
if (StringProcessor.matchesHostPattern(key, host) || host.equals("*")) {
Config.globalDataMap.remove(key);
}
});
if (!StringProcessor.matchHostIsIp(host) && !host.contains("*.")) {
String baseDomain = StringProcessor.getBaseDomain(StringProcessor.extractHostname(host));
long count = Config.globalDataMap.keySet().stream()
.filter(k -> !k.equals("*." + baseDomain))
.filter(k -> StringProcessor.matchFromEnd(k, baseDomain))
.count();
if (count == 0) {
Config.globalDataMap.remove("*." + baseDomain);
}
}
2024-05-06 12:56:56 +08:00
2024-05-30 14:37:01 +08:00
if (Config.globalDataMap.keySet().size() == 1 && Config.globalDataMap.keySet().stream().anyMatch(key -> key.contains("*"))) {
Config.globalDataMap.keySet().remove("*");
2024-05-06 12:56:56 +08:00
}
2023-10-23 21:51:12 +08:00
2024-05-24 15:00:49 +08:00
messageTableModel.deleteByHost(host);
2023-10-12 21:38:27 +08:00
}
}
2024-05-06 12:56:56 +08:00
}