mirror of
https://github.com/overcuriousity/autopsy-flatpak.git
synced 2025-07-17 18:17:43 +00:00
working through the 3 panel dao and data artifact node
This commit is contained in:
parent
1bf360f2cc
commit
258aaaddfa
@ -18,26 +18,18 @@
|
|||||||
*/
|
*/
|
||||||
package org.sleuthkit.autopsy.datamodel;
|
package org.sleuthkit.autopsy.datamodel;
|
||||||
|
|
||||||
import org.sleuthkit.autopsy.actions.ViewArtifactAction;
|
|
||||||
import org.sleuthkit.autopsy.actions.ViewOsAccountAction;
|
|
||||||
import com.google.common.annotations.Beta;
|
|
||||||
import com.google.common.cache.Cache;
|
|
||||||
import com.google.common.cache.CacheBuilder;
|
|
||||||
import java.beans.PropertyChangeEvent;
|
import java.beans.PropertyChangeEvent;
|
||||||
import java.beans.PropertyChangeListener;
|
import java.beans.PropertyChangeListener;
|
||||||
|
import org.sleuthkit.autopsy.actions.ViewArtifactAction;
|
||||||
|
import org.sleuthkit.autopsy.actions.ViewOsAccountAction;
|
||||||
import java.lang.ref.WeakReference;
|
import java.lang.ref.WeakReference;
|
||||||
import java.text.MessageFormat;
|
import java.text.MessageFormat;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.EnumSet;
|
|
||||||
import java.util.LinkedHashMap;
|
import java.util.LinkedHashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.MissingResourceException;
|
|
||||||
import java.util.Set;
|
|
||||||
import java.util.concurrent.ExecutionException;
|
|
||||||
import java.util.concurrent.TimeUnit;
|
|
||||||
import java.util.logging.Level;
|
import java.util.logging.Level;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
import java.util.stream.Stream;
|
import java.util.stream.Stream;
|
||||||
@ -51,7 +43,6 @@ import org.openide.util.Lookup;
|
|||||||
import org.openide.util.NbBundle;
|
import org.openide.util.NbBundle;
|
||||||
import org.openide.util.NbBundle.Messages;
|
import org.openide.util.NbBundle.Messages;
|
||||||
import org.openide.util.Utilities;
|
import org.openide.util.Utilities;
|
||||||
import org.openide.util.WeakListeners;
|
|
||||||
import org.openide.util.lookup.Lookups;
|
import org.openide.util.lookup.Lookups;
|
||||||
import org.sleuthkit.autopsy.actions.AddBlackboardArtifactTagAction;
|
import org.sleuthkit.autopsy.actions.AddBlackboardArtifactTagAction;
|
||||||
import org.sleuthkit.autopsy.actions.AddContentTagAction;
|
import org.sleuthkit.autopsy.actions.AddContentTagAction;
|
||||||
@ -65,14 +56,9 @@ import org.sleuthkit.autopsy.casemodule.events.CommentChangedEvent;
|
|||||||
import org.sleuthkit.autopsy.casemodule.events.ContentTagAddedEvent;
|
import org.sleuthkit.autopsy.casemodule.events.ContentTagAddedEvent;
|
||||||
import org.sleuthkit.autopsy.casemodule.events.ContentTagDeletedEvent;
|
import org.sleuthkit.autopsy.casemodule.events.ContentTagDeletedEvent;
|
||||||
import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepoDbUtil;
|
import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepoDbUtil;
|
||||||
import org.sleuthkit.autopsy.centralrepository.datamodel.CorrelationAttributeInstance;
|
|
||||||
import org.sleuthkit.autopsy.centralrepository.datamodel.CorrelationAttributeNormalizationException;
|
|
||||||
import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepoException;
|
import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepoException;
|
||||||
import org.sleuthkit.autopsy.core.UserPreferences;
|
import org.sleuthkit.autopsy.core.UserPreferences;
|
||||||
import org.sleuthkit.autopsy.corecomponents.DataResultViewerTable;
|
|
||||||
import org.sleuthkit.autopsy.coreutils.Logger;
|
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||||
import static org.sleuthkit.autopsy.datamodel.DisplayableItemNode.findLinked;
|
|
||||||
import org.sleuthkit.autopsy.corecomponents.DataResultViewerTable.HasCommentStatus;
|
|
||||||
import static org.sleuthkit.autopsy.datamodel.AbstractContentNode.backgroundTasksPool;
|
import static org.sleuthkit.autopsy.datamodel.AbstractContentNode.backgroundTasksPool;
|
||||||
import org.sleuthkit.autopsy.timeline.actions.ViewArtifactInTimelineAction;
|
import org.sleuthkit.autopsy.timeline.actions.ViewArtifactInTimelineAction;
|
||||||
import org.sleuthkit.autopsy.timeline.actions.ViewFileInTimelineAction;
|
import org.sleuthkit.autopsy.timeline.actions.ViewFileInTimelineAction;
|
||||||
@ -82,13 +68,17 @@ import org.sleuthkit.datamodel.BlackboardArtifact.ARTIFACT_TYPE;
|
|||||||
import org.sleuthkit.datamodel.BlackboardAttribute;
|
import org.sleuthkit.datamodel.BlackboardAttribute;
|
||||||
import org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE;
|
import org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE;
|
||||||
import org.sleuthkit.datamodel.Content;
|
import org.sleuthkit.datamodel.Content;
|
||||||
import org.sleuthkit.datamodel.Tag;
|
|
||||||
import org.sleuthkit.datamodel.TskCoreException;
|
import org.sleuthkit.datamodel.TskCoreException;
|
||||||
import org.sleuthkit.autopsy.datamodel.utils.IconsUtil;
|
import org.sleuthkit.autopsy.datamodel.utils.IconsUtil;
|
||||||
import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepository;
|
import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepository;
|
||||||
|
import org.sleuthkit.autopsy.centralrepository.datamodel.CorrelationAttributeInstance;
|
||||||
|
import org.sleuthkit.autopsy.centralrepository.datamodel.CorrelationAttributeNormalizationException;
|
||||||
|
import org.sleuthkit.autopsy.corecomponents.DataResultViewerTable;
|
||||||
import org.sleuthkit.autopsy.coreutils.ContextMenuExtensionPoint;
|
import org.sleuthkit.autopsy.coreutils.ContextMenuExtensionPoint;
|
||||||
import org.sleuthkit.autopsy.coreutils.TimeZoneUtils;
|
import org.sleuthkit.autopsy.coreutils.TimeZoneUtils;
|
||||||
import static org.sleuthkit.autopsy.datamodel.AbstractContentNode.NO_DESCR;
|
import static org.sleuthkit.autopsy.datamodel.AbstractContentNode.NO_DESCR;
|
||||||
|
import org.sleuthkit.autopsy.datamodel.ThreePanelDAO.DataArtifactRow;
|
||||||
|
import org.sleuthkit.autopsy.datamodel.ThreePanelDAO.DataArtifactTableDTO;
|
||||||
import org.sleuthkit.autopsy.texttranslation.TextTranslationService;
|
import org.sleuthkit.autopsy.texttranslation.TextTranslationService;
|
||||||
import org.sleuthkit.autopsy.datamodel.utils.FileNameTransTask;
|
import org.sleuthkit.autopsy.datamodel.utils.FileNameTransTask;
|
||||||
import org.sleuthkit.autopsy.directorytree.ExportCSVAction;
|
import org.sleuthkit.autopsy.directorytree.ExportCSVAction;
|
||||||
@ -97,11 +87,6 @@ import org.sleuthkit.autopsy.directorytree.ExternalViewerShortcutAction;
|
|||||||
import org.sleuthkit.autopsy.directorytree.ExtractAction;
|
import org.sleuthkit.autopsy.directorytree.ExtractAction;
|
||||||
import org.sleuthkit.autopsy.directorytree.NewWindowViewAction;
|
import org.sleuthkit.autopsy.directorytree.NewWindowViewAction;
|
||||||
import org.sleuthkit.autopsy.directorytree.ViewContextAction;
|
import org.sleuthkit.autopsy.directorytree.ViewContextAction;
|
||||||
import org.sleuthkit.autopsy.modules.embeddedfileextractor.ExtractArchiveWithPasswordAction;
|
|
||||||
import org.sleuthkit.datamodel.AnalysisResult;
|
|
||||||
import org.sleuthkit.datamodel.BlackboardArtifact.Category;
|
|
||||||
import org.sleuthkit.datamodel.HostAddress;
|
|
||||||
import org.sleuthkit.datamodel.Pool;
|
|
||||||
import org.sleuthkit.datamodel.DataArtifact;
|
import org.sleuthkit.datamodel.DataArtifact;
|
||||||
import org.sleuthkit.datamodel.DerivedFile;
|
import org.sleuthkit.datamodel.DerivedFile;
|
||||||
import org.sleuthkit.datamodel.Directory;
|
import org.sleuthkit.datamodel.Directory;
|
||||||
@ -111,13 +96,9 @@ import org.sleuthkit.datamodel.LocalDirectory;
|
|||||||
import org.sleuthkit.datamodel.LocalFile;
|
import org.sleuthkit.datamodel.LocalFile;
|
||||||
import org.sleuthkit.datamodel.OsAccount;
|
import org.sleuthkit.datamodel.OsAccount;
|
||||||
import org.sleuthkit.datamodel.Report;
|
import org.sleuthkit.datamodel.Report;
|
||||||
import org.sleuthkit.datamodel.Score;
|
|
||||||
import org.sleuthkit.datamodel.SlackFile;
|
import org.sleuthkit.datamodel.SlackFile;
|
||||||
import org.sleuthkit.datamodel.VirtualDirectory;
|
import org.sleuthkit.datamodel.VirtualDirectory;
|
||||||
import org.sleuthkit.datamodel.TskData;
|
import org.sleuthkit.datamodel.Tag;
|
||||||
import org.sleuthkit.datamodel.Volume;
|
|
||||||
import org.sleuthkit.datamodel.VolumeSystem;
|
|
||||||
import org.sleuthkit.datamodel.Image;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* An AbstractNode implementation that can be used to represent an data artifact
|
* An AbstractNode implementation that can be used to represent an data artifact
|
||||||
@ -127,37 +108,72 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(DataArtifactNodev2.class.getName());
|
private static final Logger logger = Logger.getLogger(DataArtifactNodev2.class.getName());
|
||||||
|
|
||||||
/**
|
private static Lookup createLookup(DataArtifactRow row) {
|
||||||
* Constructs an AbstractNode implementation that can be used to represent a
|
DataArtifactItem artifactItem = new DataArtifactItem(row.getDataArtifact(), row.getSrcContent());
|
||||||
* data artifact or analysis result of any type. The Lookup of the Node will
|
if (row.getSrcContent() == null) {
|
||||||
* contain the data artifact or analysis result and its parent content as
|
return Lookups.fixed(row.getDataArtifact(), artifactItem);
|
||||||
* its source content.
|
} else {
|
||||||
*
|
return Lookups.fixed(row.getDataArtifact(), artifactItem, row.getSrcContent());
|
||||||
* @param artifact The data artifact or analysis result.
|
}
|
||||||
* @param iconPath The path to the icon for the data artifact or analysis
|
|
||||||
* result type.
|
|
||||||
*/
|
|
||||||
public DataArtifactNodev2(BlackboardArtifact artifact, String iconPath) {
|
|
||||||
super(artifact, createLookup(artifact, false));
|
|
||||||
|
|
||||||
...
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private final BlackboardArtifact.Type artifactType;
|
||||||
|
private final List<BlackboardAttribute.Type> attributeTypes;
|
||||||
|
private final DataArtifactRow artifactRow;
|
||||||
|
private final boolean hasSupportedTimeStamp;
|
||||||
|
private String translatedSourceName = null;
|
||||||
|
|
||||||
/**
|
private final PropertyChangeListener fileNameTranslationListener = new PropertyChangeListener() {
|
||||||
* Constructs an AbstractNode implementation that can be used to represent a
|
@Override
|
||||||
* data artifact or analysis result of any type. The Lookup of the Node will
|
public void propertyChange(PropertyChangeEvent evt) {
|
||||||
* contain the data artifact or analysis result and its parent content as
|
String eventType = evt.getPropertyName();
|
||||||
* its source content.
|
|
||||||
*
|
if (eventType.equals(FileNameTransTask.getPropertyName())) {
|
||||||
* @param artifact The data artifact or analysis result.
|
/*
|
||||||
*/
|
* Replace the value of the Source File property with the
|
||||||
public DataArtifactNodev2(BlackboardArtifact artifact) {
|
* translated name via setDisplayName (see note in createSheet),
|
||||||
this(artifact, IconsUtil.getIconFilePath(artifact.getArtifactTypeID()));
|
* and put the untranslated name in the Original Name property
|
||||||
|
* and in the tooltip.
|
||||||
|
*/
|
||||||
|
String originalName = evt.getOldValue().toString();
|
||||||
|
translatedSourceName = evt.getNewValue().toString();
|
||||||
|
setDisplayName(translatedSourceName);
|
||||||
|
setShortDescription(originalName);
|
||||||
|
updateSheet(new NodeProperty<>(
|
||||||
|
Bundle.BlackboardArtifactNode_createSheet_srcFile_origName(),
|
||||||
|
Bundle.BlackboardArtifactNode_createSheet_srcFile_origDisplayName(),
|
||||||
|
NO_DESCR,
|
||||||
|
originalName));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
public DataArtifactNodev2(DataArtifactTableDTO tableData, DataArtifactRow artifactRow) {
|
||||||
|
this(tableData, artifactRow, IconsUtil.getIconFilePath(tableData.getArtifactType().getTypeID()));
|
||||||
|
}
|
||||||
|
|
||||||
|
public DataArtifactNodev2(DataArtifactTableDTO tableData, DataArtifactRow artifactRow, String iconPath) {
|
||||||
|
super(artifactRow.getDataArtifact(), createLookup(artifactRow));
|
||||||
|
|
||||||
|
setDisplayName(artifactRow.getSrcContent().getName());
|
||||||
|
setShortDescription(getDisplayName());
|
||||||
|
setName(Long.toString(artifactRow.getDataArtifact().getArtifactID()));
|
||||||
|
setIconBaseWithExtension(iconPath != null && iconPath.charAt(0) == '/' ? iconPath.substring(1) : iconPath);
|
||||||
|
|
||||||
|
this.artifactRow = artifactRow;
|
||||||
|
this.artifactType = tableData.getArtifactType();
|
||||||
|
this.attributeTypes = tableData.getAttributeTypes();
|
||||||
|
this.hasSupportedTimeStamp = supportedTimeStamp(this.attributeTypes, this.artifactRow.getAttributeValues());
|
||||||
|
}
|
||||||
|
|
||||||
|
private boolean supportedTimeStamp(List<BlackboardAttribute.Type> attributeTypes, Map<String, Object> attributeValues) {
|
||||||
|
return attributeTypes.stream()
|
||||||
|
.anyMatch(tp -> {
|
||||||
|
return BlackboardAttribute.TSK_BLACKBOARD_ATTRIBUTE_VALUE_TYPE.DATETIME.equals(tp.getValueType())
|
||||||
|
&& attributeValues.containsKey(tp.getTypeName());
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a list of non null actions from the given possibly null options.
|
* Returns a list of non null actions from the given possibly null options.
|
||||||
*
|
*
|
||||||
@ -176,28 +192,26 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
// groupings of actions where each group will be separated by a divider
|
// groupings of actions where each group will be separated by a divider
|
||||||
List<List<Action>> actionsLists = new ArrayList<>();
|
List<List<Action>> actionsLists = new ArrayList<>();
|
||||||
|
|
||||||
|
DataArtifact artifact = this.artifactRow.getDataArtifact();
|
||||||
|
Content srcContent = this.artifactRow.getSrcContent();
|
||||||
|
|
||||||
// view artifact in timeline
|
// view artifact in timeline
|
||||||
actionsLists.add(getNonNull(
|
actionsLists.add(getNonNull(
|
||||||
getTimelineArtifactAction(this.artifact)
|
getTimelineArtifactAction(artifact, this.hasSupportedTimeStamp)
|
||||||
));
|
));
|
||||||
|
|
||||||
// view associated file (TSK_PATH_ID attr) in directory and timeline
|
// view associated file (TSK_PATH_ID attr) in directory and timeline
|
||||||
actionsLists.add(getAssociatedFileActions(this.artifact, this.artifactType));
|
actionsLists.add(getAssociatedFileActions(artifact, this.artifactType));
|
||||||
|
|
||||||
// view source content in directory and timeline
|
// view source content in directory and timeline
|
||||||
actionsLists.add(getNonNull(
|
actionsLists.add(getNonNull(
|
||||||
getViewSrcContentAction(this.artifact, this.srcContent),
|
getViewSrcContentAction(artifact, srcContent),
|
||||||
getTimelineSrcContentAction(this.srcContent)
|
getTimelineSrcContentAction(srcContent)
|
||||||
));
|
|
||||||
|
|
||||||
// extract with password from encrypted file
|
|
||||||
actionsLists.add(getNonNull(
|
|
||||||
getExtractWithPasswordAction(this.srcContent)
|
|
||||||
));
|
));
|
||||||
|
|
||||||
// menu options for artifact with report parent
|
// menu options for artifact with report parent
|
||||||
if (this.srcContent instanceof Report) {
|
if (srcContent instanceof Report) {
|
||||||
actionsLists.add(DataModelActionsFactory.getActions(this.srcContent, false));
|
actionsLists.add(DataModelActionsFactory.getActions(srcContent, false));
|
||||||
}
|
}
|
||||||
|
|
||||||
Node parentFileNode = getParentFileNode(srcContent);
|
Node parentFileNode = getParentFileNode(srcContent);
|
||||||
@ -213,7 +227,7 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
}
|
}
|
||||||
|
|
||||||
// file and result tagging
|
// file and result tagging
|
||||||
actionsLists.add(getTagActions(parentFileNode != null, this.artifact, selectedFileCount, selectedArtifactCount));
|
actionsLists.add(getTagActions(parentFileNode != null, artifact, selectedFileCount, selectedArtifactCount));
|
||||||
|
|
||||||
// menu extension items (i.e. add to central repository)
|
// menu extension items (i.e. add to central repository)
|
||||||
actionsLists.add(ContextMenuExtensionPoint.getActions());
|
actionsLists.add(ContextMenuExtensionPoint.getActions());
|
||||||
@ -240,16 +254,16 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
* @return The artifact type name.
|
* @return The artifact type name.
|
||||||
*/
|
*/
|
||||||
@Messages({
|
@Messages({
|
||||||
"BlackboardArtifactNode_getAssociatedTypeStr_webCache=Cached File",
|
"DataArtifactNodev2_getAssociatedTypeStr_webCache=Cached File",
|
||||||
"BlackboardArtifactNode_getAssociatedTypeStr_webDownload=Downloaded File",
|
"DataArtifactNodev2_getAssociatedTypeStr_webDownload=Downloaded File",
|
||||||
"BlackboardArtifactNode_getAssociatedTypeStr_associated=Associated File",})
|
"DataArtifactNodev2_getAssociatedTypeStr_associated=Associated File",})
|
||||||
private String getAssociatedTypeStr(BlackboardArtifact.Type artifactType) {
|
private String getAssociatedTypeStr(BlackboardArtifact.Type artifactType) {
|
||||||
if (BlackboardArtifact.Type.TSK_WEB_CACHE.equals(artifactType)) {
|
if (BlackboardArtifact.Type.TSK_WEB_CACHE.equals(artifactType)) {
|
||||||
return Bundle.BlackboardArtifactNode_getAssociatedTypeStr_webCache();
|
return Bundle.DataArtifactNodev2_getAssociatedTypeStr_webCache();
|
||||||
} else if (BlackboardArtifact.Type.TSK_WEB_DOWNLOAD.equals(artifactType)) {
|
} else if (BlackboardArtifact.Type.TSK_WEB_DOWNLOAD.equals(artifactType)) {
|
||||||
return Bundle.BlackboardArtifactNode_getAssociatedTypeStr_webDownload();
|
return Bundle.DataArtifactNodev2_getAssociatedTypeStr_webDownload();
|
||||||
} else {
|
} else {
|
||||||
return Bundle.BlackboardArtifactNode_getAssociatedTypeStr_associated();
|
return Bundle.DataArtifactNodev2_getAssociatedTypeStr_associated();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -262,20 +276,20 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
* @return The name of the type of content.
|
* @return The name of the type of content.
|
||||||
*/
|
*/
|
||||||
@Messages({
|
@Messages({
|
||||||
"BlackboardArtifactNode_getViewSrcContentAction_type_File=File",
|
"DataArtifactNodev2_getViewSrcContentAction_type_File=File",
|
||||||
"BlackboardArtifactNode_getViewSrcContentAction_type_DataArtifact=Data Artifact",
|
"DataArtifactNodev2_getViewSrcContentAction_type_DataArtifact=Data Artifact",
|
||||||
"BlackboardArtifactNode_getViewSrcContentAction_type_OSAccount=OS Account",
|
"DataArtifactNodev2_getViewSrcContentAction_type_OSAccount=OS Account",
|
||||||
"BlackboardArtifactNode_getViewSrcContentAction_type_unknown=Item"
|
"DataArtifactNodev2_getViewSrcContentAction_type_unknown=Item"
|
||||||
})
|
})
|
||||||
private String getContentTypeStr(Content content) {
|
private String getContentTypeStr(Content content) {
|
||||||
if (content instanceof AbstractFile) {
|
if (content instanceof AbstractFile) {
|
||||||
return Bundle.BlackboardArtifactNode_getViewSrcContentAction_type_File();
|
return Bundle.DataArtifactNodev2_getViewSrcContentAction_type_File();
|
||||||
} else if (content instanceof DataArtifact) {
|
} else if (content instanceof DataArtifact) {
|
||||||
return Bundle.BlackboardArtifactNode_getViewSrcContentAction_type_DataArtifact();
|
return Bundle.DataArtifactNodev2_getViewSrcContentAction_type_DataArtifact();
|
||||||
} else if (content instanceof OsAccount) {
|
} else if (content instanceof OsAccount) {
|
||||||
return Bundle.BlackboardArtifactNode_getViewSrcContentAction_type_OSAccount();
|
return Bundle.DataArtifactNodev2_getViewSrcContentAction_type_OSAccount();
|
||||||
} else {
|
} else {
|
||||||
return Bundle.BlackboardArtifactNode_getViewSrcContentAction_type_unknown();
|
return Bundle.DataArtifactNodev2_getViewSrcContentAction_type_unknown();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -291,9 +305,9 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
*/
|
*/
|
||||||
@Messages({
|
@Messages({
|
||||||
"# {0} - type",
|
"# {0} - type",
|
||||||
"BlackboardArtifactNode_getAssociatedFileActions_viewAssociatedFileAction=View {0} in Directory",
|
"DataArtifactNodev2_getAssociatedFileActions_viewAssociatedFileAction=View {0} in Directory",
|
||||||
"# {0} - type",
|
"# {0} - type",
|
||||||
"BlackboardArtifactNode_getAssociatedFileActions_viewAssociatedFileInTimelineAction=View {0} in Timeline..."
|
"DataArtifactNodev2_getAssociatedFileActions_viewAssociatedFileInTimelineAction=View {0} in Timeline..."
|
||||||
})
|
})
|
||||||
private List<Action> getAssociatedFileActions(BlackboardArtifact artifact, BlackboardArtifact.Type artifactType) {
|
private List<Action> getAssociatedFileActions(BlackboardArtifact artifact, BlackboardArtifact.Type artifactType) {
|
||||||
try {
|
try {
|
||||||
@ -301,11 +315,11 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
if (associatedFile != null) {
|
if (associatedFile != null) {
|
||||||
return Arrays.asList(
|
return Arrays.asList(
|
||||||
new ViewContextAction(
|
new ViewContextAction(
|
||||||
Bundle.BlackboardArtifactNode_getAssociatedFileActions_viewAssociatedFileAction(
|
Bundle.DataArtifactNodev2_getAssociatedFileActions_viewAssociatedFileAction(
|
||||||
getAssociatedTypeStr(artifactType)),
|
getAssociatedTypeStr(artifactType)),
|
||||||
associatedFile),
|
associatedFile),
|
||||||
new ViewFileInTimelineAction(associatedFile,
|
new ViewFileInTimelineAction(associatedFile,
|
||||||
Bundle.BlackboardArtifactNode_getAssociatedFileActions_viewAssociatedFileInTimelineAction(
|
Bundle.DataArtifactNodev2_getAssociatedFileActions_viewAssociatedFileInTimelineAction(
|
||||||
getAssociatedTypeStr(artifactType)))
|
getAssociatedTypeStr(artifactType)))
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -326,22 +340,22 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
*/
|
*/
|
||||||
@Messages({
|
@Messages({
|
||||||
"# {0} - contentType",
|
"# {0} - contentType",
|
||||||
"BlackboardArtifactNode_getSrcContentAction_actionDisplayName=View Source {0} in Directory"
|
"DataArtifactNodev2_getSrcContentAction_actionDisplayName=View Source {0} in Directory"
|
||||||
})
|
})
|
||||||
private Action getViewSrcContentAction(BlackboardArtifact artifact, Content content) {
|
private Action getViewSrcContentAction(BlackboardArtifact artifact, Content content) {
|
||||||
if (content instanceof DataArtifact) {
|
if (content instanceof DataArtifact) {
|
||||||
return new ViewArtifactAction(
|
return new ViewArtifactAction(
|
||||||
(BlackboardArtifact) content,
|
(BlackboardArtifact) content,
|
||||||
Bundle.BlackboardArtifactNode_getSrcContentAction_actionDisplayName(
|
Bundle.DataArtifactNodev2_getSrcContentAction_actionDisplayName(
|
||||||
getContentTypeStr(content)));
|
getContentTypeStr(content)));
|
||||||
} else if (content instanceof OsAccount) {
|
} else if (content instanceof OsAccount) {
|
||||||
return new ViewOsAccountAction(
|
return new ViewOsAccountAction(
|
||||||
(OsAccount) content,
|
(OsAccount) content,
|
||||||
Bundle.BlackboardArtifactNode_getSrcContentAction_actionDisplayName(
|
Bundle.DataArtifactNodev2_getSrcContentAction_actionDisplayName(
|
||||||
getContentTypeStr(content)));
|
getContentTypeStr(content)));
|
||||||
} else if (content instanceof AbstractFile || artifact instanceof DataArtifact) {
|
} else if (content instanceof AbstractFile || artifact instanceof DataArtifact) {
|
||||||
return new ViewContextAction(
|
return new ViewContextAction(
|
||||||
Bundle.BlackboardArtifactNode_getSrcContentAction_actionDisplayName(
|
Bundle.DataArtifactNodev2_getSrcContentAction_actionDisplayName(
|
||||||
getContentTypeStr(content)),
|
getContentTypeStr(content)),
|
||||||
content);
|
content);
|
||||||
} else {
|
} else {
|
||||||
@ -377,29 +391,6 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns actions for extracting content from file or null if not possible.
|
|
||||||
*
|
|
||||||
* @param srcContent The source content.
|
|
||||||
*
|
|
||||||
* @return The action or null if not appropriate source content.
|
|
||||||
*/
|
|
||||||
private Action getExtractWithPasswordAction(Content srcContent) {
|
|
||||||
if ((srcContent instanceof AbstractFile)
|
|
||||||
&& FileTypeExtensions.getArchiveExtensions()
|
|
||||||
.contains("." + ((AbstractFile) srcContent).getNameExtension().toLowerCase())) {
|
|
||||||
try {
|
|
||||||
if (srcContent.getArtifacts(BlackboardArtifact.Type.TSK_ENCRYPTION_DETECTED.getTypeID()).size() > 0) {
|
|
||||||
return new ExtractArchiveWithPasswordAction((AbstractFile) srcContent);
|
|
||||||
}
|
|
||||||
} catch (TskCoreException ex) {
|
|
||||||
logger.log(Level.WARNING, "Unable to add unzip with password action to context menus", ex);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns tag actions.
|
* Returns tag actions.
|
||||||
*
|
*
|
||||||
@ -442,15 +433,15 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
* @return The list of actions or an empty list.
|
* @return The list of actions or an empty list.
|
||||||
*/
|
*/
|
||||||
@Messages({
|
@Messages({
|
||||||
"BlackboardArtifactNode_getSrcContentViewerActions_viewInNewWin=View Item in New Window",
|
"DataArtifactNodev2_getSrcContentViewerActions_viewInNewWin=View Item in New Window",
|
||||||
"BlackboardArtifactNode_getSrcContentViewerActions_openInExtViewer=Open in External Viewer Ctrl+E"
|
"DataArtifactNodev2_getSrcContentViewerActions_openInExtViewer=Open in External Viewer Ctrl+E"
|
||||||
})
|
})
|
||||||
private List<Action> getSrcContentViewerActions(Node srcFileNode, int selectedFileCount) {
|
private List<Action> getSrcContentViewerActions(Node srcFileNode, int selectedFileCount) {
|
||||||
List<Action> actionsList = new ArrayList<>();
|
List<Action> actionsList = new ArrayList<>();
|
||||||
if (srcFileNode != null) {
|
if (srcFileNode != null) {
|
||||||
actionsList.add(new NewWindowViewAction(Bundle.BlackboardArtifactNode_getSrcContentViewerActions_viewInNewWin(), srcFileNode));
|
actionsList.add(new NewWindowViewAction(Bundle.DataArtifactNodev2_getSrcContentViewerActions_viewInNewWin(), srcFileNode));
|
||||||
if (selectedFileCount == 1) {
|
if (selectedFileCount == 1) {
|
||||||
actionsList.add(new ExternalViewerAction(Bundle.BlackboardArtifactNode_getSrcContentViewerActions_openInExtViewer(), srcFileNode));
|
actionsList.add(new ExternalViewerAction(Bundle.DataArtifactNodev2_getSrcContentViewerActions_openInExtViewer(), srcFileNode));
|
||||||
} else {
|
} else {
|
||||||
actionsList.add(ExternalViewerShortcutAction.getInstance());
|
actionsList.add(ExternalViewerShortcutAction.getInstance());
|
||||||
}
|
}
|
||||||
@ -468,25 +459,26 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
*/
|
*/
|
||||||
@NbBundle.Messages({
|
@NbBundle.Messages({
|
||||||
"# {0} - contentType",
|
"# {0} - contentType",
|
||||||
"BlackboardArtifactNode_getTimelineSrcContentAction_actionDisplayName=View Source {0} in Timeline... "
|
"DataArtifactNodev2_getTimelineSrcContentAction_actionDisplayName=View Source {0} in Timeline... "
|
||||||
})
|
})
|
||||||
private Action getTimelineSrcContentAction(Content srcContent) {
|
private Action getTimelineSrcContentAction(Content srcContent) {
|
||||||
if (srcContent instanceof AbstractFile) {
|
if (srcContent instanceof AbstractFile) {
|
||||||
return new ViewFileInTimelineAction((AbstractFile) srcContent,
|
return new ViewFileInTimelineAction((AbstractFile) srcContent,
|
||||||
Bundle.BlackboardArtifactNode_getTimelineSrcContentAction_actionDisplayName(
|
Bundle.DataArtifactNodev2_getTimelineSrcContentAction_actionDisplayName(
|
||||||
getContentTypeStr(srcContent)));
|
getContentTypeStr(srcContent)));
|
||||||
} else if (srcContent instanceof DataArtifact) {
|
|
||||||
try {
|
|
||||||
if (ViewArtifactInTimelineAction.hasSupportedTimeStamp((BlackboardArtifact) srcContent)) {
|
|
||||||
return new ViewArtifactInTimelineAction((BlackboardArtifact) srcContent,
|
|
||||||
Bundle.BlackboardArtifactNode_getTimelineSrcContentAction_actionDisplayName(
|
|
||||||
getContentTypeStr(srcContent)));
|
|
||||||
}
|
|
||||||
} catch (TskCoreException ex) {
|
|
||||||
logger.log(Level.SEVERE, MessageFormat.format("Error getting source data artifact timestamp (artifact objID={0})", srcContent.getId()), ex); //NON-NLS
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// else if (srcContent instanceof DataArtifact) {
|
||||||
|
// try {
|
||||||
|
// if (hasSupportedTimeStamp((BlackboardArtifact) srcContent)) {
|
||||||
|
// return new ViewArtifactInTimelineAction((BlackboardArtifact) srcContent,
|
||||||
|
// Bundle.DataArtifactNodev2_getTimelineSrcContentAction_actionDisplayName(
|
||||||
|
// getContentTypeStr(srcContent)));
|
||||||
|
// }
|
||||||
|
// } catch (TskCoreException ex) {
|
||||||
|
// logger.log(Level.SEVERE, MessageFormat.format("Error getting source data artifact timestamp (artifact objID={0})", srcContent.getId()), ex); //NON-NLS
|
||||||
|
// }
|
||||||
|
// }
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -494,54 +486,42 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
* If the artifact represented by this node has a timestamp, an action to
|
* If the artifact represented by this node has a timestamp, an action to
|
||||||
* view it in the timeline.
|
* view it in the timeline.
|
||||||
*
|
*
|
||||||
* @param art The artifact for timeline navigation action.
|
* @param art The artifact for timeline navigation action.
|
||||||
|
* @param hasSupportedTimeStamp This artifact has a supported time stamp.
|
||||||
*
|
*
|
||||||
* @return The action or null if no action should exist.
|
* @return The action or null if no action should exist.
|
||||||
*/
|
*/
|
||||||
@Messages({
|
@Messages({
|
||||||
"BlackboardArtifactNode_getTimelineArtifactAction_displayName=View Selected Item in Timeline... "
|
"DataArtifactNodev2_getTimelineArtifactAction_displayName=View Selected Item in Timeline... "
|
||||||
})
|
})
|
||||||
private Action getTimelineArtifactAction(BlackboardArtifact art) {
|
private Action getTimelineArtifactAction(BlackboardArtifact art, boolean hasSupportedTimeStamp) {
|
||||||
try {
|
if (hasSupportedTimeStamp) {
|
||||||
// don't show ViewArtifactInTimelineAction for AnalysisResults.
|
return new ViewArtifactInTimelineAction(art, Bundle.DataArtifactNodev2_getTimelineArtifactAction_displayName());
|
||||||
if (!(art instanceof AnalysisResult) && ViewArtifactInTimelineAction.hasSupportedTimeStamp(art)) {
|
} else {
|
||||||
return new ViewArtifactInTimelineAction(art, Bundle.BlackboardArtifactNode_getTimelineArtifactAction_displayName());
|
return null;
|
||||||
}
|
|
||||||
} catch (TskCoreException ex) {
|
|
||||||
logger.log(Level.SEVERE, MessageFormat.format("Error getting artifact timestamp (artifact objID={0})", art.getId()), ex); //NON-NLS
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Gets the name of the source content of the artifact represented by this
|
|
||||||
* node.
|
|
||||||
*
|
|
||||||
* @return The source content name.
|
|
||||||
*/
|
|
||||||
public String getSourceName() {
|
|
||||||
return srcContent.getName();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@NbBundle.Messages({
|
@NbBundle.Messages({
|
||||||
"BlackboardArtifactNode.createSheet.srcFile.name=Source Name",
|
"DataArtifactNodev2.createSheet.srcFile.name=Source Name",
|
||||||
"BlackboardArtifactNode.createSheet.srcFile.displayName=Source Name",
|
"DataArtifactNodev2.createSheet.srcFile.displayName=Source Name",
|
||||||
"BlackboardArtifactNode.createSheet.srcFile.origName=Original Name",
|
"DataArtifactNodev2.createSheet.srcFile.origName=Original Name",
|
||||||
"BlackboardArtifactNode.createSheet.srcFile.origDisplayName=Original Name",
|
"DataArtifactNodev2.createSheet.srcFile.origDisplayName=Original Name",
|
||||||
"BlackboardArtifactNode.createSheet.artifactType.displayName=Result Type",
|
"DataArtifactNodev2.createSheet.artifactType.displayName=Result Type",
|
||||||
"BlackboardArtifactNode.createSheet.artifactType.name=Result Type",
|
"DataArtifactNodev2.createSheet.artifactType.name=Result Type",
|
||||||
"BlackboardArtifactNode.createSheet.artifactDetails.displayName=Result Details",
|
"DataArtifactNodev2.createSheet.artifactDetails.displayName=Result Details",
|
||||||
"BlackboardArtifactNode.createSheet.artifactDetails.name=Result Details",
|
"DataArtifactNodev2.createSheet.artifactDetails.name=Result Details",
|
||||||
"BlackboardArtifactNode.createSheet.artifactMD5.displayName=MD5 Hash",
|
"DataArtifactNodev2.createSheet.artifactMD5.displayName=MD5 Hash",
|
||||||
"BlackboardArtifactNode.createSheet.artifactMD5.name=MD5 Hash",
|
"DataArtifactNodev2.createSheet.artifactMD5.name=MD5 Hash",
|
||||||
"BlackboardArtifactNode.createSheet.fileSize.name=Size",
|
"DataArtifactNodev2.createSheet.fileSize.name=Size",
|
||||||
"BlackboardArtifactNode.createSheet.fileSize.displayName=Size",
|
"DataArtifactNodev2.createSheet.fileSize.displayName=Size",
|
||||||
"BlackboardArtifactNode.createSheet.path.displayName=Path",
|
"DataArtifactNodev2.createSheet.path.displayName=Path",
|
||||||
"BlackboardArtifactNode.createSheet.path.name=Path"
|
"DataArtifactNodev2.createSheet.path.name=Path"
|
||||||
})
|
})
|
||||||
@Override
|
@Override
|
||||||
protected Sheet createSheet() {
|
protected Sheet createSheet() {
|
||||||
|
Content srcContent = this.artifactRow.getSrcContent();
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Create an empty property sheet.
|
* Create an empty property sheet.
|
||||||
*/
|
*/
|
||||||
@ -559,19 +539,12 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
* the node's icon as well as the display name.
|
* the node's icon as well as the display name.
|
||||||
*/
|
*/
|
||||||
sheetSet.put(new NodeProperty<>(
|
sheetSet.put(new NodeProperty<>(
|
||||||
Bundle.BlackboardArtifactNode_createSheet_srcFile_name(),
|
Bundle.DataArtifactNodev2_createSheet_srcFile_name(),
|
||||||
Bundle.BlackboardArtifactNode_createSheet_srcFile_displayName(),
|
Bundle.DataArtifactNodev2_createSheet_srcFile_displayName(),
|
||||||
NO_DESCR,
|
NO_DESCR,
|
||||||
getDisplayName()));
|
getDisplayName()));
|
||||||
|
|
||||||
GetSCOTask scoTask;
|
GetSCOTask scoTask = addSCOColumns(sheetSet);
|
||||||
if (artifact instanceof AnalysisResult
|
|
||||||
&& !(artifactType.getTypeID() == BlackboardArtifact.ARTIFACT_TYPE.TSK_HASHSET_HIT.getTypeID()
|
|
||||||
|| artifactType.getTypeID() == BlackboardArtifact.ARTIFACT_TYPE.TSK_KEYWORD_HIT.getTypeID())) {
|
|
||||||
scoTask = updateSheetForAnalysisResult((AnalysisResult) artifact, sheetSet);
|
|
||||||
} else {
|
|
||||||
scoTask = addSCOColumns(sheetSet);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (TextTranslationService.getInstance().hasProvider() && UserPreferences.displayTranslatedFileNames()) {
|
if (TextTranslationService.getInstance().hasProvider() && UserPreferences.displayTranslatedFileNames()) {
|
||||||
/*
|
/*
|
||||||
@ -580,45 +553,15 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
* node to the sheet.
|
* node to the sheet.
|
||||||
*/
|
*/
|
||||||
sheetSet.put(new NodeProperty<>(
|
sheetSet.put(new NodeProperty<>(
|
||||||
Bundle.BlackboardArtifactNode_createSheet_srcFile_origName(),
|
Bundle.DataArtifactNodev2_createSheet_srcFile_origName(),
|
||||||
Bundle.BlackboardArtifactNode_createSheet_srcFile_origDisplayName(),
|
Bundle.DataArtifactNodev2_createSheet_srcFile_origDisplayName(),
|
||||||
NO_DESCR,
|
NO_DESCR,
|
||||||
translatedSourceName != null ? srcContent.getName() : ""));
|
translatedSourceName != null ? srcContent.getName() : ""));
|
||||||
if (translatedSourceName == null) {
|
if (translatedSourceName == null) {
|
||||||
/*
|
/*
|
||||||
* NOTE: The task makes its own weak reference to the listener.
|
* NOTE: The task makes its own weak reference to the listener.
|
||||||
*/
|
*/
|
||||||
new FileNameTransTask(srcContent.getName(), this, listener).submit();
|
new FileNameTransTask(srcContent.getName(), this, fileNameTranslationListener).submit();
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* If the artifact represented by this node is an interesting artifact
|
|
||||||
* hit, add the type and description of the interesting artifact to the
|
|
||||||
* sheet.
|
|
||||||
*/
|
|
||||||
if (artifact.getArtifactTypeID() == ARTIFACT_TYPE.TSK_INTERESTING_ARTIFACT_HIT.getTypeID()) {
|
|
||||||
try {
|
|
||||||
BlackboardAttribute attribute = artifact.getAttribute(new BlackboardAttribute.Type(ATTRIBUTE_TYPE.TSK_ASSOCIATED_ARTIFACT));
|
|
||||||
if (attribute != null) {
|
|
||||||
BlackboardArtifact associatedArtifact = Case.getCurrentCaseThrows().getSleuthkitCase().getBlackboardArtifact(attribute.getValueLong());
|
|
||||||
sheetSet.put(new NodeProperty<>(
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"BlackboardArtifactNode.createSheet.artifactType.name"),
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"BlackboardArtifactNode.createSheet.artifactType.displayName"),
|
|
||||||
NO_DESCR,
|
|
||||||
associatedArtifact.getDisplayName()));
|
|
||||||
sheetSet.put(new NodeProperty<>(
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"BlackboardArtifactNode.createSheet.artifactDetails.name"),
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"BlackboardArtifactNode.createSheet.artifactDetails.displayName"),
|
|
||||||
NO_DESCR,
|
|
||||||
associatedArtifact.getShortDescription()));
|
|
||||||
}
|
|
||||||
} catch (TskCoreException | NoCurrentCaseException ex) {
|
|
||||||
logger.log(Level.SEVERE, MessageFormat.format("Error getting associated artifact of TSK_INTERESTING_ARTIFACT_HIT artifact (objID={0}))", artifact.getId()), ex); //NON-NLS
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -635,177 +578,16 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
entry.getValue()));
|
entry.getValue()));
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
String dataSourceStr = this.artifactRow.getDataSourceName();
|
||||||
* Add any "custom properties" for the node to the sheet.
|
|
||||||
*/
|
|
||||||
if (customProperties != null) {
|
|
||||||
for (NodeProperty<? extends Object> np : customProperties) {
|
|
||||||
sheetSet.put(np);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
if (dataSourceStr.isEmpty() == false) {
|
||||||
* If the artifact represented by this node is a file extension mismatch
|
|
||||||
* artifact, add the extension and type of the artifact's source file to
|
|
||||||
* the sheet.
|
|
||||||
*/
|
|
||||||
final int artifactTypeId = artifact.getArtifactTypeID();
|
|
||||||
if (artifactTypeId == BlackboardArtifact.ARTIFACT_TYPE.TSK_EXT_MISMATCH_DETECTED.getTypeID()) {
|
|
||||||
String ext = ""; //NON-NLS
|
|
||||||
String actualMimeType = ""; //NON-NLS
|
|
||||||
if (srcContent instanceof AbstractFile) {
|
|
||||||
AbstractFile file = (AbstractFile) srcContent;
|
|
||||||
ext = file.getNameExtension();
|
|
||||||
actualMimeType = file.getMIMEType();
|
|
||||||
if (actualMimeType == null) {
|
|
||||||
actualMimeType = ""; //NON-NLS
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
sheetSet.put(new NodeProperty<>(
|
sheetSet.put(new NodeProperty<>(
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
NbBundle.getMessage(DataArtifactNodev2.class,
|
||||||
"BlackboardArtifactNode.createSheet.ext.name"),
|
"DataArtifactNodev2.createSheet.dataSrc.name"),
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
NbBundle.getMessage(DataArtifactNodev2.class,
|
||||||
"BlackboardArtifactNode.createSheet.ext.displayName"),
|
"DataArtifactNodev2.createSheet.dataSrc.displayName"),
|
||||||
NO_DESCR,
|
NO_DESCR,
|
||||||
ext));
|
dataSourceStr));
|
||||||
sheetSet.put(new NodeProperty<>(
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"BlackboardArtifactNode.createSheet.mimeType.name"),
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"BlackboardArtifactNode.createSheet.mimeType.displayName"),
|
|
||||||
NO_DESCR,
|
|
||||||
actualMimeType));
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* If the type of the artifact represented by this node dictates the
|
|
||||||
* addition of the source content's unique path, add it to the sheet.
|
|
||||||
*/
|
|
||||||
if (artifactType != null && artifactType.getCategory() == Category.ANALYSIS_RESULT) {
|
|
||||||
String sourcePath = ""; //NON-NLS
|
|
||||||
try {
|
|
||||||
sourcePath = srcContent.getUniquePath();
|
|
||||||
} catch (TskCoreException ex) {
|
|
||||||
logger.log(Level.SEVERE, MessageFormat.format("Error getting unique path of source content (artifact objID={0})", artifact.getId()), ex); //NON-NLS
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
if (sourcePath.isEmpty() == false) {
|
|
||||||
sheetSet.put(new NodeProperty<>(
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"BlackboardArtifactNode.createSheet.filePath.name"),
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"BlackboardArtifactNode.createSheet.filePath.displayName"),
|
|
||||||
NO_DESCR,
|
|
||||||
sourcePath));
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* If the type of the artifact represented by this node dictates the
|
|
||||||
* addition of the source content's file metadata, add it to the
|
|
||||||
* sheet. Otherwise, add the data source to the sheet.
|
|
||||||
*/
|
|
||||||
if (Arrays.asList(SHOW_FILE_METADATA).contains(artifactTypeId)) {
|
|
||||||
AbstractFile file = srcContent instanceof AbstractFile ? (AbstractFile) srcContent : null;
|
|
||||||
sheetSet.put(new NodeProperty<>(
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"ContentTagNode.createSheet.fileModifiedTime.name"),
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"ContentTagNode.createSheet.fileModifiedTime.displayName"),
|
|
||||||
"",
|
|
||||||
file == null ? "" : TimeZoneUtils.getFormattedTime(file.getMtime())));
|
|
||||||
sheetSet.put(new NodeProperty<>(
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"ContentTagNode.createSheet.fileChangedTime.name"),
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"ContentTagNode.createSheet.fileChangedTime.displayName"),
|
|
||||||
"",
|
|
||||||
file == null ? "" : TimeZoneUtils.getFormattedTime(file.getCtime())));
|
|
||||||
sheetSet.put(new NodeProperty<>(
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"ContentTagNode.createSheet.fileAccessedTime.name"),
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"ContentTagNode.createSheet.fileAccessedTime.displayName"),
|
|
||||||
"",
|
|
||||||
file == null ? "" : TimeZoneUtils.getFormattedTime(file.getAtime())));
|
|
||||||
sheetSet.put(new NodeProperty<>(
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"ContentTagNode.createSheet.fileCreatedTime.name"),
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"ContentTagNode.createSheet.fileCreatedTime.displayName"),
|
|
||||||
"",
|
|
||||||
file == null ? "" : TimeZoneUtils.getFormattedTime(file.getCrtime())));
|
|
||||||
sheetSet.put(new NodeProperty<>(
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"ContentTagNode.createSheet.fileSize.name"),
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"ContentTagNode.createSheet.fileSize.displayName"),
|
|
||||||
"",
|
|
||||||
file == null ? "" : file.getSize()));
|
|
||||||
sheetSet.put(new NodeProperty<>(
|
|
||||||
Bundle.BlackboardArtifactNode_createSheet_artifactMD5_name(),
|
|
||||||
Bundle.BlackboardArtifactNode_createSheet_artifactMD5_displayName(),
|
|
||||||
"",
|
|
||||||
file == null ? "" : StringUtils.defaultString(file.getMd5Hash())));
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
String dataSourceStr = "";
|
|
||||||
try {
|
|
||||||
Content dataSource = srcContent.getDataSource();
|
|
||||||
if (dataSource != null) {
|
|
||||||
dataSourceStr = dataSource.getName();
|
|
||||||
} else {
|
|
||||||
dataSourceStr = getRootAncestorName();
|
|
||||||
}
|
|
||||||
} catch (TskCoreException ex) {
|
|
||||||
logger.log(Level.SEVERE, MessageFormat.format("Error getting source data source name (artifact objID={0})", artifact.getId()), ex); //NON-NLS
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
if (dataSourceStr.isEmpty() == false) {
|
|
||||||
sheetSet.put(new NodeProperty<>(
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"BlackboardArtifactNode.createSheet.dataSrc.name"),
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"BlackboardArtifactNode.createSheet.dataSrc.displayName"),
|
|
||||||
NO_DESCR,
|
|
||||||
dataSourceStr));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* If the artifact represented by this node is an EXIF artifact, add the
|
|
||||||
* source file size and path to the sheet.
|
|
||||||
*/
|
|
||||||
if (artifactTypeId == BlackboardArtifact.ARTIFACT_TYPE.TSK_METADATA_EXIF.getTypeID()) {
|
|
||||||
long size = 0;
|
|
||||||
String path = ""; //NON-NLS
|
|
||||||
if (srcContent instanceof AbstractFile) {
|
|
||||||
AbstractFile af = (AbstractFile) srcContent;
|
|
||||||
size = af.getSize();
|
|
||||||
try {
|
|
||||||
path = af.getUniquePath();
|
|
||||||
} catch (TskCoreException ex) {
|
|
||||||
path = af.getParentPath();
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
sheetSet.put(new NodeProperty<>(
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"BlackboardArtifactNode.createSheet.fileSize.name"),
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"BlackboardArtifactNode.createSheet.fileSize.displayName"),
|
|
||||||
NO_DESCR,
|
|
||||||
size));
|
|
||||||
sheetSet
|
|
||||||
.put(new NodeProperty<>(
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"BlackboardArtifactNode.createSheet.path.name"),
|
|
||||||
NbBundle.getMessage(DataArtifactNodev2.class,
|
|
||||||
"BlackboardArtifactNode.createSheet.path.displayName"),
|
|
||||||
NO_DESCR,
|
|
||||||
path));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (scoTask != null) {
|
if (scoTask != null) {
|
||||||
@ -815,7 +597,6 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
return sheet;
|
return sheet;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Adds a "custom" property to the property sheet of this node, independent
|
* Adds a "custom" property to the property sheet of this node, independent
|
||||||
* of the artifact this node represents or its source content.
|
* of the artifact this node represents or its source content.
|
||||||
@ -926,11 +707,6 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public <T> T accept(DisplayableItemNodeVisitor<T> visitor) {
|
|
||||||
return visitor.visit(this);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean isLeafTypeNode() {
|
public boolean isLeafTypeNode() {
|
||||||
return true;
|
return true;
|
||||||
@ -941,21 +717,6 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
return getClass().getName();
|
return getClass().getName();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public <T> T accept(ContentNodeVisitor<T> visitor) {
|
|
||||||
return visitor.visit(this);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Messages({
|
|
||||||
"BlackboardArtifactNode_analysisSheet_sourceType_name=Source Type",
|
|
||||||
"BlackboardArtifactNode_analysisSheet_soureName_name=Source Name",
|
|
||||||
"BlackboardArtifactNode_analysisSheet_score_name=Score",
|
|
||||||
"BlackboardArtifactNode_analysisSheet_conclusion_name=Conclusion",
|
|
||||||
"BlackboardArtifactNode_analysisSheet_configuration_name=Configuration",
|
|
||||||
"BlackboardArtifactNode_analysisSheet_justifaction_name=Justification"
|
|
||||||
})
|
|
||||||
|
|
||||||
|
|
||||||
private GetSCOTask addSCOColumns(Sheet.Set sheetSet) {
|
private GetSCOTask addSCOColumns(Sheet.Set sheetSet) {
|
||||||
if (!UserPreferences.getHideSCOColumns()) {
|
if (!UserPreferences.getHideSCOColumns()) {
|
||||||
/*
|
/*
|
||||||
@ -966,19 +727,19 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
* and this node's PropertyChangeListener will update the sheet.
|
* and this node's PropertyChangeListener will update the sheet.
|
||||||
*/
|
*/
|
||||||
sheetSet.put(new NodeProperty<>(
|
sheetSet.put(new NodeProperty<>(
|
||||||
Bundle.BlackboardArtifactNode_createSheet_score_name(),
|
Bundle.DataArtifactNodev2_createSheet_score_name(),
|
||||||
Bundle.BlackboardArtifactNode_createSheet_score_displayName(),
|
Bundle.DataArtifactNodev2_createSheet_score_displayName(),
|
||||||
VALUE_LOADING,
|
VALUE_LOADING,
|
||||||
""));
|
""));
|
||||||
sheetSet.put(new NodeProperty<>(
|
sheetSet.put(new NodeProperty<>(
|
||||||
Bundle.BlackboardArtifactNode_createSheet_comment_name(),
|
Bundle.DataArtifactNodev2_createSheet_comment_name(),
|
||||||
Bundle.BlackboardArtifactNode_createSheet_comment_displayName(),
|
Bundle.DataArtifactNodev2_createSheet_comment_displayName(),
|
||||||
VALUE_LOADING,
|
VALUE_LOADING,
|
||||||
""));
|
""));
|
||||||
if (CentralRepository.isEnabled()) {
|
if (CentralRepository.isEnabled()) {
|
||||||
sheetSet.put(new NodeProperty<>(
|
sheetSet.put(new NodeProperty<>(
|
||||||
Bundle.BlackboardArtifactNode_createSheet_count_name(),
|
Bundle.DataArtifactNodev2_createSheet_count_name(),
|
||||||
Bundle.BlackboardArtifactNode_createSheet_count_displayName(),
|
Bundle.DataArtifactNodev2_createSheet_count_displayName(),
|
||||||
VALUE_LOADING,
|
VALUE_LOADING,
|
||||||
""));
|
""));
|
||||||
}
|
}
|
||||||
@ -987,42 +748,6 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns a displayable type string for the given content object.
|
|
||||||
*
|
|
||||||
* If the content object is a artifact of a custom type then this method may
|
|
||||||
* cause a DB call BlackboardArtifact.getType
|
|
||||||
*
|
|
||||||
* @param source The object to determine the type of.
|
|
||||||
*
|
|
||||||
* @return A string representing the content type.
|
|
||||||
*/
|
|
||||||
private String getSourceObjType(Content source) {
|
|
||||||
if (source instanceof BlackboardArtifact) {
|
|
||||||
BlackboardArtifact srcArtifact = (BlackboardArtifact) source;
|
|
||||||
try {
|
|
||||||
return srcArtifact.getType().getDisplayName();
|
|
||||||
} catch (TskCoreException ex) {
|
|
||||||
logger.log(Level.SEVERE, "Failed to get custom artifact type id=" + source.getId(), ex);
|
|
||||||
}
|
|
||||||
} else if (srcContent instanceof Volume) {
|
|
||||||
return TskData.ObjectType.VOL.toString();
|
|
||||||
} else if (srcContent instanceof AbstractFile) {
|
|
||||||
return TskData.ObjectType.ABSTRACTFILE.toString();
|
|
||||||
} else if (srcContent instanceof Image) {
|
|
||||||
return TskData.ObjectType.IMG.toString();
|
|
||||||
} else if (srcContent instanceof VolumeSystem) {
|
|
||||||
return TskData.ObjectType.VS.toString();
|
|
||||||
} else if (srcContent instanceof OsAccount) {
|
|
||||||
return TskData.ObjectType.OS_ACCOUNT.toString();
|
|
||||||
} else if (srcContent instanceof HostAddress) {
|
|
||||||
return TskData.ObjectType.HOST_ADDRESS.toString();
|
|
||||||
} else if (srcContent instanceof Pool) {
|
|
||||||
return TskData.ObjectType.POOL.toString();
|
|
||||||
}
|
|
||||||
return "";
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Update the SCO columns with the data retrieved in the background thread.
|
* Update the SCO columns with the data retrieved in the background thread.
|
||||||
*
|
*
|
||||||
@ -1035,21 +760,21 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
public void run() {
|
public void run() {
|
||||||
if (scoData.getScoreAndDescription() != null) {
|
if (scoData.getScoreAndDescription() != null) {
|
||||||
updateSheet(new NodeProperty<>(
|
updateSheet(new NodeProperty<>(
|
||||||
Bundle.BlackboardArtifactNode_createSheet_score_name(),
|
Bundle.DataArtifactNodev2_createSheet_score_name(),
|
||||||
Bundle.BlackboardArtifactNode_createSheet_score_displayName(),
|
Bundle.DataArtifactNodev2_createSheet_score_displayName(),
|
||||||
scoData.getScoreAndDescription().getRight(),
|
scoData.getScoreAndDescription().getRight(),
|
||||||
scoData.getScoreAndDescription().getLeft()));
|
scoData.getScoreAndDescription().getLeft()));
|
||||||
}
|
}
|
||||||
if (scoData.getComment() != null) {
|
if (scoData.getComment() != null) {
|
||||||
updateSheet(new NodeProperty<>(
|
updateSheet(new NodeProperty<>(
|
||||||
Bundle.BlackboardArtifactNode_createSheet_comment_name(),
|
Bundle.DataArtifactNodev2_createSheet_comment_name(),
|
||||||
Bundle.BlackboardArtifactNode_createSheet_comment_displayName(),
|
Bundle.DataArtifactNodev2_createSheet_comment_displayName(),
|
||||||
NO_DESCR, scoData.getComment()));
|
NO_DESCR, scoData.getComment()));
|
||||||
}
|
}
|
||||||
if (scoData.getCountAndDescription() != null) {
|
if (scoData.getCountAndDescription() != null) {
|
||||||
updateSheet(new NodeProperty<>(
|
updateSheet(new NodeProperty<>(
|
||||||
Bundle.BlackboardArtifactNode_createSheet_count_name(),
|
Bundle.DataArtifactNodev2_createSheet_count_name(),
|
||||||
Bundle.BlackboardArtifactNode_createSheet_count_displayName(),
|
Bundle.DataArtifactNodev2_createSheet_count_displayName(),
|
||||||
scoData.getCountAndDescription().getRight(),
|
scoData.getCountAndDescription().getRight(),
|
||||||
scoData.getCountAndDescription().getLeft()));
|
scoData.getCountAndDescription().getLeft()));
|
||||||
}
|
}
|
||||||
@ -1058,25 +783,96 @@ public class DataArtifactNodev2 extends AbstractContentNode<BlackboardArtifact>
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Sets the displayName of the node based on the source content.
|
* Gets all of the tags applied to the artifact represented by this node and
|
||||||
|
* its source content.
|
||||||
|
*
|
||||||
|
* @return The tags.
|
||||||
*/
|
*/
|
||||||
private void setDisplayNameBySourceContent() {
|
@Override
|
||||||
if (srcContent instanceof BlackboardArtifact) {
|
protected final List<Tag> getAllTagsFromDatabase() {
|
||||||
try {
|
List<Tag> tags = new ArrayList<>();
|
||||||
setDisplayName(((BlackboardArtifact) srcContent).getShortDescription());
|
try {
|
||||||
} catch (TskCoreException ex) {
|
tags.addAll(Case.getCurrentCaseThrows().getServices().getTagsManager().getBlackboardArtifactTagsByArtifact(artifact));
|
||||||
// Log the error, but set the display name to
|
tags.addAll(Case.getCurrentCaseThrows().getServices().getTagsManager().getContentTagsByContent(srcContent));
|
||||||
// Content.getName so there is something visible to the user.
|
} catch (TskCoreException | NoCurrentCaseException ex) {
|
||||||
logger.log(Level.WARNING, "Failed to get short description for artifact id = " + srcContent.getId(), ex);
|
logger.log(Level.SEVERE, MessageFormat.format("Error getting tags for artifact and its source content (artifact objID={0})", artifact.getId()), ex);
|
||||||
setDisplayName(srcContent.getName());
|
|
||||||
}
|
|
||||||
} else if (srcContent instanceof OsAccount) {
|
|
||||||
setDisplayName(((OsAccount) srcContent).getAddr().orElse(srcContent.getName()));
|
|
||||||
} else {
|
|
||||||
setDisplayName(srcContent.getName());
|
|
||||||
}
|
}
|
||||||
|
return tags;
|
||||||
setShortDescription(getDisplayName());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Computes the value of the comment property ("C" in S, C, O) for the
|
||||||
|
* artifact represented by this node.
|
||||||
|
*
|
||||||
|
* An icon is displayed in the property sheet if a commented tag has been
|
||||||
|
* applied to the artifact or its source content, or if there is a
|
||||||
|
* corresponding commented correlation attribute instance in the central
|
||||||
|
* repository.
|
||||||
|
*
|
||||||
|
* @param tags The tags applied to the artifact and its source
|
||||||
|
* content.
|
||||||
|
* @param attributes A correlation attribute instance for the central
|
||||||
|
* repository lookup.
|
||||||
|
*
|
||||||
|
* @return The value of the comment property.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected DataResultViewerTable.HasCommentStatus getCommentProperty(List<Tag> tags, List<CorrelationAttributeInstance> attributes) {
|
||||||
|
/*
|
||||||
|
* Has a tag with a comment been applied to the artifact or its source
|
||||||
|
* content?
|
||||||
|
*/
|
||||||
|
DataResultViewerTable.HasCommentStatus status = tags.size() > 0 ? DataResultViewerTable.HasCommentStatus.TAG_NO_COMMENT : DataResultViewerTable.HasCommentStatus.NO_COMMENT;
|
||||||
|
for (Tag tag : tags) {
|
||||||
|
if (!StringUtils.isBlank(tag.getComment())) {
|
||||||
|
status = DataResultViewerTable.HasCommentStatus.TAG_COMMENT;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*
|
||||||
|
* Is there a comment in the CR for anything that matches the value and
|
||||||
|
* type of the specified attributes.
|
||||||
|
*/
|
||||||
|
try {
|
||||||
|
if (CentralRepoDbUtil.commentExistsOnAttributes(attributes)) {
|
||||||
|
if (status == DataResultViewerTable.HasCommentStatus.TAG_COMMENT) {
|
||||||
|
status = DataResultViewerTable.HasCommentStatus.CR_AND_TAG_COMMENTS;
|
||||||
|
} else {
|
||||||
|
status = DataResultViewerTable.HasCommentStatus.CR_COMMENT;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (CentralRepoException ex) {
|
||||||
|
logger.log(Level.SEVERE, "Attempted to Query CR for presence of comments in a Blackboard Artifact node and was unable to perform query, comment column will only reflect caseDB", ex);
|
||||||
|
}
|
||||||
|
return status;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected Pair<Long, String> getCountPropertyAndDescription(CorrelationAttributeInstance attribute, String defaultDescription) {
|
||||||
|
Long count = -1L;
|
||||||
|
String description = defaultDescription;
|
||||||
|
try {
|
||||||
|
if (attribute != null && StringUtils.isNotBlank(attribute.getCorrelationValue())) {
|
||||||
|
count = CentralRepository.getInstance().getCountCasesWithOtherInstances(attribute);
|
||||||
|
description = Bundle.DataArtifactNodev2_createSheet_count_description(count, attribute.getCorrelationType().getDisplayName());
|
||||||
|
} else if (attribute != null) {
|
||||||
|
description = Bundle.DataArtifactNodev2_createSheet_count_noCorrelationValues_description();
|
||||||
|
}
|
||||||
|
} catch (CentralRepoException ex) {
|
||||||
|
logger.log(Level.SEVERE, MessageFormat.format("Error querying central repository for other occurences count (artifact objID={0}, corrAttrType={1}, corrAttrValue={2})", artifact.getId(), attribute.getCorrelationType(), attribute.getCorrelationValue()), ex);
|
||||||
|
} catch (CorrelationAttributeNormalizationException ex) {
|
||||||
|
logger.log(Level.SEVERE, MessageFormat.format("Error normalizing correlation attribute for central repository query (artifact objID={0}, corrAttrType={2}, corrAttrValue={3})", artifact.getId(), attribute.getCorrelationType(), attribute.getCorrelationValue()), ex);
|
||||||
|
}
|
||||||
|
return Pair.of(count, description);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public <T> T accept(ContentNodeVisitor<T> visitor) {
|
||||||
|
throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates.
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public <T> T accept(DisplayableItemNodeVisitor<T> visitor) {
|
||||||
|
throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates.
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -88,8 +88,8 @@ public class ThreePanelDAO {
|
|||||||
: null;
|
: null;
|
||||||
|
|
||||||
Content srcContent = artifact.getParent();
|
Content srcContent = artifact.getParent();
|
||||||
String srcContentTypeName = getSourceObjType(srcContent);
|
String dataSourceName = getDataSourceName(srcContent);
|
||||||
rows.add(new DataArtifactRow(id, attributeValues, srcContent, srcContentTypeName, linkedFile));
|
rows.add(new DataArtifactRow(id, attributeValues, artifact, srcContent, linkedFile, dataSourceName));
|
||||||
}
|
}
|
||||||
|
|
||||||
List<BlackboardAttribute.Type> attributeTypeSortedList = attributeTypes.stream()
|
List<BlackboardAttribute.Type> attributeTypeSortedList = attributeTypes.stream()
|
||||||
@ -99,6 +99,33 @@ public class ThreePanelDAO {
|
|||||||
return new DataArtifactTableDTO(artType, attributeTypeSortedList, rows);
|
return new DataArtifactTableDTO(artType, attributeTypeSortedList, rows);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private String getDataSourceName(Content srcContent) throws TskCoreException {
|
||||||
|
Content dataSource = srcContent.getDataSource();
|
||||||
|
if (dataSource != null) {
|
||||||
|
return dataSource.getName();
|
||||||
|
} else {
|
||||||
|
return getRootAncestorName(srcContent);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the name of the root ancestor of the source content for the artifact
|
||||||
|
* represented by this node.
|
||||||
|
*
|
||||||
|
* @param srcContent The source content.
|
||||||
|
*
|
||||||
|
* @return The root ancestor name or the empty string if an error occurs.
|
||||||
|
*/
|
||||||
|
private String getRootAncestorName(Content srcContent) throws TskCoreException {
|
||||||
|
String parentName = srcContent.getName();
|
||||||
|
Content parent = srcContent;
|
||||||
|
|
||||||
|
while ((parent = parent.getParent()) != null) {
|
||||||
|
parentName = parent.getName();
|
||||||
|
}
|
||||||
|
return parentName;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a displayable type string for the given content object.
|
* Returns a displayable type string for the given content object.
|
||||||
*
|
*
|
||||||
@ -226,17 +253,18 @@ public class ThreePanelDAO {
|
|||||||
|
|
||||||
private final Map<String, Object> attributeValues;
|
private final Map<String, Object> attributeValues;
|
||||||
|
|
||||||
|
private final DataArtifact dataArtifact;
|
||||||
private final Content srcContent;
|
private final Content srcContent;
|
||||||
private final String srcContentTypeName;
|
|
||||||
private final Content linkedFile;
|
private final Content linkedFile;
|
||||||
private String dataSourceName;
|
private String dataSourceName;
|
||||||
|
|
||||||
public DataArtifactRow(long id, Map<String, Object> attributeValues, Content srcContent, String srcContentTypeName, Content linkedFile) {
|
public DataArtifactRow(long id, Map<String, Object> attributeValues, DataArtifact dataArtifact, Content srcContent, Content linkedFile, String dataSourceName) {
|
||||||
this.id = id;
|
this.id = id;
|
||||||
this.attributeValues = attributeValues;
|
this.attributeValues = attributeValues;
|
||||||
|
this.dataArtifact = dataArtifact;
|
||||||
this.srcContent = srcContent;
|
this.srcContent = srcContent;
|
||||||
this.srcContentTypeName = srcContentTypeName;
|
|
||||||
this.linkedFile = linkedFile;
|
this.linkedFile = linkedFile;
|
||||||
|
this.dataSourceName = dataSourceName;
|
||||||
}
|
}
|
||||||
|
|
||||||
public long getId() {
|
public long getId() {
|
||||||
@ -247,12 +275,12 @@ public class ThreePanelDAO {
|
|||||||
return attributeValues;
|
return attributeValues;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Content getSrcContent() {
|
public DataArtifact getDataArtifact() {
|
||||||
return srcContent;
|
return dataArtifact;
|
||||||
}
|
}
|
||||||
|
|
||||||
public String getSrcContentTypeName() {
|
public Content getSrcContent() {
|
||||||
return srcContentTypeName;
|
return srcContent;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Content getLinkedFile() {
|
public Content getLinkedFile() {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user