mirror of
https://github.com/overcuriousity/autopsy-flatpak.git
synced 2025-07-15 01:07:42 +00:00
Merge branch 'master' of github.com:sleuthkit/autopsy
This commit is contained in:
commit
050f1a076c
@ -23,6 +23,7 @@ import java.awt.Cursor;
|
|||||||
import java.util.logging.Level;
|
import java.util.logging.Level;
|
||||||
import java.util.logging.Logger;
|
import java.util.logging.Logger;
|
||||||
import org.openide.nodes.Node;
|
import org.openide.nodes.Node;
|
||||||
|
import org.openide.util.Lookup;
|
||||||
import org.openide.util.lookup.ServiceProvider;
|
import org.openide.util.lookup.ServiceProvider;
|
||||||
import org.sleuthkit.autopsy.corecomponentinterfaces.DataContentViewer;
|
import org.sleuthkit.autopsy.corecomponentinterfaces.DataContentViewer;
|
||||||
import org.sleuthkit.autopsy.datamodel.DataConversion;
|
import org.sleuthkit.autopsy.datamodel.DataConversion;
|
||||||
@ -354,7 +355,8 @@ public class DataContentViewerString extends javax.swing.JPanel implements DataC
|
|||||||
@Override
|
@Override
|
||||||
public void setNode(Node selectedNode) {
|
public void setNode(Node selectedNode) {
|
||||||
if (selectedNode != null) {
|
if (selectedNode != null) {
|
||||||
Content content = selectedNode.getLookup().lookup(Content.class);
|
Lookup lookup = selectedNode.getLookup();
|
||||||
|
Content content = lookup.lookup(Content.class);
|
||||||
if (content != null) {
|
if (content != null) {
|
||||||
this.setDataView(content, 0, false);
|
this.setDataView(content, 0, false);
|
||||||
return;
|
return;
|
||||||
|
@ -23,6 +23,7 @@ import java.util.Map;
|
|||||||
import org.openide.nodes.AbstractNode;
|
import org.openide.nodes.AbstractNode;
|
||||||
import org.openide.nodes.Children;
|
import org.openide.nodes.Children;
|
||||||
import org.openide.nodes.Sheet;
|
import org.openide.nodes.Sheet;
|
||||||
|
import org.openide.util.Lookup;
|
||||||
|
|
||||||
public class KeyValueNode extends AbstractNode {
|
public class KeyValueNode extends AbstractNode {
|
||||||
|
|
||||||
@ -34,6 +35,12 @@ public class KeyValueNode extends AbstractNode {
|
|||||||
this.thing = thing;
|
this.thing = thing;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public KeyValueNode(KeyValueThing thing, Children children, Lookup lookup) {
|
||||||
|
super(children, lookup);
|
||||||
|
this.setName(thing.getName());
|
||||||
|
this.thing = thing;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected Sheet createSheet() {
|
protected Sheet createSheet() {
|
||||||
Sheet s = super.createSheet();
|
Sheet s = super.createSheet();
|
||||||
|
@ -23,7 +23,7 @@ import java.awt.event.ActionEvent;
|
|||||||
import java.awt.event.ActionListener;
|
import java.awt.event.ActionListener;
|
||||||
import java.beans.PropertyChangeEvent;
|
import java.beans.PropertyChangeEvent;
|
||||||
import java.beans.PropertyChangeListener;
|
import java.beans.PropertyChangeListener;
|
||||||
import java.util.Map;
|
import java.util.List;
|
||||||
import org.openide.util.lookup.ServiceProvider;
|
import org.openide.util.lookup.ServiceProvider;
|
||||||
import org.sleuthkit.autopsy.corecomponentinterfaces.DataExplorer;
|
import org.sleuthkit.autopsy.corecomponentinterfaces.DataExplorer;
|
||||||
import org.sleuthkit.autopsy.keywordsearch.KeywordSearch.QueryType;
|
import org.sleuthkit.autopsy.keywordsearch.KeywordSearch.QueryType;
|
||||||
@ -74,7 +74,7 @@ public class KeywordSearchDataExplorer implements DataExplorer {
|
|||||||
private void search() {
|
private void search() {
|
||||||
KeywordSearchQueryManager man = null;
|
KeywordSearchQueryManager man = null;
|
||||||
if (tc.isMultiwordQuery()) {
|
if (tc.isMultiwordQuery()) {
|
||||||
final Map<String, Boolean> keywords = tc.getQueryList();
|
final List<Keyword> keywords = tc.getQueryList();
|
||||||
if (keywords.isEmpty()) {
|
if (keywords.isEmpty()) {
|
||||||
KeywordSearchUtil.displayDialog("Keyword Search Error", "Keyword list is empty, please add at least one keyword to the list", KeywordSearchUtil.DIALOG_MESSAGE_TYPE.ERROR);
|
KeywordSearchUtil.displayDialog("Keyword Search Error", "Keyword list is empty, please add at least one keyword to the list", KeywordSearchUtil.DIALOG_MESSAGE_TYPE.ERROR);
|
||||||
return;
|
return;
|
||||||
|
@ -20,7 +20,7 @@ package org.sleuthkit.autopsy.keywordsearch;
|
|||||||
|
|
||||||
import java.awt.Component;
|
import java.awt.Component;
|
||||||
import java.awt.event.ActionListener;
|
import java.awt.event.ActionListener;
|
||||||
import java.util.Map;
|
import java.util.List;
|
||||||
import java.util.logging.Logger;
|
import java.util.logging.Logger;
|
||||||
import javax.swing.JTable;
|
import javax.swing.JTable;
|
||||||
import javax.swing.table.DefaultTableCellRenderer;
|
import javax.swing.table.DefaultTableCellRenderer;
|
||||||
@ -264,7 +264,7 @@ public final class KeywordSearchHistoryTopComponent extends TopComponent impleme
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Map<String, Boolean> getQueryList() {
|
public List<Keyword> getQueryList() {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -416,7 +416,7 @@ public final class KeywordSearchListImportExportTopComponent extends TopComponen
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Map<String, Boolean> getQueryList() {
|
public List<Keyword> getQueryList() {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -288,6 +288,9 @@
|
|||||||
<Property name="autoResizeMode" type="int" value="0"/>
|
<Property name="autoResizeMode" type="int" value="0"/>
|
||||||
<Property name="showHorizontalLines" type="boolean" value="false"/>
|
<Property name="showHorizontalLines" type="boolean" value="false"/>
|
||||||
<Property name="showVerticalLines" type="boolean" value="false"/>
|
<Property name="showVerticalLines" type="boolean" value="false"/>
|
||||||
|
<Property name="tableHeader" type="javax.swing.table.JTableHeader" editor="org.netbeans.modules.form.editors2.JTableHeaderEditor">
|
||||||
|
<TableHeader reorderingAllowed="false" resizingAllowed="true"/>
|
||||||
|
</Property>
|
||||||
</Properties>
|
</Properties>
|
||||||
</Component>
|
</Component>
|
||||||
</SubComponents>
|
</SubComponents>
|
||||||
|
@ -94,8 +94,8 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
deleteWordButton.setToolTipText("Remove selected keyword(s) from the list");
|
deleteWordButton.setToolTipText("Remove selected keyword(s) from the list");
|
||||||
deleteAllWordsButton.setToolTipText("Remove all keywords from the list (clear it)");
|
deleteAllWordsButton.setToolTipText("Remove all keywords from the list (clear it)");
|
||||||
|
|
||||||
keywordTable.setAutoscrolls(true);
|
//keywordTable.setAutoscrolls(true);
|
||||||
keywordTable.setTableHeader(null);
|
//keywordTable.setTableHeader(null);
|
||||||
keywordTable.setShowHorizontalLines(false);
|
keywordTable.setShowHorizontalLines(false);
|
||||||
keywordTable.setShowVerticalLines(false);
|
keywordTable.setShowVerticalLines(false);
|
||||||
|
|
||||||
@ -105,14 +105,15 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
keywordTable.setSize(260, 200);
|
keywordTable.setSize(260, 200);
|
||||||
final int width = keywordTable.getSize().width;
|
final int width = keywordTable.getSize().width;
|
||||||
TableColumn column = null;
|
TableColumn column = null;
|
||||||
for (int i = 0; i < 2; i++) {
|
for (int i = 0; i < 3; i++) {
|
||||||
column = keywordTable.getColumnModel().getColumn(i);
|
column = keywordTable.getColumnModel().getColumn(i);
|
||||||
if (i == 1) {
|
if (i > 0) {
|
||||||
column.setPreferredWidth(((int) (width * 0.2)));
|
column.setPreferredWidth(((int) (width * 0.15)));
|
||||||
//column.setCellRenderer(new CellTooltipRenderer());
|
//column.setCellRenderer(new CellTooltipRenderer());
|
||||||
} else {
|
}
|
||||||
|
else {
|
||||||
column.setCellRenderer(new CellTooltipRenderer());
|
column.setCellRenderer(new CellTooltipRenderer());
|
||||||
column.setPreferredWidth(((int) (width * 0.75)));
|
column.setPreferredWidth(((int) (width * 0.68)));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
keywordTable.setCellSelectionEnabled(false);
|
keywordTable.setCellSelectionEnabled(false);
|
||||||
@ -166,18 +167,19 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
//some hardcoded keywords for testing
|
//some hardcoded keywords for testing
|
||||||
|
|
||||||
//phone number
|
//phone number
|
||||||
tableModel.addKeyword("\\d\\d\\d[\\.-]\\d\\d\\d[\\.-]\\d\\d\\d\\d");
|
tableModel.addKeyword(new Keyword("\\d\\d\\d[\\.-]\\d\\d\\d[\\.-]\\d\\d\\d\\d", false));
|
||||||
tableModel.addKeyword("\\d{8,10}");
|
tableModel.addKeyword(new Keyword("\\d{8,10}", false));
|
||||||
tableModel.addKeyword("phone|fax");
|
tableModel.addKeyword(new Keyword("phone|fax", false));
|
||||||
//IP address
|
//IP address
|
||||||
tableModel.addKeyword("(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])");
|
tableModel.addKeyword(new Keyword("(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])", false));
|
||||||
//email
|
//email
|
||||||
tableModel.addKeyword("[e\\-]{0,2}mail");
|
tableModel.addKeyword(new Keyword("[e\\-]{0,2}mail", false));
|
||||||
tableModel.addKeyword("[A-Z0-9._%-]+@[A-Z0-9.-]+\\.[A-Z]{2,4}");
|
tableModel.addKeyword(new Keyword("[A-Z0-9._%-]+@[A-Z0-9.-]+\\.[A-Z]{2,4}", false));
|
||||||
//URL
|
//URL
|
||||||
tableModel.addKeyword("ftp|sftp|ssh|http|https|www");
|
tableModel.addKeyword(new Keyword("ftp|sftp|ssh|http|https|www", false));
|
||||||
//escaped literal word \d\d\d
|
//escaped literal word \d\d\d
|
||||||
tableModel.addKeyword("\\Q\\d\\d\\d\\E");
|
tableModel.addKeyword(new Keyword("\\Q\\d\\d\\d\\E", false));
|
||||||
|
tableModel.addKeyword(new Keyword("\\d\\d\\d\\d", true));
|
||||||
}
|
}
|
||||||
|
|
||||||
/** This method is called from within the constructor to
|
/** This method is called from within the constructor to
|
||||||
@ -212,7 +214,7 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
|
|
||||||
org.openide.awt.Mnemonics.setLocalizedText(filesIndexedValLabel, org.openide.util.NbBundle.getMessage(KeywordSearchListTopComponent.class, "KeywordSearchListTopComponent.filesIndexedValLabel.text")); // NOI18N
|
org.openide.awt.Mnemonics.setLocalizedText(filesIndexedValLabel, org.openide.util.NbBundle.getMessage(KeywordSearchListTopComponent.class, "KeywordSearchListTopComponent.filesIndexedValLabel.text")); // NOI18N
|
||||||
|
|
||||||
titleLabel.setFont(new java.awt.Font("Tahoma", 0, 12)); // NOI18N
|
titleLabel.setFont(new java.awt.Font("Tahoma", 0, 12));
|
||||||
org.openide.awt.Mnemonics.setLocalizedText(titleLabel, org.openide.util.NbBundle.getMessage(KeywordSearchListTopComponent.class, "KeywordSearchListTopComponent.titleLabel.text")); // NOI18N
|
org.openide.awt.Mnemonics.setLocalizedText(titleLabel, org.openide.util.NbBundle.getMessage(KeywordSearchListTopComponent.class, "KeywordSearchListTopComponent.titleLabel.text")); // NOI18N
|
||||||
|
|
||||||
org.openide.awt.Mnemonics.setLocalizedText(loadListButton, org.openide.util.NbBundle.getMessage(KeywordSearchListTopComponent.class, "KeywordSearchListTopComponent.loadListButton.text")); // NOI18N
|
org.openide.awt.Mnemonics.setLocalizedText(loadListButton, org.openide.util.NbBundle.getMessage(KeywordSearchListTopComponent.class, "KeywordSearchListTopComponent.loadListButton.text")); // NOI18N
|
||||||
@ -276,6 +278,7 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
keywordTable.setAutoResizeMode(javax.swing.JTable.AUTO_RESIZE_OFF);
|
keywordTable.setAutoResizeMode(javax.swing.JTable.AUTO_RESIZE_OFF);
|
||||||
keywordTable.setShowHorizontalLines(false);
|
keywordTable.setShowHorizontalLines(false);
|
||||||
keywordTable.setShowVerticalLines(false);
|
keywordTable.setShowVerticalLines(false);
|
||||||
|
keywordTable.getTableHeader().setReorderingAllowed(false);
|
||||||
jScrollPane1.setViewportView(keywordTable);
|
jScrollPane1.setViewportView(keywordTable);
|
||||||
|
|
||||||
org.openide.awt.Mnemonics.setLocalizedText(searchButton, org.openide.util.NbBundle.getMessage(KeywordSearchListTopComponent.class, "KeywordSearchListTopComponent.searchButton.text")); // NOI18N
|
org.openide.awt.Mnemonics.setLocalizedText(searchButton, org.openide.util.NbBundle.getMessage(KeywordSearchListTopComponent.class, "KeywordSearchListTopComponent.searchButton.text")); // NOI18N
|
||||||
@ -358,7 +361,7 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
.addGap(11, 11, 11)
|
.addGap(11, 11, 11)
|
||||||
.addComponent(curListNameLabel)
|
.addComponent(curListNameLabel)
|
||||||
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||||
.addComponent(curListValLabel, javax.swing.GroupLayout.DEFAULT_SIZE, 222, Short.MAX_VALUE)))
|
.addComponent(curListValLabel, javax.swing.GroupLayout.DEFAULT_SIZE, 296, Short.MAX_VALUE)))
|
||||||
.addGap(22, 22, 22))
|
.addGap(22, 22, 22))
|
||||||
.addGroup(layout.createSequentialGroup()
|
.addGroup(layout.createSequentialGroup()
|
||||||
.addComponent(filesIndexedNameLabel)
|
.addComponent(filesIndexedNameLabel)
|
||||||
@ -395,26 +398,21 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
private void addWordButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_addWordButtonActionPerformed
|
private void addWordButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_addWordButtonActionPerformed
|
||||||
|
|
||||||
String newWord = addWordField.getText().trim();
|
String newWord = addWordField.getText().trim();
|
||||||
String newWordEscaped = Pattern.quote(newWord);
|
boolean isLiteral = !chRegex.isSelected();
|
||||||
|
final Keyword keyword = new Keyword(newWord, isLiteral);
|
||||||
|
|
||||||
if (newWord.equals("")) {
|
if (newWord.equals("")) {
|
||||||
return;
|
return;
|
||||||
} else if (keywordExists(newWord) || keywordExists(newWordEscaped)) {
|
} else if (keywordExists(keyword)) {
|
||||||
KeywordSearchUtil.displayDialog("New Keyword Entry", "Keyword already exists in the list.", KeywordSearchUtil.DIALOG_MESSAGE_TYPE.INFO);
|
KeywordSearchUtil.displayDialog("New Keyword Entry", "Keyword already exists in the list.", KeywordSearchUtil.DIALOG_MESSAGE_TYPE.INFO);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
String toAdd = null;
|
|
||||||
if (!chRegex.isSelected()) {
|
|
||||||
toAdd = newWordEscaped;
|
|
||||||
} else {
|
|
||||||
toAdd = newWord;
|
|
||||||
}
|
|
||||||
|
|
||||||
//check if valid
|
//check if valid
|
||||||
boolean valid = true;
|
boolean valid = true;
|
||||||
try {
|
try {
|
||||||
Pattern.compile(toAdd);
|
Pattern.compile(newWord);
|
||||||
} catch (PatternSyntaxException ex1) {
|
} catch (PatternSyntaxException ex1) {
|
||||||
valid = false;
|
valid = false;
|
||||||
} catch (IllegalArgumentException ex2) {
|
} catch (IllegalArgumentException ex2) {
|
||||||
@ -426,8 +424,8 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
}
|
}
|
||||||
|
|
||||||
//add & reset checkbox
|
//add & reset checkbox
|
||||||
|
tableModel.addKeyword(keyword);
|
||||||
chRegex.setSelected(false);
|
chRegex.setSelected(false);
|
||||||
tableModel.addKeyword(toAdd);
|
|
||||||
addWordField.setText("");
|
addWordField.setText("");
|
||||||
|
|
||||||
if (deleteWordButton.isEnabled() == false) {
|
if (deleteWordButton.isEnabled() == false) {
|
||||||
@ -448,7 +446,7 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
final String FEATURE_NAME = "Save Keyword List";
|
final String FEATURE_NAME = "Save Keyword List";
|
||||||
KeywordSearchListsXML writer = KeywordSearchListsXML.getCurrent();
|
KeywordSearchListsXML writer = KeywordSearchListsXML.getCurrent();
|
||||||
|
|
||||||
List<String> keywords = tableModel.getAllKeywords();
|
List<Keyword> keywords = tableModel.getAllKeywords();
|
||||||
if (keywords.isEmpty()) {
|
if (keywords.isEmpty()) {
|
||||||
KeywordSearchUtil.displayDialog(FEATURE_NAME, "Keyword List is empty and cannot be saved", KeywordSearchUtil.DIALOG_MESSAGE_TYPE.INFO);
|
KeywordSearchUtil.displayDialog(FEATURE_NAME, "Keyword List is empty and cannot be saved", KeywordSearchUtil.DIALOG_MESSAGE_TYPE.INFO);
|
||||||
return;
|
return;
|
||||||
@ -717,20 +715,8 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Map<String, Boolean> getQueryList() {
|
public List<Keyword> getQueryList() {
|
||||||
List<String> selected = getAllKeywords();
|
return getAllKeywords();
|
||||||
//filter out blank just in case
|
|
||||||
Map<String, Boolean> ret = new LinkedHashMap<String, Boolean>();
|
|
||||||
for (String s : selected) {
|
|
||||||
if (!s.trim().equals("")) {
|
|
||||||
//use false for isLiteral because we are currently escaping
|
|
||||||
//the keyword earlier as it is stored
|
|
||||||
//might need to change and pass isLiteral
|
|
||||||
//if the query object needs to treat it specially
|
|
||||||
ret.put(s, false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -753,16 +739,15 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<String> getAllKeywords() {
|
List<Keyword> getAllKeywords() {
|
||||||
return tableModel.getAllKeywords();
|
return tableModel.getAllKeywords();
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<String> getSelectedKeywords() {
|
List<Keyword> getSelectedKeywords() {
|
||||||
return tableModel.getSelectedKeywords();
|
return tableModel.getSelectedKeywords();
|
||||||
}
|
}
|
||||||
|
|
||||||
private boolean keywordExists(String keyword) {
|
private boolean keywordExists(Keyword keyword) {
|
||||||
|
|
||||||
return tableModel.keywordExists(keyword);
|
return tableModel.keywordExists(keyword);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -773,7 +758,7 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getColumnCount() {
|
public int getColumnCount() {
|
||||||
return 2;
|
return 3;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -781,6 +766,29 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
return keywordData.size();
|
return keywordData.size();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getColumnName(int column) {
|
||||||
|
String colName = null;
|
||||||
|
|
||||||
|
switch (column) {
|
||||||
|
case 0:
|
||||||
|
colName = "Keyword";
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
colName = "RegEx.";
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
colName = "Sel.";
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
;
|
||||||
|
|
||||||
|
}
|
||||||
|
return colName;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Object getValueAt(int rowIndex, int columnIndex) {
|
public Object getValueAt(int rowIndex, int columnIndex) {
|
||||||
Object ret = null;
|
Object ret = null;
|
||||||
@ -795,6 +803,9 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
ret = (Object) entry.keyword;
|
ret = (Object) entry.keyword;
|
||||||
break;
|
break;
|
||||||
case 1:
|
case 1:
|
||||||
|
ret = (Object) !entry.isLiteral;
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
ret = (Object) entry.isActive;
|
ret = (Object) entry.isActive;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
@ -806,12 +817,12 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean isCellEditable(int rowIndex, int columnIndex) {
|
public boolean isCellEditable(int rowIndex, int columnIndex) {
|
||||||
return columnIndex == 1 ? true : false;
|
return columnIndex == 2 ? true : false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void setValueAt(Object aValue, int rowIndex, int columnIndex) {
|
public void setValueAt(Object aValue, int rowIndex, int columnIndex) {
|
||||||
if (columnIndex == 1) {
|
if (columnIndex == 2) {
|
||||||
TableEntry entry = null;
|
TableEntry entry = null;
|
||||||
//iterate until row
|
//iterate until row
|
||||||
Iterator<TableEntry> it = keywordData.iterator();
|
Iterator<TableEntry> it = keywordData.iterator();
|
||||||
@ -832,38 +843,38 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
return getValueAt(0, c).getClass();
|
return getValueAt(0, c).getClass();
|
||||||
}
|
}
|
||||||
|
|
||||||
List<String> getAllKeywords() {
|
List<Keyword> getAllKeywords() {
|
||||||
List<String> ret = new ArrayList<String>();
|
List<Keyword> ret = new ArrayList<Keyword>();
|
||||||
for (TableEntry e : keywordData) {
|
for (TableEntry e : keywordData) {
|
||||||
ret.add(e.keyword);
|
ret.add(new Keyword(e.keyword, e.isLiteral));
|
||||||
}
|
}
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
List<String> getSelectedKeywords() {
|
List<Keyword> getSelectedKeywords() {
|
||||||
List<String> ret = new ArrayList<String>();
|
List<Keyword> ret = new ArrayList<Keyword>();
|
||||||
for (TableEntry e : keywordData) {
|
for (TableEntry e : keywordData) {
|
||||||
if (e.isActive && !e.keyword.equals("")) {
|
if (e.isActive && !e.keyword.equals("")) {
|
||||||
ret.add(e.keyword);
|
ret.add(new Keyword(e.keyword, e.isLiteral));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
boolean keywordExists(String keyword) {
|
boolean keywordExists(Keyword keyword) {
|
||||||
List<String> all = getAllKeywords();
|
List<Keyword> all = getAllKeywords();
|
||||||
return all.contains(keyword);
|
return all.contains(keyword);
|
||||||
}
|
}
|
||||||
|
|
||||||
void addKeyword(String keyword) {
|
void addKeyword(Keyword keyword) {
|
||||||
if (!keywordExists(keyword)) {
|
if (!keywordExists(keyword)) {
|
||||||
keywordData.add(new TableEntry(keyword));
|
keywordData.add(new TableEntry(keyword));
|
||||||
}
|
}
|
||||||
fireTableDataChanged();
|
fireTableDataChanged();
|
||||||
}
|
}
|
||||||
|
|
||||||
void addKeywords(List<String> keywords) {
|
void addKeywords(List<Keyword> keywords) {
|
||||||
for (String keyword : keywords) {
|
for (Keyword keyword : keywords) {
|
||||||
if (!keywordExists(keyword)) {
|
if (!keywordExists(keyword)) {
|
||||||
keywordData.add(new TableEntry(keyword));
|
keywordData.add(new TableEntry(keyword));
|
||||||
}
|
}
|
||||||
@ -874,7 +885,7 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
void resync(String listName) {
|
void resync(String listName) {
|
||||||
KeywordSearchListsXML loader = KeywordSearchListsXML.getCurrent();
|
KeywordSearchListsXML loader = KeywordSearchListsXML.getCurrent();
|
||||||
KeywordSearchList list = loader.getList(listName);
|
KeywordSearchList list = loader.getList(listName);
|
||||||
List<String> keywords = list.getKeywords();
|
List<Keyword> keywords = list.getKeywords();
|
||||||
|
|
||||||
deleteAll();
|
deleteAll();
|
||||||
addKeywords(keywords);
|
addKeywords(keywords);
|
||||||
@ -903,22 +914,37 @@ public final class KeywordSearchListTopComponent extends TopComponent implements
|
|||||||
class TableEntry implements Comparable {
|
class TableEntry implements Comparable {
|
||||||
|
|
||||||
String keyword;
|
String keyword;
|
||||||
|
Boolean isLiteral;
|
||||||
Boolean isActive;
|
Boolean isActive;
|
||||||
|
|
||||||
TableEntry(String keyword, Boolean isActive) {
|
TableEntry(Keyword keyword, Boolean isActive) {
|
||||||
this.keyword = keyword;
|
this.keyword = keyword.getQuery();
|
||||||
|
this.isLiteral = keyword.isLiteral();
|
||||||
this.isActive = isActive;
|
this.isActive = isActive;
|
||||||
}
|
}
|
||||||
|
|
||||||
TableEntry(String keyword) {
|
TableEntry(Keyword keyword) {
|
||||||
|
this.keyword = keyword.getQuery();
|
||||||
|
this.isLiteral = keyword.isLiteral();
|
||||||
|
this.isActive = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
TableEntry(String keyword, Boolean isLiteral) {
|
||||||
this.keyword = keyword;
|
this.keyword = keyword;
|
||||||
|
this.isLiteral = isLiteral;
|
||||||
this.isActive = false;
|
this.isActive = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
|
|
||||||
|
@Override
|
||||||
public int compareTo(Object o) {
|
public int compareTo(Object o) {
|
||||||
return this.keyword.compareTo(((TableEntry) o).keyword);
|
int keywords = this.keyword.compareTo(((TableEntry) o).keyword);
|
||||||
|
if (keywords != 0)
|
||||||
|
return keywords;
|
||||||
|
else return this.isLiteral.compareTo(((TableEntry) o).isLiteral);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -66,6 +66,7 @@ public class KeywordSearchListsXML {
|
|||||||
private static final String LIST_CREATE_ATTR = "created";
|
private static final String LIST_CREATE_ATTR = "created";
|
||||||
private static final String LIST_MOD_ATTR = "modified";
|
private static final String LIST_MOD_ATTR = "modified";
|
||||||
private static final String KEYWORD_EL = "keyword";
|
private static final String KEYWORD_EL = "keyword";
|
||||||
|
private static final String KEYWORD_LITERAL_ATTR = "literal";
|
||||||
private static final String CUR_LISTS_FILE_NAME = "keywords.xml";
|
private static final String CUR_LISTS_FILE_NAME = "keywords.xml";
|
||||||
private static final String DATE_FORMAT = "yyyy-MM-dd HH:mm:ss";
|
private static final String DATE_FORMAT = "yyyy-MM-dd HH:mm:ss";
|
||||||
private static final String ENCODING = "UTF-8";
|
private static final String ENCODING = "UTF-8";
|
||||||
@ -182,7 +183,7 @@ public class KeywordSearchListsXML {
|
|||||||
* @param newList list of keywords
|
* @param newList list of keywords
|
||||||
* @return true if old list was replaced
|
* @return true if old list was replaced
|
||||||
*/
|
*/
|
||||||
boolean addList(String name, List<String> newList) {
|
boolean addList(String name, List<Keyword> newList) {
|
||||||
boolean replaced = false;
|
boolean replaced = false;
|
||||||
KeywordSearchList curList = getList(name);
|
KeywordSearchList curList = getList(name);
|
||||||
final Date now = new Date();
|
final Date now = new Date();
|
||||||
@ -264,16 +265,18 @@ public class KeywordSearchListsXML {
|
|||||||
KeywordSearchList list = theLists.get(listName);
|
KeywordSearchList list = theLists.get(listName);
|
||||||
String created = dateFormatter.format(list.getDateCreated());
|
String created = dateFormatter.format(list.getDateCreated());
|
||||||
String modified = dateFormatter.format(list.getDateModified());
|
String modified = dateFormatter.format(list.getDateModified());
|
||||||
List<String> keywords = list.getKeywords();
|
List<Keyword> keywords = list.getKeywords();
|
||||||
|
|
||||||
Element listEl = doc.createElement(LIST_EL);
|
Element listEl = doc.createElement(LIST_EL);
|
||||||
listEl.setAttribute(LIST_NAME_ATTR, listName);
|
listEl.setAttribute(LIST_NAME_ATTR, listName);
|
||||||
listEl.setAttribute(LIST_CREATE_ATTR, created);
|
listEl.setAttribute(LIST_CREATE_ATTR, created);
|
||||||
listEl.setAttribute(LIST_MOD_ATTR, modified);
|
listEl.setAttribute(LIST_MOD_ATTR, modified);
|
||||||
|
|
||||||
for (String keyword : keywords) {
|
for (Keyword keyword : keywords) {
|
||||||
Element keywordEl = doc.createElement(KEYWORD_EL);
|
Element keywordEl = doc.createElement(KEYWORD_EL);
|
||||||
keywordEl.setTextContent(keyword);
|
String regex = keyword.isLiteral()==false?"true":"false";
|
||||||
|
keywordEl.setAttribute(KEYWORD_LITERAL_ATTR, regex);
|
||||||
|
keywordEl.setTextContent(keyword.getQuery());
|
||||||
listEl.appendChild(keywordEl);
|
listEl.appendChild(keywordEl);
|
||||||
}
|
}
|
||||||
rootEl.appendChild(listEl);
|
rootEl.appendChild(listEl);
|
||||||
@ -310,7 +313,7 @@ public class KeywordSearchListsXML {
|
|||||||
final String modified = listEl.getAttribute(LIST_MOD_ATTR);
|
final String modified = listEl.getAttribute(LIST_MOD_ATTR);
|
||||||
Date createdDate = dateFormatter.parse(created);
|
Date createdDate = dateFormatter.parse(created);
|
||||||
Date modDate = dateFormatter.parse(modified);
|
Date modDate = dateFormatter.parse(modified);
|
||||||
List<String> words = new ArrayList<String>();
|
List<Keyword> words = new ArrayList<Keyword>();
|
||||||
KeywordSearchList list = new KeywordSearchList(name, createdDate, modDate, words);
|
KeywordSearchList list = new KeywordSearchList(name, createdDate, modDate, words);
|
||||||
|
|
||||||
//parse all words
|
//parse all words
|
||||||
@ -318,7 +321,9 @@ public class KeywordSearchListsXML {
|
|||||||
final int numKeywords = wordsNList.getLength();
|
final int numKeywords = wordsNList.getLength();
|
||||||
for (int j = 0; j < numKeywords; ++j) {
|
for (int j = 0; j < numKeywords; ++j) {
|
||||||
Element wordEl = (Element) wordsNList.item(j);
|
Element wordEl = (Element) wordsNList.item(j);
|
||||||
words.add(wordEl.getTextContent());
|
String regex = wordEl.getAttribute(KEYWORD_LITERAL_ATTR);
|
||||||
|
boolean isRegex = regex.equals("true");
|
||||||
|
words.add(new Keyword(wordEl.getTextContent(), isRegex));
|
||||||
|
|
||||||
}
|
}
|
||||||
theLists.put(name, list);
|
theLists.put(name, list);
|
||||||
@ -405,9 +410,9 @@ class KeywordSearchList {
|
|||||||
private String name;
|
private String name;
|
||||||
private Date created;
|
private Date created;
|
||||||
private Date modified;
|
private Date modified;
|
||||||
private List<String> keywords;
|
private List<Keyword> keywords;
|
||||||
|
|
||||||
KeywordSearchList(String name, Date created, Date modified, List<String> keywords) {
|
KeywordSearchList(String name, Date created, Date modified, List<Keyword> keywords) {
|
||||||
this.name = name;
|
this.name = name;
|
||||||
this.created = created;
|
this.created = created;
|
||||||
this.modified = modified;
|
this.modified = modified;
|
||||||
@ -447,7 +452,7 @@ class KeywordSearchList {
|
|||||||
return modified;
|
return modified;
|
||||||
}
|
}
|
||||||
|
|
||||||
List<String> getKeywords() {
|
List<Keyword> getKeywords() {
|
||||||
return keywords;
|
return keywords;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -49,6 +49,12 @@ public interface KeywordSearchQuery {
|
|||||||
*/
|
*/
|
||||||
public void escape();
|
public void escape();
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @return true if query was escaped
|
||||||
|
*/
|
||||||
|
public boolean isEscaped();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* return original query string
|
* return original query string
|
||||||
* @return the query String supplied originally
|
* @return the query String supplied originally
|
||||||
|
@ -45,14 +45,14 @@ public class KeywordSearchQueryManager implements KeywordSearchQuery {
|
|||||||
|
|
||||||
COLLAPSE, DETAIL
|
COLLAPSE, DETAIL
|
||||||
};
|
};
|
||||||
//map query->boolean (true if literal, false otherwise)
|
|
||||||
private Map<String, Boolean> queries;
|
private List<Keyword> queries;
|
||||||
private Presentation presentation;
|
private Presentation presentation;
|
||||||
private List<KeywordSearchQuery> queryDelegates;
|
private List<KeywordSearchQuery> queryDelegates;
|
||||||
private QueryType queryType;
|
private QueryType queryType;
|
||||||
private static Logger logger = Logger.getLogger(KeywordSearchQueryManager.class.getName());
|
private static Logger logger = Logger.getLogger(KeywordSearchQueryManager.class.getName());
|
||||||
|
|
||||||
public KeywordSearchQueryManager(Map<String, Boolean> queries, Presentation presentation) {
|
public KeywordSearchQueryManager(List<Keyword> queries, Presentation presentation) {
|
||||||
this.queries = queries;
|
this.queries = queries;
|
||||||
this.presentation = presentation;
|
this.presentation = presentation;
|
||||||
queryType = QueryType.REGEX;
|
queryType = QueryType.REGEX;
|
||||||
@ -60,16 +60,16 @@ public class KeywordSearchQueryManager implements KeywordSearchQuery {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public KeywordSearchQueryManager(String query, QueryType qt, Presentation presentation) {
|
public KeywordSearchQueryManager(String query, QueryType qt, Presentation presentation) {
|
||||||
queries = new LinkedHashMap<String, Boolean>();
|
queries = new ArrayList<Keyword>();
|
||||||
queries.put(query, false);
|
queries.add(new Keyword(query, false));
|
||||||
this.presentation = presentation;
|
this.presentation = presentation;
|
||||||
queryType = qt;
|
queryType = qt;
|
||||||
init();
|
init();
|
||||||
}
|
}
|
||||||
|
|
||||||
public KeywordSearchQueryManager(String query, boolean isLiteral, Presentation presentation) {
|
public KeywordSearchQueryManager(String query, boolean isLiteral, Presentation presentation) {
|
||||||
queries = new LinkedHashMap<String, Boolean>();
|
queries = new ArrayList<Keyword>();
|
||||||
queries.put(query, isLiteral);
|
queries.add(new Keyword(query, isLiteral));
|
||||||
this.presentation = presentation;
|
this.presentation = presentation;
|
||||||
queryType = QueryType.REGEX;
|
queryType = QueryType.REGEX;
|
||||||
init();
|
init();
|
||||||
@ -77,22 +77,24 @@ public class KeywordSearchQueryManager implements KeywordSearchQuery {
|
|||||||
|
|
||||||
private void init() {
|
private void init() {
|
||||||
queryDelegates = new ArrayList<KeywordSearchQuery>();
|
queryDelegates = new ArrayList<KeywordSearchQuery>();
|
||||||
for (String query : queries.keySet()) {
|
for (Keyword query : queries) {
|
||||||
KeywordSearchQuery del = null;
|
KeywordSearchQuery del = null;
|
||||||
switch (queryType) {
|
switch (queryType) {
|
||||||
case WORD:
|
case WORD:
|
||||||
del = new LuceneQuery(query);
|
del = new LuceneQuery(query.getQuery());
|
||||||
break;
|
break;
|
||||||
case REGEX:
|
case REGEX:
|
||||||
del = new TermComponentQuery(query);
|
del = new TermComponentQuery(query.getQuery());
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
;
|
;
|
||||||
}
|
}
|
||||||
|
if (query.isLiteral())
|
||||||
|
del.escape();
|
||||||
queryDelegates.add(del);
|
queryDelegates.add(del);
|
||||||
|
|
||||||
}
|
}
|
||||||
escape();
|
//escape();
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -115,16 +117,17 @@ public class KeywordSearchQueryManager implements KeywordSearchQuery {
|
|||||||
}
|
}
|
||||||
|
|
||||||
Node rootNode = null;
|
Node rootNode = null;
|
||||||
|
|
||||||
if (things.size() > 0) {
|
if (things.size() > 0) {
|
||||||
Children childThingNodes =
|
Children childThingNodes =
|
||||||
Children.create(new KeywordSearchResultFactory(queries.keySet(), things, Presentation.COLLAPSE), true);
|
Children.create(new KeywordSearchResultFactory(queries, things, Presentation.COLLAPSE), true);
|
||||||
|
|
||||||
rootNode = new AbstractNode(childThingNodes);
|
rootNode = new AbstractNode(childThingNodes);
|
||||||
} else {
|
} else {
|
||||||
rootNode = Node.EMPTY;
|
rootNode = Node.EMPTY;
|
||||||
}
|
}
|
||||||
|
|
||||||
final String pathText = "Keyword query";
|
final String pathText = "Keyword search";
|
||||||
TopComponent searchResultWin = DataResultTopComponent.createInstance("Keyword search", pathText, rootNode, things.size());
|
TopComponent searchResultWin = DataResultTopComponent.createInstance("Keyword search", pathText, rootNode, things.size());
|
||||||
searchResultWin.requestActive();
|
searchResultWin.requestActive();
|
||||||
}
|
}
|
||||||
@ -132,13 +135,7 @@ public class KeywordSearchQueryManager implements KeywordSearchQuery {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void escape() {
|
public void escape() {
|
||||||
for (KeywordSearchQuery q : queryDelegates) {
|
|
||||||
boolean shouldEscape = queries.get(q.getQueryString());
|
|
||||||
if (shouldEscape) {
|
|
||||||
q.escape();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -169,6 +166,11 @@ public class KeywordSearchQueryManager implements KeywordSearchQuery {
|
|||||||
}
|
}
|
||||||
return sb.toString();
|
return sb.toString();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isEscaped() {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getQueryString() {
|
public String getQueryString() {
|
||||||
@ -186,7 +188,7 @@ public class KeywordSearchQueryManager implements KeywordSearchQuery {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* custom KeyValueThing that also stores query object to execute
|
* custom KeyValueThing that also stores query object to execute
|
||||||
*/
|
*/
|
||||||
class KeyValueThingQuery extends KeyValueThing {
|
class KeyValueThingQuery extends KeyValueThing {
|
||||||
@ -202,3 +204,47 @@ class KeyValueThingQuery extends KeyValueThing {
|
|||||||
this.query = query;
|
this.query = query;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* representation of Keyword input from user
|
||||||
|
*/
|
||||||
|
class Keyword {
|
||||||
|
|
||||||
|
private String query;
|
||||||
|
private boolean isLiteral;
|
||||||
|
|
||||||
|
Keyword(String query, boolean isLiteral) {
|
||||||
|
this.query = query;
|
||||||
|
this.isLiteral = isLiteral;
|
||||||
|
}
|
||||||
|
String getQuery() {return query;}
|
||||||
|
boolean isLiteral() {return isLiteral;}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(Object obj) {
|
||||||
|
if (obj == null) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (getClass() != obj.getClass()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
final Keyword other = (Keyword) obj;
|
||||||
|
if ((this.query == null) ? (other.query != null) : !this.query.equals(other.query)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (this.isLiteral != other.isLiteral) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int hashCode() {
|
||||||
|
int hash = 7;
|
||||||
|
hash = 17 * hash + (this.query != null ? this.query.hashCode() : 0);
|
||||||
|
hash = 17 * hash + (this.isLiteral ? 1 : 0);
|
||||||
|
return hash;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@ -34,6 +34,7 @@ import org.openide.nodes.ChildFactory;
|
|||||||
import org.openide.nodes.Children;
|
import org.openide.nodes.Children;
|
||||||
import org.openide.nodes.Node;
|
import org.openide.nodes.Node;
|
||||||
import org.openide.util.Lookup;
|
import org.openide.util.Lookup;
|
||||||
|
import org.openide.util.lookup.Lookups;
|
||||||
import org.sleuthkit.autopsy.corecomponentinterfaces.DataResultViewer;
|
import org.sleuthkit.autopsy.corecomponentinterfaces.DataResultViewer;
|
||||||
import org.sleuthkit.autopsy.corecomponents.DataResultViewerTable;
|
import org.sleuthkit.autopsy.corecomponents.DataResultViewerTable;
|
||||||
import org.sleuthkit.autopsy.datamodel.AbstractFsContentNode;
|
import org.sleuthkit.autopsy.datamodel.AbstractFsContentNode;
|
||||||
@ -57,11 +58,17 @@ public class KeywordSearchResultFactory extends ChildFactory<KeyValueThing> {
|
|||||||
//these are merged with FsContentPropertyType defined properties
|
//these are merged with FsContentPropertyType defined properties
|
||||||
public static enum CommonPropertyTypes {
|
public static enum CommonPropertyTypes {
|
||||||
|
|
||||||
QUERY {
|
KEYWORD {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return "Query";
|
return "Keyword";
|
||||||
|
}
|
||||||
|
},
|
||||||
|
REGEX {
|
||||||
|
@Override
|
||||||
|
public String toString() {
|
||||||
|
return "Regex";
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
MATCH {
|
MATCH {
|
||||||
@ -72,19 +79,19 @@ public class KeywordSearchResultFactory extends ChildFactory<KeyValueThing> {
|
|||||||
}
|
}
|
||||||
},}
|
},}
|
||||||
private Presentation presentation;
|
private Presentation presentation;
|
||||||
private Collection<String> queries;
|
private List<Keyword> queries;
|
||||||
private Collection<KeyValueThing> things;
|
private Collection<KeyValueThing> things;
|
||||||
private static final Logger logger = Logger.getLogger(KeywordSearchResultFactory.class.getName());
|
private static final Logger logger = Logger.getLogger(KeywordSearchResultFactory.class.getName());
|
||||||
|
|
||||||
KeywordSearchResultFactory(Collection<String> queries, Collection<KeyValueThing> things, Presentation presentation) {
|
KeywordSearchResultFactory(List<Keyword> queries, Collection<KeyValueThing> things, Presentation presentation) {
|
||||||
this.queries = queries;
|
this.queries = queries;
|
||||||
this.things = things;
|
this.things = things;
|
||||||
this.presentation = presentation;
|
this.presentation = presentation;
|
||||||
}
|
}
|
||||||
|
|
||||||
KeywordSearchResultFactory(String query, Collection<KeyValueThing> things, Presentation presentation) {
|
KeywordSearchResultFactory(String query, Collection<KeyValueThing> things, Presentation presentation) {
|
||||||
queries = new ArrayList<String>();
|
queries = new ArrayList<Keyword>();
|
||||||
queries.add(query);
|
queries.add(new Keyword(query, false));
|
||||||
this.presentation = presentation;
|
this.presentation = presentation;
|
||||||
this.things = things;
|
this.things = things;
|
||||||
}
|
}
|
||||||
@ -114,15 +121,21 @@ public class KeywordSearchResultFactory extends ChildFactory<KeyValueThing> {
|
|||||||
final String typeStr = type.toString();
|
final String typeStr = type.toString();
|
||||||
toSet.put(typeStr, value);
|
toSet.put(typeStr, value);
|
||||||
}
|
}
|
||||||
|
public static void setCommonProperty(Map<String, Object> toSet, CommonPropertyTypes type, Boolean value) {
|
||||||
|
final String typeStr = type.toString();
|
||||||
|
toSet.put(typeStr, value);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected boolean createKeys(List<KeyValueThing> toPopulate) {
|
protected boolean createKeys(List<KeyValueThing> toPopulate) {
|
||||||
int id = 0;
|
int id = 0;
|
||||||
if (presentation == Presentation.DETAIL) {
|
if (presentation == Presentation.DETAIL) {
|
||||||
for (String query : queries) {
|
for (Keyword keyword : queries) {
|
||||||
Map<String, Object> map = new LinkedHashMap<String, Object>();
|
Map<String, Object> map = new LinkedHashMap<String, Object>();
|
||||||
|
final String query = keyword.getQuery();
|
||||||
initCommonProperties(map);
|
initCommonProperties(map);
|
||||||
setCommonProperty(map, CommonPropertyTypes.QUERY, query);
|
setCommonProperty(map, CommonPropertyTypes.KEYWORD, query);
|
||||||
|
setCommonProperty(map, CommonPropertyTypes.REGEX, Boolean.valueOf(!keyword.isLiteral()));
|
||||||
toPopulate.add(new KeyValueThing(query, map, ++id));
|
toPopulate.add(new KeyValueThing(query, map, ++id));
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
@ -131,7 +144,9 @@ public class KeywordSearchResultFactory extends ChildFactory<KeyValueThing> {
|
|||||||
Map<String, Object> map = thing.getMap();
|
Map<String, Object> map = thing.getMap();
|
||||||
initCommonProperties(map);
|
initCommonProperties(map);
|
||||||
final String query = thing.getName();
|
final String query = thing.getName();
|
||||||
setCommonProperty(map, CommonPropertyTypes.QUERY, query);
|
setCommonProperty(map, CommonPropertyTypes.KEYWORD, query);
|
||||||
|
KeyValueThingQuery thingQuery = (KeyValueThingQuery) thing;
|
||||||
|
setCommonProperty(map, CommonPropertyTypes.REGEX, Boolean.valueOf(!thingQuery.getQuery().isEscaped()));
|
||||||
//toPopulate.add(new KeyValueThing(query, map, ++id));
|
//toPopulate.add(new KeyValueThing(query, map, ++id));
|
||||||
toPopulate.add(thing);
|
toPopulate.add(thing);
|
||||||
}
|
}
|
||||||
@ -230,7 +245,7 @@ public class KeywordSearchResultFactory extends ChildFactory<KeyValueThing> {
|
|||||||
final Content content = thingContent.getContent();
|
final Content content = thingContent.getContent();
|
||||||
final String query = thingContent.getQuery();
|
final String query = thingContent.getQuery();
|
||||||
|
|
||||||
Node kvNode = new KeyValueNode(thingContent, Children.LEAF);
|
Node kvNode = new KeyValueNode(thingContent, Children.LEAF, Lookups.singleton(content));
|
||||||
//wrap in KeywordSearchFilterNode for the markup content, might need to override FilterNode for more customization
|
//wrap in KeywordSearchFilterNode for the markup content, might need to override FilterNode for more customization
|
||||||
HighlightedMatchesSource highlights = new HighlightedMatchesSource(content, query);
|
HighlightedMatchesSource highlights = new HighlightedMatchesSource(content, query);
|
||||||
return new KeywordSearchFilterNode(highlights, kvNode, query);
|
return new KeywordSearchFilterNode(highlights, kvNode, query);
|
||||||
@ -306,7 +321,7 @@ public class KeywordSearchResultFactory extends ChildFactory<KeyValueThing> {
|
|||||||
|
|
||||||
//postprocess
|
//postprocess
|
||||||
//make sure Solr result contains a match (this gets rid of large number of false positives)
|
//make sure Solr result contains a match (this gets rid of large number of false positives)
|
||||||
boolean postprocess = true;
|
final boolean postprocess = false;
|
||||||
boolean matchFound = true;
|
boolean matchFound = true;
|
||||||
if (postprocess) {
|
if (postprocess) {
|
||||||
if (contentStr != null) {//if not null, some error getting from Solr, handle it by not filtering out
|
if (contentStr != null) {//if not null, some error getting from Solr, handle it by not filtering out
|
||||||
@ -323,7 +338,7 @@ public class KeywordSearchResultFactory extends ChildFactory<KeyValueThing> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (matchFound) {
|
if (matchFound) {
|
||||||
Node kvNode = new KeyValueNode(thingContent, Children.LEAF);
|
Node kvNode = new KeyValueNode(thingContent, Children.LEAF, Lookups.singleton(content));
|
||||||
//wrap in KeywordSearchFilterNode for the markup content
|
//wrap in KeywordSearchFilterNode for the markup content
|
||||||
HighlightedMatchesSource highlights = new HighlightedMatchesSource(content, query);
|
HighlightedMatchesSource highlights = new HighlightedMatchesSource(content, query);
|
||||||
return new KeywordSearchFilterNode(highlights, kvNode, query);
|
return new KeywordSearchFilterNode(highlights, kvNode, query);
|
||||||
|
@ -19,8 +19,7 @@
|
|||||||
package org.sleuthkit.autopsy.keywordsearch;
|
package org.sleuthkit.autopsy.keywordsearch;
|
||||||
|
|
||||||
import java.awt.event.ActionListener;
|
import java.awt.event.ActionListener;
|
||||||
import java.util.Map;
|
import java.util.List;
|
||||||
import java.util.logging.Level;
|
|
||||||
import java.util.logging.Logger;
|
import java.util.logging.Logger;
|
||||||
import org.openide.windows.TopComponent;
|
import org.openide.windows.TopComponent;
|
||||||
|
|
||||||
@ -194,7 +193,7 @@ public class KeywordSearchSimpleTopComponent extends TopComponent implements Key
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Map<String, Boolean> getQueryList() {
|
public List<Keyword> getQueryList() {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -18,11 +18,10 @@
|
|||||||
*/
|
*/
|
||||||
package org.sleuthkit.autopsy.keywordsearch;
|
package org.sleuthkit.autopsy.keywordsearch;
|
||||||
|
|
||||||
import java.awt.Component;
|
|
||||||
import java.awt.event.ActionListener;
|
import java.awt.event.ActionListener;
|
||||||
import java.beans.PropertyChangeEvent;
|
import java.beans.PropertyChangeEvent;
|
||||||
import java.beans.PropertyChangeListener;
|
import java.beans.PropertyChangeListener;
|
||||||
import java.util.Map;
|
import java.util.List;
|
||||||
import java.util.logging.Level;
|
import java.util.logging.Level;
|
||||||
import java.util.logging.Logger;
|
import java.util.logging.Logger;
|
||||||
import org.apache.solr.client.solrj.SolrServerException;
|
import org.apache.solr.client.solrj.SolrServerException;
|
||||||
@ -146,7 +145,7 @@ public final class KeywordSearchTabsTopComponent extends TopComponent implements
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Map<String, Boolean> getQueryList() {
|
public List<Keyword> getQueryList() {
|
||||||
KeywordSearchTopComponentInterface selected = (KeywordSearchTopComponentInterface) tabs.getSelectedComponent();
|
KeywordSearchTopComponentInterface selected = (KeywordSearchTopComponentInterface) tabs.getSelectedComponent();
|
||||||
if (selected == null) {
|
if (selected == null) {
|
||||||
return null;
|
return null;
|
||||||
|
@ -19,20 +19,20 @@
|
|||||||
package org.sleuthkit.autopsy.keywordsearch;
|
package org.sleuthkit.autopsy.keywordsearch;
|
||||||
|
|
||||||
import java.awt.event.ActionListener;
|
import java.awt.event.ActionListener;
|
||||||
import java.util.Map;
|
import java.util.List;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* common methods for the KeywordSearch TCs / tabs
|
* common methods for the KeywordSearch TCs / tabs
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public interface KeywordSearchTopComponentInterface {
|
interface KeywordSearchTopComponentInterface {
|
||||||
|
|
||||||
boolean isMultiwordQuery();
|
boolean isMultiwordQuery();
|
||||||
boolean isLuceneQuerySelected();
|
boolean isLuceneQuerySelected();
|
||||||
boolean isRegexQuerySelected();
|
boolean isRegexQuerySelected();
|
||||||
String getQueryText();
|
String getQueryText();
|
||||||
Map<String, Boolean> getQueryList();
|
List<Keyword> getQueryList();
|
||||||
void setFilesIndexed(int filesIndexed);
|
void setFilesIndexed(int filesIndexed);
|
||||||
void addSearchButtonListener(ActionListener l);
|
void addSearchButtonListener(ActionListener l);
|
||||||
|
|
||||||
|
@ -59,6 +59,11 @@ public class LuceneQuery implements KeywordSearchQuery {
|
|||||||
queryEscaped = KeywordSearchUtil.escapeLuceneQuery(query, true, false);
|
queryEscaped = KeywordSearchUtil.escapeLuceneQuery(query, true, false);
|
||||||
isEscaped = true;
|
isEscaped = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isEscaped() {
|
||||||
|
return isEscaped;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getEscapedQueryString() {
|
public String getEscapedQueryString() {
|
||||||
|
@ -49,7 +49,7 @@ import org.sleuthkit.autopsy.keywordsearch.KeywordSearchQueryManager.Presentatio
|
|||||||
import org.sleuthkit.datamodel.FsContent;
|
import org.sleuthkit.datamodel.FsContent;
|
||||||
|
|
||||||
public class TermComponentQuery implements KeywordSearchQuery {
|
public class TermComponentQuery implements KeywordSearchQuery {
|
||||||
|
|
||||||
private static final int TERMS_UNLIMITED = -1;
|
private static final int TERMS_UNLIMITED = -1;
|
||||||
//corresponds to field in Solr schema, analyzed with white-space tokenizer only
|
//corresponds to field in Solr schema, analyzed with white-space tokenizer only
|
||||||
private static final String TERMS_SEARCH_FIELD = "content_ws";
|
private static final String TERMS_SEARCH_FIELD = "content_ws";
|
||||||
@ -60,30 +60,26 @@ public class TermComponentQuery implements KeywordSearchQuery {
|
|||||||
private String queryEscaped;
|
private String queryEscaped;
|
||||||
private boolean isEscaped;
|
private boolean isEscaped;
|
||||||
private List<Term> terms;
|
private List<Term> terms;
|
||||||
|
|
||||||
public TermComponentQuery(String query) {
|
public TermComponentQuery(String query) {
|
||||||
this.termsQuery = query;
|
this.termsQuery = query;
|
||||||
this.queryEscaped = query;
|
this.queryEscaped = query;
|
||||||
isEscaped = false;
|
isEscaped = false;
|
||||||
terms = null;
|
terms = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void escape() {
|
public void escape() {
|
||||||
//treat as literal
|
|
||||||
//TODO for actual literal query to work in Java/Solr
|
|
||||||
//might need to either: use terms prefix (not regex) query with the literal
|
|
||||||
//or append .* to the literal regex
|
|
||||||
queryEscaped = Pattern.quote(termsQuery);
|
queryEscaped = Pattern.quote(termsQuery);
|
||||||
isEscaped = true;
|
isEscaped = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean validate() {
|
public boolean validate() {
|
||||||
if (queryEscaped.equals("")) {
|
if (queryEscaped.equals("")) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
boolean valid = true;
|
boolean valid = true;
|
||||||
try {
|
try {
|
||||||
Pattern.compile(queryEscaped);
|
Pattern.compile(queryEscaped);
|
||||||
@ -95,6 +91,11 @@ public class TermComponentQuery implements KeywordSearchQuery {
|
|||||||
return valid;
|
return valid;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isEscaped() {
|
||||||
|
return isEscaped;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* helper method to create a Solr terms component query
|
* helper method to create a Solr terms component query
|
||||||
*/
|
*/
|
||||||
@ -110,9 +111,9 @@ public class TermComponentQuery implements KeywordSearchQuery {
|
|||||||
q.setTermsRegex(queryEscaped);
|
q.setTermsRegex(queryEscaped);
|
||||||
q.addTermsField(TERMS_SEARCH_FIELD);
|
q.addTermsField(TERMS_SEARCH_FIELD);
|
||||||
q.setTimeAllowed(TERMS_TIMEOUT);
|
q.setTimeAllowed(TERMS_TIMEOUT);
|
||||||
|
|
||||||
return q;
|
return q;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -120,7 +121,7 @@ public class TermComponentQuery implements KeywordSearchQuery {
|
|||||||
*/
|
*/
|
||||||
protected List<Term> executeQuery(SolrQuery q) {
|
protected List<Term> executeQuery(SolrQuery q) {
|
||||||
Server.Core solrCore = KeywordSearch.getServer().getCore();
|
Server.Core solrCore = KeywordSearch.getServer().getCore();
|
||||||
|
|
||||||
List<Term> termsCol = null;
|
List<Term> termsCol = null;
|
||||||
try {
|
try {
|
||||||
TermsResponse tr = solrCore.queryTerms(q);
|
TermsResponse tr = solrCore.queryTerms(q);
|
||||||
@ -131,17 +132,17 @@ public class TermComponentQuery implements KeywordSearchQuery {
|
|||||||
return null; //no need to create result view, just display error dialog
|
return null; //no need to create result view, just display error dialog
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getEscapedQueryString() {
|
public String getEscapedQueryString() {
|
||||||
return this.queryEscaped;
|
return this.queryEscaped;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getQueryString() {
|
public String getQueryString() {
|
||||||
return this.termsQuery;
|
return this.termsQuery;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Collection<Term> getTerms() {
|
public Collection<Term> getTerms() {
|
||||||
return terms;
|
return terms;
|
||||||
@ -154,7 +155,7 @@ public class TermComponentQuery implements KeywordSearchQuery {
|
|||||||
@Override
|
@Override
|
||||||
public List<FsContent> performQuery() {
|
public List<FsContent> performQuery() {
|
||||||
List<FsContent> results = new ArrayList<FsContent>();
|
List<FsContent> results = new ArrayList<FsContent>();
|
||||||
|
|
||||||
final SolrQuery q = createQuery();
|
final SolrQuery q = createQuery();
|
||||||
terms = executeQuery(q);
|
terms = executeQuery(q);
|
||||||
|
|
||||||
@ -179,7 +180,7 @@ public class TermComponentQuery implements KeywordSearchQuery {
|
|||||||
++curTerm;
|
++curTerm;
|
||||||
}
|
}
|
||||||
List<FsContent> uniqueMatches = new ArrayList<FsContent>();
|
List<FsContent> uniqueMatches = new ArrayList<FsContent>();
|
||||||
|
|
||||||
if (!terms.isEmpty()) {
|
if (!terms.isEmpty()) {
|
||||||
LuceneQuery filesQuery = new LuceneQuery(filesQueryB.toString());
|
LuceneQuery filesQuery = new LuceneQuery(filesQueryB.toString());
|
||||||
//filesQuery.escape();
|
//filesQuery.escape();
|
||||||
@ -206,18 +207,18 @@ public class TermComponentQuery implements KeywordSearchQuery {
|
|||||||
} else {
|
} else {
|
||||||
results.addAll(uniqueMatches);
|
results.addAll(uniqueMatches);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
return results;
|
return results;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void execute() {
|
public void execute() {
|
||||||
SolrQuery q = createQuery();
|
SolrQuery q = createQuery();
|
||||||
|
|
||||||
logger.log(Level.INFO, "Executing TermsComponent query: " + q.toString());
|
logger.log(Level.INFO, "Executing TermsComponent query: " + q.toString());
|
||||||
|
|
||||||
final SwingWorker worker = new TermsQueryWorker(q);
|
final SwingWorker worker = new TermsQueryWorker(q);
|
||||||
worker.execute();
|
worker.execute();
|
||||||
}
|
}
|
||||||
@ -227,9 +228,9 @@ public class TermComponentQuery implements KeywordSearchQuery {
|
|||||||
* @param terms
|
* @param terms
|
||||||
*/
|
*/
|
||||||
private void publishNodes(List<Term> terms) {
|
private void publishNodes(List<Term> terms) {
|
||||||
|
|
||||||
Collection<KeyValueThing> things = new ArrayList<KeyValueThing>();
|
Collection<KeyValueThing> things = new ArrayList<KeyValueThing>();
|
||||||
|
|
||||||
Iterator<Term> it = terms.iterator();
|
Iterator<Term> it = terms.iterator();
|
||||||
int termID = 0;
|
int termID = 0;
|
||||||
//long totalMatches = 0;
|
//long totalMatches = 0;
|
||||||
@ -243,17 +244,17 @@ public class TermComponentQuery implements KeywordSearchQuery {
|
|||||||
things.add(new KeyValueThing(match, kvs, ++termID));
|
things.add(new KeyValueThing(match, kvs, ++termID));
|
||||||
//totalMatches += matches;
|
//totalMatches += matches;
|
||||||
}
|
}
|
||||||
|
|
||||||
Node rootNode = null;
|
Node rootNode = null;
|
||||||
if (things.size() > 0) {
|
if (things.size() > 0) {
|
||||||
Children childThingNodes =
|
Children childThingNodes =
|
||||||
Children.create(new KeywordSearchResultFactory(termsQuery, things, Presentation.DETAIL), true);
|
Children.create(new KeywordSearchResultFactory(termsQuery, things, Presentation.DETAIL), true);
|
||||||
|
|
||||||
rootNode = new AbstractNode(childThingNodes);
|
rootNode = new AbstractNode(childThingNodes);
|
||||||
} else {
|
} else {
|
||||||
rootNode = Node.EMPTY;
|
rootNode = Node.EMPTY;
|
||||||
}
|
}
|
||||||
|
|
||||||
final String pathText = "Term query";
|
final String pathText = "Term query";
|
||||||
// String pathText = "RegEx query: " + termsQuery
|
// String pathText = "RegEx query: " + termsQuery
|
||||||
//+ " Files with exact matches: " + Long.toString(totalMatches) + " (also listing approximate matches)";
|
//+ " Files with exact matches: " + Long.toString(totalMatches) + " (also listing approximate matches)";
|
||||||
@ -262,29 +263,29 @@ public class TermComponentQuery implements KeywordSearchQuery {
|
|||||||
searchResultWin.requestActive(); // make it the active top component
|
searchResultWin.requestActive(); // make it the active top component
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class TermsQueryWorker extends SwingWorker<List<Term>, Void> {
|
class TermsQueryWorker extends SwingWorker<List<Term>, Void> {
|
||||||
|
|
||||||
private SolrQuery q;
|
private SolrQuery q;
|
||||||
private ProgressHandle progress;
|
private ProgressHandle progress;
|
||||||
|
|
||||||
TermsQueryWorker(SolrQuery q) {
|
TermsQueryWorker(SolrQuery q) {
|
||||||
this.q = q;
|
this.q = q;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected List<Term> doInBackground() throws Exception {
|
protected List<Term> doInBackground() throws Exception {
|
||||||
progress = ProgressHandleFactory.createHandle("Terms query task");
|
progress = ProgressHandleFactory.createHandle("Terms query task");
|
||||||
progress.start();
|
progress.start();
|
||||||
progress.progress("Running Terms query.");
|
progress.progress("Running Terms query.");
|
||||||
|
|
||||||
terms = executeQuery(q);
|
terms = executeQuery(q);
|
||||||
|
|
||||||
progress.progress("Terms query completed.");
|
progress.progress("Terms query completed.");
|
||||||
|
|
||||||
return terms;
|
return terms;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void done() {
|
protected void done() {
|
||||||
if (!this.isCancelled()) {
|
if (!this.isCancelled()) {
|
||||||
@ -293,7 +294,7 @@ public class TermComponentQuery implements KeywordSearchQuery {
|
|||||||
publishNodes(terms);
|
publishNodes(terms);
|
||||||
} catch (InterruptedException e) {
|
} catch (InterruptedException e) {
|
||||||
logger.log(Level.INFO, "Exception while executing regex query,", e);
|
logger.log(Level.INFO, "Exception while executing regex query,", e);
|
||||||
|
|
||||||
} catch (ExecutionException e) {
|
} catch (ExecutionException e) {
|
||||||
logger.log(Level.INFO, "Exception while executing regex query,", e);
|
logger.log(Level.INFO, "Exception while executing regex query,", e);
|
||||||
} finally {
|
} finally {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user