import burp.api.montoya.BurpExtension;
import burp.api.montoya.MontoyaApi;
import burp.api.montoya.http.HttpService;
import burp.api.montoya.http.message.requests.HttpRequest;
import burp.api.montoya.http.message.responses.HttpResponse;
import burp.api.montoya.core.ToolType;
import burp.api.montoya.ui.swing.SwingUtils;
import javax.swing.*;
import javax.swing.table.DefaultTableModel;
import java.awt.*;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.ArrayList;
public class BurpExtender implements BurpExtension {
private MontoyaApi api;
private JTable resultTable;
private DefaultTableModel tableModel;
private JTextArea requestTextArea;
private JTextArea responseTextArea;
private List<HttpRequest> requests = new ArrayList<>();
private List<HttpResponse> responses = new ArrayList<>();
@Override
public void initialize(MontoyaApi api) {
this.api = api;
api.extension().setName("Dir Index Checker (Montoya)");
JPanel panel = buildUI();
api.userInterface().registerSuiteTab("Dir Index Checker", panel);
}
private JPanel buildUI() {
JPanel mainPanel = new JPanel(new BorderLayout());
JButton scanButton = new JButton("Scan Site Map for Directory Indexing");
scanButton.addActionListener(e -> scanSiteMap());
JPanel topPanel = new JPanel(new FlowLayout(FlowLayout.LEFT));
topPanel.add(scanButton);
mainPanel.add(topPanel, BorderLayout.NORTH);
String[] columns = {"URL", "Status", "Indexing", "Time"};
tableModel = new DefaultTableModel(columns, 0);
resultTable = new JTable(tableModel);
JScrollPane tableScroll = new JScrollPane(resultTable);
mainPanel.add(tableScroll, BorderLayout.CENTER);
requestTextArea = new JTextArea();
responseTextArea = new JTextArea();
JSplitPane splitPane = new JSplitPane(JSplitPane.HORIZONTAL_SPLIT,
new JScrollPane(requestTextArea), new JScrollPane(responseTextArea));
splitPane.setDividerLocation(400);
mainPanel.add(splitPane, BorderLayout.SOUTH);
resultTable.getSelectionModel().addListSelectionListener(e -> {
int row = resultTable.getSelectedRow();
if (row >= 0 && row < requests.size()) {
requestTextArea.setText(requests.get(row).toString());
responseTextArea.setText(responses.get(row).toString());
}
});
return mainPanel;
}
private void scanSiteMap() {
tableModel.setRowCount(0);
requests.clear();
responses.clear();
List<HttpRequest> siteMapRequests = api.siteMap().requests();
for (HttpRequest req : siteMapRequests) {
String path = req.url().getPath();
if (!path.endsWith("/")) continue;
HttpResponse resp = api.http().sendRequest(req);
if (resp == null || resp.bodyToString() == null) continue;
String body = resp.bodyToString();
boolean isIndexed = body.contains("Index of")
|| body.toLowerCase().contains("<title>index of")
|| body.toLowerCase().contains("<a href=");
String indexingStr = isIndexed ? "YES" : "NO";
String timeStr = new SimpleDateFormat("HH:mm:ss").format(new Date());
tableModel.addRow(new Object[]{req.url().toString(), resp.statusCode(), indexingStr, timeStr});
requests.add(req);
responses.add(resp);
}
}
}