mirror of
https://github.com/elisspace/autopsy.git
synced 2026-10-03 07:49:52 +00:00
Merge branch 'master' of https://github.com/sleuthkit/autopsy
This commit is contained in:
+2
-2
@@ -1,8 +1,8 @@
|
||||
Manifest-Version: 1.0
|
||||
OpenIDE-Module: org.sleuthkit.autopsy.core/5
|
||||
OpenIDE-Module: org.sleuthkit.autopsy.core/6
|
||||
OpenIDE-Module-Localizing-Bundle: org/sleuthkit/autopsy/core/Bundle.properties
|
||||
OpenIDE-Module-Layer: org/sleuthkit/autopsy/core/layer.xml
|
||||
OpenIDE-Module-Implementation-Version: 3
|
||||
OpenIDE-Module-Implementation-Version: 4
|
||||
OpenIDE-Module-Requires: org.openide.windows.WindowManager, org.netbeans.api.javahelp.Help
|
||||
AutoUpdate-Show-In-Client: true
|
||||
AutoUpdate-Essential-Module: true
|
||||
|
||||
@@ -5,5 +5,5 @@ license.file=../LICENSE-2.0.txt
|
||||
nbm.homepage=http://www.sleuthkit.org/
|
||||
nbm.module.author=Brian Carrier
|
||||
nbm.needs.restart=true
|
||||
spec.version.base=3.0
|
||||
spec.version.base=4.0
|
||||
|
||||
|
||||
@@ -80,4 +80,11 @@ public interface DataResultViewer {
|
||||
* @return True if supported, else false
|
||||
*/
|
||||
public boolean isSupported(Node selectedNode);
|
||||
|
||||
/**
|
||||
* Set a custom content viewer to respond to selection events from this result viewer.
|
||||
* If not set, the default content viewer is user
|
||||
* @param contentViewer content viewer to respond to selection events from this viewer
|
||||
*/
|
||||
public void setContentViewer(DataContent contentViewer);
|
||||
}
|
||||
|
||||
@@ -43,9 +43,19 @@ public abstract class AbstractDataResultViewer extends JPanel implements
|
||||
private static final Logger logger = Logger.getLogger(AbstractDataResultViewer.class.getName());
|
||||
protected transient ExplorerManager em = new ExplorerManager();
|
||||
private PropertyChangeListener nodeSelListener;
|
||||
|
||||
/**
|
||||
* Content viewer to respond to selection events
|
||||
* Either the main one, or custom one if set
|
||||
*/
|
||||
protected DataContent contentViewer;
|
||||
|
||||
public AbstractDataResultViewer() {
|
||||
|
||||
//DataContent is designed to return only the default viewer from lookup
|
||||
//use the default one unless set otherwise
|
||||
contentViewer = Lookup.getDefault().lookup(DataContent.class);
|
||||
|
||||
//property listener to send nodes to content viewer
|
||||
nodeSelListener = new PropertyChangeListener() {
|
||||
|
||||
@@ -70,17 +80,16 @@ public abstract class AbstractDataResultViewer extends JPanel implements
|
||||
|
||||
nodeSelected(selectedNode);
|
||||
|
||||
// DataContent is designed to return only the default viewer
|
||||
DataContent dataContent = Lookup.getDefault().lookup(DataContent.class);
|
||||
|
||||
|
||||
if (selectedNode != null) {
|
||||
// there's a new/changed node to display
|
||||
Node newSelectedNode = selectedNode; // get the selected Node on the table
|
||||
// push the node to default "DataContent"
|
||||
dataContent.setNode(newSelectedNode);
|
||||
contentViewer.setNode(newSelectedNode);
|
||||
} else {
|
||||
// clear the node viewer
|
||||
dataContent.setNode(null);
|
||||
contentViewer.setNode(null);
|
||||
}
|
||||
} finally {
|
||||
setCursor(null);
|
||||
@@ -155,4 +164,9 @@ public abstract class AbstractDataResultViewer extends JPanel implements
|
||||
logger.log(Level.WARNING, "Couldn't set selected nodes.", ex);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setContentViewer(DataContent contentViewer) {
|
||||
this.contentViewer = contentViewer;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -18,7 +18,6 @@
|
||||
*/
|
||||
package org.sleuthkit.autopsy.corecomponents;
|
||||
|
||||
import java.awt.Component;
|
||||
import java.awt.Cursor;
|
||||
import java.beans.PropertyChangeListener;
|
||||
import org.sleuthkit.autopsy.corecomponentinterfaces.DataResult;
|
||||
@@ -33,6 +32,7 @@ import org.openide.windows.TopComponent;
|
||||
import org.openide.nodes.Node;
|
||||
import org.openide.util.Lookup;
|
||||
import org.sleuthkit.autopsy.casemodule.Case;
|
||||
import org.sleuthkit.autopsy.corecomponentinterfaces.DataContent;
|
||||
import org.sleuthkit.autopsy.corecomponentinterfaces.DataResultViewer;
|
||||
|
||||
/**
|
||||
@@ -52,7 +52,15 @@ public final class DataResultTopComponent extends TopComponent implements DataRe
|
||||
public static String REMOVE_FILESEARCH = "RemoveFileSearchTopComponent";
|
||||
// Different DataResultsViewers
|
||||
private List<UpdateWrapper> viewers = new ArrayList<UpdateWrapper>();
|
||||
|
||||
//custom content viewer to send selections to, or null if the main one
|
||||
private DataContent customContentViewer;
|
||||
|
||||
/**
|
||||
* Create a new data result top component
|
||||
* @param isMain whether it is the main, application default result viewer, there can be only 1 main result viewer
|
||||
* @param title title of the data result window
|
||||
*/
|
||||
public DataResultTopComponent(boolean isMain, String title) {
|
||||
initComponents();
|
||||
setToolTipText(NbBundle.getMessage(DataResultTopComponent.class, "HINT_NodeTableTopComponent"));
|
||||
@@ -65,6 +73,19 @@ public final class DataResultTopComponent extends TopComponent implements DataRe
|
||||
|
||||
this.dataResultTabbedPanel.addChangeListener(this);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new, custom data result top component, in addition to the application main one
|
||||
* @param title title of the data result window
|
||||
* @param customContentViewer custom content viewer to send selection events to
|
||||
*/
|
||||
public DataResultTopComponent(String title, DataContentTopComponent customContentViewer) {
|
||||
this(false, title);
|
||||
|
||||
//custom content viewer tc to setup for every result viewer
|
||||
this.customContentViewer = customContentViewer;
|
||||
}
|
||||
|
||||
|
||||
private static class UpdateWrapper {
|
||||
|
||||
@@ -102,8 +123,23 @@ public final class DataResultTopComponent extends TopComponent implements DataRe
|
||||
boolean isSupported(Node selectedNode) {
|
||||
return this.wrapped.isSupported(selectedNode);
|
||||
}
|
||||
|
||||
void setContentViewer(DataContent contentViewer) {
|
||||
this.wrapped.setContentViewer(contentViewer);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private static void createInstanceCommon(String pathText, Node givenNode, int totalMatches, DataResultTopComponent newDataResult) {
|
||||
newDataResult.numberMatchLabel.setText(Integer.toString(totalMatches));
|
||||
|
||||
newDataResult.open(); // open it first so the component can be initialized
|
||||
|
||||
// set the tree table view
|
||||
newDataResult.setNode(givenNode);
|
||||
newDataResult.setPath(pathText);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a new non-default DataResult component
|
||||
*
|
||||
@@ -116,13 +152,25 @@ public final class DataResultTopComponent extends TopComponent implements DataRe
|
||||
public static DataResultTopComponent createInstance(String title, String pathText, Node givenNode, int totalMatches) {
|
||||
DataResultTopComponent newDataResult = new DataResultTopComponent(false, title);
|
||||
|
||||
newDataResult.numberMatchLabel.setText(Integer.toString(totalMatches));
|
||||
createInstanceCommon(pathText, givenNode, totalMatches, newDataResult);
|
||||
|
||||
newDataResult.open(); // open it first so the component can be initialized
|
||||
return newDataResult;
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a new non-default DataResult component
|
||||
*
|
||||
* @param title Title of the component window
|
||||
* @param pathText Descriptive text about the source of the nodes displayed
|
||||
* @param givenNode The new root node
|
||||
* @param totalMatches Cardinality of root node's children
|
||||
* @param dataContentWindow a handle to data content top component window to send events to from the new result viewer
|
||||
* @return
|
||||
*/
|
||||
public static DataResultTopComponent createInstance(String title, String pathText, Node givenNode, int totalMatches, DataContentTopComponent dataContentWindow) {
|
||||
DataResultTopComponent newDataResult = new DataResultTopComponent(title, dataContentWindow);
|
||||
|
||||
// set the tree table view
|
||||
newDataResult.setNode(givenNode);
|
||||
newDataResult.setPath(pathText);
|
||||
createInstanceCommon(pathText, givenNode, totalMatches, newDataResult);
|
||||
|
||||
return newDataResult;
|
||||
}
|
||||
@@ -191,8 +239,14 @@ public final class DataResultTopComponent extends TopComponent implements DataRe
|
||||
// find all dataContentViewer and add them to the tabbed pane
|
||||
for (DataResultViewer factory : Lookup.getDefault().lookupAll(DataResultViewer.class)) {
|
||||
DataResultViewer drv = factory.getInstance();
|
||||
this.viewers.add(new UpdateWrapper(drv));
|
||||
UpdateWrapper resultViewer = new UpdateWrapper(drv);
|
||||
if (customContentViewer != null) {
|
||||
//set custom content viewer to respond to events from this result viewer
|
||||
resultViewer.setContentViewer(customContentViewer);
|
||||
}
|
||||
this.viewers.add(resultViewer);
|
||||
this.dataResultTabbedPanel.addTab(drv.getTitle(), drv.getComponent());
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -21,6 +21,7 @@ package org.sleuthkit.autopsy.coreutils;
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.util.logging.Level;
|
||||
import java.util.regex.Matcher;
|
||||
import org.openide.filesystems.FileObject;
|
||||
|
||||
/**
|
||||
@@ -149,4 +150,15 @@ public class FileUtil {
|
||||
|
||||
return created.getPath();
|
||||
}
|
||||
|
||||
/**
|
||||
* Escape special characters in a file name or a file name component
|
||||
* @param fileName to escape
|
||||
* @return escaped string
|
||||
*/
|
||||
public static String escapeFileName(String fileName) {
|
||||
//for now escaping / (not valid in file name, at least on Windows)
|
||||
//with underscores. Windows/Java seem to ignore \\/ and \\\\/ escapings
|
||||
return fileName.replaceAll("/", "_");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,203 @@
|
||||
/*
|
||||
* Autopsy Forensic Browser
|
||||
*
|
||||
* Copyright 2013 Basis Technology Corp.
|
||||
* Contact: carrier <at> sleuthkit <dot> org
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.sleuthkit.autopsy.coreutils;
|
||||
|
||||
import java.awt.event.ActionEvent;
|
||||
import java.awt.event.ActionListener;
|
||||
import java.net.URL;
|
||||
import java.util.logging.Level;
|
||||
import javax.swing.Icon;
|
||||
import javax.swing.ImageIcon;
|
||||
import org.openide.DialogDisplayer;
|
||||
import org.openide.NotifyDescriptor;
|
||||
import org.openide.awt.NotificationDisplayer;
|
||||
import org.openide.util.ImageUtilities;
|
||||
|
||||
/**
|
||||
* Utility for displaying messages and notifications in status area. Wraps
|
||||
* around NB RCP NotificationDisplayer.
|
||||
*
|
||||
* Messages can optionally contain click-able Actions.
|
||||
*
|
||||
* Based on:
|
||||
* http://qbeukes.blogspot.com/2009/11/netbeans-platform-notifications.html
|
||||
*
|
||||
* @license Apache License 2.0
|
||||
*/
|
||||
public class MessageNotifyUtil {
|
||||
|
||||
private MessageNotifyUtil() {
|
||||
}
|
||||
|
||||
public enum MessageType {
|
||||
|
||||
INFO(NotifyDescriptor.INFORMATION_MESSAGE, "info-icon-16.png"),
|
||||
ERROR(NotifyDescriptor.ERROR_MESSAGE, "error-icon-16.png"),
|
||||
WARNING(NotifyDescriptor.WARNING_MESSAGE, "warning-icon-16.png");
|
||||
private int notifyDescriptorType;
|
||||
private Icon icon;
|
||||
|
||||
private MessageType(int notifyDescriptorType, String resourceName) {
|
||||
this.notifyDescriptorType = notifyDescriptorType;
|
||||
if (resourceName == null) {
|
||||
icon = new ImageIcon();
|
||||
} else {
|
||||
icon = loadIcon(resourceName);
|
||||
}
|
||||
}
|
||||
|
||||
private static Icon loadIcon(String resourceName) {
|
||||
Icon icon = ImageUtilities.loadImageIcon("org/sleuthkit/autopsy/images/" + resourceName, false);
|
||||
if (icon == null) {
|
||||
Logger logger = Logger.getLogger(org.sleuthkit.autopsy.coreutils.MessageNotifyUtil.MessageType.class.getName());
|
||||
logger.log(Level.SEVERE, "Failed to load icon resource: " + resourceName + ". Using blank image.");
|
||||
icon = new ImageIcon();
|
||||
}
|
||||
return icon;
|
||||
}
|
||||
|
||||
int getNotifyDescriptorType() {
|
||||
return notifyDescriptorType;
|
||||
}
|
||||
|
||||
Icon getIcon() {
|
||||
return icon;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Utility to display messages
|
||||
*/
|
||||
public static class Message {
|
||||
|
||||
private Message() {
|
||||
}
|
||||
|
||||
/**
|
||||
* @return The dialog displayer used to show message boxes
|
||||
*/
|
||||
public static DialogDisplayer getDialogDisplayer() {
|
||||
return DialogDisplayer.getDefault();
|
||||
}
|
||||
|
||||
/**
|
||||
* Show a message of the specified type
|
||||
*
|
||||
* @param message message to show
|
||||
* @param messageType message type to show
|
||||
*/
|
||||
public static void show(String message, MessageType messageType) {
|
||||
getDialogDisplayer().notify(new NotifyDescriptor.Message(message,
|
||||
messageType.getNotifyDescriptorType()));
|
||||
}
|
||||
|
||||
/**
|
||||
* Show an information dialog
|
||||
*
|
||||
* @param message message to show
|
||||
*/
|
||||
public static void info(String message) {
|
||||
show(message, MessageType.INFO);
|
||||
}
|
||||
|
||||
/**
|
||||
* Show an error dialog
|
||||
*
|
||||
* @param message message to shpw
|
||||
*/
|
||||
public static void error(String message) {
|
||||
show(message, MessageType.ERROR);
|
||||
}
|
||||
|
||||
/**
|
||||
* Show an warning dialog
|
||||
*
|
||||
* @param message message to show
|
||||
*/
|
||||
public static void warn(String message) {
|
||||
show(message, MessageType.WARNING);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Utility to display notifications with baloons
|
||||
*/
|
||||
public static class Notify {
|
||||
|
||||
private Notify() {
|
||||
}
|
||||
|
||||
/**
|
||||
* Show message with the specified type and action listener
|
||||
*/
|
||||
public static void show(String title, String message, MessageType type, ActionListener actionListener) {
|
||||
NotificationDisplayer.getDefault().notify(title, type.getIcon(), message, actionListener);
|
||||
}
|
||||
|
||||
/**
|
||||
* Show message with the specified type and a default action which
|
||||
* displays the message using MessageNotifyUtil.Message with the same
|
||||
* message type
|
||||
*
|
||||
* @param title message title
|
||||
* @param message message text
|
||||
* @param type type of the message
|
||||
*/
|
||||
public static void show(String title, final String message, final MessageType type) {
|
||||
ActionListener actionListener = new ActionListener() {
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
MessageNotifyUtil.Message.show(message, type);
|
||||
}
|
||||
};
|
||||
|
||||
show(title, message, type, actionListener);
|
||||
}
|
||||
|
||||
/**
|
||||
* Show an information notification
|
||||
*
|
||||
* @param title message title
|
||||
* @param message message text
|
||||
*/
|
||||
public static void info(String title, String message) {
|
||||
show(title, message, MessageType.INFO);
|
||||
}
|
||||
|
||||
/**
|
||||
* Show an error notification
|
||||
*
|
||||
* @param title message title
|
||||
* @param message message text
|
||||
*/
|
||||
public static void error(String title, String message) {
|
||||
show(title, message, MessageType.ERROR);
|
||||
}
|
||||
|
||||
/**
|
||||
* Show an warning notification
|
||||
*
|
||||
* @param title message title
|
||||
* @param message message text
|
||||
*/
|
||||
public static void warn(String title, String message) {
|
||||
show(title, message, MessageType.WARNING);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -26,12 +26,12 @@ import org.sleuthkit.autopsy.datamodel.KeywordHits.KeywordHitsRootNode;
|
||||
import org.sleuthkit.datamodel.Directory;
|
||||
import org.sleuthkit.datamodel.File;
|
||||
import org.sleuthkit.datamodel.Image;
|
||||
import org.sleuthkit.datamodel.VirtualDirectory;
|
||||
import org.sleuthkit.datamodel.SleuthkitVisitableItem;
|
||||
import org.sleuthkit.datamodel.SleuthkitItemVisitor;
|
||||
import org.sleuthkit.datamodel.TskException;
|
||||
import org.sleuthkit.datamodel.Volume;
|
||||
import org.sleuthkit.datamodel.LayoutFile;
|
||||
import org.sleuthkit.datamodel.SleuthkitItemVisitor;
|
||||
import org.sleuthkit.datamodel.SleuthkitVisitableItem;
|
||||
import org.sleuthkit.datamodel.TskException;
|
||||
import org.sleuthkit.datamodel.VirtualDirectory;
|
||||
import org.sleuthkit.datamodel.Volume;
|
||||
|
||||
/**
|
||||
* Abstract subclass for ContentChildren and RootContentChildren implementations
|
||||
@@ -137,11 +137,16 @@ abstract class AbstractContentChildren<T> extends Keys<T> {
|
||||
return ee.new EmailExtractedRootNode();
|
||||
}
|
||||
|
||||
@Override
|
||||
@Override
|
||||
public AbstractNode visit(Bookmarks bks) {
|
||||
return bks.new BookmarksRootNode();
|
||||
}
|
||||
|
||||
@Override
|
||||
public AbstractNode visit(Tags t) {
|
||||
return t.new TagsRootNode();
|
||||
}
|
||||
|
||||
@Override
|
||||
public AbstractNode visit(Images i) {
|
||||
try {
|
||||
|
||||
@@ -104,6 +104,22 @@ public class ArtifactStringContent implements StringContent {
|
||||
buffer.append("</td>");
|
||||
buffer.append("</tr>");
|
||||
}
|
||||
|
||||
//add file path
|
||||
buffer.append("<tr>");
|
||||
buffer.append("<td>Source File</td>");
|
||||
buffer.append("<td>");
|
||||
final Content content = getAssociatedContent(wrapped);
|
||||
buffer.append(content.getName());
|
||||
buffer.append("</td>");
|
||||
buffer.append("</tr>");
|
||||
buffer.append("<tr>");
|
||||
buffer.append("<td>Source File Path</td>");
|
||||
buffer.append("<td>");
|
||||
buffer.append(DataConversion.getformattedPath(ContentUtils.getDisplayPath(content), 0, 1));
|
||||
buffer.append("</td>");
|
||||
buffer.append("</tr>");
|
||||
|
||||
buffer.append("</table>");
|
||||
buffer.append("</html>");
|
||||
return buffer.toString();
|
||||
|
||||
@@ -34,6 +34,7 @@ public interface AutopsyItemVisitor<T> {
|
||||
T visit(HashsetHits hh);
|
||||
T visit(EmailExtracted ee);
|
||||
T visit(Bookmarks bks);
|
||||
T visit(Tags t);
|
||||
T visit(Images i);
|
||||
T visit(Views v);
|
||||
T visit(Results r);
|
||||
@@ -92,6 +93,11 @@ public interface AutopsyItemVisitor<T> {
|
||||
return defaultVisit(bks);
|
||||
}
|
||||
|
||||
@Override
|
||||
public T visit(Tags t) {
|
||||
return defaultVisit(t);
|
||||
}
|
||||
|
||||
@Override
|
||||
public T visit(Images i) {
|
||||
return defaultVisit(i);
|
||||
|
||||
@@ -28,7 +28,7 @@ import org.sleuthkit.datamodel.Content;
|
||||
* Class for Children of all ContentNodes. Handles creating child ContentNodes.
|
||||
* TODO consider a ContentChildren child factory
|
||||
*/
|
||||
class ContentChildren extends AbstractContentChildren {
|
||||
class ContentChildren extends AbstractContentChildren<Content> {
|
||||
|
||||
private static final Logger logger = Logger.getLogger(ContentChildren.class.getName());
|
||||
//private static final int MAX_CHILD_COUNT = 1000000;
|
||||
@@ -72,7 +72,7 @@ class ContentChildren extends AbstractContentChildren {
|
||||
@Override
|
||||
protected void removeNotify() {
|
||||
super.removeNotify();
|
||||
setKeys(Collections.EMPTY_SET);
|
||||
setKeys(new ArrayList<Content>());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -28,6 +28,8 @@ import org.sleuthkit.autopsy.datamodel.HashsetHits.HashsetHitsSetNode;
|
||||
import org.sleuthkit.autopsy.datamodel.KeywordHits.KeywordHitsKeywordNode;
|
||||
import org.sleuthkit.autopsy.datamodel.KeywordHits.KeywordHitsListNode;
|
||||
import org.sleuthkit.autopsy.datamodel.KeywordHits.KeywordHitsRootNode;
|
||||
import org.sleuthkit.autopsy.datamodel.Tags.TagsNodeRoot;
|
||||
import org.sleuthkit.autopsy.datamodel.Tags.TagsRootNode;
|
||||
|
||||
/**
|
||||
* Visitor pattern for DisplayableItemNodes
|
||||
@@ -55,6 +57,8 @@ public interface DisplayableItemNodeVisitor<T> {
|
||||
T visit(EmailExtractedFolderNode eefn);
|
||||
T visit(BookmarksRootNode bksrn);
|
||||
T visit(BookmarksNodeRoot bksrn);
|
||||
T visit(TagsRootNode bksrn);
|
||||
T visit(TagsNodeRoot bksrn);
|
||||
T visit(ViewsNode vn);
|
||||
T visit(ResultsNode rn);
|
||||
T visit(ImagesNode in);
|
||||
@@ -204,5 +208,15 @@ public interface DisplayableItemNodeVisitor<T> {
|
||||
public T visit(BookmarksNodeRoot bksnr) {
|
||||
return defaultVisit(bksnr);
|
||||
}
|
||||
|
||||
@Override
|
||||
public T visit(TagsRootNode bksrn) {
|
||||
return defaultVisit(bksrn);
|
||||
}
|
||||
|
||||
@Override
|
||||
public T visit(TagsNodeRoot bksnr) {
|
||||
return defaultVisit(bksnr);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -60,6 +60,7 @@ public class EmailExtracted implements AutopsyVisitableItem {
|
||||
accounts = new LinkedHashMap<String, Map<String, List<Long>>>();
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
private void initArtifacts() {
|
||||
accounts.clear();
|
||||
try {
|
||||
|
||||
@@ -28,6 +28,7 @@ import org.sleuthkit.autopsy.coreutils.Logger;
|
||||
import org.openide.nodes.AbstractNode;
|
||||
import org.openide.nodes.ChildFactory;
|
||||
import org.openide.nodes.Node;
|
||||
import org.openide.util.Exceptions;
|
||||
import org.openide.util.lookup.Lookups;
|
||||
import org.sleuthkit.autopsy.datamodel.SearchFilters.FileSearchFilter;
|
||||
import org.sleuthkit.datamodel.Content;
|
||||
@@ -69,22 +70,29 @@ class FileSearchFilterChildren extends ChildFactory<Content> {
|
||||
return query;
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
private List<FsContent> runQuery(){
|
||||
ResultSet rs = null;
|
||||
List<FsContent> list = new ArrayList<FsContent>();
|
||||
try {
|
||||
ResultSet rs = skCase.runQuery(createQuery());
|
||||
rs = skCase.runQuery(createQuery());
|
||||
for(FsContent c : skCase.resultSetToFsContents(rs)){
|
||||
if(c.isFile()){
|
||||
list.add(c);
|
||||
}
|
||||
}
|
||||
Statement s = rs.getStatement();
|
||||
rs.close();
|
||||
if (s != null)
|
||||
s.close();
|
||||
} catch (SQLException ex) {
|
||||
logger.log(Level.WARNING, "Couldn't get search results", ex);
|
||||
}
|
||||
finally {
|
||||
if (rs != null) {
|
||||
try {
|
||||
skCase.closeRunQuery(rs);
|
||||
} catch (SQLException ex) {
|
||||
logger.log(Level.SEVERE, "Error closing result set after executing fscontents query for file search results", ex);
|
||||
}
|
||||
}
|
||||
}
|
||||
return list;
|
||||
|
||||
}
|
||||
|
||||
@@ -34,6 +34,7 @@ import org.openide.nodes.ChildFactory;
|
||||
import org.openide.nodes.Children;
|
||||
import org.openide.nodes.Node;
|
||||
import org.openide.nodes.Sheet;
|
||||
import org.openide.util.Exceptions;
|
||||
import org.openide.util.lookup.Lookups;
|
||||
import org.sleuthkit.datamodel.BlackboardArtifact;
|
||||
import org.sleuthkit.datamodel.BlackboardAttribute;
|
||||
@@ -56,8 +57,10 @@ public class HashsetHits implements AutopsyVisitableItem {
|
||||
hashSetHitsMap = new LinkedHashMap<String, Set<Long>>();
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
private void initArtifacts() {
|
||||
hashSetHitsMap.clear();
|
||||
ResultSet rs = null;
|
||||
try {
|
||||
int setNameId = BlackboardAttribute.ATTRIBUTE_TYPE.TSK_SET_NAME.getTypeID();
|
||||
int artId = BlackboardArtifact.ARTIFACT_TYPE.TSK_HASHSET_HIT.getTypeID();
|
||||
@@ -66,7 +69,7 @@ public class HashsetHits implements AutopsyVisitableItem {
|
||||
+ "attribute_type_id=" + setNameId
|
||||
+ " AND blackboard_attributes.artifact_id=blackboard_artifacts.artifact_id"
|
||||
+ " AND blackboard_artifacts.artifact_type_id=" + artId;
|
||||
ResultSet rs = skCase.runQuery(query);
|
||||
rs = skCase.runQuery(query);
|
||||
while (rs.next()) {
|
||||
String value = rs.getString("value_text");
|
||||
long artifactId = rs.getLong("artifact_id");
|
||||
@@ -76,14 +79,19 @@ public class HashsetHits implements AutopsyVisitableItem {
|
||||
hashSetHitsMap.get(value).add(artifactId);
|
||||
|
||||
}
|
||||
Statement s = rs.getStatement();
|
||||
rs.close();
|
||||
if (s != null) {
|
||||
s.close();
|
||||
}
|
||||
|
||||
} catch (SQLException ex) {
|
||||
logger.log(Level.WARNING, "SQL Exception occurred: ", ex);
|
||||
}
|
||||
finally {
|
||||
if (rs != null) {
|
||||
try {
|
||||
skCase.closeRunQuery(rs);
|
||||
} catch (SQLException ex) {
|
||||
logger.log(Level.WARNING, "Error closing result set after getting hashset hits", ex);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -106,8 +106,10 @@ public class KeywordHits implements AutopsyVisitableItem {
|
||||
}
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
private void initArtifacts() {
|
||||
artifacts.clear();
|
||||
ResultSet rs = null;
|
||||
try {
|
||||
int setId = BlackboardAttribute.ATTRIBUTE_TYPE.TSK_SET_NAME.getTypeID();
|
||||
int wordId = BlackboardAttribute.ATTRIBUTE_TYPE.TSK_KEYWORD.getTypeID();
|
||||
@@ -120,7 +122,7 @@ public class KeywordHits implements AutopsyVisitableItem {
|
||||
+ ") AND (attribute_type_id=" + setId + " OR "
|
||||
+ "attribute_type_id=" + wordId + " OR "
|
||||
+ "attribute_type_id=" + regexId + ")";
|
||||
ResultSet rs = skCase.runQuery(query);
|
||||
rs = skCase.runQuery(query);
|
||||
while (rs.next()) {
|
||||
String value = rs.getString("value_text");
|
||||
long artifactId = rs.getLong("artifact_id");
|
||||
@@ -133,14 +135,19 @@ public class KeywordHits implements AutopsyVisitableItem {
|
||||
}
|
||||
|
||||
}
|
||||
Statement s = rs.getStatement();
|
||||
rs.close();
|
||||
if (s != null) {
|
||||
s.close();
|
||||
}
|
||||
|
||||
} catch (SQLException ex) {
|
||||
logger.log(Level.WARNING, "SQL Exception occurred: ", ex);
|
||||
}
|
||||
finally {
|
||||
if (rs != null) {
|
||||
try {
|
||||
skCase.closeRunQuery(rs);
|
||||
} catch (SQLException ex) {
|
||||
logger.log(Level.WARNING, "Error closing result set after getting keyword hits", ex);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -34,12 +34,12 @@ import org.sleuthkit.datamodel.SleuthkitCase;
|
||||
*
|
||||
* @author dfickling
|
||||
*/
|
||||
public class RecentFilesChildren extends ChildFactory<RecentFiles.RecentFilesFilter>{
|
||||
|
||||
public class RecentFilesChildren extends ChildFactory<RecentFiles.RecentFilesFilter> {
|
||||
|
||||
SleuthkitCase skCase;
|
||||
Calendar lastDay;
|
||||
private final static Logger logger = Logger.getLogger(RecentFilesChildren.class.getName());
|
||||
|
||||
|
||||
public RecentFilesChildren(SleuthkitCase skCase) {
|
||||
this.skCase = skCase;
|
||||
}
|
||||
@@ -48,7 +48,7 @@ public class RecentFilesChildren extends ChildFactory<RecentFiles.RecentFilesFil
|
||||
protected boolean createKeys(List<RecentFiles.RecentFilesFilter> list) {
|
||||
list.addAll(Arrays.asList(RecentFiles.RecentFilesFilter.values()));
|
||||
lastDay = Calendar.getInstance();
|
||||
lastDay.setTimeInMillis(getLastTime()*1000);
|
||||
lastDay.setTimeInMillis(getLastTime() * 1000);
|
||||
lastDay.set(Calendar.HOUR_OF_DAY, 0);
|
||||
lastDay.set(Calendar.MINUTE, 0);
|
||||
lastDay.set(Calendar.SECOND, 0);
|
||||
@@ -57,10 +57,10 @@ public class RecentFilesChildren extends ChildFactory<RecentFiles.RecentFilesFil
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Node createNodeForKey(RecentFiles.RecentFilesFilter key){
|
||||
protected Node createNodeForKey(RecentFiles.RecentFilesFilter key) {
|
||||
return new RecentFilesFilterNode(skCase, key, lastDay);
|
||||
}
|
||||
|
||||
|
||||
private long getLastTime() {
|
||||
String query = createMaxQuery("crtime");
|
||||
long maxcr = runTimeQuery(query);
|
||||
@@ -73,25 +73,29 @@ public class RecentFilesChildren extends ChildFactory<RecentFiles.RecentFilesFil
|
||||
//return Math.max(maxcr, Math.max(maxc, Math.max(maxm, maxa)));
|
||||
return Math.max(maxcr, Math.max(maxc, maxm));
|
||||
}
|
||||
|
||||
private String createMaxQuery(String attr){
|
||||
return "select max(" + attr + ") from tsk_files where " + attr + " < " + System.currentTimeMillis()/1000;
|
||||
|
||||
private String createMaxQuery(String attr) {
|
||||
return "select max(" + attr + ") from tsk_files where " + attr + " < " + System.currentTimeMillis() / 1000;
|
||||
}
|
||||
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
private long runTimeQuery(String query) {
|
||||
long result = 0;
|
||||
ResultSet rs = null;
|
||||
try {
|
||||
ResultSet rs = skCase.runQuery(query);
|
||||
rs = skCase.runQuery(query);
|
||||
result = rs.getLong(1);
|
||||
Statement s = rs.getStatement();
|
||||
rs.close();
|
||||
if (s != null)
|
||||
s.close();
|
||||
} catch (SQLException ex) {
|
||||
Logger.getLogger(RecentFilesFilterChildren.class.getName())
|
||||
.log(Level.WARNING, "Couldn't get search results", ex);
|
||||
logger.log(Level.WARNING, "Couldn't get recent files results", ex);
|
||||
} finally {
|
||||
if (rs != null) {
|
||||
try {
|
||||
skCase.closeRunQuery(rs);
|
||||
} catch (SQLException ex) {
|
||||
logger.log(Level.WARNING, "Error closing result set after getting recent files results", ex);
|
||||
}
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -41,8 +41,8 @@ import org.sleuthkit.datamodel.SleuthkitCase;
|
||||
*
|
||||
* @author dfickling
|
||||
*/
|
||||
public class RecentFilesFilterChildren extends ChildFactory<Content>{
|
||||
|
||||
public class RecentFilesFilterChildren extends ChildFactory<Content> {
|
||||
|
||||
SleuthkitCase skCase;
|
||||
RecentFilesFilter filter;
|
||||
Calendar prevDay;
|
||||
@@ -61,13 +61,13 @@ public class RecentFilesFilterChildren extends ChildFactory<Content>{
|
||||
list.addAll(runFsQuery());
|
||||
return true;
|
||||
}
|
||||
|
||||
private String createQuery(){
|
||||
|
||||
private String createQuery() {
|
||||
String query = "select * from tsk_files where known <> 1 and (";
|
||||
long lowerLimit = prevDay.getTimeInMillis()/1000;
|
||||
long lowerLimit = prevDay.getTimeInMillis() / 1000;
|
||||
prevDay.add(Calendar.DATE, 1);
|
||||
prevDay.add(Calendar.MILLISECOND, -1);
|
||||
long upperLimit = prevDay.getTimeInMillis()/1000;
|
||||
long upperLimit = prevDay.getTimeInMillis() / 1000;
|
||||
query += "(crtime between " + lowerLimit + " and " + upperLimit + ") or ";
|
||||
query += "(ctime between " + lowerLimit + " and " + upperLimit + ") or ";
|
||||
//query += "(atime between " + lowerLimit + " and " + upperLimit + ") or ";
|
||||
@@ -75,33 +75,39 @@ public class RecentFilesFilterChildren extends ChildFactory<Content>{
|
||||
//query += " limit " + MAX_OBJECTS;
|
||||
return query;
|
||||
}
|
||||
|
||||
private List<FsContent> runFsQuery(){
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
private List<FsContent> runFsQuery() {
|
||||
List<FsContent> list = new ArrayList<FsContent>();
|
||||
ResultSet rs = null;
|
||||
try {
|
||||
ResultSet rs = skCase.runQuery(createQuery());
|
||||
for(FsContent c : skCase.resultSetToFsContents(rs)){
|
||||
if(c.isFile()){
|
||||
rs = skCase.runQuery(createQuery());
|
||||
for (FsContent c : skCase.resultSetToFsContents(rs)) {
|
||||
if (c.isFile()) {
|
||||
list.add(c);
|
||||
}
|
||||
}
|
||||
Statement s = rs.getStatement();
|
||||
rs.close();
|
||||
if (s != null)
|
||||
s.close();
|
||||
|
||||
} catch (SQLException ex) {
|
||||
logger.log(Level.WARNING, "Couldn't get search results", ex);
|
||||
} finally {
|
||||
if (rs != null) {
|
||||
try {
|
||||
skCase.closeRunQuery(rs);
|
||||
} catch (SQLException ex) {
|
||||
logger.log(Level.WARNING, "Error closing result set after getting recent files results", ex);
|
||||
}
|
||||
}
|
||||
}
|
||||
return list;
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
protected Node createNodeForKey(Content key){
|
||||
return key.accept(new ContentVisitor.Default<AbstractNode>(){
|
||||
|
||||
protected Node createNodeForKey(Content key) {
|
||||
return key.accept(new ContentVisitor.Default<AbstractNode>() {
|
||||
@Override
|
||||
public FileNode visit(File f){
|
||||
public FileNode visit(File f) {
|
||||
return new FileNode(f, false);
|
||||
}
|
||||
|
||||
@@ -109,7 +115,6 @@ public class RecentFilesFilterChildren extends ChildFactory<Content>{
|
||||
protected AbstractNode defaultVisit(Content di) {
|
||||
throw new UnsupportedOperationException("Not supported for this type of Displayable Item: " + di.toString());
|
||||
}
|
||||
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -36,7 +36,8 @@ public class ResultsNode extends DisplayableItemNode {
|
||||
new KeywordHits(sleuthkitCase),
|
||||
new HashsetHits(sleuthkitCase),
|
||||
new EmailExtracted(sleuthkitCase),
|
||||
new Bookmarks(sleuthkitCase) //TODO move to the top of the tree
|
||||
new Bookmarks(sleuthkitCase), //TODO move to the top of the tree
|
||||
new Tags(sleuthkitCase) //TODO move to the top of the tree
|
||||
)), Lookups.singleton(NAME));
|
||||
setName(NAME);
|
||||
setDisplayName(NAME);
|
||||
|
||||
@@ -21,7 +21,6 @@ package org.sleuthkit.autopsy.datamodel;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||
import org.sleuthkit.datamodel.BlackboardArtifact;
|
||||
|
||||
/**
|
||||
@@ -73,12 +72,16 @@ public class RootContentChildren extends AbstractContentChildren<Object> {
|
||||
case TSK_TAG_FILE:
|
||||
if (o instanceof Bookmarks)
|
||||
this.refreshKey(o);
|
||||
if (o instanceof Tags)
|
||||
this.refreshKey(o);
|
||||
break;
|
||||
|
||||
//TODO check
|
||||
case TSK_TAG_ARTIFACT:
|
||||
if (o instanceof Bookmarks)
|
||||
this.refreshKey(o);
|
||||
if (o instanceof Tags)
|
||||
this.refreshKey(o);
|
||||
break;
|
||||
default:
|
||||
if (o instanceof ExtractedContent)
|
||||
@@ -95,6 +98,8 @@ public class RootContentChildren extends AbstractContentChildren<Object> {
|
||||
this.refreshKey(o);
|
||||
else if (o instanceof Bookmarks)
|
||||
this.refreshKey(o);
|
||||
else if (o instanceof Tags)
|
||||
this.refreshKey(o);
|
||||
else if (o instanceof ExtractedContent)
|
||||
this.refreshKey(o);
|
||||
}
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/*
|
||||
* Autopsy Forensic Browser
|
||||
*
|
||||
* Copyright 2012 Basis Technology Corp.
|
||||
* Copyright 2013 Basis Technology Corp.
|
||||
* Contact: carrier <at> sleuthkit <dot> org
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
@@ -21,8 +21,17 @@ package org.sleuthkit.autopsy.datamodel;
|
||||
import java.sql.ResultSet;
|
||||
import java.sql.SQLException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Random;
|
||||
import java.util.logging.Level;
|
||||
import org.openide.nodes.ChildFactory;
|
||||
import org.openide.nodes.Children;
|
||||
import org.openide.nodes.Node;
|
||||
import org.openide.nodes.Sheet;
|
||||
import org.openide.util.lookup.Lookups;
|
||||
import org.sleuthkit.autopsy.casemodule.Case;
|
||||
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||
import org.sleuthkit.datamodel.AbstractFile;
|
||||
@@ -32,15 +41,195 @@ import org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE;
|
||||
import org.sleuthkit.datamodel.SleuthkitCase;
|
||||
import org.sleuthkit.datamodel.TskCoreException;
|
||||
|
||||
public class Tags {
|
||||
public class Tags implements AutopsyVisitableItem {
|
||||
private static final Logger logger = Logger.getLogger(Tags.class.getName());
|
||||
private SleuthkitCase skCase;
|
||||
|
||||
public static final String NAME = "Tags";
|
||||
private static final String TAG_ICON_PATH = "org/sleuthkit/autopsy/images/tag-folder-blue-icon-16.png";
|
||||
private Map<String, List<BlackboardArtifact>> tags = new HashMap<String, List<BlackboardArtifact>>();
|
||||
|
||||
Tags(SleuthkitCase skCase) {
|
||||
this.skCase = skCase;
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> T accept(AutopsyItemVisitor<T> v) {
|
||||
return v.visit(this);
|
||||
}
|
||||
|
||||
/**
|
||||
* Root of all Tag nodes. This node is shown directly under Results
|
||||
* in the directory tree.
|
||||
*/
|
||||
public class TagsRootNode extends DisplayableItemNode {
|
||||
|
||||
public TagsRootNode() {
|
||||
super(Children.create(new Tags.TagsRootChildren(), true), Lookups.singleton(NAME));
|
||||
super.setName(NAME);
|
||||
super.setDisplayName(NAME);
|
||||
this.setIconBaseWithExtension(TAG_ICON_PATH);
|
||||
initData();
|
||||
}
|
||||
|
||||
private void initData() {
|
||||
try {
|
||||
// Get all file and artifact tags
|
||||
tags = new HashMap<String, List<BlackboardArtifact>>();
|
||||
List<BlackboardArtifact> tagArtifacts = skCase.getBlackboardArtifacts(BlackboardArtifact.ARTIFACT_TYPE.TSK_TAG_FILE);
|
||||
tagArtifacts.addAll(skCase.getBlackboardArtifacts(BlackboardArtifact.ARTIFACT_TYPE.TSK_TAG_ARTIFACT));
|
||||
|
||||
for (BlackboardArtifact artifact : tagArtifacts) {
|
||||
for (BlackboardAttribute attribute : artifact.getAttributes()) {
|
||||
if (attribute.getAttributeTypeID() == ATTRIBUTE_TYPE.TSK_TAG_NAME.getTypeID()) {
|
||||
String tagName = attribute.getValueString();
|
||||
if (tagName.equals(Bookmarks.BOOKMARK_TAG_NAME)) {
|
||||
break; // Don't add bookmarks
|
||||
} else if (tags.containsKey(tagName)) {
|
||||
List<BlackboardArtifact> list = new ArrayList<BlackboardArtifact>(tags.get(tagName));
|
||||
list.add(artifact);
|
||||
tags.put(tagName, list);
|
||||
} else {
|
||||
tags.put(tagName, Arrays.asList(artifact));
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
} catch (TskCoreException ex) {
|
||||
logger.log(Level.WARNING, "Count not initialize bookmark nodes, ", ex);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> T accept(DisplayableItemNodeVisitor<T> v) {
|
||||
return v.visit(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Sheet createSheet() {
|
||||
Sheet s = super.createSheet();
|
||||
Sheet.Set ss = s.get(Sheet.PROPERTIES);
|
||||
if (ss == null) {
|
||||
ss = Sheet.createPropertiesSet();
|
||||
s.put(ss);
|
||||
}
|
||||
|
||||
ss.put(new NodeProperty("Name",
|
||||
"Name",
|
||||
"no description",
|
||||
getName()));
|
||||
|
||||
return s;
|
||||
}
|
||||
|
||||
@Override
|
||||
public DisplayableItemNode.TYPE getDisplayableItemNodeType() {
|
||||
return DisplayableItemNode.TYPE.ARTIFACT;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Child factory to add all the Tag artifacts to a TagsRootNode
|
||||
* with the tag name.
|
||||
*/
|
||||
private class TagsRootChildren extends ChildFactory<String> {
|
||||
|
||||
@Override
|
||||
protected boolean createKeys(List<String> list) {
|
||||
for (String tagName : tags.keySet()) {
|
||||
list.add(tagName);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Node createNodeForKey(String key) {
|
||||
return new Tags.TagsNodeRoot(key, tags.get(key));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Node for each unique tag name. Shown directly under Results > Tags.
|
||||
*/
|
||||
public class TagsNodeRoot extends DisplayableItemNode {
|
||||
|
||||
public TagsNodeRoot(String tagName, List<BlackboardArtifact> artifacts) {
|
||||
super(Children.create(new Tags.TagsChildrenNode(artifacts), true), Lookups.singleton(tagName));
|
||||
|
||||
super.setName(tagName);
|
||||
super.setDisplayName(tagName + " (" + tags.get(tagName).size() + ")");
|
||||
|
||||
this.setIconBaseWithExtension(TAG_ICON_PATH);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Sheet createSheet() {
|
||||
Sheet s = super.createSheet();
|
||||
Sheet.Set ss = s.get(Sheet.PROPERTIES);
|
||||
if (ss == null) {
|
||||
ss = Sheet.createPropertiesSet();
|
||||
s.put(ss);
|
||||
}
|
||||
|
||||
ss.put(new NodeProperty("Name",
|
||||
"Name",
|
||||
"no description",
|
||||
getName()));
|
||||
|
||||
return s;
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> T accept(DisplayableItemNodeVisitor<T> v) {
|
||||
return v.visit(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public DisplayableItemNode.TYPE getDisplayableItemNodeType() {
|
||||
return DisplayableItemNode.TYPE.ARTIFACT;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isLeafTypeNode() {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Node representing an individual Tag artifact. For each TagsNodeRoot
|
||||
* under Results > Tags, this is one of the nodes listed in the result viewer.
|
||||
*/
|
||||
private class TagsChildrenNode extends ChildFactory<BlackboardArtifact> {
|
||||
|
||||
private List<BlackboardArtifact> artifacts;
|
||||
|
||||
private TagsChildrenNode(List<BlackboardArtifact> artifacts) {
|
||||
super();
|
||||
this.artifacts = artifacts;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected boolean createKeys(List<BlackboardArtifact> list) {
|
||||
list.addAll(artifacts);
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Node createNodeForKey(BlackboardArtifact artifact) {
|
||||
return new BlackboardArtifactNode(artifact, TAG_ICON_PATH);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a tag for a file with TSK_TAG_NAME as tagName.
|
||||
* @param file to create tag for
|
||||
* @param tagName TSK_TAG_NAME
|
||||
* @param comment the tag comment
|
||||
*/
|
||||
static void createTag(AbstractFile file, String tagName, String comment) {
|
||||
public static void createTag(AbstractFile file, String tagName, String comment) {
|
||||
try {
|
||||
final BlackboardArtifact bookArt = file.newArtifact(BlackboardArtifact.ARTIFACT_TYPE.TSK_TAG_FILE);
|
||||
List<BlackboardAttribute> attrs = new ArrayList<BlackboardAttribute>();
|
||||
@@ -62,8 +251,9 @@ public class Tags {
|
||||
* Create a tag for an artifact with TSK_TAG_NAME as tagName.
|
||||
* @param artifact to create tag for
|
||||
* @param tagName TSK_TAG_NAME
|
||||
* @param comment the tag comment
|
||||
*/
|
||||
static void createTag(BlackboardArtifact artifact, String tagName, String comment) {
|
||||
public static void createTag(BlackboardArtifact artifact, String tagName, String comment) {
|
||||
try {
|
||||
Case currentCase = Case.getCurrentCase();
|
||||
SleuthkitCase skCase = currentCase.getSleuthkitCase();
|
||||
@@ -91,6 +281,7 @@ public class Tags {
|
||||
/**
|
||||
* Create a bookmark tag for a file.
|
||||
* @param file to create bookmark tag for
|
||||
* @param comment the bookmark comment
|
||||
*/
|
||||
public static void createBookmark(AbstractFile file, String comment) {
|
||||
createTag(file, Bookmarks.BOOKMARK_TAG_NAME, comment);
|
||||
@@ -99,6 +290,7 @@ public class Tags {
|
||||
/**
|
||||
* Create a bookmark tag for an artifact.
|
||||
* @param artifact to create bookmark tag for
|
||||
* @param comment the bookmark comment
|
||||
*/
|
||||
public static void createBookmark(BlackboardArtifact artifact, String comment) {
|
||||
createTag(artifact, Bookmarks.BOOKMARK_TAG_NAME, comment);
|
||||
@@ -124,6 +316,7 @@ public class Tags {
|
||||
* Uses a custom query for speed when dealing with thousands of Tags.
|
||||
* @return a list of all tag names.
|
||||
*/
|
||||
@SuppressWarnings("deprecation")
|
||||
public static List<String> getTagNames() {
|
||||
Case currentCase = Case.getCurrentCase();
|
||||
SleuthkitCase skCase = currentCase.getSleuthkitCase();
|
||||
@@ -145,6 +338,7 @@ public class Tags {
|
||||
try {
|
||||
skCase.closeRunQuery(rs);
|
||||
} catch (SQLException ex) {
|
||||
logger.log(Level.SEVERE, "Failed to close the query for blackboard for tag names.");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,122 +0,0 @@
|
||||
/*
|
||||
* Autopsy Forensic Browser
|
||||
*
|
||||
* Copyright 2011 Basis Technology Corp.
|
||||
* Contact: carrier <at> sleuthkit <dot> org
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.sleuthkit.autopsy.directorytree;
|
||||
|
||||
import java.awt.event.ActionEvent;
|
||||
import javax.swing.AbstractAction;
|
||||
import javax.swing.JOptionPane;
|
||||
import org.openide.nodes.Node;
|
||||
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||
import org.sleuthkit.autopsy.datamodel.ContentUtils;
|
||||
import org.sleuthkit.autopsy.datamodel.Tags;
|
||||
import org.sleuthkit.datamodel.AbstractFile;
|
||||
import org.sleuthkit.datamodel.BlackboardArtifact;
|
||||
import org.sleuthkit.datamodel.Content;
|
||||
import org.sleuthkit.datamodel.ContentVisitor;
|
||||
import org.sleuthkit.datamodel.Directory;
|
||||
|
||||
/**
|
||||
* Action on a file or artifact that bookmarks a file and/or artifact
|
||||
* and reloads the bookmark view.
|
||||
* Supports bookmarking of a fs file, directory and layout file and layout
|
||||
* directory (virtual files/dirs for unalloc content)
|
||||
*
|
||||
* TODO add use enters description and hierarchy (TSK_TAG_NAME with slashes)
|
||||
*/
|
||||
public class BookmarkAction extends AbstractAction {
|
||||
|
||||
private static final Logger logger = Logger.getLogger(BookmarkAction.class.getName());
|
||||
//content to bookmark
|
||||
private AbstractFile bookmarkFile;
|
||||
private BlackboardArtifact bookmarkArtifact;
|
||||
private final InitializeBookmarkFileV initializer = new InitializeBookmarkFileV();
|
||||
|
||||
public BookmarkAction(String title, Node contentNode) {
|
||||
super(title);
|
||||
Content content = contentNode.getLookup().lookup(Content.class);
|
||||
|
||||
bookmarkArtifact = null;
|
||||
bookmarkFile = content.accept(initializer);
|
||||
this.setEnabled(bookmarkFile != null);
|
||||
}
|
||||
|
||||
public BookmarkAction(String title, Content content) {
|
||||
super(title);
|
||||
|
||||
bookmarkArtifact = null;
|
||||
bookmarkFile = content.accept(initializer);
|
||||
this.setEnabled(bookmarkFile != null);
|
||||
}
|
||||
|
||||
public BookmarkAction(String title, BlackboardArtifact art) {
|
||||
super(title);
|
||||
|
||||
bookmarkArtifact = art;
|
||||
bookmarkFile = null;
|
||||
this.setEnabled(bookmarkArtifact != null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the FsContent if it is supported, otherwise null
|
||||
*/
|
||||
private static class InitializeBookmarkFileV extends ContentVisitor.Default<AbstractFile> {
|
||||
|
||||
@Override
|
||||
public AbstractFile visit(org.sleuthkit.datamodel.File f) {
|
||||
return f;
|
||||
}
|
||||
|
||||
@Override
|
||||
public AbstractFile visit(org.sleuthkit.datamodel.LayoutFile lf) {
|
||||
return lf;
|
||||
}
|
||||
|
||||
@Override
|
||||
public AbstractFile visit(org.sleuthkit.datamodel.VirtualDirectory ld) {
|
||||
return ld;
|
||||
}
|
||||
|
||||
@Override
|
||||
public AbstractFile visit(Directory dir) {
|
||||
return ContentUtils.isDotDirectory(dir) ? null : dir;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected AbstractFile defaultVisit(Content cntnt) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
String comment = JOptionPane.showInputDialog(null, "Please enter a comment for the bookmark:", "Bookmark Comment", JOptionPane.PLAIN_MESSAGE);
|
||||
if(comment == null || comment.isEmpty()) {
|
||||
comment = "No Comment";
|
||||
}
|
||||
if(bookmarkArtifact != null) {
|
||||
Tags.createBookmark(bookmarkArtifact, comment);
|
||||
} else if(bookmarkFile != null) {
|
||||
Tags.createBookmark(bookmarkFile, comment);
|
||||
}
|
||||
|
||||
DirectoryTreeTopComponent viewer = DirectoryTreeTopComponent.findInstance();
|
||||
viewer.refreshTree(BlackboardArtifact.ARTIFACT_TYPE.TSK_TAG_FILE);
|
||||
viewer.refreshTree(BlackboardArtifact.ARTIFACT_TYPE.TSK_TAG_ARTIFACT);
|
||||
}
|
||||
}
|
||||
@@ -47,3 +47,11 @@ ImageDetailsPanel.imgSectorSizeLabel.text=Sector Size:
|
||||
ImageDetailsPanel.imgSectorSizeValue.text=...
|
||||
DirectoryTreeTopComponent.backButton.text=
|
||||
DirectoryTreeTopComponent.forwardButton.text=
|
||||
CreateTagDialog.cancelButton.text=Cancel
|
||||
CreateTagDialog.okButton.text=OK
|
||||
CreateTagDialog.tagNameField.text=
|
||||
CreateTagDialog.tagCommentField.text=
|
||||
CreateTagDialog.tagNameLabel.text=Tag Name:
|
||||
CreateTagDialog.tagCommentLabel.text=Tag Comment:
|
||||
CreateTagDialog.preexistingLabel.text=Pre-existing Tags:
|
||||
CreateTagDialog.newTagPanel.border.title=New Tag
|
||||
|
||||
@@ -0,0 +1,212 @@
|
||||
<?xml version="1.0" encoding="UTF-8" ?>
|
||||
|
||||
<Form version="1.5" maxVersion="1.8" type="org.netbeans.modules.form.forminfo.JDialogFormInfo">
|
||||
<Properties>
|
||||
<Property name="defaultCloseOperation" type="int" value="2"/>
|
||||
</Properties>
|
||||
<SyntheticProperties>
|
||||
<SyntheticProperty name="formSizePolicy" type="int" value="1"/>
|
||||
</SyntheticProperties>
|
||||
<Events>
|
||||
<EventHandler event="keyReleased" listener="java.awt.event.KeyListener" parameters="java.awt.event.KeyEvent" handler="formKeyReleased"/>
|
||||
</Events>
|
||||
<AuxValues>
|
||||
<AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="1"/>
|
||||
<AuxValue name="FormSettings_autoSetComponentName" type="java.lang.Boolean" value="false"/>
|
||||
<AuxValue name="FormSettings_generateFQN" type="java.lang.Boolean" value="true"/>
|
||||
<AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="true"/>
|
||||
<AuxValue name="FormSettings_i18nAutoMode" type="java.lang.Boolean" value="true"/>
|
||||
<AuxValue name="FormSettings_layoutCodeTarget" type="java.lang.Integer" value="1"/>
|
||||
<AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/>
|
||||
<AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/>
|
||||
<AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/>
|
||||
</AuxValues>
|
||||
|
||||
<Layout>
|
||||
<DimensionLayout dim="0">
|
||||
<Group type="103" groupAlignment="0" attributes="0">
|
||||
<Group type="102" attributes="0">
|
||||
<EmptySpace max="-2" attributes="0"/>
|
||||
<Group type="103" groupAlignment="0" attributes="0">
|
||||
<Component id="jScrollPane1" alignment="0" min="-2" pref="198" max="-2" attributes="0"/>
|
||||
<Component id="preexistingLabel" alignment="0" min="-2" max="-2" attributes="0"/>
|
||||
</Group>
|
||||
<EmptySpace type="unrelated" max="-2" attributes="0"/>
|
||||
<Group type="103" groupAlignment="0" attributes="0">
|
||||
<Group type="102" attributes="0">
|
||||
<EmptySpace min="0" pref="233" max="32767" attributes="0"/>
|
||||
<Component id="okButton" min="-2" max="-2" attributes="0"/>
|
||||
<EmptySpace type="unrelated" max="-2" attributes="0"/>
|
||||
<Component id="cancelButton" min="-2" max="-2" attributes="0"/>
|
||||
</Group>
|
||||
<Component id="newTagPanel" max="32767" attributes="0"/>
|
||||
</Group>
|
||||
<EmptySpace max="-2" attributes="0"/>
|
||||
</Group>
|
||||
</Group>
|
||||
</DimensionLayout>
|
||||
<DimensionLayout dim="1">
|
||||
<Group type="103" groupAlignment="0" attributes="0">
|
||||
<Group type="102" alignment="0" attributes="0">
|
||||
<EmptySpace max="-2" attributes="0"/>
|
||||
<Group type="103" groupAlignment="0" attributes="0">
|
||||
<Group type="102" attributes="0">
|
||||
<Component id="preexistingLabel" min="-2" max="-2" attributes="0"/>
|
||||
<EmptySpace max="-2" attributes="0"/>
|
||||
<Component id="jScrollPane1" pref="0" max="32767" attributes="0"/>
|
||||
</Group>
|
||||
<Component id="newTagPanel" max="32767" attributes="0"/>
|
||||
</Group>
|
||||
<EmptySpace max="-2" attributes="0"/>
|
||||
<Group type="103" groupAlignment="3" attributes="0">
|
||||
<Component id="cancelButton" alignment="3" min="-2" max="-2" attributes="0"/>
|
||||
<Component id="okButton" alignment="3" min="-2" max="-2" attributes="0"/>
|
||||
</Group>
|
||||
<EmptySpace max="-2" attributes="0"/>
|
||||
</Group>
|
||||
</Group>
|
||||
</DimensionLayout>
|
||||
</Layout>
|
||||
<SubComponents>
|
||||
<Component class="javax.swing.JButton" name="cancelButton">
|
||||
<Properties>
|
||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||
<ResourceString bundle="org/sleuthkit/autopsy/directorytree/Bundle.properties" key="CreateTagDialog.cancelButton.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||
</Property>
|
||||
</Properties>
|
||||
<Events>
|
||||
<EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="cancelButtonActionPerformed"/>
|
||||
</Events>
|
||||
</Component>
|
||||
<Component class="javax.swing.JButton" name="okButton">
|
||||
<Properties>
|
||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||
<ResourceString bundle="org/sleuthkit/autopsy/directorytree/Bundle.properties" key="CreateTagDialog.okButton.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||
</Property>
|
||||
</Properties>
|
||||
<Events>
|
||||
<EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="okButtonActionPerformed"/>
|
||||
</Events>
|
||||
</Component>
|
||||
<Container class="javax.swing.JScrollPane" name="jScrollPane1">
|
||||
<Properties>
|
||||
<Property name="background" type="java.awt.Color" editor="org.netbeans.beaninfo.editors.ColorEditor">
|
||||
<Color blue="ff" green="ff" red="ff" type="rgb"/>
|
||||
</Property>
|
||||
</Properties>
|
||||
<AuxValues>
|
||||
<AuxValue name="autoScrollPane" type="java.lang.Boolean" value="true"/>
|
||||
</AuxValues>
|
||||
|
||||
<Layout class="org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout"/>
|
||||
<SubComponents>
|
||||
<Component class="javax.swing.JTable" name="tagsTable">
|
||||
<Properties>
|
||||
<Property name="model" type="javax.swing.table.TableModel" editor="org.netbeans.modules.form.editors2.TableModelEditor">
|
||||
<Table columnCount="0" rowCount="0"/>
|
||||
</Property>
|
||||
<Property name="columnModel" type="javax.swing.table.TableColumnModel" editor="org.netbeans.modules.form.editors2.TableColumnModelEditor">
|
||||
<TableColumnModel selectionModel="0"/>
|
||||
</Property>
|
||||
<Property name="showHorizontalLines" type="boolean" value="false"/>
|
||||
<Property name="showVerticalLines" type="boolean" value="false"/>
|
||||
<Property name="tableHeader" type="javax.swing.table.JTableHeader" editor="org.netbeans.modules.form.RADConnectionPropertyEditor">
|
||||
<Connection code="null" type="code"/>
|
||||
</Property>
|
||||
</Properties>
|
||||
</Component>
|
||||
</SubComponents>
|
||||
</Container>
|
||||
<Component class="javax.swing.JLabel" name="preexistingLabel">
|
||||
<Properties>
|
||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||
<ResourceString bundle="org/sleuthkit/autopsy/directorytree/Bundle.properties" key="CreateTagDialog.preexistingLabel.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||
</Property>
|
||||
</Properties>
|
||||
</Component>
|
||||
<Container class="javax.swing.JPanel" name="newTagPanel">
|
||||
<Properties>
|
||||
<Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor">
|
||||
<Border info="org.netbeans.modules.form.compat2.border.TitledBorderInfo">
|
||||
<TitledBorder title="New Tag">
|
||||
<ResourceString PropertyName="titleX" bundle="org/sleuthkit/autopsy/directorytree/Bundle.properties" key="CreateTagDialog.newTagPanel.border.title" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||
</TitledBorder>
|
||||
</Border>
|
||||
</Property>
|
||||
</Properties>
|
||||
|
||||
<Layout>
|
||||
<DimensionLayout dim="0">
|
||||
<Group type="103" groupAlignment="0" attributes="0">
|
||||
<Group type="102" attributes="0">
|
||||
<EmptySpace max="-2" attributes="0"/>
|
||||
<Group type="103" groupAlignment="0" attributes="0">
|
||||
<Component id="tagCommentLabel" alignment="0" min="-2" max="-2" attributes="0"/>
|
||||
<Component id="tagNameLabel" alignment="0" min="-2" max="-2" attributes="0"/>
|
||||
</Group>
|
||||
<EmptySpace type="separate" max="-2" attributes="0"/>
|
||||
<Group type="103" groupAlignment="0" attributes="0">
|
||||
<Component id="tagNameField" max="32767" attributes="0"/>
|
||||
<Component id="tagCommentField" max="32767" attributes="0"/>
|
||||
</Group>
|
||||
<EmptySpace max="-2" attributes="0"/>
|
||||
</Group>
|
||||
</Group>
|
||||
</DimensionLayout>
|
||||
<DimensionLayout dim="1">
|
||||
<Group type="103" groupAlignment="0" attributes="0">
|
||||
<Group type="102" attributes="0">
|
||||
<EmptySpace max="-2" attributes="0"/>
|
||||
<Group type="103" groupAlignment="3" attributes="0">
|
||||
<Component id="tagNameLabel" alignment="3" min="-2" max="-2" attributes="0"/>
|
||||
<Component id="tagNameField" alignment="3" min="-2" max="-2" attributes="0"/>
|
||||
</Group>
|
||||
<EmptySpace max="-2" attributes="0"/>
|
||||
<Group type="103" groupAlignment="3" attributes="0">
|
||||
<Component id="tagCommentLabel" alignment="3" min="-2" max="-2" attributes="0"/>
|
||||
<Component id="tagCommentField" alignment="3" min="-2" max="-2" attributes="0"/>
|
||||
</Group>
|
||||
<EmptySpace pref="138" max="32767" attributes="0"/>
|
||||
</Group>
|
||||
</Group>
|
||||
</DimensionLayout>
|
||||
</Layout>
|
||||
<SubComponents>
|
||||
<Component class="javax.swing.JTextField" name="tagCommentField">
|
||||
<Properties>
|
||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||
<ResourceString bundle="org/sleuthkit/autopsy/directorytree/Bundle.properties" key="CreateTagDialog.tagCommentField.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||
</Property>
|
||||
</Properties>
|
||||
<Events>
|
||||
<EventHandler event="keyReleased" listener="java.awt.event.KeyListener" parameters="java.awt.event.KeyEvent" handler="tagCommentFieldKeyReleased"/>
|
||||
</Events>
|
||||
</Component>
|
||||
<Component class="javax.swing.JLabel" name="tagNameLabel">
|
||||
<Properties>
|
||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||
<ResourceString bundle="org/sleuthkit/autopsy/directorytree/Bundle.properties" key="CreateTagDialog.tagNameLabel.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||
</Property>
|
||||
</Properties>
|
||||
</Component>
|
||||
<Component class="javax.swing.JLabel" name="tagCommentLabel">
|
||||
<Properties>
|
||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||
<ResourceString bundle="org/sleuthkit/autopsy/directorytree/Bundle.properties" key="CreateTagDialog.tagCommentLabel.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||
</Property>
|
||||
</Properties>
|
||||
</Component>
|
||||
<Component class="javax.swing.JTextField" name="tagNameField">
|
||||
<Properties>
|
||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||
<ResourceString bundle="org/sleuthkit/autopsy/directorytree/Bundle.properties" key="CreateTagDialog.tagNameField.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||
</Property>
|
||||
</Properties>
|
||||
<Events>
|
||||
<EventHandler event="keyReleased" listener="java.awt.event.KeyListener" parameters="java.awt.event.KeyEvent" handler="tagNameFieldKeyReleased"/>
|
||||
</Events>
|
||||
</Component>
|
||||
</SubComponents>
|
||||
</Container>
|
||||
</SubComponents>
|
||||
</Form>
|
||||
@@ -0,0 +1,319 @@
|
||||
/*
|
||||
* Autopsy Forensic Browser
|
||||
*
|
||||
* Copyright 2013 Basis Technology Corp.
|
||||
* Contact: carrier <at> sleuthkit <dot> org
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.sleuthkit.autopsy.directorytree;
|
||||
|
||||
import java.awt.Dimension;
|
||||
import java.awt.Toolkit;
|
||||
import java.awt.event.KeyEvent;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import javax.swing.JOptionPane;
|
||||
import javax.swing.ListSelectionModel;
|
||||
import javax.swing.event.ListSelectionEvent;
|
||||
import javax.swing.event.ListSelectionListener;
|
||||
import javax.swing.table.AbstractTableModel;
|
||||
import org.sleuthkit.autopsy.datamodel.Tags;
|
||||
|
||||
public class CreateTagDialog extends javax.swing.JDialog {
|
||||
private Map<String, String> tagMap = null;
|
||||
TagsTableModel tagsTableModel;
|
||||
TagSelectionListener tagSelectionListener;
|
||||
|
||||
/**
|
||||
* Creates new form CreateTagDialog
|
||||
*/
|
||||
public CreateTagDialog(java.awt.Frame parent, boolean modal) {
|
||||
super(parent, modal);
|
||||
initComponents();
|
||||
|
||||
tagsTableModel = new TagsTableModel();
|
||||
tagSelectionListener = new TagSelectionListener();
|
||||
tagsTable.setModel(tagsTableModel);
|
||||
tagsTable.getSelectionModel().addListSelectionListener(tagSelectionListener);
|
||||
tagsTable.setTableHeader(null);
|
||||
tagsTable.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
|
||||
tagsTable.setRowHeight(tagsTable.getRowHeight() + 5);
|
||||
}
|
||||
|
||||
public Map<String, String> display() {
|
||||
this.setTitle("Create a new tag");
|
||||
|
||||
Dimension screenDimension = Toolkit.getDefaultToolkit().getScreenSize();
|
||||
// set the popUp window / JFrame
|
||||
int w = this.getSize().width;
|
||||
int h = this.getSize().height;
|
||||
|
||||
// set the location of the popUp Window on the center of the screen
|
||||
setLocation((screenDimension.width - w) / 2, (screenDimension.height - h) / 2);
|
||||
this.setVisible(true);
|
||||
|
||||
return this.tagMap;
|
||||
}
|
||||
|
||||
private boolean containsIllegalCharacters(String content) {
|
||||
if ((content.contains("\\") || content.contains(":") || content.contains("*")
|
||||
|| content.contains("?") || content.contains("\"") || content.contains("<")
|
||||
|| content.contains(">") || content.contains("|"))) {
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* This method is called from within the constructor to initialize the form.
|
||||
* WARNING: Do NOT modify this code. The content of this method is always
|
||||
* regenerated by the Form Editor.
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
// <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
|
||||
private void initComponents() {
|
||||
|
||||
cancelButton = new javax.swing.JButton();
|
||||
okButton = new javax.swing.JButton();
|
||||
jScrollPane1 = new javax.swing.JScrollPane();
|
||||
tagsTable = new javax.swing.JTable();
|
||||
preexistingLabel = new javax.swing.JLabel();
|
||||
newTagPanel = new javax.swing.JPanel();
|
||||
tagCommentField = new javax.swing.JTextField();
|
||||
tagNameLabel = new javax.swing.JLabel();
|
||||
tagCommentLabel = new javax.swing.JLabel();
|
||||
tagNameField = new javax.swing.JTextField();
|
||||
|
||||
setDefaultCloseOperation(javax.swing.WindowConstants.DISPOSE_ON_CLOSE);
|
||||
addKeyListener(new java.awt.event.KeyAdapter() {
|
||||
public void keyReleased(java.awt.event.KeyEvent evt) {
|
||||
formKeyReleased(evt);
|
||||
}
|
||||
});
|
||||
|
||||
org.openide.awt.Mnemonics.setLocalizedText(cancelButton, org.openide.util.NbBundle.getMessage(CreateTagDialog.class, "CreateTagDialog.cancelButton.text")); // NOI18N
|
||||
cancelButton.addActionListener(new java.awt.event.ActionListener() {
|
||||
public void actionPerformed(java.awt.event.ActionEvent evt) {
|
||||
cancelButtonActionPerformed(evt);
|
||||
}
|
||||
});
|
||||
|
||||
org.openide.awt.Mnemonics.setLocalizedText(okButton, org.openide.util.NbBundle.getMessage(CreateTagDialog.class, "CreateTagDialog.okButton.text")); // NOI18N
|
||||
okButton.addActionListener(new java.awt.event.ActionListener() {
|
||||
public void actionPerformed(java.awt.event.ActionEvent evt) {
|
||||
okButtonActionPerformed(evt);
|
||||
}
|
||||
});
|
||||
|
||||
jScrollPane1.setBackground(new java.awt.Color(255, 255, 255));
|
||||
|
||||
tagsTable.setModel(new javax.swing.table.DefaultTableModel(
|
||||
new Object [][] {
|
||||
|
||||
},
|
||||
new String [] {
|
||||
|
||||
}
|
||||
));
|
||||
tagsTable.setShowHorizontalLines(false);
|
||||
tagsTable.setShowVerticalLines(false);
|
||||
tagsTable.setTableHeader(null);
|
||||
jScrollPane1.setViewportView(tagsTable);
|
||||
|
||||
org.openide.awt.Mnemonics.setLocalizedText(preexistingLabel, org.openide.util.NbBundle.getMessage(CreateTagDialog.class, "CreateTagDialog.preexistingLabel.text")); // NOI18N
|
||||
|
||||
newTagPanel.setBorder(javax.swing.BorderFactory.createTitledBorder(org.openide.util.NbBundle.getMessage(CreateTagDialog.class, "CreateTagDialog.newTagPanel.border.title"))); // NOI18N
|
||||
|
||||
tagCommentField.setText(org.openide.util.NbBundle.getMessage(CreateTagDialog.class, "CreateTagDialog.tagCommentField.text")); // NOI18N
|
||||
tagCommentField.addKeyListener(new java.awt.event.KeyAdapter() {
|
||||
public void keyReleased(java.awt.event.KeyEvent evt) {
|
||||
tagCommentFieldKeyReleased(evt);
|
||||
}
|
||||
});
|
||||
|
||||
org.openide.awt.Mnemonics.setLocalizedText(tagNameLabel, org.openide.util.NbBundle.getMessage(CreateTagDialog.class, "CreateTagDialog.tagNameLabel.text")); // NOI18N
|
||||
|
||||
org.openide.awt.Mnemonics.setLocalizedText(tagCommentLabel, org.openide.util.NbBundle.getMessage(CreateTagDialog.class, "CreateTagDialog.tagCommentLabel.text")); // NOI18N
|
||||
|
||||
tagNameField.setText(org.openide.util.NbBundle.getMessage(CreateTagDialog.class, "CreateTagDialog.tagNameField.text")); // NOI18N
|
||||
tagNameField.addKeyListener(new java.awt.event.KeyAdapter() {
|
||||
public void keyReleased(java.awt.event.KeyEvent evt) {
|
||||
tagNameFieldKeyReleased(evt);
|
||||
}
|
||||
});
|
||||
|
||||
javax.swing.GroupLayout newTagPanelLayout = new javax.swing.GroupLayout(newTagPanel);
|
||||
newTagPanel.setLayout(newTagPanelLayout);
|
||||
newTagPanelLayout.setHorizontalGroup(
|
||||
newTagPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||
.addGroup(newTagPanelLayout.createSequentialGroup()
|
||||
.addContainerGap()
|
||||
.addGroup(newTagPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||
.addComponent(tagCommentLabel)
|
||||
.addComponent(tagNameLabel))
|
||||
.addGap(18, 18, 18)
|
||||
.addGroup(newTagPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||
.addComponent(tagNameField)
|
||||
.addComponent(tagCommentField))
|
||||
.addContainerGap())
|
||||
);
|
||||
newTagPanelLayout.setVerticalGroup(
|
||||
newTagPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||
.addGroup(newTagPanelLayout.createSequentialGroup()
|
||||
.addContainerGap()
|
||||
.addGroup(newTagPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
|
||||
.addComponent(tagNameLabel)
|
||||
.addComponent(tagNameField, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
|
||||
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||
.addGroup(newTagPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
|
||||
.addComponent(tagCommentLabel)
|
||||
.addComponent(tagCommentField, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
|
||||
.addContainerGap(138, Short.MAX_VALUE))
|
||||
);
|
||||
|
||||
javax.swing.GroupLayout layout = new javax.swing.GroupLayout(getContentPane());
|
||||
getContentPane().setLayout(layout);
|
||||
layout.setHorizontalGroup(
|
||||
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||
.addGroup(layout.createSequentialGroup()
|
||||
.addContainerGap()
|
||||
.addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||
.addComponent(jScrollPane1, javax.swing.GroupLayout.PREFERRED_SIZE, 198, javax.swing.GroupLayout.PREFERRED_SIZE)
|
||||
.addComponent(preexistingLabel))
|
||||
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
|
||||
.addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||
.addGroup(layout.createSequentialGroup()
|
||||
.addGap(0, 233, Short.MAX_VALUE)
|
||||
.addComponent(okButton)
|
||||
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
|
||||
.addComponent(cancelButton))
|
||||
.addComponent(newTagPanel, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
|
||||
.addContainerGap())
|
||||
);
|
||||
layout.setVerticalGroup(
|
||||
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||
.addGroup(layout.createSequentialGroup()
|
||||
.addContainerGap()
|
||||
.addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||
.addGroup(layout.createSequentialGroup()
|
||||
.addComponent(preexistingLabel)
|
||||
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||
.addComponent(jScrollPane1, javax.swing.GroupLayout.PREFERRED_SIZE, 0, Short.MAX_VALUE))
|
||||
.addComponent(newTagPanel, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
|
||||
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||
.addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
|
||||
.addComponent(cancelButton)
|
||||
.addComponent(okButton))
|
||||
.addContainerGap())
|
||||
);
|
||||
|
||||
pack();
|
||||
}// </editor-fold>//GEN-END:initComponents
|
||||
|
||||
private void cancelButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_cancelButtonActionPerformed
|
||||
this.tagMap = null;
|
||||
this.dispose();
|
||||
}//GEN-LAST:event_cancelButtonActionPerformed
|
||||
|
||||
private void okButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_okButtonActionPerformed
|
||||
String tagName = tagNameField.getText();
|
||||
String tagComment = tagCommentField.getText();
|
||||
if (tagName.isEmpty()) {
|
||||
JOptionPane.showMessageDialog(null, "Must supply a tag name to continue.", "Tag Name", JOptionPane.ERROR_MESSAGE);
|
||||
} else if (containsIllegalCharacters(tagName)) {
|
||||
JOptionPane.showMessageDialog(null, "The tag name contains illegal characters.\nCannot contain any of the following symbols: \\ : * ? \" < > |",
|
||||
"Illegal Characters", JOptionPane.ERROR_MESSAGE);
|
||||
} else {
|
||||
this.tagMap = new HashMap<String, String>();
|
||||
tagMap.put("Name", tagName);
|
||||
tagMap.put("Comment", tagComment.isEmpty() ? "No Comment" : tagComment);
|
||||
this.dispose();
|
||||
}
|
||||
}//GEN-LAST:event_okButtonActionPerformed
|
||||
|
||||
private void formKeyReleased(java.awt.event.KeyEvent evt) {//GEN-FIRST:event_formKeyReleased
|
||||
if (evt.getKeyCode() == KeyEvent.VK_ENTER) {
|
||||
okButtonActionPerformed(null);
|
||||
}
|
||||
}//GEN-LAST:event_formKeyReleased
|
||||
|
||||
private void tagNameFieldKeyReleased(java.awt.event.KeyEvent evt) {//GEN-FIRST:event_tagNameFieldKeyReleased
|
||||
if (evt.getKeyCode() == KeyEvent.VK_ENTER) {
|
||||
okButtonActionPerformed(null);
|
||||
}
|
||||
}//GEN-LAST:event_tagNameFieldKeyReleased
|
||||
|
||||
private void tagCommentFieldKeyReleased(java.awt.event.KeyEvent evt) {//GEN-FIRST:event_tagCommentFieldKeyReleased
|
||||
if (evt.getKeyCode() == KeyEvent.VK_ENTER) {
|
||||
okButtonActionPerformed(null);
|
||||
}
|
||||
}//GEN-LAST:event_tagCommentFieldKeyReleased
|
||||
|
||||
// Variables declaration - do not modify//GEN-BEGIN:variables
|
||||
private javax.swing.JButton cancelButton;
|
||||
private javax.swing.JScrollPane jScrollPane1;
|
||||
private javax.swing.JPanel newTagPanel;
|
||||
private javax.swing.JButton okButton;
|
||||
private javax.swing.JLabel preexistingLabel;
|
||||
private javax.swing.JTextField tagCommentField;
|
||||
private javax.swing.JLabel tagCommentLabel;
|
||||
private javax.swing.JTextField tagNameField;
|
||||
private javax.swing.JLabel tagNameLabel;
|
||||
private javax.swing.JTable tagsTable;
|
||||
// End of variables declaration//GEN-END:variables
|
||||
|
||||
private class TagsTableModel extends AbstractTableModel {
|
||||
List<String> tagNames;
|
||||
|
||||
TagsTableModel() {
|
||||
tagNames = Tags.getTagNames();
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getRowCount() {
|
||||
return tagNames.size();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isCellEditable(int rowIndex, int columnIndex) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getColumnCount() {
|
||||
return 1;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getValueAt(int rowIndex, int columnIndex) {
|
||||
return tagNames.get(rowIndex);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private class TagSelectionListener implements ListSelectionListener {
|
||||
|
||||
@Override
|
||||
public void valueChanged(ListSelectionEvent e) {
|
||||
Object row = tagsTable.getValueAt(tagsTable.getSelectedRow(), 0);
|
||||
if (row != null) {
|
||||
String tagName = row.toString();
|
||||
tagNameField.setText(tagName);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -174,7 +174,7 @@ public class DataResultFilterNode extends FilterNode {
|
||||
actions.add(null); // creates a menu separator
|
||||
actions.add(new ExtractAction("Extract Directory", dir));
|
||||
actions.add(null); // creates a menu separator
|
||||
actions.add(new BookmarkAction("Bookmark Directory", dir));
|
||||
actions.add(new TagFileAction(dir));
|
||||
return actions;
|
||||
}
|
||||
|
||||
@@ -187,7 +187,7 @@ public class DataResultFilterNode extends FilterNode {
|
||||
actions.add(null); // creates a menu separator
|
||||
actions.add(new ExtractAction("Extract File", lf));
|
||||
actions.add(null); // creates a menu separator
|
||||
actions.add(new BookmarkAction("Bookmark File", lf));
|
||||
actions.add(new TagFileAction(lf));
|
||||
return actions;
|
||||
}
|
||||
|
||||
@@ -195,7 +195,7 @@ public class DataResultFilterNode extends FilterNode {
|
||||
public List<Action> visit(VirtualDirectoryNode ld) {
|
||||
List<Action> actions = new ArrayList<Action>();
|
||||
|
||||
actions.add(new BookmarkAction("Bookmark Directory", ld));
|
||||
actions.add(new TagFileAction(ld));
|
||||
return actions;
|
||||
}
|
||||
|
||||
@@ -212,7 +212,7 @@ public class DataResultFilterNode extends FilterNode {
|
||||
actions.add(new ExtractAction("Extract File", f));
|
||||
actions.add(new HashSearchAction("Search for files with the same MD5 hash", f));
|
||||
actions.add(null); // creates a menu separator
|
||||
actions.add(new BookmarkAction("Bookmark File", f));
|
||||
actions.add(new TagFileAction(f));
|
||||
return actions;
|
||||
}
|
||||
|
||||
@@ -246,8 +246,8 @@ public class DataResultFilterNode extends FilterNode {
|
||||
//add file bookmark if itself is not a file bookmark
|
||||
if (artifactTypeID != BlackboardArtifact.ARTIFACT_TYPE.TSK_TAG_FILE.getTypeID()) {
|
||||
actions.add(null); // creates a menu separator
|
||||
actions.add(new BookmarkAction("Bookmark File", f));
|
||||
actions.add(new BookmarkAction("Bookmark Result", ba));
|
||||
actions.add(new TagFileAction(f));
|
||||
actions.add(new TagResultAction(ba));
|
||||
}
|
||||
}
|
||||
if (( d = ban.getLookup().lookup(Directory.class)) != null) {
|
||||
@@ -260,8 +260,8 @@ public class DataResultFilterNode extends FilterNode {
|
||||
//add file bookmark if itself is not a file bookmark
|
||||
if (artifactTypeID != BlackboardArtifact.ARTIFACT_TYPE.TSK_TAG_FILE.getTypeID()) {
|
||||
actions.add(null); // creates a menu separator
|
||||
actions.add(new BookmarkAction("Bookmark Directory", d));
|
||||
actions.add(new BookmarkAction("Bookmark Result Directory", ba));
|
||||
actions.add(new TagFileAction( d));
|
||||
actions.add(new TagResultAction(ba));
|
||||
}
|
||||
}
|
||||
else if ( ( lf = ban.getLookup().lookup(LayoutFile.class)) != null) {
|
||||
@@ -274,8 +274,8 @@ public class DataResultFilterNode extends FilterNode {
|
||||
//add file bookmark if itself is not a file bookmark
|
||||
if (artifactTypeID != BlackboardArtifact.ARTIFACT_TYPE.TSK_TAG_FILE.getTypeID()) {
|
||||
actions.add(null); // creates a menu separator
|
||||
actions.add(new BookmarkAction("Bookmark File", lf));
|
||||
actions.add(new BookmarkAction("Bookmark Result", ba));
|
||||
actions.add(new TagFileAction(lf));
|
||||
actions.add(new TagResultAction(ba));
|
||||
}
|
||||
}
|
||||
//if (artifactTypeID == BlackboardArtifact.ARTIFACT_TYPE.TSK_KEYWORD_HIT.getTypeID()) {
|
||||
|
||||
@@ -378,7 +378,7 @@ public final class ExtractUnallocAction extends AbstractAction {
|
||||
/**
|
||||
* LayoutDirectory has all the Layout(Unallocated) files
|
||||
*
|
||||
* @param ld LayoutDirectory the visitor encountered
|
||||
* @param vd VirtualDirectory the visitor encountered
|
||||
* @return A list<LayoutFile> containing all the LayoutFile in ld,
|
||||
* returns null if it fails
|
||||
*/
|
||||
|
||||
@@ -33,7 +33,9 @@ import org.sleuthkit.datamodel.SleuthkitCase;
|
||||
|
||||
/**
|
||||
* Action that deletes blackboard artifacts requested and reloads the view
|
||||
* @deprecated do not use, it is here in case we ever pick up on this work
|
||||
*/
|
||||
@Deprecated
|
||||
public class ResultDeleteAction extends AbstractAction {
|
||||
|
||||
private enum ActionType {
|
||||
@@ -100,6 +102,7 @@ public class ResultDeleteAction extends AbstractAction {
|
||||
}
|
||||
|
||||
//TODO should be moved to SleuthkitCase and BlackboardArtifact API
|
||||
@SuppressWarnings("deprecation")
|
||||
private static void deleteArtifact(BlackboardArtifact art) {
|
||||
final SleuthkitCase skCase = Case.getCurrentCase().getSleuthkitCase();
|
||||
final long artId = art.getArtifactID();
|
||||
@@ -117,15 +120,17 @@ public class ResultDeleteAction extends AbstractAction {
|
||||
}
|
||||
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
private static void deleteArtifactsByAttributeValue(BlackboardArtifact.ARTIFACT_TYPE artType,
|
||||
BlackboardAttribute.ATTRIBUTE_TYPE attrType, String value) {
|
||||
|
||||
final SleuthkitCase skCase = Case.getCurrentCase().getSleuthkitCase();
|
||||
ResultSet rs = null;
|
||||
try {
|
||||
//first to select to get artifact ids to delete
|
||||
//then join delete attrs
|
||||
//then delete arts by id
|
||||
ResultSet rs = skCase.runQuery("DELETE FROM blackboard_attributes WHERE artifact_id IN "
|
||||
rs = skCase.runQuery("DELETE FROM blackboard_attributes WHERE artifact_id IN "
|
||||
+ "(SELECT blackboard_artifacts.artifact_id FROM blackboard_artifacts "
|
||||
+ "INNER JOIN blackboard_attributes ON (blackboard_attributes.artifact_id = blackboard_artifacts.artifact_id) "
|
||||
+ "WHERE blackboard_artifacts.artifact_type_id = "
|
||||
@@ -134,7 +139,7 @@ public class ResultDeleteAction extends AbstractAction {
|
||||
+ " AND blackboard_attributes.value_type = " + BlackboardAttribute.TSK_BLACKBOARD_ATTRIBUTE_VALUE_TYPE.STRING.getType()
|
||||
+ " AND blackboard_attributes.value_text = '" + value + "'"
|
||||
+ ")");
|
||||
skCase.closeRunQuery(rs);
|
||||
|
||||
|
||||
//rs = skCase.runQuery("DELETE from blackboard_artifacts where artifact_type_id = "
|
||||
// + Integer.toString(artType.getTypeID()));
|
||||
@@ -143,10 +148,20 @@ public class ResultDeleteAction extends AbstractAction {
|
||||
} catch (SQLException ex) {
|
||||
logger.log(Level.WARNING, "Could not delete artifacts by type id: " + artType.getTypeID(), ex);
|
||||
}
|
||||
finally {
|
||||
if (rs != null) {
|
||||
try {
|
||||
skCase.closeRunQuery(rs);
|
||||
} catch (SQLException ex) {
|
||||
logger.log(Level.WARNING, "Error closing result set after deleting", ex);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//TODO should be moved to SleuthkitCase
|
||||
@SuppressWarnings("deprecation")
|
||||
private static void deleteArtifacts(BlackboardArtifact.ARTIFACT_TYPE artType) {
|
||||
// SELECT * from blackboard_attributes INNER JOIN blackboard_artifacts ON blackboard_artifacts.artifact_id = blackboard_attributes.artifact_ID AND blackboard_artifacts.artifact_type_id = 9;
|
||||
final SleuthkitCase skCase = Case.getCurrentCase().getSleuthkitCase();
|
||||
|
||||
@@ -0,0 +1,179 @@
|
||||
/*
|
||||
* Autopsy Forensic Browser
|
||||
*
|
||||
* Copyright 2013 Basis Technology Corp.
|
||||
* Contact: carrier <at> sleuthkit <dot> org
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.sleuthkit.autopsy.directorytree;
|
||||
|
||||
import java.awt.event.ActionEvent;
|
||||
import java.awt.event.ActionListener;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import javax.swing.AbstractAction;
|
||||
import javax.swing.JFrame;
|
||||
import javax.swing.JMenu;
|
||||
import javax.swing.JMenuItem;
|
||||
import javax.swing.JOptionPane;
|
||||
import org.openide.nodes.Node;
|
||||
import org.openide.util.actions.Presenter;
|
||||
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||
import org.sleuthkit.autopsy.datamodel.Bookmarks;
|
||||
import org.sleuthkit.autopsy.datamodel.ContentUtils;
|
||||
import org.sleuthkit.autopsy.datamodel.Tags;
|
||||
import org.sleuthkit.datamodel.AbstractFile;
|
||||
import org.sleuthkit.datamodel.BlackboardArtifact;
|
||||
import org.sleuthkit.datamodel.Content;
|
||||
import org.sleuthkit.datamodel.ContentVisitor;
|
||||
import org.sleuthkit.datamodel.Directory;
|
||||
|
||||
/**
|
||||
* Action on a file or artifact that bookmarks a file and/or artifact
|
||||
* and reloads the bookmark view.
|
||||
* Supports bookmarking of a fs file, directory and layout file and layout
|
||||
* directory (virtual files/dirs for unalloc content)
|
||||
*
|
||||
* TODO add use enters description and hierarchy (TSK_TAG_NAME with slashes)
|
||||
*/
|
||||
public class TagFileAction extends AbstractAction implements Presenter.Popup {
|
||||
|
||||
private static final Logger logger = Logger.getLogger(TagFileAction.class.getName());
|
||||
//content to bookmark
|
||||
private AbstractFile tagFile;
|
||||
private final InitializeBookmarkFileV initializer = new InitializeBookmarkFileV();
|
||||
|
||||
public TagFileAction(Node contentNode) {
|
||||
Content content = contentNode.getLookup().lookup(Content.class);
|
||||
tagFile = content.accept(initializer);
|
||||
}
|
||||
|
||||
public TagFileAction(Content content) {
|
||||
tagFile = content.accept(initializer);
|
||||
}
|
||||
|
||||
private String getComment() {
|
||||
String comment = JOptionPane.showInputDialog(null,
|
||||
"Please enter a comment for the tag (optional):",
|
||||
"Tag Comment",
|
||||
JOptionPane.PLAIN_MESSAGE);
|
||||
if(comment == null || comment.isEmpty()) {
|
||||
comment = "No Comment";
|
||||
}
|
||||
return comment;
|
||||
}
|
||||
|
||||
private void refreshDirectoryTree() {
|
||||
DirectoryTreeTopComponent viewer = DirectoryTreeTopComponent.findInstance();
|
||||
viewer.refreshTree(BlackboardArtifact.ARTIFACT_TYPE.TSK_TAG_FILE);
|
||||
viewer.refreshTree(BlackboardArtifact.ARTIFACT_TYPE.TSK_TAG_ARTIFACT);
|
||||
}
|
||||
|
||||
@Override
|
||||
public JMenuItem getPopupPresenter() {
|
||||
JMenu result = new JMenu("Tag File");
|
||||
|
||||
JMenuItem contentItem = new JMenuItem("Bookmark File");
|
||||
contentItem.addActionListener(new ActionListener() {
|
||||
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
Tags.createBookmark(tagFile, getComment());
|
||||
refreshDirectoryTree();
|
||||
}
|
||||
|
||||
});
|
||||
result.add(contentItem);
|
||||
result.addSeparator();
|
||||
|
||||
JMenuItem newTagItem = new JMenuItem("Create a new tag");
|
||||
newTagItem.addActionListener(new ActionListener() {
|
||||
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
Map<String, String> tagMap = new CreateTagDialog(new JFrame(), true).display();
|
||||
if (tagMap != null) {
|
||||
Tags.createTag(tagFile, tagMap.get("Name"), tagMap.get("Comment"));
|
||||
refreshDirectoryTree();
|
||||
}
|
||||
}
|
||||
|
||||
});
|
||||
result.add(newTagItem);
|
||||
result.addSeparator();
|
||||
|
||||
List<String> tagNames = Tags.getTagNames();
|
||||
if (tagNames.isEmpty()) {
|
||||
JMenuItem empty = new JMenuItem("No tags");
|
||||
empty.setEnabled(false);
|
||||
result.add(empty);
|
||||
} else {
|
||||
for (final String tagName : tagNames) {
|
||||
if (tagName.equals(Bookmarks.BOOKMARK_TAG_NAME)) {
|
||||
continue;
|
||||
}
|
||||
JMenuItem tagItem = new JMenuItem(tagName);
|
||||
tagItem.addActionListener(new ActionListener() {
|
||||
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
Tags.createTag(tagFile, tagName, getComment());
|
||||
refreshDirectoryTree();
|
||||
}
|
||||
|
||||
});
|
||||
result.add(tagItem);
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the FsContent if it is supported, otherwise null
|
||||
*/
|
||||
private static class InitializeBookmarkFileV extends ContentVisitor.Default<AbstractFile> {
|
||||
|
||||
@Override
|
||||
public AbstractFile visit(org.sleuthkit.datamodel.File f) {
|
||||
return f;
|
||||
}
|
||||
|
||||
@Override
|
||||
public AbstractFile visit(org.sleuthkit.datamodel.LayoutFile lf) {
|
||||
return lf;
|
||||
}
|
||||
|
||||
@Override
|
||||
public AbstractFile visit(org.sleuthkit.datamodel.VirtualDirectory ld) {
|
||||
return ld;
|
||||
}
|
||||
|
||||
@Override
|
||||
public AbstractFile visit(Directory dir) {
|
||||
return ContentUtils.isDotDirectory(dir) ? null : dir;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected AbstractFile defaultVisit(Content cntnt) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
// Do nothing - this action should never be performed
|
||||
// Submenu actions are invoked instead
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,136 @@
|
||||
/*
|
||||
* Autopsy Forensic Browser
|
||||
*
|
||||
* Copyright 2013 Basis Technology Corp.
|
||||
* Contact: carrier <at> sleuthkit <dot> org
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.sleuthkit.autopsy.directorytree;
|
||||
|
||||
import java.awt.event.ActionEvent;
|
||||
import java.awt.event.ActionListener;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import javax.swing.AbstractAction;
|
||||
import javax.swing.JFrame;
|
||||
import javax.swing.JMenu;
|
||||
import javax.swing.JMenuItem;
|
||||
import javax.swing.JOptionPane;
|
||||
import org.openide.util.actions.Presenter;
|
||||
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||
import org.sleuthkit.autopsy.datamodel.Bookmarks;
|
||||
import org.sleuthkit.autopsy.datamodel.Tags;
|
||||
import org.sleuthkit.datamodel.BlackboardArtifact;
|
||||
|
||||
/**
|
||||
* Action on a file or artifact that bookmarks a file and/or artifact
|
||||
* and reloads the bookmark view.
|
||||
* Supports bookmarking of a fs file, directory and layout file and layout
|
||||
* directory (virtual files/dirs for unalloc content)
|
||||
*
|
||||
* TODO add use enters description and hierarchy (TSK_TAG_NAME with slashes)
|
||||
*/
|
||||
public class TagResultAction extends AbstractAction implements Presenter.Popup {
|
||||
|
||||
private static final Logger logger = Logger.getLogger(TagFileAction.class.getName());
|
||||
//content to bookmark
|
||||
private BlackboardArtifact tagArtifact;
|
||||
|
||||
public TagResultAction(BlackboardArtifact artifact) {
|
||||
tagArtifact = artifact;
|
||||
}
|
||||
|
||||
private String getComment() {
|
||||
String comment = JOptionPane.showInputDialog(null,
|
||||
"Please enter a comment for the tag (optional):",
|
||||
"Tag Comment",
|
||||
JOptionPane.PLAIN_MESSAGE);
|
||||
if(comment == null || comment.isEmpty()) {
|
||||
comment = "No Comment";
|
||||
}
|
||||
return comment;
|
||||
}
|
||||
|
||||
private void refreshDirectoryTree() {
|
||||
DirectoryTreeTopComponent viewer = DirectoryTreeTopComponent.findInstance();
|
||||
viewer.refreshTree(BlackboardArtifact.ARTIFACT_TYPE.TSK_TAG_FILE);
|
||||
viewer.refreshTree(BlackboardArtifact.ARTIFACT_TYPE.TSK_TAG_ARTIFACT);
|
||||
}
|
||||
|
||||
@Override
|
||||
public JMenuItem getPopupPresenter() {
|
||||
JMenu result = new JMenu("Tag Result");
|
||||
|
||||
JMenuItem contentItem = new JMenuItem("Bookmark Result");
|
||||
contentItem.addActionListener(new ActionListener() {
|
||||
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
Tags.createBookmark(tagArtifact, getComment());
|
||||
refreshDirectoryTree();
|
||||
}
|
||||
|
||||
});
|
||||
result.add(contentItem);
|
||||
result.addSeparator();
|
||||
|
||||
JMenuItem newTagItem = new JMenuItem("Create a new tag");
|
||||
newTagItem.addActionListener(new ActionListener() {
|
||||
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
Map<String, String> tagMap = new CreateTagDialog(new JFrame(), true).display();
|
||||
if (tagMap != null) {
|
||||
Tags.createTag(tagArtifact, tagMap.get("Name"), tagMap.get("Comment"));
|
||||
refreshDirectoryTree();
|
||||
}
|
||||
}
|
||||
|
||||
});
|
||||
result.add(newTagItem);
|
||||
result.addSeparator();
|
||||
|
||||
List<String> tagNames = Tags.getTagNames();
|
||||
if (tagNames.isEmpty()) {
|
||||
JMenuItem empty = new JMenuItem("No tags");
|
||||
empty.setEnabled(false);
|
||||
result.add(empty);
|
||||
} else {
|
||||
for (final String tagName : Tags.getTagNames()) {
|
||||
if (tagName.equals(Bookmarks.BOOKMARK_TAG_NAME)) {
|
||||
continue;
|
||||
}
|
||||
JMenuItem tagItem = new JMenuItem(tagName);
|
||||
tagItem.addActionListener(new ActionListener() {
|
||||
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
Tags.createTag(tagArtifact, tagName, getComment());
|
||||
refreshDirectoryTree();
|
||||
}
|
||||
|
||||
});
|
||||
result.add(tagItem);
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
// Do nothing - this action should never be performed
|
||||
// Submenu actions are invoked instead
|
||||
}
|
||||
}
|
||||
@@ -153,6 +153,7 @@ public class FileSearchPanel extends javax.swing.JPanel {
|
||||
* Action when the "Search" button is pressed.
|
||||
*
|
||||
*/
|
||||
@SuppressWarnings("deprecation")
|
||||
private void search() {
|
||||
// change the cursor to "waiting cursor" for this operation
|
||||
this.setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
|
||||
@@ -170,16 +171,12 @@ public class FileSearchPanel extends javax.swing.JPanel {
|
||||
SleuthkitCase tempDb = currentCase.getSleuthkitCase();
|
||||
ResultSet rs = tempDb.runQuery(this.getQuery("count(*) as TotalMatches"));
|
||||
totalMatches = totalMatches + rs.getInt("TotalMatches");
|
||||
Statement s = rs.getStatement();
|
||||
rs.close();
|
||||
if (s != null)
|
||||
s.close();
|
||||
tempDb.closeRunQuery(rs);
|
||||
|
||||
rs = tempDb.runQuery(this.getQuery(null));
|
||||
currentDbList = tempDb.resultSetToFsContents(rs);
|
||||
s = rs.getStatement();
|
||||
rs.close();
|
||||
if (s != null)
|
||||
s.close();
|
||||
tempDb.closeRunQuery(rs);
|
||||
|
||||
fsContentList.addAll(currentDbList);
|
||||
} catch (SQLException ex) {
|
||||
Logger logger = Logger.getLogger(this.getClass().getName());
|
||||
|
||||
@@ -150,6 +150,7 @@ public final class FileSearchTopComponent extends TopComponent implements DataEx
|
||||
* Action when the "Search" button is pressed.
|
||||
*
|
||||
*/
|
||||
@SuppressWarnings("deprecation")
|
||||
private void search() {
|
||||
// change the cursor to "waiting cursor" for this operation
|
||||
this.setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
|
||||
@@ -167,16 +168,12 @@ public final class FileSearchTopComponent extends TopComponent implements DataEx
|
||||
SleuthkitCase tempDb = currentCase.getSleuthkitCase();
|
||||
ResultSet rs = tempDb.runQuery(this.getQuery("count(*) as TotalMatches"));
|
||||
totalMatches = totalMatches + rs.getInt("TotalMatches");
|
||||
Statement s = rs.getStatement();
|
||||
rs.close();
|
||||
if (s != null)
|
||||
s.close();
|
||||
tempDb.closeRunQuery(rs);
|
||||
|
||||
rs = tempDb.runQuery(this.getQuery(null));
|
||||
currentDbList = tempDb.resultSetToFsContents(rs);
|
||||
s = rs.getStatement();
|
||||
rs.close();
|
||||
if (s != null)
|
||||
s.close();
|
||||
tempDb.closeRunQuery(rs);
|
||||
|
||||
fsContentList.addAll(currentDbList);
|
||||
} catch (SQLException ex) {
|
||||
Logger logger = Logger.getLogger(this.getClass().getName());
|
||||
|
||||
Binary file not shown.
|
After Width: | Height: | Size: 619 B |
Binary file not shown.
|
After Width: | Height: | Size: 791 B |
Binary file not shown.
|
After Width: | Height: | Size: 867 B |
@@ -690,7 +690,16 @@ public class IngestManager {
|
||||
sb.append("Errors per module:");
|
||||
for (IngestModuleAbstract module : errors.keySet()) {
|
||||
final int errorsModule = errors.get(module);
|
||||
sb.append("\t").append(module.getName()).append(": ").append(errorsModule).append(EOL);
|
||||
String moduleName;
|
||||
if (module != null) {
|
||||
moduleName = module.getName();
|
||||
}
|
||||
else {
|
||||
//manager message
|
||||
moduleName = "System";
|
||||
}
|
||||
|
||||
sb.append("\t").append(moduleName).append(": ").append(errorsModule).append(EOL);
|
||||
}
|
||||
}
|
||||
return sb.toString();
|
||||
|
||||
@@ -241,4 +241,8 @@ public class IngestMessage {
|
||||
static IngestMessage createManagerMessage(String subject, String detailsHtml) {
|
||||
return new IngestMessage(++managerMessageId, MessageType.INFO, null, subject, detailsHtml, null);
|
||||
}
|
||||
|
||||
static IngestMessage createManagerErrorMessage(String subject, String detailsHtml) {
|
||||
return new IngestMessage(++managerMessageId, MessageType.ERROR, null, subject, detailsHtml, null);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -18,10 +18,14 @@
|
||||
*/
|
||||
package org.sleuthkit.autopsy.ingest;
|
||||
|
||||
import java.awt.event.ActionEvent;
|
||||
import java.awt.event.ActionListener;
|
||||
import java.beans.PropertyChangeEvent;
|
||||
import java.beans.PropertyChangeListener;
|
||||
import java.util.List;
|
||||
import java.util.logging.Level;
|
||||
import java.util.regex.Matcher;
|
||||
import java.util.regex.Pattern;
|
||||
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||
import javax.swing.Action;
|
||||
import javax.swing.BoxLayout;
|
||||
@@ -33,6 +37,8 @@ import org.openide.windows.Mode;
|
||||
import org.openide.windows.TopComponent;
|
||||
import org.openide.windows.WindowManager;
|
||||
import org.sleuthkit.autopsy.casemodule.Case;
|
||||
import org.sleuthkit.autopsy.coreutils.MessageNotifyUtil;
|
||||
import org.sleuthkit.autopsy.ingest.IngestMessage.MessageType;
|
||||
import org.sleuthkit.datamodel.Image;
|
||||
|
||||
/**
|
||||
@@ -45,6 +51,8 @@ public final class IngestMessageTopComponent extends TopComponent implements Ing
|
||||
private IngestMessageMainPanel messagePanel;
|
||||
private IngestManager manager;
|
||||
private static String PREFERRED_ID = "IngestMessageTopComponent";
|
||||
private ActionListener showIngestInboxAction;
|
||||
private static final Pattern tagRemove = Pattern.compile("<.+?>");
|
||||
|
||||
public IngestMessageTopComponent() {
|
||||
initComponents();
|
||||
@@ -54,6 +62,13 @@ public final class IngestMessageTopComponent extends TopComponent implements Ing
|
||||
setToolTipText(NbBundle.getMessage(IngestMessageTopComponent.class, "HINT_IngestMessageTopComponent"));
|
||||
//putClientProperty(TopComponent.PROP_CLOSING_DISABLED, Boolean.TRUE);
|
||||
|
||||
showIngestInboxAction = new ActionListener() {
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
IngestMessagesToolbar.getDefault().showIngestMessages();
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
private static synchronized IngestMessageTopComponent getDefault() {
|
||||
@@ -79,13 +94,11 @@ public final class IngestMessageTopComponent extends TopComponent implements Ing
|
||||
protected String preferredID() {
|
||||
return PREFERRED_ID;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/** This method is called from within the constructor to
|
||||
* initialize the form.
|
||||
* WARNING: Do NOT modify this code. The content of this method is
|
||||
* always regenerated by the Form Editor.
|
||||
/**
|
||||
* This method is called from within the constructor to initialize the form.
|
||||
* WARNING: Do NOT modify this code. The content of this method is always
|
||||
* regenerated by the Form Editor.
|
||||
*/
|
||||
// <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
|
||||
private void initComponents() {
|
||||
@@ -124,11 +137,11 @@ public final class IngestMessageTopComponent extends TopComponent implements Ing
|
||||
super.componentClosed();
|
||||
|
||||
/*
|
||||
Mode mode = WindowManager.getDefault().findMode("dockedBottom");
|
||||
if (mode != null) {
|
||||
mode.dockInto(this);
|
||||
this.open();
|
||||
}
|
||||
Mode mode = WindowManager.getDefault().findMode("dockedBottom");
|
||||
if (mode != null) {
|
||||
mode.dockInto(this);
|
||||
this.open();
|
||||
}
|
||||
* */
|
||||
|
||||
//this.close();
|
||||
@@ -204,7 +217,6 @@ public final class IngestMessageTopComponent extends TopComponent implements Ing
|
||||
private void registerListeners() {
|
||||
//handle case change
|
||||
Case.addPropertyChangeListener(new PropertyChangeListener() {
|
||||
|
||||
@Override
|
||||
public void propertyChange(PropertyChangeEvent evt) {
|
||||
if (evt.getPropertyName().equals(Case.CASE_CURRENT_CASE)) {
|
||||
@@ -219,8 +231,7 @@ public final class IngestMessageTopComponent extends TopComponent implements Ing
|
||||
}
|
||||
try {
|
||||
manager.stopAll();
|
||||
}
|
||||
finally {
|
||||
} finally {
|
||||
//clear inbox
|
||||
clearMessages();
|
||||
}
|
||||
@@ -257,7 +268,7 @@ public final class IngestMessageTopComponent extends TopComponent implements Ing
|
||||
|
||||
final String reportActionName = "org.sleuthkit.autopsy.report.ReportAction";
|
||||
Action reportAction = null;
|
||||
|
||||
|
||||
//find action by name from action lookup, without introducing cyclic dependency
|
||||
if (choice == JOptionPane.NO_OPTION) {
|
||||
List<? extends Action> actions = Utilities.actionsForPath("Toolbars/File");
|
||||
@@ -270,11 +281,13 @@ public final class IngestMessageTopComponent extends TopComponent implements Ing
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (reportAction == null)
|
||||
|
||||
if (reportAction == null) {
|
||||
logger.log(Level.SEVERE, "Could not locate Action: " + reportActionName);
|
||||
else reportAction.actionPerformed(null);
|
||||
|
||||
} else {
|
||||
reportAction.actionPerformed(null);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -285,6 +298,28 @@ public final class IngestMessageTopComponent extends TopComponent implements Ing
|
||||
@Override
|
||||
public void displayMessage(IngestMessage ingestMessage) {
|
||||
messagePanel.addMessage(ingestMessage);
|
||||
|
||||
|
||||
//post special messages to notification area
|
||||
MessageType ingestMessageType = ingestMessage.getMessageType();
|
||||
if (ingestMessageType.equals(MessageType.ERROR)
|
||||
|| ingestMessageType.equals(MessageType.WARNING)) {
|
||||
MessageNotifyUtil.MessageType notifyMessageType =
|
||||
ingestMessageType.equals(MessageType.ERROR)
|
||||
? MessageNotifyUtil.MessageType.ERROR
|
||||
: MessageNotifyUtil.MessageType.WARNING;
|
||||
|
||||
String subject = ingestMessage.getSubject();
|
||||
String details = ingestMessage.getDetails();
|
||||
if (details == null) {
|
||||
details = "";
|
||||
}
|
||||
//strip html tags in case they are present in ingest message
|
||||
details = stripHtmlTags(details);
|
||||
|
||||
MessageNotifyUtil.Notify.show(subject, details,
|
||||
notifyMessageType, showIngestInboxAction);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -292,8 +327,6 @@ public final class IngestMessageTopComponent extends TopComponent implements Ing
|
||||
return messagePanel.getMessagesCount();
|
||||
}
|
||||
|
||||
|
||||
|
||||
@Override
|
||||
public void clearMessages() {
|
||||
messagePanel.clearMessages();
|
||||
@@ -302,9 +335,9 @@ public final class IngestMessageTopComponent extends TopComponent implements Ing
|
||||
@Override
|
||||
public void displayIngestDialog(final Image image) {
|
||||
/*
|
||||
final IngestDialog ingestDialog = new IngestDialog();
|
||||
ingestDialog.setImage(image);
|
||||
ingestDialog.display();
|
||||
final IngestDialog ingestDialog = new IngestDialog();
|
||||
ingestDialog.setImage(image);
|
||||
ingestDialog.display();
|
||||
*/
|
||||
}
|
||||
|
||||
@@ -318,4 +351,13 @@ public final class IngestMessageTopComponent extends TopComponent implements Ing
|
||||
//disable TC toolbar actions
|
||||
return new Action[0];
|
||||
}
|
||||
|
||||
private static String stripHtmlTags(String string) {
|
||||
if (string == null || string.length() == 0) {
|
||||
return string;
|
||||
}
|
||||
|
||||
Matcher m = tagRemove.matcher(string);
|
||||
return m.replaceAll("");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -130,7 +130,10 @@ public class IngestMessagesToolbar extends javax.swing.JPanel {
|
||||
});
|
||||
}
|
||||
|
||||
private void showIngestMessages() {
|
||||
/**
|
||||
* Pop up and show ingest messages window
|
||||
*/
|
||||
void showIngestMessages() {
|
||||
IngestMessageTopComponent tc = IngestMessageTopComponent.findInstance();
|
||||
|
||||
Mode mode = WindowManager.getDefault().findMode("floatingLeftBottom");
|
||||
|
||||
@@ -118,7 +118,10 @@ public class IngestMonitor {
|
||||
final String diskPath = root.getAbsolutePath();
|
||||
logger.log(Level.SEVERE, "Stopping ingest due to low disk space on disk " + diskPath);
|
||||
manager.stopAll();
|
||||
manager.postMessage(IngestMessage.createManagerMessage("Stopping ingest due to low disk space on disk " + diskPath, "Stopping ingest due to low disk space on disk " + diskPath + ". Please ensure the drive where Case is located has at least 1GB free space (more for large images) and restart ingest."));
|
||||
manager.postMessage(IngestMessage.createManagerErrorMessage
|
||||
("Ingest stopped - low disk space on " + diskPath,
|
||||
"Stopping ingest due to low disk space on disk " + diskPath
|
||||
+ ". \nEnsure the Case drive has at least 1GB free space and restart ingest."));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -123,6 +123,7 @@ public class ReportExcel implements TableReportModule {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Start a new sheet for the given data type.
|
||||
@@ -130,6 +131,7 @@ public class ReportExcel implements TableReportModule {
|
||||
*/
|
||||
@Override
|
||||
public void startDataType(String title) {
|
||||
title = escapeForExcel(title);
|
||||
sheet = wb.createSheet(title);
|
||||
sheet.setAutobreaks(true);
|
||||
currentDataType = title;
|
||||
@@ -154,6 +156,7 @@ public class ReportExcel implements TableReportModule {
|
||||
*/
|
||||
@Override
|
||||
public void startSet(String setName) {
|
||||
setName = escapeForExcel(setName);
|
||||
Row temp = sheet.createRow(rowCount);
|
||||
temp.setRowStyle(setStyle);
|
||||
temp.createCell(0).setCellValue(setName);
|
||||
@@ -179,6 +182,7 @@ public class ReportExcel implements TableReportModule {
|
||||
*/
|
||||
@Override
|
||||
public void addSetElement(String elementName) {
|
||||
elementName = escapeForExcel(elementName);
|
||||
Row temp = sheet.createRow(rowCount);
|
||||
temp.setRowStyle(elementStyle);
|
||||
temp.createCell(0).setCellValue(elementName);
|
||||
@@ -248,4 +252,13 @@ public class ReportExcel implements TableReportModule {
|
||||
return "Excel.xlsx";
|
||||
}
|
||||
|
||||
/**
|
||||
* Escape special chars for Excel that would cause errors/hangs in generating report
|
||||
* The following are not valid for sheet names: ? / \ * :
|
||||
* @param text
|
||||
* @return
|
||||
*/
|
||||
private static String escapeForExcel(String text) {
|
||||
return text.replaceAll("[\\/\\:\\?\\*\\\\]", "_");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -98,7 +98,6 @@ public class ReportHTML implements TableReportModule {
|
||||
* Start this report by setting the path, refreshing member variables,
|
||||
* and writing the skeleton for the HTML report.
|
||||
* @param path path to save the report
|
||||
* @param info map of info to display in the summary
|
||||
*/
|
||||
@Override
|
||||
public void startReport(String path) {
|
||||
@@ -140,9 +139,12 @@ public class ReportHTML implements TableReportModule {
|
||||
*/
|
||||
@Override
|
||||
public void startDataType(String title) {
|
||||
String fTitle = org.sleuthkit.autopsy.coreutils.FileUtil.escapeFileName(title);
|
||||
// Make a new out for this page
|
||||
try {
|
||||
out = new BufferedWriter(new OutputStreamWriter(new FileOutputStream(path + title + getExtension()), "UTF-8"));
|
||||
//escape out slashes tha that appear in title
|
||||
|
||||
out = new BufferedWriter(new OutputStreamWriter(new FileOutputStream(path + fTitle + getExtension()), "UTF-8"));
|
||||
} catch (FileNotFoundException ex) {
|
||||
logger.log(Level.SEVERE, "File not found: {0}", ex);
|
||||
} catch (UnsupportedEncodingException ex) {
|
||||
@@ -425,7 +427,12 @@ public class ReportHTML implements TableReportModule {
|
||||
nav.append("<li style=\"background: url(summary.png) left center no-repeat;\"><a href=\"summary.html\" target=\"content\">Case Summary</a></li>\n");
|
||||
|
||||
for (String dataType : dataTypes.keySet()) {
|
||||
nav.append("<li style=\"background: url('").append(dataType).append(".png') left center no-repeat;\"><a href=\"").append(dataType).append(".html\" target=\"content\">").append(dataType).append(" (").append(dataTypes.get(dataType)).append(")</a></li>\n");
|
||||
String dataTypeEsc = org.sleuthkit.autopsy.coreutils.FileUtil.escapeFileName(dataType);
|
||||
nav.append("<li style=\"background: url('").append(dataType)
|
||||
.append(".png') left center no-repeat;\"><a href=\"")
|
||||
.append(dataTypeEsc).append(".html\" target=\"content\">")
|
||||
.append(dataType).append(" (").append(dataTypes.get(dataType))
|
||||
.append(")</a></li>\n");
|
||||
}
|
||||
nav.append("</ul>\n");
|
||||
nav.append("</div>\n</body>\n</html>");
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
Manifest-Version: 1.0
|
||||
AutoUpdate-Show-In-Client: true
|
||||
OpenIDE-Module: org.sleuthkit.autopsy.exifparser/3
|
||||
OpenIDE-Module-Implementation-Version: 3
|
||||
OpenIDE-Module-Implementation-Version: 4
|
||||
OpenIDE-Module-Layer: org/sleuthkit/autopsy/exifparser/layer.xml
|
||||
OpenIDE-Module-Localizing-Bundle: org/sleuthkit/autopsy/exifparser/Bundle.properties
|
||||
|
||||
@@ -11,8 +11,8 @@
|
||||
<build-prerequisite/>
|
||||
<compile-dependency/>
|
||||
<run-dependency>
|
||||
<release-version>5</release-version>
|
||||
<specification-version>3.0</specification-version>
|
||||
<release-version>6</release-version>
|
||||
<specification-version>4.0</specification-version>
|
||||
</run-dependency>
|
||||
</dependency>
|
||||
</module-dependencies>
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
Manifest-Version: 1.0
|
||||
AutoUpdate-Show-In-Client: true
|
||||
OpenIDE-Module: org.sleuthkit.autopsy.hashdatabase/3
|
||||
OpenIDE-Module-Implementation-Version: 3
|
||||
OpenIDE-Module-Implementation-Version: 4
|
||||
OpenIDE-Module-Layer: org/sleuthkit/autopsy/hashdatabase/layer.xml
|
||||
OpenIDE-Module-Localizing-Bundle: org/sleuthkit/autopsy/hashdatabase/Bundle.properties
|
||||
|
||||
|
||||
@@ -77,8 +77,8 @@
|
||||
<build-prerequisite/>
|
||||
<compile-dependency/>
|
||||
<run-dependency>
|
||||
<release-version>5</release-version>
|
||||
<specification-version>3.0</specification-version>
|
||||
<release-version>6</release-version>
|
||||
<specification-version>4.0</specification-version>
|
||||
</run-dependency>
|
||||
</dependency>
|
||||
</module-dependencies>
|
||||
|
||||
@@ -1,6 +1,20 @@
|
||||
/*
|
||||
* To change this template, choose Tools | Templates
|
||||
* and open the template in the editor.
|
||||
* Autopsy Forensic Browser
|
||||
*
|
||||
* Copyright 2011 Basis Technology Corp.
|
||||
* Contact: carrier <at> sleuthkit <dot> org
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.sleuthkit.autopsy.hashdatabase;
|
||||
|
||||
@@ -13,7 +27,7 @@ import org.openide.util.lookup.Lookups;
|
||||
import org.sleuthkit.autopsy.datamodel.DirectoryNode;
|
||||
import org.sleuthkit.autopsy.datamodel.FileNode;
|
||||
import org.sleuthkit.autopsy.datamodel.KeyValueNode;
|
||||
import org.sleuthkit.autopsy.directorytree.BookmarkAction;
|
||||
import org.sleuthkit.autopsy.directorytree.TagFileAction;
|
||||
import org.sleuthkit.autopsy.directorytree.ExternalViewerAction;
|
||||
import org.sleuthkit.autopsy.directorytree.ExtractAction;
|
||||
import org.sleuthkit.autopsy.directorytree.HashSearchAction;
|
||||
@@ -75,7 +89,7 @@ public class KeyValueFileNode extends KeyValueNode {
|
||||
actions.add(new ExtractAction("Extract File", new FileNode(f)));
|
||||
actions.add(new HashSearchAction("Search for files with the same MD5 hash", new FileNode(f)));
|
||||
actions.add(null); // creates a menu separator
|
||||
actions.add(new BookmarkAction("Bookmark File", new FileNode(f)));
|
||||
actions.add(new TagFileAction(new FileNode(f)));
|
||||
return actions;
|
||||
}
|
||||
|
||||
|
||||
@@ -17,9 +17,14 @@
|
||||
<dependency conf="autopsy->*" org="org.apache.solr" name="solr-solrj" rev="4.0.0"/>
|
||||
<dependency conf="autopsy->*" org="commons-lang" name="commons-lang" rev="2.4"/>
|
||||
<dependency conf="autopsy->*" org="org.apache.tika" name="tika-parsers" rev="1.2"/>
|
||||
<!-- icu4j for pdfbox bidirectional text support, needs to be defined explicitely (it is optional) -->
|
||||
<dependency conf="autopsy->*" org="com.ibm.icu" name="icu4j" rev="3.8"/>
|
||||
|
||||
<!-- TODO update jetty to eclipse.jetty 8 -->
|
||||
<dependency conf="start-solr->default" org="org.mortbay.jetty" name="start" rev="6.1.26"/>
|
||||
<dependency conf="jetty-libs->default" org="org.mortbay.jetty" name="jetty" rev="6.1.26"/>
|
||||
<dependency conf="jetty-libs->default" org="org.mortbay.jetty" name="jsp-2.1" rev="6.1.14"/>
|
||||
|
||||
<dependency conf="autopsy->*" org="net.htmlparser.jericho" name="jericho-html" rev="3.3"/>
|
||||
</dependencies>
|
||||
</ivy-module>
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
Manifest-Version: 1.0
|
||||
AutoUpdate-Show-In-Client: true
|
||||
OpenIDE-Module: org.sleuthkit.autopsy.keywordsearch/4
|
||||
OpenIDE-Module-Implementation-Version: 3
|
||||
OpenIDE-Module-Implementation-Version: 4
|
||||
OpenIDE-Module-Install: org/sleuthkit/autopsy/keywordsearch/Installer.class
|
||||
OpenIDE-Module-Layer: org/sleuthkit/autopsy/keywordsearch/layer.xml
|
||||
OpenIDE-Module-Localizing-Bundle: org/sleuthkit/autopsy/keywordsearch/Bundle.properties
|
||||
|
||||
@@ -3,4 +3,4 @@ javac.compilerargs=-Xlint -Xlint:-serial
|
||||
license.file=../LICENSE-2.0.txt
|
||||
nbm.homepage=http://www.sleuthkit.org/autopsy/
|
||||
nbm.needs.restart=true
|
||||
spec.version.base=2.0
|
||||
spec.version.base=2.1
|
||||
|
||||
@@ -95,8 +95,8 @@
|
||||
<build-prerequisite/>
|
||||
<compile-dependency/>
|
||||
<run-dependency>
|
||||
<release-version>5</release-version>
|
||||
<specification-version>3.0</specification-version>
|
||||
<release-version>6</release-version>
|
||||
<specification-version>4.0</specification-version>
|
||||
</run-dependency>
|
||||
</dependency>
|
||||
</module-dependencies>
|
||||
@@ -144,21 +144,29 @@
|
||||
<binary-origin>release/modules/ext/vorbis-java-core-0.1-tests.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/log4j-over-slf4j-1.6.4.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/log4j-over-slf4j-1.6.4.jar</binary-origin>
|
||||
<runtime-relative-path>ext/tika-parsers-1.2-javadoc.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/tika-parsers-1.2-javadoc.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/isoparser-1.0-RC-1.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/isoparser-1.0-RC-1.jar</binary-origin>
|
||||
<runtime-relative-path>ext/log4j-over-slf4j-1.6.4.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/log4j-over-slf4j-1.6.4.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/vorbis-java-tika-0.1.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/vorbis-java-tika-0.1.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/isoparser-1.0-RC-1.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/isoparser-1.0-RC-1.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/httpcore-4.1.4.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/httpcore-4.1.4.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/tika-parsers-1.2-sources.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/tika-parsers-1.2-sources.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/aspectjrt-1.6.11.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/aspectjrt-1.6.11.jar</binary-origin>
|
||||
@@ -187,6 +195,10 @@
|
||||
<runtime-relative-path>ext/httpclient-4.1.3.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/httpclient-4.1.3.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/icu4j-3.8.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/icu4j-3.8.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/juniversalchardet-1.0.3.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/juniversalchardet-1.0.3.jar</binary-origin>
|
||||
@@ -195,6 +207,10 @@
|
||||
<runtime-relative-path>ext/pdfbox-1.7.0.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/pdfbox-1.7.0.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/jericho-html-3.3-sources.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/jericho-html-3.3-sources.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/jdom-1.0.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/jdom-1.0.jar</binary-origin>
|
||||
@@ -227,10 +243,18 @@
|
||||
<runtime-relative-path>ext/slf4j-api-1.7.2.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/slf4j-api-1.7.2.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/commons-lang-2.4-javadoc.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/commons-lang-2.4-javadoc.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/jempbox-1.7.0.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/jempbox-1.7.0.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/jericho-html-3.3-javadoc.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/jericho-html-3.3-javadoc.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/wstx-asl-3.2.7.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/wstx-asl-3.2.7.jar</binary-origin>
|
||||
@@ -239,6 +263,10 @@
|
||||
<runtime-relative-path>ext/netcdf-4.2-min.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/netcdf-4.2-min.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/solr-solrj-4.0.0-javadoc.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/solr-solrj-4.0.0-javadoc.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/xmlbeans-2.3.0.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/xmlbeans-2.3.0.jar</binary-origin>
|
||||
@@ -287,18 +315,26 @@
|
||||
<runtime-relative-path>ext/poi-ooxml-schemas-3.8.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/poi-ooxml-schemas-3.8.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/jericho-html-3.3.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/jericho-html-3.3.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/bcprov-jdk15-1.45.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/bcprov-jdk15-1.45.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/jericho-html-3.3.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/jericho-html-3.3.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/solr-solrj-4.0.0.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/solr-solrj-4.0.0.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/commons-lang-2.4-sources.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/commons-lang-2.4-sources.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/solr-solrj-4.0.0-sources.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/solr-solrj-4.0.0-sources.jar</binary-origin>
|
||||
</class-path-extension>
|
||||
<class-path-extension>
|
||||
<runtime-relative-path>ext/apache-mime4j-dom-0.7.2.jar</runtime-relative-path>
|
||||
<binary-origin>release/modules/ext/apache-mime4j-dom-0.7.2.jar</binary-origin>
|
||||
|
||||
@@ -321,7 +321,7 @@
|
||||
-->
|
||||
<autoCommit>
|
||||
<maxDocs>15000</maxDocs>
|
||||
<openSearcher>false</openSearcher>
|
||||
<openSearcher>true</openSearcher>
|
||||
</autoCommit>
|
||||
|
||||
<!-- softAutoCommit is like autoCommit except it causes a
|
||||
|
||||
@@ -28,7 +28,7 @@ import org.openide.nodes.PropertySupport;
|
||||
import org.openide.nodes.Sheet;
|
||||
import org.openide.util.lookup.Lookups;
|
||||
import org.openide.util.lookup.ProxyLookup;
|
||||
import org.sleuthkit.autopsy.directorytree.BookmarkAction;
|
||||
import org.sleuthkit.autopsy.directorytree.TagFileAction;
|
||||
import org.sleuthkit.autopsy.directorytree.ExternalViewerAction;
|
||||
import org.sleuthkit.autopsy.directorytree.ExtractAction;
|
||||
import org.sleuthkit.autopsy.directorytree.HashSearchAction;
|
||||
@@ -144,7 +144,7 @@ class KeywordSearchFilterNode extends FilterNode {
|
||||
actions.add(new ExtractAction("Extract File", getOriginal()));
|
||||
actions.add(new HashSearchAction("Search for files with the same MD5 hash", getOriginal()));
|
||||
actions.add(null); // creates a menu separator
|
||||
actions.add(new BookmarkAction("Bookmark File", getOriginal()));
|
||||
actions.add(new TagFileAction(getOriginal()));
|
||||
return actions;
|
||||
}
|
||||
|
||||
|
||||
+20
-11
@@ -252,9 +252,9 @@ public final class KeywordSearchIngestModule implements IngestModuleAbstractFile
|
||||
logger.log(Level.WARNING, "Error executing Solr query to check number of indexed files/chunks: ", ex);
|
||||
} catch (KeywordSearchModuleException se) {
|
||||
logger.log(Level.WARNING, "Error executing Solr query to check number of indexed files/chunks: ", se);
|
||||
} finally {
|
||||
cleanup();
|
||||
}
|
||||
|
||||
//cleanup done in final searcher
|
||||
|
||||
//postSummary();
|
||||
}
|
||||
@@ -290,13 +290,13 @@ public final class KeywordSearchIngestModule implements IngestModuleAbstractFile
|
||||
}
|
||||
|
||||
/**
|
||||
* Common cleanup code when module stops or completes
|
||||
* Common cleanup code when module stops or final searcher completes
|
||||
*/
|
||||
private void cleanup() {
|
||||
ingestStatus.clear();
|
||||
currentResults.clear();
|
||||
currentSearcher = null;
|
||||
finalSearcher = null;
|
||||
//finalSearcher = null; //do not collect, might be finalizing
|
||||
|
||||
commitTimer.stop();
|
||||
searchTimer.stop();
|
||||
@@ -888,13 +888,16 @@ public final class KeywordSearchIngestModule implements IngestModuleAbstractFile
|
||||
return null;
|
||||
}
|
||||
|
||||
final String queryStr = keywordQuery.getQuery();
|
||||
final KeywordSearchList list = keywordToList.get(queryStr);
|
||||
final String listName = list.getName();
|
||||
|
||||
//new subProgress will be active after the initial query
|
||||
//when we know number of hits to start() with
|
||||
if (keywordsSearched > 0) {
|
||||
subProgresses[keywordsSearched - 1].finish();
|
||||
}
|
||||
|
||||
final String queryStr = keywordQuery.getQuery();
|
||||
final KeywordSearchList list = keywordToList.get(queryStr);
|
||||
final String listName = list.getName();
|
||||
|
||||
KeywordSearchQuery del = null;
|
||||
|
||||
@@ -1080,11 +1083,14 @@ public final class KeywordSearchIngestModule implements IngestModuleAbstractFile
|
||||
if (!newArtifacts.isEmpty()) {
|
||||
services.fireModuleDataEvent(new ModuleDataEvent(MODULE_NAME, ARTIFACT_TYPE.TSK_KEYWORD_HIT, newArtifacts));
|
||||
}
|
||||
}
|
||||
|
||||
} //if has results
|
||||
|
||||
//reset the status text before it goes away
|
||||
subProgresses[keywordsSearched].progress("");
|
||||
|
||||
++keywordsSearched;
|
||||
|
||||
}
|
||||
} //for each keyword
|
||||
|
||||
} //end try block
|
||||
catch (Exception ex) {
|
||||
@@ -1142,8 +1148,11 @@ public final class KeywordSearchIngestModule implements IngestModuleAbstractFile
|
||||
//this is the final searcher
|
||||
logger.log(Level.INFO, "The final searcher in this ingest done.");
|
||||
finalSearcherDone = true;
|
||||
|
||||
|
||||
services.postMessage(IngestMessage.createMessage(++messageID, MessageType.INFO, KeywordSearchIngestModule.instance, "Completed"));
|
||||
|
||||
//run module cleanup
|
||||
cleanup();
|
||||
} else {
|
||||
//start counting time for a new searcher to start
|
||||
//unless final searcher is pending
|
||||
|
||||
@@ -51,7 +51,7 @@ public class LuceneQuery implements KeywordSearchQuery {
|
||||
private Keyword keywordQuery = null;
|
||||
private KeywordQueryFilter filter = null;
|
||||
private String field = null;
|
||||
private static final int MAX_RESULTS = 10000;
|
||||
private static final int MAX_RESULTS = 20000;
|
||||
static final int SNIPPET_LENGTH = 50;
|
||||
//can use different highlight schema fields for regex and literal search
|
||||
static final String HIGHLIGHT_FIELD_LITERAL = Server.Schema.CONTENT.toString();
|
||||
|
||||
@@ -1,17 +1,31 @@
|
||||
---------------- VERSION 3.0.3 --------------
|
||||
---------------- VERSION Current (development) --------------
|
||||
|
||||
New features:
|
||||
- Results and files can be tagged with custom tags and assigned different categories, and
|
||||
they can be reported on based on those categories.
|
||||
|
||||
Improvements:
|
||||
- Keyword Search indexing and search speed improvements
|
||||
- Improved Keyword Search highlighting in Text View: highlighted tokens are no longer delimiter separated
|
||||
- Better progress updates from Keyword Search ingest
|
||||
- Upgrade to Solr4.0 / Tika 1.2
|
||||
- Better error reporting in the UI using the notification area.
|
||||
|
||||
|
||||
Bugfixes:
|
||||
- fixed crash and hang in html and excel report generation, due to special characters present
|
||||
|
||||
|
||||
---------------- VERSION 3.0.3 --------------
|
||||
|
||||
*Note: Due to major changes in Keyword search module indexing this release is not fully backward compatible.
|
||||
As a workaround, you will need to rebuild index by re-running Keyword Search ingest on Cases created with previous versions.
|
||||
|
||||
Improvements:
|
||||
- Upgrade to Solr4.0 / Tika 1.2: Improved performance and highlighting
|
||||
- Remake of reporting UI and functionality
|
||||
- Significant increase in reporting speed
|
||||
- New option to keep the most specific file viewer (default) or the lastly used viewer active.
|
||||
|
||||
|
||||
Bugfixes:
|
||||
- Keyword search now indexes and searches entire extracted content from files
|
||||
- Fixed bug that caused the ends of large amounts of text to not be indexed (occurs mostly in unallocated space).
|
||||
- Fix scrolling to first keyword hit when Text View is first loaded
|
||||
- Imported keyword lists are now always enabled for ingest by default
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
Manifest-Version: 1.0
|
||||
OpenIDE-Module: org.sleuthkit.autopsy.recentactivity/4
|
||||
OpenIDE-Module-Implementation-Version: 3
|
||||
OpenIDE-Module-Implementation-Version: 4
|
||||
OpenIDE-Module-Layer: org/sleuthkit/autopsy/recentactivity/layer.xml
|
||||
OpenIDE-Module-Localizing-Bundle: org/sleuthkit/autopsy/recentactivity/Bundle.properties
|
||||
OpenIDE-Module-Requires:
|
||||
|
||||
@@ -35,8 +35,8 @@
|
||||
<build-prerequisite/>
|
||||
<compile-dependency/>
|
||||
<run-dependency>
|
||||
<release-version>5</release-version>
|
||||
<specification-version>3.0</specification-version>
|
||||
<release-version>6</release-version>
|
||||
<specification-version>4.0</specification-version>
|
||||
</run-dependency>
|
||||
</dependency>
|
||||
</module-dependencies>
|
||||
|
||||
@@ -58,6 +58,7 @@ abstract public class Extract implements IngestModuleImage{
|
||||
* @param query is a sql string query that is to be run
|
||||
* @return FFSqlitedb is a List of FsContent objects
|
||||
*/
|
||||
@SuppressWarnings("deprecation")
|
||||
public List<FsContent> extractFiles(Image image, String query) {
|
||||
|
||||
Collection<FileSystem> imageFS = tskCase.getFileSystems(image);
|
||||
@@ -78,20 +79,23 @@ abstract public class Extract implements IngestModuleImage{
|
||||
}
|
||||
}
|
||||
List<FsContent> FFSqlitedb = null;
|
||||
ResultSet rs = null;
|
||||
try {
|
||||
ResultSet rs = tskCase.runQuery(query + allFS);
|
||||
rs = tskCase.runQuery(query + allFS);
|
||||
FFSqlitedb = tskCase.resultSetToFsContents(rs);
|
||||
Statement s = rs.getStatement();
|
||||
rs.close();
|
||||
if (s != null) {
|
||||
s.close();
|
||||
}
|
||||
rs.close();
|
||||
rs.getStatement().close();
|
||||
} catch (SQLException ex) {
|
||||
logger.log(Level.SEVERE, "Error while trying to extract files for:" + this.getClass().getName(), ex);
|
||||
this.addErrorMessage(this.getName() + ": Error while trying to extract files to analyze.");
|
||||
}
|
||||
finally {
|
||||
if (rs != null) {
|
||||
try {
|
||||
tskCase.closeRunQuery(rs);
|
||||
} catch (SQLException ex) {
|
||||
logger.log(Level.SEVERE, "Error while trying to close result set after extract files for:" + this.getClass().getName(), ex);
|
||||
}
|
||||
}
|
||||
}
|
||||
return FFSqlitedb;
|
||||
}
|
||||
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
Manifest-Version: 1.0
|
||||
AutoUpdate-Show-In-Client: false
|
||||
OpenIDE-Module: org.sleuthkit.autopsy.testing/3
|
||||
OpenIDE-Module-Implementation-Version: 3
|
||||
OpenIDE-Module-Implementation-Version: 4
|
||||
OpenIDE-Module-Localizing-Bundle: org/sleuthkit/autopsy/testing/Bundle.properties
|
||||
|
||||
|
||||
@@ -11,8 +11,8 @@
|
||||
<build-prerequisite/>
|
||||
<compile-dependency/>
|
||||
<run-dependency>
|
||||
<release-version>5</release-version>
|
||||
<specification-version>3.0</specification-version>
|
||||
<release-version>6</release-version>
|
||||
<specification-version>4.0</specification-version>
|
||||
</run-dependency>
|
||||
</dependency>
|
||||
</module-dependencies>
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
Manifest-Version: 1.0
|
||||
AutoUpdate-Show-In-Client: true
|
||||
OpenIDE-Module: org.sleuthkit.autopsy.thunderbirdparser/3
|
||||
OpenIDE-Module-Implementation-Version: 3
|
||||
OpenIDE-Module-Implementation-Version: 4
|
||||
OpenIDE-Module-Layer: org/sleuthkit/autopsy/thunderbirdparser/layer.xml
|
||||
OpenIDE-Module-Localizing-Bundle: org/sleuthkit/autopsy/thunderbirdparser/Bundle.properties
|
||||
|
||||
|
||||
@@ -11,8 +11,8 @@
|
||||
<build-prerequisite/>
|
||||
<compile-dependency/>
|
||||
<run-dependency>
|
||||
<release-version>5</release-version>
|
||||
<specification-version>3.0</specification-version>
|
||||
<release-version>6</release-version>
|
||||
<specification-version>4.0</specification-version>
|
||||
</run-dependency>
|
||||
</dependency>
|
||||
</module-dependencies>
|
||||
|
||||
Reference in New Issue
Block a user