mirror of
https://github.com/overcuriousity/autopsy-flatpak.git
synced 2025-07-12 16:06:15 +00:00
Merge remote-tracking branch 'upstream/develop' into 3873_RefineEncryptionDetectionHeuristics
This commit is contained in:
commit
fc8587cd0d
@ -96,6 +96,10 @@
|
|||||||
<get src="https://drive.google.com/uc?id=1bghoSm7z7nhmGIxlllyY1MMlbLntxm7n" dest="${test-input}/local_files_test.zip" skipexisting="true"/>
|
<get src="https://drive.google.com/uc?id=1bghoSm7z7nhmGIxlllyY1MMlbLntxm7n" dest="${test-input}/local_files_test.zip" skipexisting="true"/>
|
||||||
<get src="https://drive.google.com/uc?id=1BrSiUQ1fzxFS9vIaK4mYKX6qIVp9kRWT" dest="${test-input}/password_detection_test.img" skipexisting="true"/>
|
<get src="https://drive.google.com/uc?id=1BrSiUQ1fzxFS9vIaK4mYKX6qIVp9kRWT" dest="${test-input}/password_detection_test.img" skipexisting="true"/>
|
||||||
<get src="https://drive.google.com/uc?id=1HD8s4rculgHV1qZT5g80Kg7j4m1qccrN" dest="${test-input}/veracrypt_detection_test.vhd" skipexisting="true"/>
|
<get src="https://drive.google.com/uc?id=1HD8s4rculgHV1qZT5g80Kg7j4m1qccrN" dest="${test-input}/veracrypt_detection_test.vhd" skipexisting="true"/>
|
||||||
|
<get src="https://drive.google.com/uc?id=1O5D09fFCFpXZqw0uLEs8kVLtfYTxqXAd" dest="${test-input}/commonfiles_image1_v1.vhd" skipexisting="true"/>
|
||||||
|
<get src="https://drive.google.com/uc?id=1rMP1QTI0LdppzdypbG-4BDwkKcR3tHXc" dest="${test-input}/commonfiles_image2_v1.vhd" skipexisting="true"/>
|
||||||
|
<get src="https://drive.google.com/uc?id=1OdwyJ2lru55ZPdvwzj3pq6sXIys27i4x" dest="${test-input}/commonfiles_image3_v1.vhd" skipexisting="true"/>
|
||||||
|
<get src="https://drive.google.com/uc?id=1GoF2x0km5AyFvE926ttN20lrMX1oLN7E" dest="${test-input}/commonfiles_image4_v1.vhd" skipexisting="true"/>
|
||||||
</target>
|
</target>
|
||||||
|
|
||||||
<target name="get-deps" depends="init-ivy,getTSKJars,get-thirdparty-dependencies,get-InternalPythonModules, download-binlist,getTestDataFiles">
|
<target name="get-deps" depends="init-ivy,getTSKJars,get-thirdparty-dependencies,get-InternalPythonModules, download-binlist,getTestDataFiles">
|
||||||
|
@ -24,7 +24,7 @@ import java.util.Map;
|
|||||||
/**
|
/**
|
||||||
* Provides logic for selecting common files from all data sources.
|
* Provides logic for selecting common files from all data sources.
|
||||||
*/
|
*/
|
||||||
final class AllDataSourcesCommonFilesAlgorithm extends CommonFilesMetadataBuilder {
|
final public class AllDataSourcesCommonFilesAlgorithm extends CommonFilesMetadataBuilder {
|
||||||
|
|
||||||
private static final String WHERE_CLAUSE = "%s md5 in (select md5 from tsk_files where (known != 1 OR known IS NULL)%s GROUP BY md5 HAVING COUNT(*) > 1) order by md5"; //NON-NLS
|
private static final String WHERE_CLAUSE = "%s md5 in (select md5 from tsk_files where (known != 1 OR known IS NULL)%s GROUP BY md5 HAVING COUNT(*) > 1) order by md5"; //NON-NLS
|
||||||
|
|
||||||
@ -36,7 +36,7 @@ final class AllDataSourcesCommonFilesAlgorithm extends CommonFilesMetadataBuilde
|
|||||||
* @param filterByMediaMimeType match only on files whose mime types can be broadly categorized as media types
|
* @param filterByMediaMimeType match only on files whose mime types can be broadly categorized as media types
|
||||||
* @param filterByDocMimeType match only on files whose mime types can be broadly categorized as document types
|
* @param filterByDocMimeType match only on files whose mime types can be broadly categorized as document types
|
||||||
*/
|
*/
|
||||||
AllDataSourcesCommonFilesAlgorithm(Map<Long, String> dataSourceIdMap, boolean filterByMediaMimeType, boolean filterByDocMimeType) {
|
public AllDataSourcesCommonFilesAlgorithm(Map<Long, String> dataSourceIdMap, boolean filterByMediaMimeType, boolean filterByDocMimeType) {
|
||||||
super(dataSourceIdMap, filterByMediaMimeType, filterByDocMimeType);
|
super(dataSourceIdMap, filterByMediaMimeType, filterByDocMimeType);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -26,7 +26,7 @@ import java.util.Map;
|
|||||||
* Utility and wrapper model around data required for Common Files Search results.
|
* Utility and wrapper model around data required for Common Files Search results.
|
||||||
* Subclass this to implement different selections of files from the case.
|
* Subclass this to implement different selections of files from the case.
|
||||||
*/
|
*/
|
||||||
final class CommonFilesMetadata {
|
final public class CommonFilesMetadata {
|
||||||
|
|
||||||
private final Map<String, Md5Metadata> metadata;
|
private final Map<String, Md5Metadata> metadata;
|
||||||
|
|
||||||
@ -52,7 +52,7 @@ final class CommonFilesMetadata {
|
|||||||
return this.metadata.get(md5);
|
return this.metadata.get(md5);
|
||||||
}
|
}
|
||||||
|
|
||||||
Map<String, Md5Metadata> getMetadata() {
|
public Map<String, Md5Metadata> getMetadata() {
|
||||||
return Collections.unmodifiableMap(this.metadata);
|
return Collections.unmodifiableMap(this.metadata);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -60,7 +60,7 @@ final class CommonFilesMetadata {
|
|||||||
* How many distinct file instances exist for this metadata?
|
* How many distinct file instances exist for this metadata?
|
||||||
* @return number of file instances
|
* @return number of file instances
|
||||||
*/
|
*/
|
||||||
int size() {
|
public int size() {
|
||||||
int count = 0;
|
int count = 0;
|
||||||
for (Md5Metadata data : this.metadata.values()) {
|
for (Md5Metadata data : this.metadata.values()) {
|
||||||
count += data.size();
|
count += data.size();
|
||||||
|
@ -46,7 +46,7 @@ import org.sleuthkit.datamodel.TskCoreException;
|
|||||||
* This entire thing runs on a background thread where exceptions are handled.
|
* This entire thing runs on a background thread where exceptions are handled.
|
||||||
*/
|
*/
|
||||||
@SuppressWarnings("PMD.AbstractNaming")
|
@SuppressWarnings("PMD.AbstractNaming")
|
||||||
abstract class CommonFilesMetadataBuilder {
|
public abstract class CommonFilesMetadataBuilder {
|
||||||
|
|
||||||
private final Map<Long, String> dataSourceIdToNameMap;
|
private final Map<Long, String> dataSourceIdToNameMap;
|
||||||
private final boolean filterByMedia;
|
private final boolean filterByMedia;
|
||||||
|
@ -18,12 +18,9 @@
|
|||||||
*/
|
*/
|
||||||
package org.sleuthkit.autopsy.commonfilesearch;
|
package org.sleuthkit.autopsy.commonfilesearch;
|
||||||
|
|
||||||
import java.io.File;
|
|
||||||
import java.sql.ResultSet;
|
|
||||||
import java.sql.SQLException;
|
import java.sql.SQLException;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Map.Entry;
|
import java.util.Map.Entry;
|
||||||
import java.util.concurrent.ExecutionException;
|
import java.util.concurrent.ExecutionException;
|
||||||
@ -33,7 +30,6 @@ import javax.swing.SwingUtilities;
|
|||||||
import javax.swing.SwingWorker;
|
import javax.swing.SwingWorker;
|
||||||
import org.openide.explorer.ExplorerManager;
|
import org.openide.explorer.ExplorerManager;
|
||||||
import org.openide.util.NbBundle;
|
import org.openide.util.NbBundle;
|
||||||
import org.sleuthkit.autopsy.casemodule.Case;
|
|
||||||
import org.sleuthkit.autopsy.casemodule.NoCurrentCaseException;
|
import org.sleuthkit.autopsy.casemodule.NoCurrentCaseException;
|
||||||
import org.sleuthkit.autopsy.corecomponentinterfaces.DataResultViewer;
|
import org.sleuthkit.autopsy.corecomponentinterfaces.DataResultViewer;
|
||||||
import org.sleuthkit.autopsy.corecomponents.DataResultTopComponent;
|
import org.sleuthkit.autopsy.corecomponents.DataResultTopComponent;
|
||||||
@ -42,8 +38,6 @@ import org.sleuthkit.autopsy.corecomponents.TableFilterNode;
|
|||||||
import org.sleuthkit.autopsy.coreutils.Logger;
|
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||||
import org.sleuthkit.autopsy.coreutils.MessageNotifyUtil;
|
import org.sleuthkit.autopsy.coreutils.MessageNotifyUtil;
|
||||||
import org.sleuthkit.autopsy.directorytree.DataResultFilterNode;
|
import org.sleuthkit.autopsy.directorytree.DataResultFilterNode;
|
||||||
import org.sleuthkit.datamodel.SleuthkitCase;
|
|
||||||
import org.sleuthkit.datamodel.SleuthkitCase.CaseDbQuery;
|
|
||||||
import org.sleuthkit.datamodel.TskCoreException;
|
import org.sleuthkit.datamodel.TskCoreException;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -76,7 +70,7 @@ public final class CommonFilesPanel extends javax.swing.JPanel {
|
|||||||
initComponents();
|
initComponents();
|
||||||
|
|
||||||
this.setupDataSources();
|
this.setupDataSources();
|
||||||
|
|
||||||
this.errorText.setVisible(false);
|
this.errorText.setVisible(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -97,10 +91,6 @@ public final class CommonFilesPanel extends javax.swing.JPanel {
|
|||||||
|
|
||||||
new SwingWorker<Map<Long, String>, Void>() {
|
new SwingWorker<Map<Long, String>, Void>() {
|
||||||
|
|
||||||
private static final String SELECT_DATA_SOURCES_LOGICAL = "select obj_id, name from tsk_files where obj_id in (SELECT obj_id FROM tsk_objects WHERE obj_id in (select obj_id from data_source_info))";
|
|
||||||
|
|
||||||
private static final String SELECT_DATA_SOURCES_IMAGE = "select obj_id, name from tsk_image_names where obj_id in (SELECT obj_id FROM tsk_objects WHERE obj_id in (select obj_id from data_source_info))";
|
|
||||||
|
|
||||||
private void updateUi() {
|
private void updateUi() {
|
||||||
|
|
||||||
String[] dataSourcesNames = new String[CommonFilesPanel.this.dataSourceMap.size()];
|
String[] dataSourcesNames = new String[CommonFilesPanel.this.dataSourceMap.size()];
|
||||||
@ -131,48 +121,10 @@ public final class CommonFilesPanel extends javax.swing.JPanel {
|
|||||||
return CommonFilesPanel.this.dataSourceMap.size() >= 2;
|
return CommonFilesPanel.this.dataSourceMap.size() >= 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void loadLogicalSources(SleuthkitCase tskDb, Map<Long, String> dataSouceMap) throws TskCoreException, SQLException {
|
|
||||||
//try block releases resources - exceptions are handled in done()
|
|
||||||
try (
|
|
||||||
CaseDbQuery query = tskDb.executeQuery(SELECT_DATA_SOURCES_LOGICAL);
|
|
||||||
ResultSet resultSet = query.getResultSet()) {
|
|
||||||
while (resultSet.next()) {
|
|
||||||
Long objectId = resultSet.getLong(1);
|
|
||||||
String dataSourceName = resultSet.getString(2);
|
|
||||||
dataSouceMap.put(objectId, dataSourceName);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void loadImageSources(SleuthkitCase tskDb, Map<Long, String> dataSouceMap) throws SQLException, TskCoreException {
|
|
||||||
//try block releases resources - exceptions are handled in done()
|
|
||||||
try (
|
|
||||||
CaseDbQuery query = tskDb.executeQuery(SELECT_DATA_SOURCES_IMAGE);
|
|
||||||
ResultSet resultSet = query.getResultSet()) {
|
|
||||||
|
|
||||||
while (resultSet.next()) {
|
|
||||||
Long objectId = resultSet.getLong(1);
|
|
||||||
String dataSourceName = resultSet.getString(2);
|
|
||||||
File image = new File(dataSourceName);
|
|
||||||
String dataSourceNameTrimmed = image.getName();
|
|
||||||
dataSouceMap.put(objectId, dataSourceNameTrimmed);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected Map<Long, String> doInBackground() throws NoCurrentCaseException, TskCoreException, SQLException {
|
protected Map<Long, String> doInBackground() throws NoCurrentCaseException, TskCoreException, SQLException {
|
||||||
|
DataSourceLoader loader = new DataSourceLoader();
|
||||||
Map<Long, String> dataSouceMap = new HashMap<>();
|
return loader.getDataSourceMap();
|
||||||
|
|
||||||
Case currentCase = Case.getCurrentCaseThrows();
|
|
||||||
SleuthkitCase tskDb = currentCase.getSleuthkitCase();
|
|
||||||
|
|
||||||
loadLogicalSources(tskDb, dataSouceMap);
|
|
||||||
|
|
||||||
loadImageSources(tskDb, dataSouceMap);
|
|
||||||
|
|
||||||
return dataSouceMap;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -295,10 +247,10 @@ public final class CommonFilesPanel extends javax.swing.JPanel {
|
|||||||
TableFilterNode tableFilterWithDescendantsNode = new TableFilterNode(dataResultFilterNode);
|
TableFilterNode tableFilterWithDescendantsNode = new TableFilterNode(dataResultFilterNode);
|
||||||
|
|
||||||
DataResultViewerTable table = new DataResultViewerTable();
|
DataResultViewerTable table = new DataResultViewerTable();
|
||||||
|
|
||||||
Collection<DataResultViewer> viewers = new ArrayList<>(1);
|
Collection<DataResultViewer> viewers = new ArrayList<>(1);
|
||||||
viewers.add(table);
|
viewers.add(table);
|
||||||
|
|
||||||
DataResultTopComponent.createInstance(tabTitle, pathText, tableFilterWithDescendantsNode, metadata.size(), viewers);
|
DataResultTopComponent.createInstance(tabTitle, pathText, tableFilterWithDescendantsNode, metadata.size(), viewers);
|
||||||
|
|
||||||
} catch (InterruptedException ex) {
|
} catch (InterruptedException ex) {
|
||||||
@ -590,7 +542,7 @@ public final class CommonFilesPanel extends javax.swing.JPanel {
|
|||||||
|
|
||||||
this.pictureVideoCheckbox.setEnabled(true);
|
this.pictureVideoCheckbox.setEnabled(true);
|
||||||
this.documentsCheckbox.setEnabled(true);
|
this.documentsCheckbox.setEnabled(true);
|
||||||
|
|
||||||
this.toggleErrorTextAndSearchBox();
|
this.toggleErrorTextAndSearchBox();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -0,0 +1,95 @@
|
|||||||
|
/*
|
||||||
|
*
|
||||||
|
* Autopsy Forensic Browser
|
||||||
|
*
|
||||||
|
* Copyright 2018 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.commonfilesearch;
|
||||||
|
|
||||||
|
import java.io.File;
|
||||||
|
import java.sql.ResultSet;
|
||||||
|
import java.sql.SQLException;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.Map;
|
||||||
|
import org.sleuthkit.autopsy.casemodule.Case;
|
||||||
|
import org.sleuthkit.autopsy.casemodule.NoCurrentCaseException;
|
||||||
|
import org.sleuthkit.datamodel.SleuthkitCase;
|
||||||
|
import org.sleuthkit.datamodel.TskCoreException;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Encapsulates logic required to create a mapping of data sources in the
|
||||||
|
* current case to their data source IDs.
|
||||||
|
*
|
||||||
|
* Intended to be used within the context of a SwingWorker or other background
|
||||||
|
* thread.
|
||||||
|
*/
|
||||||
|
public class DataSourceLoader {
|
||||||
|
|
||||||
|
private static final String SELECT_DATA_SOURCES_LOGICAL = "select obj_id, name from tsk_files where obj_id in (SELECT obj_id FROM tsk_objects WHERE obj_id in (select obj_id from data_source_info))";
|
||||||
|
|
||||||
|
private static final String SELECT_DATA_SOURCES_IMAGE = "select obj_id, name from tsk_image_names where obj_id in (SELECT obj_id FROM tsk_objects WHERE obj_id in (select obj_id from data_source_info))";
|
||||||
|
|
||||||
|
private void loadLogicalSources(SleuthkitCase tskDb, Map<Long, String> dataSouceMap) throws TskCoreException, SQLException {
|
||||||
|
//try block releases resources - exceptions are handled in done()
|
||||||
|
try (
|
||||||
|
SleuthkitCase.CaseDbQuery query = tskDb.executeQuery(SELECT_DATA_SOURCES_LOGICAL);
|
||||||
|
ResultSet resultSet = query.getResultSet()
|
||||||
|
) {
|
||||||
|
while (resultSet.next()) {
|
||||||
|
Long objectId = resultSet.getLong(1);
|
||||||
|
String dataSourceName = resultSet.getString(2);
|
||||||
|
dataSouceMap.put(objectId, dataSourceName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void loadImageSources(SleuthkitCase tskDb, Map<Long, String> dataSouceMap) throws SQLException, TskCoreException {
|
||||||
|
//try block releases resources - exceptions are handled in done()
|
||||||
|
try (
|
||||||
|
SleuthkitCase.CaseDbQuery query = tskDb.executeQuery(SELECT_DATA_SOURCES_IMAGE);
|
||||||
|
ResultSet resultSet = query.getResultSet()) {
|
||||||
|
|
||||||
|
while (resultSet.next()) {
|
||||||
|
Long objectId = resultSet.getLong(1);
|
||||||
|
String dataSourceName = resultSet.getString(2);
|
||||||
|
File image = new File(dataSourceName);
|
||||||
|
String dataSourceNameTrimmed = image.getName();
|
||||||
|
dataSouceMap.put(objectId, dataSourceNameTrimmed);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get a map of data source Ids to their string names for the current case.
|
||||||
|
*
|
||||||
|
* @return Map of Long (id) to String (name)
|
||||||
|
* @throws NoCurrentCaseException
|
||||||
|
* @throws TskCoreException
|
||||||
|
* @throws SQLException
|
||||||
|
*/
|
||||||
|
public Map<Long, String> getDataSourceMap() throws NoCurrentCaseException, TskCoreException, SQLException {
|
||||||
|
Map<Long, String> dataSouceMap = new HashMap<>();
|
||||||
|
|
||||||
|
Case currentCase = Case.getCurrentCaseThrows();
|
||||||
|
SleuthkitCase tskDb = currentCase.getSleuthkitCase();
|
||||||
|
|
||||||
|
loadLogicalSources(tskDb, dataSouceMap);
|
||||||
|
|
||||||
|
loadImageSources(tskDb, dataSouceMap);
|
||||||
|
|
||||||
|
return dataSouceMap;
|
||||||
|
}
|
||||||
|
}
|
@ -24,7 +24,7 @@ import java.util.Map;
|
|||||||
/**
|
/**
|
||||||
* Provides logic for selecting common files from a single data source.
|
* Provides logic for selecting common files from a single data source.
|
||||||
*/
|
*/
|
||||||
final class SingleDataSource extends CommonFilesMetadataBuilder {
|
final public class SingleDataSource extends CommonFilesMetadataBuilder {
|
||||||
|
|
||||||
private static final String WHERE_CLAUSE = "%s md5 in (select md5 from tsk_files where md5 in (select md5 from tsk_files where (known != 1 OR known IS NULL) and data_source_obj_id=%s%s) GROUP BY md5 HAVING COUNT(*) > 1) order by md5"; //NON-NLS
|
private static final String WHERE_CLAUSE = "%s md5 in (select md5 from tsk_files where md5 in (select md5 from tsk_files where (known != 1 OR known IS NULL) and data_source_obj_id=%s%s) GROUP BY md5 HAVING COUNT(*) > 1) order by md5"; //NON-NLS
|
||||||
private final Long selectedDataSourceId;
|
private final Long selectedDataSourceId;
|
||||||
@ -35,10 +35,12 @@ final class SingleDataSource extends CommonFilesMetadataBuilder {
|
|||||||
* once in the given data source
|
* once in the given data source
|
||||||
* @param dataSourceId data source id for which common files must appear at least once
|
* @param dataSourceId data source id for which common files must appear at least once
|
||||||
* @param dataSourceIdMap a map of obj_id to datasource name
|
* @param dataSourceIdMap a map of obj_id to datasource name
|
||||||
* @param filterByMediaMimeType match only on files whose mime types can be broadly categorized as media types
|
* @param filterByMediaMimeType match only on files whose mime types can be
|
||||||
* @param filterByDocMimeType match only on files whose mime types can be broadly categorized as document types
|
* broadly categorized as media types
|
||||||
|
* @param filterByDocMimeType match only on files whose mime types can be
|
||||||
|
* broadly categorized as document types
|
||||||
*/
|
*/
|
||||||
SingleDataSource(Long dataSourceId, Map<Long, String> dataSourceIdMap, boolean filterByMediaMimeType, boolean filterByDocMimeType) {
|
public SingleDataSource(Long dataSourceId, Map<Long, String> dataSourceIdMap, boolean filterByMediaMimeType, boolean filterByDocMimeType) {
|
||||||
super(dataSourceIdMap, filterByMediaMimeType, filterByDocMimeType);
|
super(dataSourceIdMap, filterByMediaMimeType, filterByDocMimeType);
|
||||||
this.selectedDataSourceId = dataSourceId;
|
this.selectedDataSourceId = dataSourceId;
|
||||||
this.dataSourceName = dataSourceIdMap.get(this.selectedDataSourceId);
|
this.dataSourceName = dataSourceIdMap.get(this.selectedDataSourceId);
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
/*
|
/*
|
||||||
* Autopsy Forensic Browser
|
* Autopsy Forensic Browser
|
||||||
*
|
*
|
||||||
* Copyright 2011-2017 Basis Technology Corp.
|
* Copyright 2011-2018 Basis Technology Corp.
|
||||||
* Contact: carrier <at> sleuthkit <dot> org
|
* Contact: carrier <at> sleuthkit <dot> org
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
@ -28,7 +28,9 @@ import org.openide.nodes.Children;
|
|||||||
import org.openide.nodes.Sheet;
|
import org.openide.nodes.Sheet;
|
||||||
import org.openide.util.Lookup;
|
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.lookup.Lookups;
|
import org.openide.util.lookup.Lookups;
|
||||||
|
import org.sleuthkit.autopsy.directorytree.ViewContextAction;
|
||||||
import org.sleuthkit.autopsy.timeline.actions.ViewFileInTimelineAction;
|
import org.sleuthkit.autopsy.timeline.actions.ViewFileInTimelineAction;
|
||||||
import org.sleuthkit.datamodel.AbstractFile;
|
import org.sleuthkit.datamodel.AbstractFile;
|
||||||
|
|
||||||
@ -107,17 +109,21 @@ public class KeyValueNode extends AbstractNode {
|
|||||||
*
|
*
|
||||||
* @return actions
|
* @return actions
|
||||||
*/
|
*/
|
||||||
|
@Messages({
|
||||||
|
"KeyValueNode.menuItemText.viewFileInDir=View Source File in Directory"
|
||||||
|
})
|
||||||
@Override
|
@Override
|
||||||
public Action[] getActions(boolean popup) {
|
public Action[] getActions(boolean popup) {
|
||||||
List<Action> actions = new ArrayList<>();
|
List<Action> actionsList = new ArrayList<>();
|
||||||
actions.addAll(Arrays.asList(super.getActions(popup)));
|
actionsList.addAll(Arrays.asList(super.getActions(popup)));
|
||||||
//if this artifact has associated content, add the action to view the content in the timeline
|
// If this artifact has associated content, add the actions.
|
||||||
AbstractFile file = getLookup().lookup(AbstractFile.class);
|
AbstractFile file = getLookup().lookup(AbstractFile.class);
|
||||||
if (null != file) {
|
if (null != file) {
|
||||||
actions.add(ViewFileInTimelineAction.createViewSourceFileAction(file));
|
actionsList.add(ViewFileInTimelineAction.createViewSourceFileAction(file));
|
||||||
|
actionsList.add(new ViewContextAction(Bundle.KeyValueNode_menuItemText_viewFileInDir(), file));
|
||||||
}
|
}
|
||||||
actions.add(null); // creates a menu separator
|
actionsList.add(null); // creates a menu separator
|
||||||
|
|
||||||
return actions.toArray(new Action[actions.size()]);
|
return actionsList.toArray(new Action[actionsList.size()]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -65,10 +65,12 @@ public class DataSourcePanel extends javax.swing.JPanel {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void mouseMoved(MouseEvent evt) {
|
public void mouseMoved(MouseEvent evt) {
|
||||||
JList<String> DsList = (JList<String>) evt.getSource();
|
if (evt.getSource() instanceof JList<?>) {
|
||||||
int index = DsList.locationToIndex(evt.getPoint());
|
JList<?> dsList = (JList<?>) evt.getSource();
|
||||||
if (index > -1) {
|
int index = dsList.locationToIndex(evt.getPoint());
|
||||||
DsList.setToolTipText(toolTipList.get(index));
|
if (index > -1) {
|
||||||
|
dsList.setToolTipText(toolTipList.get(index));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
@ -190,7 +190,7 @@ public final class EnterpriseHealthMonitor implements PropertyChangeListener {
|
|||||||
stopTimer();
|
stopTimer();
|
||||||
|
|
||||||
healthMonitorOutputTimer = new ScheduledThreadPoolExecutor(1, new ThreadFactoryBuilder().setNameFormat("health_monitor_timer").build());
|
healthMonitorOutputTimer = new ScheduledThreadPoolExecutor(1, new ThreadFactoryBuilder().setNameFormat("health_monitor_timer").build());
|
||||||
healthMonitorOutputTimer.scheduleWithFixedDelay(new PeriodicHealthMonitorTask(), DATABASE_WRITE_INTERVAL, DATABASE_WRITE_INTERVAL, TimeUnit.MINUTES);
|
healthMonitorOutputTimer.scheduleWithFixedDelay(new PeriodicHealthMonitorTask(false), DATABASE_WRITE_INTERVAL, DATABASE_WRITE_INTERVAL, TimeUnit.MINUTES);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -356,11 +356,16 @@ public final class EnterpriseHealthMonitor implements PropertyChangeListener {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Collect metrics at a scheduled time.
|
* Collect metrics at a scheduled time.
|
||||||
|
* @param caseIsClosing True if this was triggered from a case closed event
|
||||||
* @throws HealthMonitorException
|
* @throws HealthMonitorException
|
||||||
*/
|
*/
|
||||||
private void gatherTimerBasedMetrics() throws HealthMonitorException {
|
private void gatherTimerBasedMetrics(boolean caseIsClosing) throws HealthMonitorException {
|
||||||
// Time a database query
|
// Time a database query. If this was triggered from a case close event
|
||||||
performDatabaseQuery();
|
// it will fail - since we're on a new thread the case database will
|
||||||
|
// be in the process of closing. In that case, skip collecting the metric.
|
||||||
|
if( ! caseIsClosing) {
|
||||||
|
performDatabaseQuery();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -806,17 +811,23 @@ public final class EnterpriseHealthMonitor implements PropertyChangeListener {
|
|||||||
*/
|
*/
|
||||||
static final class PeriodicHealthMonitorTask implements Runnable {
|
static final class PeriodicHealthMonitorTask implements Runnable {
|
||||||
|
|
||||||
|
boolean caseIsClosing;
|
||||||
|
|
||||||
|
PeriodicHealthMonitorTask(boolean caseIsClosing) {
|
||||||
|
this.caseIsClosing = caseIsClosing;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Perform all periodic tasks:
|
* Perform all periodic tasks:
|
||||||
* - Check if monitoring has been enabled / disabled in the database
|
* - Check if monitoring has been enabled / disabled in the database
|
||||||
* - Gather any additional metrics
|
* - Calculate any final metrics
|
||||||
* - Write current metric data to the database
|
* - Write current metric data to the database
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
try {
|
try {
|
||||||
getInstance().updateFromGlobalEnabledStatus();
|
getInstance().updateFromGlobalEnabledStatus();
|
||||||
getInstance().gatherTimerBasedMetrics();
|
getInstance().gatherTimerBasedMetrics(caseIsClosing);
|
||||||
getInstance().writeCurrentStateToDatabase();
|
getInstance().writeCurrentStateToDatabase();
|
||||||
} catch (HealthMonitorException ex) {
|
} catch (HealthMonitorException ex) {
|
||||||
logger.log(Level.SEVERE, "Error performing periodic task", ex); //NON-NLS
|
logger.log(Level.SEVERE, "Error performing periodic task", ex); //NON-NLS
|
||||||
@ -832,7 +843,7 @@ public final class EnterpriseHealthMonitor implements PropertyChangeListener {
|
|||||||
case CURRENT_CASE:
|
case CURRENT_CASE:
|
||||||
if ((null == evt.getNewValue()) && (evt.getOldValue() instanceof Case)) {
|
if ((null == evt.getNewValue()) && (evt.getOldValue() instanceof Case)) {
|
||||||
// When a case is closed, write the current metrics to the database
|
// When a case is closed, write the current metrics to the database
|
||||||
healthMonitorExecutor.submit(new EnterpriseHealthMonitor.PeriodicHealthMonitorTask());
|
healthMonitorExecutor.submit(new EnterpriseHealthMonitor.PeriodicHealthMonitorTask(true));
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -373,7 +373,7 @@ class TimingMetricGraphPanel extends JPanel {
|
|||||||
}
|
}
|
||||||
} else if (y0value > maxValueOnYAxis) {
|
} else if (y0value > maxValueOnYAxis) {
|
||||||
try {
|
try {
|
||||||
y0value = minValueOnYAxis;
|
y0value = maxValueOnYAxis;
|
||||||
x0value = trendLine.getXGivenY(y0value);
|
x0value = trendLine.getXGivenY(y0value);
|
||||||
} catch (HealthMonitorException ex) {
|
} catch (HealthMonitorException ex) {
|
||||||
// The exception is caused by a slope of zero on the trend line, which
|
// The exception is caused by a slope of zero on the trend line, which
|
||||||
|
@ -9,8 +9,8 @@ OpenIDE-Module-Name=Embedded File Extraction
|
|||||||
OpenIDE-Module-Short-Description=Embedded File Extraction Ingest Module
|
OpenIDE-Module-Short-Description=Embedded File Extraction Ingest Module
|
||||||
EmbeddedFileExtractorIngestModule.SevenZipContentReadStream.seek.exception.invalidOrigin=Invalid seek origin\: {0}
|
EmbeddedFileExtractorIngestModule.SevenZipContentReadStream.seek.exception.invalidOrigin=Invalid seek origin\: {0}
|
||||||
EmbeddedFileExtractorIngestModule.SevenZipContentReadStream.read.exception.errReadStream=Error reading content stream.
|
EmbeddedFileExtractorIngestModule.SevenZipContentReadStream.read.exception.errReadStream=Error reading content stream.
|
||||||
EmbeddedFileExtractorIngestModule.ArchiveExtractor.encryptionFileLevel=File-level Encryption
|
EmbeddedFileExtractorIngestModule.ArchiveExtractor.encryptionFileLevel=Content-only Encryption (Archive File)
|
||||||
EmbeddedFileExtractorIngestModule.ArchiveExtractor.encryptionFull=Full Encryption
|
EmbeddedFileExtractorIngestModule.ArchiveExtractor.encryptionFull=Full Encryption (Archive File)
|
||||||
EmbeddedFileExtractorIngestModule.ArchiveExtractor.init.errInitModule.details=Error initializing output dir\: {0}\: {1}
|
EmbeddedFileExtractorIngestModule.ArchiveExtractor.init.errInitModule.details=Error initializing output dir\: {0}\: {1}
|
||||||
EmbeddedFileExtractorIngestModule.ArchiveExtractor.isZipBombCheck.warnMsg=Possible ZIP bomb detected in archive\: {0}, item\: {1}
|
EmbeddedFileExtractorIngestModule.ArchiveExtractor.isZipBombCheck.warnMsg=Possible ZIP bomb detected in archive\: {0}, item\: {1}
|
||||||
EmbeddedFileExtractorIngestModule.ArchiveExtractor.isZipBombCheck.warnDetails=Compression ratio is {0}, skipping item in {1}.
|
EmbeddedFileExtractorIngestModule.ArchiveExtractor.isZipBombCheck.warnDetails=Compression ratio is {0}, skipping item in {1}.
|
||||||
|
@ -18,8 +18,6 @@
|
|||||||
*/
|
*/
|
||||||
package org.sleuthkit.autopsy.modules.hashdatabase;
|
package org.sleuthkit.autopsy.modules.hashdatabase;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.List;
|
|
||||||
import org.openide.util.NbBundle;
|
import org.openide.util.NbBundle;
|
||||||
import org.openide.util.lookup.ServiceProvider;
|
import org.openide.util.lookup.ServiceProvider;
|
||||||
import org.sleuthkit.autopsy.casemodule.NoCurrentCaseException;
|
import org.sleuthkit.autopsy.casemodule.NoCurrentCaseException;
|
||||||
|
@ -0,0 +1,465 @@
|
|||||||
|
/*
|
||||||
|
*
|
||||||
|
* Autopsy Forensic Browser
|
||||||
|
*
|
||||||
|
* Copyright 2018 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.commonfilessearch;
|
||||||
|
|
||||||
|
import java.sql.SQLException;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
import junit.framework.Test;
|
||||||
|
import org.netbeans.junit.NbModuleSuite;
|
||||||
|
import org.netbeans.junit.NbTestCase;
|
||||||
|
import org.openide.util.Exceptions;
|
||||||
|
import org.python.icu.impl.Assert;
|
||||||
|
import org.sleuthkit.autopsy.casemodule.Case;
|
||||||
|
import org.sleuthkit.autopsy.casemodule.NoCurrentCaseException;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.AllDataSourcesCommonFilesAlgorithm;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.CommonFilesMetadata;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.CommonFilesMetadataBuilder;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.SingleDataSource;
|
||||||
|
import static org.sleuthkit.autopsy.commonfilessearch.IntraCaseUtils.*;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestJobSettings;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestJobSettings.IngestType;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestModuleTemplate;
|
||||||
|
import org.sleuthkit.autopsy.modules.filetypeid.FileTypeIdModuleFactory;
|
||||||
|
import org.sleuthkit.autopsy.modules.hashdatabase.HashLookupModuleFactory;
|
||||||
|
import org.sleuthkit.autopsy.testutils.IngestUtils;
|
||||||
|
import org.sleuthkit.datamodel.AbstractFile;
|
||||||
|
import org.sleuthkit.datamodel.TskCoreException;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add set 1, set 2, set 3, and set 4 to case and ingest with hash algorithm.
|
||||||
|
*/
|
||||||
|
public class IngestedWithHashAndFileType extends NbTestCase {
|
||||||
|
|
||||||
|
public static Test suite() {
|
||||||
|
NbModuleSuite.Configuration conf = NbModuleSuite.createConfiguration(IngestedWithHashAndFileType.class).
|
||||||
|
clusters(".*").
|
||||||
|
enableModules(".*");
|
||||||
|
return conf.suite();
|
||||||
|
}
|
||||||
|
|
||||||
|
private final IntraCaseUtils utils;
|
||||||
|
|
||||||
|
public IngestedWithHashAndFileType(String name) {
|
||||||
|
super(name);
|
||||||
|
|
||||||
|
this.utils = new IntraCaseUtils(this, "IngestedWithHashAndFileTypeTests");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setUp() {
|
||||||
|
this.utils.setUp();
|
||||||
|
|
||||||
|
IngestModuleTemplate hashLookupTemplate = IngestUtils.getIngestModuleTemplate(new HashLookupModuleFactory());
|
||||||
|
IngestModuleTemplate mimeTypeLookupTemplate = IngestUtils.getIngestModuleTemplate(new FileTypeIdModuleFactory());
|
||||||
|
|
||||||
|
ArrayList<IngestModuleTemplate> templates = new ArrayList<>();
|
||||||
|
templates.add(hashLookupTemplate);
|
||||||
|
templates.add(mimeTypeLookupTemplate);
|
||||||
|
|
||||||
|
IngestJobSettings ingestJobSettings = new IngestJobSettings(IngestedWithHashAndFileType.class.getCanonicalName(), IngestType.FILES_ONLY, templates);
|
||||||
|
|
||||||
|
try {
|
||||||
|
IngestUtils.runIngestJob(Case.getCurrentCaseThrows().getDataSources(), ingestJobSettings);
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void tearDown() {
|
||||||
|
this.utils.tearDown();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Find all matches & all file types. Confirm file.jpg is found on all three
|
||||||
|
* and file.docx is found on two.
|
||||||
|
*/
|
||||||
|
public void testOneA() {
|
||||||
|
try {
|
||||||
|
Map<Long, String> dataSources = this.utils.getDataSourceMap();
|
||||||
|
|
||||||
|
CommonFilesMetadataBuilder allSourcesBuilder = new AllDataSourcesCommonFilesAlgorithm(dataSources, false, false);
|
||||||
|
CommonFilesMetadata metadata = allSourcesBuilder.findCommonFiles();
|
||||||
|
|
||||||
|
Map<Long, String> objectIdToDataSource = IntraCaseUtils.mapFileInstancesToDataSources(metadata);
|
||||||
|
|
||||||
|
List<AbstractFile> files = IntraCaseUtils.getFiles(objectIdToDataSource.keySet());
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET1, 2));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET2, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET3, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET1, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET3, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET1, 0));
|
||||||
|
assertTrue(IntraCaseUtils.verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET4, 0));
|
||||||
|
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException | SQLException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Find all matches & only image types. Confirm file.jpg is found on all
|
||||||
|
* three.
|
||||||
|
*/
|
||||||
|
public void testOneB() {
|
||||||
|
try {
|
||||||
|
Map<Long, String> dataSources = this.utils.getDataSourceMap();
|
||||||
|
|
||||||
|
CommonFilesMetadataBuilder allSourcesBuilder = new AllDataSourcesCommonFilesAlgorithm(dataSources, true, false);
|
||||||
|
CommonFilesMetadata metadata = allSourcesBuilder.findCommonFiles();
|
||||||
|
|
||||||
|
Map<Long, String> objectIdToDataSource = mapFileInstancesToDataSources(metadata);
|
||||||
|
|
||||||
|
List<AbstractFile> files = getFiles(objectIdToDataSource.keySet());
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET1, 2));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET2, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET3, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET4, 0));
|
||||||
|
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException | SQLException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Find all matches & only image types. Confirm file.jpg is found on all
|
||||||
|
* three.
|
||||||
|
*/
|
||||||
|
public void testOneC() {
|
||||||
|
try {
|
||||||
|
Map<Long, String> dataSources = this.utils.getDataSourceMap();
|
||||||
|
|
||||||
|
CommonFilesMetadataBuilder allSourcesBuilder = new AllDataSourcesCommonFilesAlgorithm(dataSources, false, true);
|
||||||
|
CommonFilesMetadata metadata = allSourcesBuilder.findCommonFiles();
|
||||||
|
|
||||||
|
Map<Long, String> objectIdToDataSource = mapFileInstancesToDataSources(metadata);
|
||||||
|
|
||||||
|
List<AbstractFile> files = getFiles(objectIdToDataSource.keySet());
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET1, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET3, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET4, 0));
|
||||||
|
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException | SQLException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Find matches on set 1 & all file types. Confirm same results.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public void testTwoA() {
|
||||||
|
try {
|
||||||
|
Map<Long, String> dataSources = this.utils.getDataSourceMap();
|
||||||
|
Long first = getDataSourceIdByName(SET1, dataSources);
|
||||||
|
|
||||||
|
CommonFilesMetadataBuilder singleSourceBuilder = new SingleDataSource(first, dataSources, false, false);
|
||||||
|
CommonFilesMetadata metadata = singleSourceBuilder.findCommonFiles();
|
||||||
|
|
||||||
|
Map<Long, String> objectIdToDataSource = mapFileInstancesToDataSources(metadata);
|
||||||
|
|
||||||
|
List<AbstractFile> files = getFiles(objectIdToDataSource.keySet());
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET1, 2));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET2, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET3, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET1, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET3, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET4, 0));
|
||||||
|
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException | SQLException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Find matches on set 1 & only media types. Confirm same results.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public void testTwoB() {
|
||||||
|
try {
|
||||||
|
Map<Long, String> dataSources = this.utils.getDataSourceMap();
|
||||||
|
Long first = getDataSourceIdByName(SET1, dataSources);
|
||||||
|
|
||||||
|
CommonFilesMetadataBuilder singleSourceBuilder = new SingleDataSource(first, dataSources, true, false);
|
||||||
|
CommonFilesMetadata metadata = singleSourceBuilder.findCommonFiles();
|
||||||
|
|
||||||
|
Map<Long, String> objectIdToDataSource = mapFileInstancesToDataSources(metadata);
|
||||||
|
|
||||||
|
List<AbstractFile> files = getFiles(objectIdToDataSource.keySet());
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET1, 2));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET2, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET3, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET4, 0));
|
||||||
|
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException | SQLException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Find matches on set 1 & all file types. Confirm same results.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public void testTwoC() {
|
||||||
|
try {
|
||||||
|
Map<Long, String> dataSources = this.utils.getDataSourceMap();
|
||||||
|
Long first = getDataSourceIdByName(SET1, dataSources);
|
||||||
|
|
||||||
|
CommonFilesMetadataBuilder singleSourceBuilder = new SingleDataSource(first, dataSources, false, true);
|
||||||
|
CommonFilesMetadata metadata = singleSourceBuilder.findCommonFiles();
|
||||||
|
|
||||||
|
Map<Long, String> objectIdToDataSource = mapFileInstancesToDataSources(metadata);
|
||||||
|
|
||||||
|
List<AbstractFile> files = getFiles(objectIdToDataSource.keySet());
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET1, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET3, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET4, 0));
|
||||||
|
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException | SQLException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Find matches on set 2 & all file types: Confirm file.jpg.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public void testThree() {
|
||||||
|
try {
|
||||||
|
Map<Long, String> dataSources = this.utils.getDataSourceMap();
|
||||||
|
Long second = getDataSourceIdByName(SET2, dataSources);
|
||||||
|
|
||||||
|
CommonFilesMetadataBuilder singleSourceBuilder = new SingleDataSource(second, dataSources, false, false);
|
||||||
|
CommonFilesMetadata metadata = singleSourceBuilder.findCommonFiles();
|
||||||
|
|
||||||
|
Map<Long, String> objectIdToDataSource = mapFileInstancesToDataSources(metadata);
|
||||||
|
|
||||||
|
List<AbstractFile> files = getFiles(objectIdToDataSource.keySet());
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET1, 2));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET2, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET3, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET4, 0));
|
||||||
|
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException | SQLException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Find matches on set 4 & all file types: Confirm nothing is found.
|
||||||
|
*/
|
||||||
|
public void testFour() {
|
||||||
|
try {
|
||||||
|
Map<Long, String> dataSources = this.utils.getDataSourceMap();
|
||||||
|
Long last = getDataSourceIdByName(SET4, dataSources);
|
||||||
|
|
||||||
|
CommonFilesMetadataBuilder singleSourceBuilder = new SingleDataSource(last, dataSources, false, false);
|
||||||
|
CommonFilesMetadata metadata = singleSourceBuilder.findCommonFiles();
|
||||||
|
|
||||||
|
Map<Long, String> objectIdToDataSource = mapFileInstancesToDataSources(metadata);
|
||||||
|
|
||||||
|
List<AbstractFile> files = getFiles(objectIdToDataSource.keySet());
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET4, 0));
|
||||||
|
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException | SQLException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Find matches on set 3 & all file types: Confirm file.jpg and file.docx.
|
||||||
|
*/
|
||||||
|
public void testFive() {
|
||||||
|
try {
|
||||||
|
Map<Long, String> dataSources = this.utils.getDataSourceMap();
|
||||||
|
Long third = getDataSourceIdByName(SET3, dataSources);
|
||||||
|
|
||||||
|
CommonFilesMetadataBuilder singleSourceBuilder = new SingleDataSource(third, dataSources, false, false);
|
||||||
|
CommonFilesMetadata metadata = singleSourceBuilder.findCommonFiles();
|
||||||
|
|
||||||
|
Map<Long, String> objectIdToDataSource = mapFileInstancesToDataSources(metadata);
|
||||||
|
|
||||||
|
List<AbstractFile> files = getFiles(objectIdToDataSource.keySet());
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET1, 2));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET2, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET3, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, IMG, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET1, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET3, 1));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, DOC, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, PDF, SET4, 0));
|
||||||
|
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET1, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET2, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET3, 0));
|
||||||
|
assertTrue(verifyFileExistanceAndCount(files, objectIdToDataSource, EMPTY, SET4, 0));
|
||||||
|
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException | SQLException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,140 @@
|
|||||||
|
/*
|
||||||
|
*
|
||||||
|
* Autopsy Forensic Browser
|
||||||
|
*
|
||||||
|
* Copyright 2018 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.commonfilessearch;
|
||||||
|
|
||||||
|
import java.sql.SQLException;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
import static junit.framework.Assert.assertTrue;
|
||||||
|
import junit.framework.Test;
|
||||||
|
import org.netbeans.junit.NbModuleSuite;
|
||||||
|
import org.netbeans.junit.NbTestCase;
|
||||||
|
import org.openide.util.Exceptions;
|
||||||
|
import org.python.icu.impl.Assert;
|
||||||
|
import org.sleuthkit.autopsy.casemodule.Case;
|
||||||
|
import org.sleuthkit.autopsy.casemodule.NoCurrentCaseException;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.AllDataSourcesCommonFilesAlgorithm;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.CommonFilesMetadata;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.CommonFilesMetadataBuilder;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.SingleDataSource;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestJobSettings;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestModuleTemplate;
|
||||||
|
import org.sleuthkit.autopsy.modules.hashdatabase.HashLookupModuleFactory;
|
||||||
|
import org.sleuthkit.autopsy.testutils.IngestUtils;
|
||||||
|
import static org.sleuthkit.autopsy.testutils.IngestUtils.getIngestModuleTemplate;
|
||||||
|
import org.sleuthkit.datamodel.AbstractFile;
|
||||||
|
import org.sleuthkit.datamodel.TskCoreException;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Ingested w/o mime type info added to DB.
|
||||||
|
*
|
||||||
|
* Setup:
|
||||||
|
*
|
||||||
|
* Add images set 1, set 2, set 3, and set 4 to case. Do not run mime type
|
||||||
|
* module.
|
||||||
|
*/
|
||||||
|
public class IngestedWithNoFileTypes extends NbTestCase {
|
||||||
|
|
||||||
|
public static Test suite() {
|
||||||
|
NbModuleSuite.Configuration conf = NbModuleSuite.createConfiguration(IngestedWithNoFileTypes.class).
|
||||||
|
clusters(".*").
|
||||||
|
enableModules(".*");
|
||||||
|
return conf.suite();
|
||||||
|
}
|
||||||
|
|
||||||
|
private final IntraCaseUtils utils;
|
||||||
|
|
||||||
|
public IngestedWithNoFileTypes(String name) {
|
||||||
|
super(name);
|
||||||
|
|
||||||
|
this.utils = new IntraCaseUtils(this, "IngestedWithNoFileTypes");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setUp() {
|
||||||
|
this.utils.setUp();
|
||||||
|
|
||||||
|
IngestModuleTemplate hashLookupTemplate = getIngestModuleTemplate(new HashLookupModuleFactory());
|
||||||
|
|
||||||
|
ArrayList<IngestModuleTemplate> templates = new ArrayList<>();
|
||||||
|
templates.add(hashLookupTemplate);
|
||||||
|
|
||||||
|
IngestJobSettings ingestJobSettings = new IngestJobSettings(IngestedWithHashAndFileType.class.getCanonicalName(), IngestJobSettings.IngestType.FILES_ONLY, templates);
|
||||||
|
|
||||||
|
try {
|
||||||
|
IngestUtils.runIngestJob(Case.getCurrentCaseThrows().getDataSources(), ingestJobSettings);
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void tearDown(){
|
||||||
|
this.utils.tearDown();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Search using all data sources and filtering for media types. We should
|
||||||
|
* find nothing and no errors should arise.
|
||||||
|
*/
|
||||||
|
public void testOne() {
|
||||||
|
try {
|
||||||
|
Map<Long, String> dataSources = this.utils.getDataSourceMap();
|
||||||
|
|
||||||
|
CommonFilesMetadataBuilder allSourcesBuilder = new AllDataSourcesCommonFilesAlgorithm(dataSources, true, false);
|
||||||
|
CommonFilesMetadata metadata = allSourcesBuilder.findCommonFiles();
|
||||||
|
|
||||||
|
Map<Long, String> objectIdToDataSource = IntraCaseUtils.mapFileInstancesToDataSources(metadata);
|
||||||
|
|
||||||
|
List<AbstractFile> files = IntraCaseUtils.getFiles(objectIdToDataSource.keySet());
|
||||||
|
|
||||||
|
assertTrue(files.isEmpty());
|
||||||
|
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException | SQLException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Search using single data source and filtering for doc types. Observe that
|
||||||
|
* nothing is found and that nothing blows up.
|
||||||
|
*/
|
||||||
|
public void testTwo() {
|
||||||
|
try {
|
||||||
|
Map<Long, String> dataSources = this.utils.getDataSourceMap();
|
||||||
|
Long third = IntraCaseUtils.getDataSourceIdByName(IntraCaseUtils.SET3, dataSources);
|
||||||
|
|
||||||
|
CommonFilesMetadataBuilder singleSourceBuilder = new SingleDataSource(third, dataSources, true, false);
|
||||||
|
CommonFilesMetadata metadata = singleSourceBuilder.findCommonFiles();
|
||||||
|
|
||||||
|
Map<Long, String> objectIdToDataSource = IntraCaseUtils.mapFileInstancesToDataSources(metadata);
|
||||||
|
|
||||||
|
List<AbstractFile> files = IntraCaseUtils.getFiles(objectIdToDataSource.keySet());
|
||||||
|
|
||||||
|
assertTrue(files.isEmpty());
|
||||||
|
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException | SQLException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,220 @@
|
|||||||
|
/*
|
||||||
|
*
|
||||||
|
* Autopsy Forensic Browser
|
||||||
|
*
|
||||||
|
* Copyright 2018 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.commonfilessearch;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.nio.file.Path;
|
||||||
|
import java.nio.file.Paths;
|
||||||
|
import java.sql.SQLException;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Set;
|
||||||
|
import org.netbeans.junit.NbTestCase;
|
||||||
|
import org.openide.util.Exceptions;
|
||||||
|
import org.python.icu.impl.Assert;
|
||||||
|
import org.sleuthkit.autopsy.casemodule.Case;
|
||||||
|
import org.sleuthkit.autopsy.casemodule.ImageDSProcessor;
|
||||||
|
import org.sleuthkit.autopsy.casemodule.NoCurrentCaseException;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.CommonFilesMetadata;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.DataSourceLoader;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.FileInstanceMetadata;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.Md5Metadata;
|
||||||
|
import org.sleuthkit.autopsy.testutils.CaseUtils;
|
||||||
|
import org.sleuthkit.autopsy.testutils.IngestUtils;
|
||||||
|
import org.sleuthkit.datamodel.AbstractFile;
|
||||||
|
import org.sleuthkit.datamodel.TskCoreException;
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* Provides setup and utility for testing presence of files in different data
|
||||||
|
* sets discoverable by Common Files Features.
|
||||||
|
*
|
||||||
|
* Data set definitions:
|
||||||
|
*
|
||||||
|
* set 1
|
||||||
|
* + file1
|
||||||
|
* - IMG_6175.jpg
|
||||||
|
* + file2
|
||||||
|
* - IMG_6175.jpg
|
||||||
|
* + file3
|
||||||
|
* - BasicStyleGuide.doc
|
||||||
|
*
|
||||||
|
* set 2
|
||||||
|
* - adsf.pdf
|
||||||
|
* - IMG_6175.jpg
|
||||||
|
*
|
||||||
|
* set 3
|
||||||
|
* - BasicStyleGuide.doc
|
||||||
|
* - IMG_6175.jpg
|
||||||
|
*
|
||||||
|
* set 4
|
||||||
|
* - file.dat (empty file)
|
||||||
|
*/
|
||||||
|
class IntraCaseUtils {
|
||||||
|
|
||||||
|
private static final String CASE_NAME = "IntraCaseCommonFilesSearchTest";
|
||||||
|
static final Path CASE_DIRECTORY_PATH = Paths.get(System.getProperty("java.io.tmpdir"), CASE_NAME);
|
||||||
|
|
||||||
|
private final Path imagePath1;
|
||||||
|
private final Path imagePath2;
|
||||||
|
private final Path imagePath3;
|
||||||
|
private final Path imagePath4;
|
||||||
|
|
||||||
|
static final String IMG = "IMG_6175.jpg";
|
||||||
|
static final String DOC = "BasicStyleGuide.doc";
|
||||||
|
static final String PDF = "adsf.pdf"; //not a typo - it appears this way in the test image
|
||||||
|
static final String EMPTY = "file.dat";
|
||||||
|
|
||||||
|
static final String SET1 = "commonfiles_image1_v1.vhd";
|
||||||
|
static final String SET2 = "commonfiles_image2_v1.vhd";
|
||||||
|
static final String SET3 = "commonfiles_image3_v1.vhd";
|
||||||
|
static final String SET4 = "commonfiles_image4_v1.vhd";
|
||||||
|
|
||||||
|
private final DataSourceLoader dataSourceLoader;
|
||||||
|
|
||||||
|
private final String caseName;
|
||||||
|
|
||||||
|
IntraCaseUtils(NbTestCase nbTestCase, String caseName){
|
||||||
|
imagePath1 = Paths.get(nbTestCase.getDataDir().toString(), "commonfiles_image1_v1.vhd");
|
||||||
|
imagePath2 = Paths.get(nbTestCase.getDataDir().toString(), "commonfiles_image2_v1.vhd");
|
||||||
|
imagePath3 = Paths.get(nbTestCase.getDataDir().toString(), "commonfiles_image3_v1.vhd");
|
||||||
|
imagePath4 = Paths.get(nbTestCase.getDataDir().toString(), "commonfiles_image4_v1.vhd");
|
||||||
|
|
||||||
|
this.dataSourceLoader = new DataSourceLoader();
|
||||||
|
|
||||||
|
this.caseName = caseName;
|
||||||
|
}
|
||||||
|
|
||||||
|
void setUp(){
|
||||||
|
CaseUtils.createAsCurrentCase(this.caseName);
|
||||||
|
|
||||||
|
final ImageDSProcessor imageDSProcessor = new ImageDSProcessor();
|
||||||
|
|
||||||
|
IngestUtils.addDataSource(imageDSProcessor, imagePath1);
|
||||||
|
IngestUtils.addDataSource(imageDSProcessor, imagePath2);
|
||||||
|
IngestUtils.addDataSource(imageDSProcessor, imagePath3);
|
||||||
|
IngestUtils.addDataSource(imageDSProcessor, imagePath4);
|
||||||
|
}
|
||||||
|
|
||||||
|
Map<Long, String> getDataSourceMap() throws NoCurrentCaseException, TskCoreException, SQLException{
|
||||||
|
return this.dataSourceLoader.getDataSourceMap();
|
||||||
|
}
|
||||||
|
|
||||||
|
void tearDown(){
|
||||||
|
CaseUtils.closeCurrentCase(false);
|
||||||
|
try {
|
||||||
|
CaseUtils.deleteCaseDir(CASE_DIRECTORY_PATH.toFile());
|
||||||
|
} catch (IOException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
//does not represent a failure in the common files search feature
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Verify that the given file appears a precise number times in the given
|
||||||
|
* data source.
|
||||||
|
*
|
||||||
|
* @param files search domain
|
||||||
|
* @param objectIdToDataSource mapping of file ids to data source names
|
||||||
|
* @param name name of file to search for
|
||||||
|
* @param dataSource name of data source where file should appear
|
||||||
|
* @param count number of appearances of the given file
|
||||||
|
* @return true if a file with the given name exists the specified number
|
||||||
|
* of times in the given data source
|
||||||
|
*/
|
||||||
|
static boolean verifyFileExistanceAndCount(List<AbstractFile> files, Map<Long, String> objectIdToDataSource, String name, String dataSource, int count) {
|
||||||
|
|
||||||
|
int tally = 0;
|
||||||
|
|
||||||
|
for (AbstractFile file : files) {
|
||||||
|
|
||||||
|
Long objectId = file.getId();
|
||||||
|
|
||||||
|
String fileName = file.getName();
|
||||||
|
|
||||||
|
String dataSourceName = objectIdToDataSource.get(objectId);
|
||||||
|
|
||||||
|
if (fileName.equals(name) && dataSourceName.equals(dataSource)) {
|
||||||
|
tally++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return tally == count;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convenience method which verifies that a file exists within a given data
|
||||||
|
* source exactly once.
|
||||||
|
*
|
||||||
|
* @param files search domain
|
||||||
|
* @param objectIdToDataSource mapping of file ids to data source names
|
||||||
|
* @param name name of file to search for
|
||||||
|
* @param dataSource name of data source where file should appear
|
||||||
|
* @return true if a file with the given name exists once in the given data
|
||||||
|
* source
|
||||||
|
*/
|
||||||
|
static boolean verifySingularFileExistance(List<AbstractFile> files, Map<Long, String> objectIdToDataSource, String name, String dataSource) {
|
||||||
|
return verifyFileExistanceAndCount(files, objectIdToDataSource, name, dataSource, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
static Map<Long, String> mapFileInstancesToDataSources(CommonFilesMetadata metadata) {
|
||||||
|
Map<Long, String> instanceIdToDataSource = new HashMap<>();
|
||||||
|
|
||||||
|
for (Map.Entry<String, Md5Metadata> entry : metadata.getMetadata().entrySet()) {
|
||||||
|
for (FileInstanceMetadata md : entry.getValue().getMetadata()) {
|
||||||
|
instanceIdToDataSource.put(md.getObjectId(), md.getDataSourceName());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return instanceIdToDataSource;
|
||||||
|
}
|
||||||
|
|
||||||
|
static List<AbstractFile> getFiles(Set<Long> objectIds) {
|
||||||
|
List<AbstractFile> files = new ArrayList<>(objectIds.size());
|
||||||
|
|
||||||
|
for (Long id : objectIds) {
|
||||||
|
try {
|
||||||
|
AbstractFile file = Case.getCurrentCaseThrows().getSleuthkitCase().getAbstractFileById(id);
|
||||||
|
files.add(file);
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return files;
|
||||||
|
}
|
||||||
|
|
||||||
|
static Long getDataSourceIdByName(String name, Map<Long, String> dataSources){
|
||||||
|
|
||||||
|
if(dataSources.containsValue(name)){
|
||||||
|
for(Map.Entry<Long, String> dataSource : dataSources.entrySet()){
|
||||||
|
if(dataSource.getValue().equals(name)){
|
||||||
|
return dataSource.getKey();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
throw new IndexOutOfBoundsException(String.format("Name should be one of: {0}", String.join(",", dataSources.values())));
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,114 @@
|
|||||||
|
/*
|
||||||
|
*
|
||||||
|
* Autopsy Forensic Browser
|
||||||
|
*
|
||||||
|
* Copyright 2018 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.commonfilessearch;
|
||||||
|
|
||||||
|
import java.sql.SQLException;
|
||||||
|
import java.util.Map;
|
||||||
|
import static junit.framework.Assert.assertEquals;
|
||||||
|
import junit.framework.Test;
|
||||||
|
import org.netbeans.junit.NbModuleSuite;
|
||||||
|
import org.netbeans.junit.NbTestCase;
|
||||||
|
import org.openide.util.Exceptions;
|
||||||
|
import org.python.icu.impl.Assert;
|
||||||
|
import org.sleuthkit.autopsy.casemodule.NoCurrentCaseException;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.AllDataSourcesCommonFilesAlgorithm;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.CommonFilesMetadata;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.CommonFilesMetadataBuilder;
|
||||||
|
import org.sleuthkit.autopsy.commonfilesearch.SingleDataSource;
|
||||||
|
import static org.sleuthkit.autopsy.commonfilessearch.IntraCaseUtils.SET1;
|
||||||
|
import static org.sleuthkit.autopsy.commonfilessearch.IntraCaseUtils.getDataSourceIdByName;
|
||||||
|
import org.sleuthkit.datamodel.TskCoreException;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Test that cases which are created but have not run any ingest modules turn up
|
||||||
|
* no results.
|
||||||
|
*
|
||||||
|
* Setup:
|
||||||
|
*
|
||||||
|
* Add images set 1, set 2, set 3, and set 4 to case. Do not ingest.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public class UningestedCases extends NbTestCase {
|
||||||
|
|
||||||
|
public static Test suite() {
|
||||||
|
NbModuleSuite.Configuration conf = NbModuleSuite.createConfiguration(UningestedCases.class).
|
||||||
|
clusters(".*").
|
||||||
|
enableModules(".*");
|
||||||
|
return conf.suite();
|
||||||
|
}
|
||||||
|
|
||||||
|
private final IntraCaseUtils utils;
|
||||||
|
|
||||||
|
public UningestedCases(String name) {
|
||||||
|
super(name);
|
||||||
|
|
||||||
|
this.utils = new IntraCaseUtils(this, "UningestedCasesTests");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setUp(){
|
||||||
|
this.utils.setUp();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void tearDown(){
|
||||||
|
this.utils.tearDown();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Find all matches & all file types. Confirm no matches are found (since
|
||||||
|
* there are no hashes to match).
|
||||||
|
*/
|
||||||
|
public void testOne() {
|
||||||
|
try {
|
||||||
|
Map<Long, String> dataSources = this.utils.getDataSourceMap();
|
||||||
|
|
||||||
|
CommonFilesMetadataBuilder allSourcesBuilder = new AllDataSourcesCommonFilesAlgorithm(dataSources, false, false);
|
||||||
|
CommonFilesMetadata metadata = allSourcesBuilder.findCommonFiles();
|
||||||
|
|
||||||
|
int resultCount = metadata.size();
|
||||||
|
assertEquals(resultCount, 0);
|
||||||
|
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException | SQLException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Find all matches on image #1 & all file types. Confirm no matches.
|
||||||
|
*/
|
||||||
|
public void testTwo() {
|
||||||
|
try {
|
||||||
|
Map<Long, String> dataSources = this.utils.getDataSourceMap();
|
||||||
|
Long first = getDataSourceIdByName(SET1, dataSources);
|
||||||
|
|
||||||
|
CommonFilesMetadataBuilder singleSourceBuilder = new SingleDataSource(first, dataSources, false, false);
|
||||||
|
CommonFilesMetadata metadata = singleSourceBuilder.findCommonFiles();
|
||||||
|
|
||||||
|
int resultCount = metadata.size();
|
||||||
|
assertEquals(resultCount, 0);
|
||||||
|
|
||||||
|
} catch (NoCurrentCaseException | TskCoreException | SQLException ex) {
|
||||||
|
Exceptions.printStackTrace(ex);
|
||||||
|
Assert.fail(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -125,5 +125,4 @@ public final class CaseUtils {
|
|||||||
*/
|
*/
|
||||||
private CaseUtils() {
|
private CaseUtils() {
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -41,7 +41,7 @@ import org.sleuthkit.autopsy.guiutils.StatusIconCellRenderer;
|
|||||||
* Each job with the specified status will have a child node representing it.
|
* Each job with the specified status will have a child node representing it.
|
||||||
*/
|
*/
|
||||||
final class AutoIngestJobsNode extends AbstractNode {
|
final class AutoIngestJobsNode extends AbstractNode {
|
||||||
|
|
||||||
//Event bus is non static so that each instance of this will only listen to events sent to that instance
|
//Event bus is non static so that each instance of this will only listen to events sent to that instance
|
||||||
private final EventBus refreshChildrenEventBus;
|
private final EventBus refreshChildrenEventBus;
|
||||||
|
|
||||||
@ -59,9 +59,14 @@ final class AutoIngestJobsNode extends AbstractNode {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Construct a new AutoIngestJobsNode.
|
* Construct a new AutoIngestJobsNode.
|
||||||
|
*
|
||||||
|
* @param snapshot the snapshot which contains the AutoIngestJobs
|
||||||
|
* @param status the status of the jobs being displayed
|
||||||
|
* @param eventBus the event bus which will be used to send and receive
|
||||||
|
* refresh events
|
||||||
*/
|
*/
|
||||||
AutoIngestJobsNode(AutoIngestJobStatus status, EventBus eventBus) {
|
AutoIngestJobsNode(JobsSnapshot jobsSnapshot, AutoIngestJobStatus status, EventBus eventBus) {
|
||||||
super(Children.create(new AutoIngestNodeChildren(status, eventBus), false));
|
super(Children.create(new AutoIngestNodeChildren(jobsSnapshot, status, eventBus), false));
|
||||||
refreshChildrenEventBus = eventBus;
|
refreshChildrenEventBus = eventBus;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -88,9 +93,11 @@ final class AutoIngestJobsNode extends AbstractNode {
|
|||||||
*
|
*
|
||||||
* @param snapshot the snapshot which contains the AutoIngestJobs
|
* @param snapshot the snapshot which contains the AutoIngestJobs
|
||||||
* @param status the status of the jobs being displayed
|
* @param status the status of the jobs being displayed
|
||||||
|
* @param eventBus the event bus which the class registers to for
|
||||||
|
* refresh events
|
||||||
*/
|
*/
|
||||||
AutoIngestNodeChildren(AutoIngestJobStatus status, EventBus eventBus) {
|
AutoIngestNodeChildren(JobsSnapshot snapshot, AutoIngestJobStatus status, EventBus eventBus) {
|
||||||
jobsSnapshot = new JobsSnapshot();
|
jobsSnapshot = snapshot;
|
||||||
autoIngestJobStatus = status;
|
autoIngestJobStatus = status;
|
||||||
refreshEventBus = eventBus;
|
refreshEventBus = eventBus;
|
||||||
refreshChildrenSubscriber.register(refreshEventBus);
|
refreshChildrenSubscriber.register(refreshEventBus);
|
||||||
|
@ -171,7 +171,7 @@ final class AutoIngestJobsPanel extends javax.swing.JPanel implements ExplorerMa
|
|||||||
((AutoIngestJobsNode) explorerManager.getRootContext()).refresh(refreshEvent);
|
((AutoIngestJobsNode) explorerManager.getRootContext()).refresh(refreshEvent);
|
||||||
} else {
|
} else {
|
||||||
//Make a new AutoIngestJobsNode with it's own EventBus and set it as the root context
|
//Make a new AutoIngestJobsNode with it's own EventBus and set it as the root context
|
||||||
explorerManager.setRootContext(new AutoIngestJobsNode(status, new EventBus("AutoIngestJobsNodeEventBus")));
|
explorerManager.setRootContext(new AutoIngestJobsNode(refreshEvent.getJobsSnapshot(), status, new EventBus("AutoIngestJobsNodeEventBus")));
|
||||||
}
|
}
|
||||||
outline.setRowSelectionAllowed(true);
|
outline.setRowSelectionAllowed(true);
|
||||||
outline.setFocusable(true);
|
outline.setFocusable(true);
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
#Updated by build script
|
#Updated by build script
|
||||||
#Mon, 19 Mar 2018 11:17:11 -0700
|
#Tue, 08 May 2018 10:29:55 -0600
|
||||||
LBL_splash_window_title=Starting Autopsy
|
LBL_splash_window_title=Starting Autopsy
|
||||||
SPLASH_HEIGHT=314
|
SPLASH_HEIGHT=314
|
||||||
SPLASH_WIDTH=538
|
SPLASH_WIDTH=538
|
||||||
@ -8,4 +8,4 @@ SplashRunningTextBounds=0,289,538,18
|
|||||||
SplashRunningTextColor=0x0
|
SplashRunningTextColor=0x0
|
||||||
SplashRunningTextFontSize=19
|
SplashRunningTextFontSize=19
|
||||||
|
|
||||||
currentVersion=Autopsy 4.6.0
|
currentVersion=Autopsy 4.7.0
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
#Updated by build script
|
#Updated by build script
|
||||||
#Fri, 09 Mar 2018 13:03:41 -0700
|
#Tue, 08 May 2018 10:29:55 -0600
|
||||||
CTL_MainWindow_Title=Autopsy 4.6.0
|
CTL_MainWindow_Title=Autopsy 4.7.0
|
||||||
CTL_MainWindow_Title_No_Project=Autopsy 4.6.0
|
CTL_MainWindow_Title_No_Project=Autopsy 4.7.0
|
||||||
|
Loading…
x
Reference in New Issue
Block a user