Merge pull request #3169 from millmanorama/867-message-listing

867 message listing
This commit is contained in:
Richard Cordovano 2017-11-01 19:56:54 -04:00 committed by GitHub
commit 79b08e8afa
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
20 changed files with 856 additions and 599 deletions

View File

@ -0,0 +1,88 @@
/*
* Autopsy Forensic Browser
*
* Copyright 2011-2017 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.communications;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.logging.Level;
import org.openide.nodes.AbstractNode;
import org.openide.nodes.Children;
import org.openide.nodes.Node;
import org.sleuthkit.autopsy.coreutils.Logger;
import org.sleuthkit.datamodel.Account;
import org.sleuthkit.datamodel.BlackboardArtifact;
import org.sleuthkit.datamodel.CommunicationsFilter;
import org.sleuthkit.datamodel.CommunicationsManager;
import org.sleuthkit.datamodel.TskCoreException;
class AccountDetailsNode extends AbstractNode {
private final static Logger logger = Logger.getLogger(AccountDetailsNode.class.getName());
private final CommunicationsFilter filter; //TODO: Use this
AccountDetailsNode(Set<Account> accounts,CommunicationsFilter filter, CommunicationsManager commsManager) {
super(new AccountRelationshipChildren(accounts, commsManager, filter));
this.filter = filter;
}
/**
* Children object for the relationships that the account is a member of.
*/
private static class AccountRelationshipChildren extends Children.Keys<BlackboardArtifact> {
private final Set<Account> accounts;
private final CommunicationsManager commsManager;
private final CommunicationsFilter filter;//TODO: Use this
private AccountRelationshipChildren(Set<Account> accounts, CommunicationsManager commsManager, CommunicationsFilter filter) {
this.accounts = accounts;
this.commsManager = commsManager;
this.filter = filter;
}
@Override
protected Node[] createNodes(BlackboardArtifact key) {
return new Node[]{new RelationShipFilterNode(key)};
}
@Override
protected void addNotify() {
Set<BlackboardArtifact> keys = new HashSet<>();
for (Account account : accounts) {
List<Account> accountsWithRelationship = new ArrayList<>();
try {
accountsWithRelationship.addAll(commsManager.getAccountsWithRelationship(account)); //TODO: Use filter here
} catch (TskCoreException ex) {
logger.log(Level.WARNING, "Error loading with relationships to " + account, ex);
}
accountsWithRelationship.forEach(otherAcount -> {
try {
keys.addAll(commsManager.getRelationships(account, otherAcount)); //TODO:Use filter here
} catch (TskCoreException ex) {
logger.log(Level.WARNING, "Error loading relationships between " + account + " and " + otherAcount, ex);
}
});
}
setKeys(keys);
}
}
}

View File

@ -1,90 +0,0 @@
/*
* Autopsy Forensic Browser
*
* Copyright 2011-2017 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.communications;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.openide.nodes.AbstractNode;
import org.openide.nodes.Children;
import org.openide.nodes.Sheet;
import org.openide.util.NbBundle;
import org.openide.util.lookup.Lookups;
import org.sleuthkit.autopsy.casemodule.Case;
import org.sleuthkit.autopsy.datamodel.NodeProperty;
import org.sleuthkit.datamodel.AccountDeviceInstance;
import org.sleuthkit.datamodel.CommunicationsFilter;
import org.sleuthkit.datamodel.TskCoreException;
/**
* Node to represent an Account in the AccountsBrowser
*/
class AccountDeviceInstanceNode extends AbstractNode {
private static final Logger LOGGER = Logger.getLogger(AccountDeviceInstanceNode.class.getName());
private final AccountDeviceInstance accountDeviceInstance;
private final CommunicationsFilter filter;
AccountDeviceInstanceNode(AccountDeviceInstance accountDeviceInstance, CommunicationsFilter filter) {
super(Children.LEAF, Lookups.fixed(accountDeviceInstance));
this.accountDeviceInstance = accountDeviceInstance;
this.filter = filter;
setName(accountDeviceInstance.getAccount().getAccountUniqueID());
setIconBaseWithExtension("org/sleuthkit/autopsy/communications/images/"
+ AccountUtils.getIconFileName(accountDeviceInstance.getAccount().getAccountType()));
}
@Override
@NbBundle.Messages({
"AccountNode.device=Device",
"AccountNode.accountName=Account",
"AccountNode.accountType=Type",
"AccountNode.messageCount=Msg Count"})
protected Sheet createSheet() {
Sheet s = super.createSheet();
Sheet.Set properties = s.get(Sheet.PROPERTIES);
if (properties == null) {
properties = Sheet.createPropertiesSet();
s.put(properties);
}
long msgCount = 0;
try {
msgCount = Case.getCurrentCase().getSleuthkitCase().getCommunicationsManager().getRelationshipsCount(this.filter, accountDeviceInstance);
} catch (TskCoreException ex) {
LOGGER.log(Level.WARNING, "Failed to get message count for account", ex); //NON-NLS
}
properties.put(new NodeProperty<>("type",
Bundle.AccountNode_accountType(),
"type",
accountDeviceInstance.getAccount().getAccountType().getDisplayName())); // NON-NLS
properties.put(new NodeProperty<>("count",
Bundle.AccountNode_messageCount(),
"count",
msgCount)); // NON-NLS
properties.put(new NodeProperty<>("device",
Bundle.AccountNode_device(),
"device",
accountDeviceInstance.getDeviceId())); // NON-NLS
return s;
}
}

View File

@ -1,62 +0,0 @@
/*
* Autopsy Forensic Browser
*
* Copyright 2011-2017 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.communications;
import java.util.Collections;
import java.util.List;
import org.openide.nodes.Children;
import org.openide.nodes.Node;
class AccountDeviceInstancesNodeChildren extends Children.Keys<AccountDeviceInstanceKey> {
private final List<AccountDeviceInstanceKey> accountDeviceInstanceKeys;
AccountDeviceInstancesNodeChildren(List<AccountDeviceInstanceKey> accountDeviceInstanceKeys) {
super(true);
this.accountDeviceInstanceKeys = accountDeviceInstanceKeys;
}
@Override
protected void removeNotify() {
super.removeNotify();
setKeys(Collections.emptySet());
}
@Override
protected void addNotify() {
super.addNotify();
setKeys(accountDeviceInstanceKeys);
}
//These are the methods for ChildFactory. I am going to keep them around but commented until we make a final descision.
// @Override
// protected boolean createKeys(List<Account> list) {
// list.addAll(accounts);
// return true;
// }
//
// @Override
// protected Node createNodeForKey(Account key) {
// return new AccountDeviceInstanceNode(key);
// }
@Override
protected Node[] createNodes(AccountDeviceInstanceKey key) {
return new Node[]{new AccountDeviceInstanceNode(key.getAccountDeviceInstance(), key.getCommunicationsFilter())};
}
}

View File

@ -1,62 +0,0 @@
/*
* Autopsy Forensic Browser
*
* Copyright 2011-2017 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.communications;
import java.util.Collections;
import java.util.List;
import org.openide.nodes.Children;
import org.openide.nodes.Node;
class AccountsDeviceInstanceChildren extends Children.Keys<AccountDeviceInstanceKey> {
private final List<AccountDeviceInstanceKey> accountDeviceInstanceKeys;
AccountsDeviceInstanceChildren(List<AccountDeviceInstanceKey> accountDeviceInstanceKeys) {
super(true);
this.accountDeviceInstanceKeys = accountDeviceInstanceKeys;
}
@Override
protected void removeNotify() {
super.removeNotify();
setKeys(Collections.emptySet());
}
@Override
protected void addNotify() {
super.addNotify();
setKeys(accountDeviceInstanceKeys);
}
//These are the methods for ChildFactory. I am going to keep them around but commented until we make a final descision.
// @Override
// protected boolean createKeys(List<Account> list) {
// list.addAll(accounts);
// return true;
// }
//
// @Override
// protected Node createNodeForKey(Account key) {
// return new AccountDeviceInstanceNode(key);
// }
@Override
protected Node[] createNodes(AccountDeviceInstanceKey key) {
return new Node[]{new AccountDeviceInstanceNode(key.getAccountDeviceInstance(), key.getCommunicationsFilter())};
}
}

View File

@ -0,0 +1,128 @@
/*
* Autopsy Forensic Browser
*
* Copyright 2011-2017 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.communications;
import java.util.Collections;
import java.util.List;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.openide.nodes.AbstractNode;
import org.openide.nodes.Children;
import org.openide.nodes.Node;
import org.openide.nodes.Sheet;
import org.openide.util.NbBundle;
import org.openide.util.lookup.Lookups;
import org.sleuthkit.autopsy.datamodel.NodeProperty;
import org.sleuthkit.datamodel.AccountDeviceInstance;
import org.sleuthkit.datamodel.CommunicationsFilter;
import org.sleuthkit.datamodel.CommunicationsManager;
import org.sleuthkit.datamodel.TskCoreException;
class AccountsRootChildren extends Children.Keys<AccountDeviceInstanceKey> {
private final List<AccountDeviceInstanceKey> accountDeviceInstanceKeys;
private final CommunicationsManager commsManager;
AccountsRootChildren(List<AccountDeviceInstanceKey> accountDeviceInstanceKeys, CommunicationsManager commsManager) {
super(true);
this.accountDeviceInstanceKeys = accountDeviceInstanceKeys;
this.commsManager = commsManager;
}
@Override
protected void removeNotify() {
super.removeNotify();
setKeys(Collections.emptySet());
}
@Override
protected void addNotify() {
super.addNotify();
setKeys(accountDeviceInstanceKeys);
}
//These are the methods for ChildFactory. I am going to keep them around but commented until we make a final descision.
// @Override
// protected boolean createKeys(List<Account> list) {
// list.addAll(accounts);
// return true;
// }
//
// @Override
// protected Node createNodeForKey(Account key) {
// return new AccountDeviceInstanceNode(key);
// }
@Override
protected Node[] createNodes(AccountDeviceInstanceKey key) {
return new Node[]{new AccountDeviceInstanceNode(key, commsManager)};
}
/**
* Node to represent an Account in the AccountsBrowser
*/
static class AccountDeviceInstanceNode extends AbstractNode {
private static final Logger LOGGER = Logger.getLogger(AccountDeviceInstanceNode.class.getName());
private final AccountDeviceInstance accountDeviceInstance;
private final CommunicationsManager commsManager;
private final CommunicationsFilter filter;
private AccountDeviceInstanceNode(AccountDeviceInstanceKey accountDeviceInstanceKey, CommunicationsManager commsManager) {
super(Children.LEAF, Lookups.fixed(accountDeviceInstanceKey, commsManager));
this.accountDeviceInstance = accountDeviceInstanceKey.getAccountDeviceInstance();
this.commsManager = commsManager;
this.filter = accountDeviceInstanceKey.getCommunicationsFilter();
setName(accountDeviceInstance.getAccount().getAccountUniqueID());
setIconBaseWithExtension("org/sleuthkit/autopsy/communications/images/" + AccountUtils.getIconFileName(accountDeviceInstance.getAccount().getAccountType()));
}
public AccountDeviceInstance getAccountDeviceInstance() {
return accountDeviceInstance;
}
public CommunicationsManager getCommsManager() {
return commsManager;
}
public CommunicationsFilter getFilter() {
return filter;
}
@Override
@NbBundle.Messages(value = {"AccountNode.device=Device", "AccountNode.accountName=Account", "AccountNode.accountType=Type", "AccountNode.messageCount=Msg Count"})
protected Sheet createSheet() {
Sheet s = super.createSheet();
Sheet.Set properties = s.get(Sheet.PROPERTIES);
if (properties == null) {
properties = Sheet.createPropertiesSet();
s.put(properties);
}
long msgCount = 0;
try {
msgCount = commsManager.getRelationshipsCount(filter, accountDeviceInstance);
} catch (TskCoreException ex) {
LOGGER.log(Level.WARNING, "Failed to get message count for account", ex); //NON-NLS
}
properties.put(new NodeProperty<>("type", Bundle.AccountNode_accountType(), "type", accountDeviceInstance.getAccount().getAccountType().getDisplayName())); // NON-NLS
properties.put(new NodeProperty<>("count", Bundle.AccountNode_messageCount(), "count", msgCount)); // NON-NLS
properties.put(new NodeProperty<>("device", Bundle.AccountNode_device(), "device", accountDeviceInstance.getDeviceId())); // NON-NLS
return s;
}
}
}

View File

@ -1,11 +1,9 @@
CVTTopComponent.jTextField1.text=place holder for messages ,thumbnail list, etc
CVTTopComponent.jTextField2.text=place holder for message viewer
CVTTopComponent.TabConstraints.tabTitle=Visualize
CVTTopComponent.accountsBrowser.TabConstraints.tabTitle=Browse
FiltersPanel.applyFiltersButton.text=Apply Filters
FiltersPanel.applyFiltersButton.text=Apply
FiltersPanel.devicesLabel.text=Devices:
FiltersPanel.accountTypesLabel.text=Account Types:
FiltersPanel.filtersTitleLabel.text=Filters
FiltersPanel.filtersTitleLabel.text=Account Filters
FiltersPanel.unCheckAllAccountTypesButton.text=Uncheck All
FiltersPanel.checkAllAccountTypesButton.text=Check All
FiltersPanel.unCheckAllDevicesButton.text=Uncheck All

View File

@ -17,10 +17,10 @@
<DimensionLayout dim="0">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" alignment="0" attributes="0">
<EmptySpace max="-2" attributes="0"/>
<Component id="filtersPane" min="-2" pref="244" max="-2" attributes="0"/>
<EmptySpace type="unrelated" max="-2" attributes="0"/>
<Component id="HSplitPane" pref="1322" max="32767" attributes="0"/>
<EmptySpace min="-2" max="-2" attributes="0"/>
<Component id="filtersPane" pref="244" max="32767" attributes="0"/>
<EmptySpace type="unrelated" min="-2" max="-2" attributes="0"/>
<Component id="splitPane" pref="1322" max="32767" attributes="0"/>
<EmptySpace min="-2" max="-2" attributes="0"/>
</Group>
</Group>
@ -31,7 +31,7 @@
<EmptySpace min="-2" max="-2" attributes="0"/>
<Group type="103" groupAlignment="0" attributes="0">
<Component id="filtersPane" max="32767" attributes="0"/>
<Component id="HSplitPane" max="32767" attributes="0"/>
<Component id="splitPane" max="32767" attributes="0"/>
</Group>
<EmptySpace min="-2" max="-2" attributes="0"/>
</Group>
@ -39,9 +39,10 @@
</DimensionLayout>
</Layout>
<SubComponents>
<Container class="javax.swing.JSplitPane" name="HSplitPane">
<Container class="javax.swing.JSplitPane" name="splitPane">
<Properties>
<Property name="dividerLocation" type="int" value="600"/>
<Property name="resizeWeight" type="double" value="0.3"/>
</Properties>
<Layout class="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout"/>
@ -106,45 +107,6 @@
</Container>
</SubComponents>
</Container>
<Container class="javax.swing.JSplitPane" name="VSplitPane">
<Properties>
<Property name="dividerLocation" type="int" value="200"/>
<Property name="orientation" type="int" value="0"/>
</Properties>
<Constraints>
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout" value="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription">
<JSplitPaneConstraints position="right"/>
</Constraint>
</Constraints>
<Layout class="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout"/>
<SubComponents>
<Component class="javax.swing.JTextField" name="jTextField1">
<Properties>
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
<ResourceString bundle="org/sleuthkit/autopsy/communications/Bundle.properties" key="CVTTopComponent.jTextField1.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, &quot;{key}&quot;)"/>
</Property>
</Properties>
<Constraints>
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout" value="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription">
<JSplitPaneConstraints position="top"/>
</Constraint>
</Constraints>
</Component>
<Component class="javax.swing.JTextField" name="jTextField2">
<Properties>
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
<ResourceString bundle="org/sleuthkit/autopsy/communications/Bundle.properties" key="CVTTopComponent.jTextField2.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, &quot;{key}&quot;)"/>
</Property>
</Properties>
<Constraints>
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout" value="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription">
<JSplitPaneConstraints position="right"/>
</Constraint>
</Constraints>
</Component>
</SubComponents>
</Container>
</SubComponents>
</Container>
<Component class="org.sleuthkit.autopsy.communications.FiltersPanel" name="filtersPane">

View File

@ -46,8 +46,10 @@ public final class CVTTopComponent extends TopComponent implements ExplorerManag
private final ExplorerManager em = new ExplorerManager();
public CVTTopComponent() {
initComponents();
setName(Bundle.CVTTopComponent_name());
splitPane.setRightComponent(new MessageBrowser());
}
/**
@ -58,16 +60,14 @@ public final class CVTTopComponent extends TopComponent implements ExplorerManag
// <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
private void initComponents() {
HSplitPane = new javax.swing.JSplitPane();
splitPane = new javax.swing.JSplitPane();
BrowseVisualizeTabPane = new javax.swing.JTabbedPane();
accountsBrowser = new org.sleuthkit.autopsy.communications.AccountsBrowser();
jPanel1 = new javax.swing.JPanel();
VSplitPane = new javax.swing.JSplitPane();
jTextField1 = new javax.swing.JTextField();
jTextField2 = new javax.swing.JTextField();
filtersPane = new org.sleuthkit.autopsy.communications.FiltersPanel();
HSplitPane.setDividerLocation(600);
splitPane.setDividerLocation(600);
splitPane.setResizeWeight(0.3);
BrowseVisualizeTabPane.setFont(new java.awt.Font("Tahoma", 0, 18)); // NOI18N
BrowseVisualizeTabPane.addTab(org.openide.util.NbBundle.getMessage(CVTTopComponent.class, "CVTTopComponent.accountsBrowser.TabConstraints.tabTitle"), new javax.swing.ImageIcon(getClass().getResource("/org/sleuthkit/autopsy/communications/images/table.png")), accountsBrowser); // NOI18N
@ -87,18 +87,7 @@ public final class CVTTopComponent extends TopComponent implements ExplorerManag
BrowseVisualizeTabPane.addTab(org.openide.util.NbBundle.getMessage(CVTTopComponent.class, "CVTTopComponent.TabConstraints.tabTitle"), new javax.swing.ImageIcon(getClass().getResource("/org/sleuthkit/autopsy/communications/images/emblem-web.png")), jPanel1); // NOI18N
HSplitPane.setLeftComponent(BrowseVisualizeTabPane);
VSplitPane.setDividerLocation(200);
VSplitPane.setOrientation(javax.swing.JSplitPane.VERTICAL_SPLIT);
jTextField1.setText(org.openide.util.NbBundle.getMessage(CVTTopComponent.class, "CVTTopComponent.jTextField1.text")); // NOI18N
VSplitPane.setTopComponent(jTextField1);
jTextField2.setText(org.openide.util.NbBundle.getMessage(CVTTopComponent.class, "CVTTopComponent.jTextField2.text")); // NOI18N
VSplitPane.setRightComponent(jTextField2);
HSplitPane.setRightComponent(VSplitPane);
splitPane.setLeftComponent(BrowseVisualizeTabPane);
filtersPane.setBorder(javax.swing.BorderFactory.createEtchedBorder());
filtersPane.setMinimumSize(new java.awt.Dimension(256, 495));
@ -109,9 +98,9 @@ public final class CVTTopComponent extends TopComponent implements ExplorerManag
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(layout.createSequentialGroup()
.addContainerGap()
.addComponent(filtersPane, javax.swing.GroupLayout.PREFERRED_SIZE, 244, javax.swing.GroupLayout.PREFERRED_SIZE)
.addComponent(filtersPane, javax.swing.GroupLayout.PREFERRED_SIZE, 244, Short.MAX_VALUE)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
.addComponent(HSplitPane, javax.swing.GroupLayout.DEFAULT_SIZE, 1322, Short.MAX_VALUE)
.addComponent(splitPane, javax.swing.GroupLayout.DEFAULT_SIZE, 1322, Short.MAX_VALUE)
.addContainerGap())
);
layout.setVerticalGroup(
@ -120,7 +109,7 @@ public final class CVTTopComponent extends TopComponent implements ExplorerManag
.addContainerGap()
.addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addComponent(filtersPane, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addComponent(HSplitPane))
.addComponent(splitPane))
.addContainerGap())
);
}// </editor-fold>//GEN-END:initComponents
@ -128,13 +117,10 @@ public final class CVTTopComponent extends TopComponent implements ExplorerManag
// Variables declaration - do not modify//GEN-BEGIN:variables
private javax.swing.JTabbedPane BrowseVisualizeTabPane;
private javax.swing.JSplitPane HSplitPane;
private javax.swing.JSplitPane VSplitPane;
private org.sleuthkit.autopsy.communications.AccountsBrowser accountsBrowser;
private org.sleuthkit.autopsy.communications.FiltersPanel filtersPane;
private javax.swing.JPanel jPanel1;
private javax.swing.JTextField jTextField1;
private javax.swing.JTextField jTextField2;
private javax.swing.JSplitPane splitPane;
// End of variables declaration//GEN-END:variables
@Override

View File

@ -28,11 +28,6 @@
</SubComponents>
</Container>
</NonVisualComponents>
<Properties>
<Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
<Dimension value="[256, 469]"/>
</Property>
</Properties>
<AuxValues>
<AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="1"/>
<AuxValue name="FormSettings_autoSetComponentName" type="java.lang.Boolean" value="false"/>
@ -56,7 +51,7 @@
<Group type="102" alignment="0" attributes="0">
<Component id="filtersTitleLabel" min="-2" max="-2" attributes="0"/>
<EmptySpace max="32767" attributes="0"/>
<Component id="applyFiltersButton" min="-2" max="-2" attributes="0"/>
<Component id="applyFiltersButton" min="-2" pref="83" max="-2" attributes="0"/>
</Group>
</Group>
<EmptySpace max="-2" attributes="0"/>
@ -90,6 +85,9 @@
<ResourceString bundle="org/sleuthkit/autopsy/communications/Bundle.properties" key="FiltersPanel.applyFiltersButton.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, &quot;{key}&quot;)"/>
</Property>
<Property name="horizontalTextPosition" type="int" value="10"/>
<Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
<Dimension value="null"/>
</Property>
</Properties>
<Events>
<EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="applyFiltersButtonActionPerformed"/>
@ -98,7 +96,7 @@
<Component class="javax.swing.JLabel" name="filtersTitleLabel">
<Properties>
<Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor">
<Font name="Tahoma" size="18" style="0"/>
<Font name="Tahoma" size="16" style="0"/>
</Property>
<Property name="icon" type="javax.swing.Icon" editor="org.netbeans.modules.form.editors2.IconEditor">
<Image iconType="3" name="/org/sleuthkit/autopsy/communications/images/funnel.png"/>
@ -116,7 +114,7 @@
<Group type="102" attributes="0">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" alignment="1" attributes="0">
<EmptySpace pref="51" max="32767" attributes="0"/>
<EmptySpace pref="43" max="32767" attributes="0"/>
<Component id="unCheckAllAccountTypesButton" min="-2" max="-2" attributes="0"/>
<EmptySpace max="-2" attributes="0"/>
<Component id="checkAllAccountTypesButton" min="-2" max="-2" attributes="0"/>

View File

@ -33,15 +33,16 @@ import org.sleuthkit.autopsy.coreutils.Logger;
import org.sleuthkit.autopsy.coreutils.ThreadConfined;
import org.sleuthkit.datamodel.Account;
import org.sleuthkit.datamodel.AccountDeviceInstance;
import org.sleuthkit.datamodel.AccountTypeFilter;
import org.sleuthkit.datamodel.CommunicationsFilter;
import org.sleuthkit.datamodel.CommunicationsManager;
import org.sleuthkit.datamodel.DataSource;
import org.sleuthkit.datamodel.DeviceFilter;
import org.sleuthkit.datamodel.AccountTypeFilter;
import org.sleuthkit.datamodel.TskCoreException;
/**
*
* Panel that holds the Filter control widgets and translates user filtering
* changes into queries against the CommunicationsManager
*/
final public class FiltersPanel extends javax.swing.JPanel {
@ -133,8 +134,6 @@ final public class FiltersPanel extends javax.swing.JPanel {
// <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
private void initComponents() {
jList1 = new javax.swing.JList<>();
jList1.setModel(new javax.swing.AbstractListModel<String>() {
String[] strings = { "Item 1", "Item 2", "Item 3", "Item 4", "Item 5" };
public int getSize() { return strings.length; }
@ -142,18 +141,17 @@ final public class FiltersPanel extends javax.swing.JPanel {
});
jScrollPane1.setViewportView(jList1);
setPreferredSize(new java.awt.Dimension(256, 469));
applyFiltersButton.setIcon(new javax.swing.ImageIcon(getClass().getResource("/org/sleuthkit/autopsy/communications/images/control-double.png"))); // NOI18N
applyFiltersButton.setText(org.openide.util.NbBundle.getMessage(FiltersPanel.class, "FiltersPanel.applyFiltersButton.text")); // NOI18N
applyFiltersButton.setHorizontalTextPosition(javax.swing.SwingConstants.LEADING);
applyFiltersButton.setPreferredSize(null);
applyFiltersButton.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
applyFiltersButtonActionPerformed(evt);
}
});
filtersTitleLabel.setFont(new java.awt.Font("Tahoma", 0, 18)); // NOI18N
filtersTitleLabel.setFont(new java.awt.Font("Tahoma", 0, 16)); // NOI18N
filtersTitleLabel.setIcon(new javax.swing.ImageIcon(getClass().getResource("/org/sleuthkit/autopsy/communications/images/funnel.png"))); // NOI18N
filtersTitleLabel.setText(org.openide.util.NbBundle.getMessage(FiltersPanel.class, "FiltersPanel.filtersTitleLabel.text")); // NOI18N
@ -184,7 +182,7 @@ final public class FiltersPanel extends javax.swing.JPanel {
.addGroup(jPanel2Layout.createSequentialGroup()
.addGroup(jPanel2Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(javax.swing.GroupLayout.Alignment.TRAILING, jPanel2Layout.createSequentialGroup()
.addContainerGap(51, Short.MAX_VALUE)
.addContainerGap(43, Short.MAX_VALUE)
.addComponent(unCheckAllAccountTypesButton)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(checkAllAccountTypesButton))
@ -232,15 +230,12 @@ final public class FiltersPanel extends javax.swing.JPanel {
.addGroup(jPanel3Layout.createSequentialGroup()
.addComponent(devicesLabel)
.addContainerGap(javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
.addComponent(devicesPane, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addGroup(jPanel3Layout.createSequentialGroup()
.addGroup(jPanel3Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addComponent(devicesPane, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addGroup(jPanel3Layout.createSequentialGroup()
.addContainerGap(javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addComponent(unCheckAllDevicesButton)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(checkAllDevicesButton)))
.addGap(0, 0, 0))
.addContainerGap(javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addComponent(unCheckAllDevicesButton)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(checkAllDevicesButton))
);
jPanel3Layout.setVerticalGroup(
jPanel3Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
@ -268,7 +263,7 @@ final public class FiltersPanel extends javax.swing.JPanel {
.addGroup(javax.swing.GroupLayout.Alignment.LEADING, layout.createSequentialGroup()
.addComponent(filtersTitleLabel)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addComponent(applyFiltersButton)))
.addComponent(applyFiltersButton, javax.swing.GroupLayout.PREFERRED_SIZE, 83, javax.swing.GroupLayout.PREFERRED_SIZE)))
.addContainerGap())
);
layout.setVerticalGroup(
@ -277,7 +272,7 @@ final public class FiltersPanel extends javax.swing.JPanel {
.addContainerGap()
.addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
.addComponent(filtersTitleLabel)
.addComponent(applyFiltersButton))
.addComponent(applyFiltersButton, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
.addGap(18, 18, 18)
.addComponent(jPanel3, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
@ -304,15 +299,14 @@ final public class FiltersPanel extends javax.swing.JPanel {
commsFilter.addAndFilter(getDevceFilter());
commsFilter.addAndFilter(getAccountTypeFilter());
final CommunicationsManager communicationsManager = Case.getCurrentCase().getSleuthkitCase().getCommunicationsManager();
accountDeviceInstances.addAll(communicationsManager.getAccountDeviceInstancesWithRelationships(commsFilter));
final CommunicationsManager commsManager = Case.getCurrentCase().getSleuthkitCase().getCommunicationsManager();
accountDeviceInstances.addAll(commsManager.getAccountDeviceInstancesWithRelationships(commsFilter));
List<AccountDeviceInstanceKey> accountDeviceInstanceKeys = new ArrayList<>();
accountDeviceInstances.forEach((accountDevInstance) -> {
accountDeviceInstanceKeys.add(new AccountDeviceInstanceKey(accountDevInstance, commsFilter ) );
});
em.setRootContext(new AbstractNode(new AccountsDeviceInstanceChildren(accountDeviceInstanceKeys)));
accountDeviceInstances.forEach(accountDeviceInstance
-> accountDeviceInstanceKeys.add(new AccountDeviceInstanceKey(accountDeviceInstance, commsFilter)));
em.setRootContext(new AbstractNode(new AccountsRootChildren(accountDeviceInstanceKeys, commsManager)));
} catch (TskCoreException ex) {
logger.log(Level.SEVERE, "There was a error loading the accounts.", ex);
}
@ -331,7 +325,7 @@ final public class FiltersPanel extends javax.swing.JPanel {
.map(entry -> entry.getKey()).collect(Collectors.toSet()));
return accountTypeFilter;
}
@ThreadConfined(type = ThreadConfined.ThreadType.AWT)
private void setAllTypesSelected(boolean selected) {
setAllSelected(accountTypeMap, selected);
@ -372,7 +366,7 @@ final public class FiltersPanel extends javax.swing.JPanel {
private final javax.swing.JLabel devicesLabel = new javax.swing.JLabel();
private final javax.swing.JPanel devicesPane = new javax.swing.JPanel();
private final javax.swing.JLabel filtersTitleLabel = new javax.swing.JLabel();
private javax.swing.JList<String> jList1;
private final javax.swing.JList<String> jList1 = new javax.swing.JList<>();
private final javax.swing.JPanel jPanel2 = new javax.swing.JPanel();
private final javax.swing.JPanel jPanel3 = new javax.swing.JPanel();
private final javax.swing.JScrollPane jScrollPane1 = new javax.swing.JScrollPane();

View File

@ -0,0 +1,61 @@
<?xml version="1.0" encoding="UTF-8" ?>
<Form version="1.4" maxVersion="1.9" type="org.netbeans.modules.form.forminfo.JPanelFormInfo">
<AuxValues>
<AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="1"/>
<AuxValue name="FormSettings_autoSetComponentName" type="java.lang.Boolean" value="false"/>
<AuxValue name="FormSettings_generateFQN" type="java.lang.Boolean" value="true"/>
<AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/>
<AuxValue name="FormSettings_i18nAutoMode" type="java.lang.Boolean" value="true"/>
<AuxValue name="FormSettings_layoutCodeTarget" type="java.lang.Integer" value="1"/>
<AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/>
<AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/>
<AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/>
</AuxValues>
<Layout>
<DimensionLayout dim="0">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" alignment="1" attributes="0">
<EmptySpace min="-2" pref="0" max="-2" attributes="0"/>
<Component id="splitPane" pref="652" max="32767" attributes="0"/>
</Group>
</Group>
</DimensionLayout>
<DimensionLayout dim="1">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" alignment="0" attributes="0">
<EmptySpace min="-2" pref="0" max="-2" attributes="0"/>
<Component id="splitPane" pref="1083" max="32767" attributes="0"/>
<EmptySpace min="-2" pref="0" max="-2" attributes="0"/>
</Group>
</Group>
</DimensionLayout>
</Layout>
<SubComponents>
<Container class="javax.swing.JSplitPane" name="splitPane">
<Properties>
<Property name="dividerLocation" type="int" value="400"/>
<Property name="dividerSize" type="int" value="10"/>
<Property name="orientation" type="int" value="0"/>
<Property name="resizeWeight" type="double" value="0.4"/>
</Properties>
<Layout class="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout"/>
<SubComponents>
<Component class="org.sleuthkit.autopsy.communications.MessageDataContent" name="messageDataContent">
<Properties>
<Property name="minimumSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
<Dimension value="null"/>
</Property>
</Properties>
<Constraints>
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout" value="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription">
<JSplitPaneConstraints position="bottom"/>
</Constraint>
</Constraints>
</Component>
</SubComponents>
</Container>
</SubComponents>
</Form>

View File

@ -0,0 +1,151 @@
/*
* Autopsy Forensic Browser
*
* Copyright 2011-2017 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 obt ain 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.communications;
import com.google.common.collect.Iterables;
import java.util.HashSet;
import java.util.Set;
import java.util.logging.Level;
import org.openide.explorer.ExplorerManager;
import org.openide.nodes.Node;
import org.sleuthkit.autopsy.communications.AccountsRootChildren.AccountDeviceInstanceNode;
import org.sleuthkit.autopsy.corecomponents.DataResultPanel;
import org.sleuthkit.autopsy.corecomponents.TableFilterNode;
import org.sleuthkit.autopsy.coreutils.Logger;
import org.sleuthkit.datamodel.Account;
import org.sleuthkit.datamodel.CommunicationsFilter;
import org.sleuthkit.datamodel.CommunicationsManager;
/**
* The right hand side of the CVT. Has a DataResultPanel to show messages and
* account details, and a Content viewer to show individual
*/
final class MessageBrowser extends javax.swing.JPanel implements ExplorerManager.Provider {
private static final Logger logger = Logger.getLogger(MessageBrowser.class.getName());
private static final long serialVersionUID = 1L;
private ExplorerManager parentExplorereManager;
private final DataResultPanel messagesResultPanel;
private ExplorerManager internalExplorerManager;
MessageBrowser() {
initComponents();
messagesResultPanel = DataResultPanel.createInstanceUninitialized("Account", "", Node.EMPTY, 0, messageDataContent);
splitPane.setTopComponent(messagesResultPanel);
splitPane.setBottomComponent(messageDataContent);
}
@Override
public void addNotify() {
super.addNotify();
this.parentExplorereManager = ExplorerManager.find(this);
internalExplorerManager = new ExplorerManager();
parentExplorereManager.addPropertyChangeListener(pce -> {
if (pce.getPropertyName().equals(ExplorerManager.PROP_SELECTED_NODES)) {
final Node[] selectedNodes = parentExplorereManager.getSelectedNodes();
if (selectedNodes.length == 0) {
messagesResultPanel.setNode(null);
messagesResultPanel.setPath("");
} else {
Set<Account> accounts = new HashSet<>();
CommunicationsFilter filter = null;
CommunicationsManager commsManager = null;
for (Node n : selectedNodes) {
if (n instanceof AccountDeviceInstanceNode) {
final AccountDeviceInstanceNode adiNode = (AccountDeviceInstanceNode) n;
accounts.add(adiNode.getAccountDeviceInstance().getAccount());
if (commsManager == null) {
commsManager = adiNode.getCommsManager();
}
if (filter == null) {
filter = adiNode.getFilter();
} else if (filter != adiNode.getFilter()) {
///this should never happen...
logger.log(Level.WARNING, "Not all AccountDeviceInstanceNodes have the same filter. Using the first.");
}
} else {
///this should never happen...
logger.log(Level.WARNING, "Unexpected Node encountered: " + n.toString());
}
}
messagesResultPanel.setNode(new TableFilterNode(new AccountDetailsNode(accounts, filter, commsManager), true));
if (accounts.size() == 1) {
messagesResultPanel.setPath(Iterables.getOnlyElement(accounts).getAccountUniqueID());
} else {
messagesResultPanel.setPath(accounts.size() + " accounts");
}
}
}
});
messagesResultPanel.open();
}
/**
* This method is called from within the constructor to initialize the form.
* WARNING: Do NOT modify this code. The content of this method is always
* regenerated by the Form Editor.
*/
@SuppressWarnings("unchecked")
// <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
private void initComponents() {
splitPane = new javax.swing.JSplitPane();
messageDataContent = new org.sleuthkit.autopsy.communications.MessageDataContent();
splitPane.setDividerLocation(400);
splitPane.setDividerSize(10);
splitPane.setOrientation(javax.swing.JSplitPane.VERTICAL_SPLIT);
splitPane.setResizeWeight(0.4);
messageDataContent.setMinimumSize(null);
splitPane.setBottomComponent(messageDataContent);
javax.swing.GroupLayout layout = new javax.swing.GroupLayout(this);
this.setLayout(layout);
layout.setHorizontalGroup(
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(javax.swing.GroupLayout.Alignment.TRAILING, layout.createSequentialGroup()
.addGap(0, 0, 0)
.addComponent(splitPane, javax.swing.GroupLayout.DEFAULT_SIZE, 652, Short.MAX_VALUE))
);
layout.setVerticalGroup(
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(layout.createSequentialGroup()
.addGap(0, 0, 0)
.addComponent(splitPane, javax.swing.GroupLayout.DEFAULT_SIZE, 1083, Short.MAX_VALUE)
.addGap(0, 0, 0))
);
}// </editor-fold>//GEN-END:initComponents
// Variables declaration - do not modify//GEN-BEGIN:variables
private org.sleuthkit.autopsy.communications.MessageDataContent messageDataContent;
private javax.swing.JSplitPane splitPane;
// End of variables declaration//GEN-END:variables
@Override
public ExplorerManager getExplorerManager() {
return internalExplorerManager;
}
}

View File

@ -0,0 +1,38 @@
/*
* Autopsy Forensic Browser
*
* Copyright 2011-2017 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.communications;
import java.beans.PropertyChangeEvent;
import org.sleuthkit.autopsy.contentviewers.MessageContentViewer;
import org.sleuthkit.autopsy.corecomponentinterfaces.DataContent;
/**
* Extend MessageContentViewer so that it implements DataContent and can be set
* as the only ContentViewer for a DataResultPanel
*/
public class MessageDataContent extends MessageContentViewer implements DataContent {
private static final long serialVersionUID = 1L;
@Override
public void propertyChange(PropertyChangeEvent evt) {
throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates.
}
}

View File

@ -0,0 +1,124 @@
/*
* Autopsy Forensic Browser
*
* Copyright 2011-2017 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.communications;
import java.util.logging.Level;
import org.apache.commons.lang3.StringUtils;
import org.openide.nodes.Sheet;
import org.sleuthkit.autopsy.coreutils.Logger;
import org.sleuthkit.autopsy.datamodel.BlackboardArtifactNode;
import org.sleuthkit.autopsy.datamodel.NodeProperty;
import org.sleuthkit.datamodel.BlackboardArtifact;
import org.sleuthkit.datamodel.BlackboardAttribute;
import org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE;
import static org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE.TSK_DATETIME;
import static org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE.TSK_DATETIME_SENT;
import static org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE.TSK_DATETIME_START;
import static org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE.TSK_EMAIL_FROM;
import static org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE.TSK_EMAIL_TO;
import static org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE.TSK_PHONE_NUMBER_FROM;
import static org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE.TSK_PHONE_NUMBER_TO;
import static org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE.TSK_SUBJECT;
import org.sleuthkit.datamodel.TskCoreException;
/**
*
*/
public class RelationShipFilterNode extends BlackboardArtifactNode {
private static final Logger logger = Logger.getLogger(RelationShipFilterNode.class.getName());
public RelationShipFilterNode(BlackboardArtifact artifact) {
super(artifact);
final String stripEnd = StringUtils.stripEnd(artifact.getDisplayName(), "s");
String removeEndIgnoreCase = StringUtils.removeEndIgnoreCase(stripEnd, "message");
setDisplayName(removeEndIgnoreCase.isEmpty() ? stripEnd : removeEndIgnoreCase);
}
@Override
protected Sheet createSheet() {
Sheet s = new Sheet();
Sheet.Set ss = s.get(Sheet.PROPERTIES);
if (ss == null) {
ss = Sheet.createPropertiesSet();
s.put(ss);
}
ss.put(new NodeProperty<>("Type", "Type", "Type", getDisplayName()));
final BlackboardArtifact artifact = getArtifact();
BlackboardArtifact.ARTIFACT_TYPE fromID = BlackboardArtifact.ARTIFACT_TYPE.fromID(getArtifact().getArtifactTypeID());
if (null != fromID) {
switch (fromID) {
case TSK_EMAIL_MSG:
ss.put(new NodeProperty<>("From", "From", "From",
getAttributeDisplayString(artifact, TSK_EMAIL_FROM)));
ss.put(new NodeProperty<>("To", "To", "To",
getAttributeDisplayString(artifact, TSK_EMAIL_TO)));
ss.put(new NodeProperty<>("Date", "Date", "Date",
getAttributeDisplayString(artifact, TSK_DATETIME_SENT)));
ss.put(new NodeProperty<>("Subject", "Subject", "Subject",
getAttributeDisplayString(artifact, TSK_SUBJECT)));
break;
case TSK_MESSAGE:
ss.put(new NodeProperty<>("From", "From", "From",
getAttributeDisplayString(artifact, TSK_PHONE_NUMBER_FROM)));
ss.put(new NodeProperty<>("To", "To", "To",
getAttributeDisplayString(artifact, TSK_PHONE_NUMBER_TO)));
ss.put(new NodeProperty<>("Date", "Date", "Date",
getAttributeDisplayString(artifact, TSK_DATETIME)));
ss.put(new NodeProperty<>("Subject", "Subject", "Subject",
getAttributeDisplayString(artifact, TSK_SUBJECT)));
break;
case TSK_CALLLOG:
ss.put(new NodeProperty<>("From", "From", "From",
getAttributeDisplayString(artifact, TSK_PHONE_NUMBER_FROM)));
ss.put(new NodeProperty<>("To", "To", "To",
getAttributeDisplayString(artifact, TSK_PHONE_NUMBER_TO)));
ss.put(new NodeProperty<>("Date", "Date", "Date",
getAttributeDisplayString(artifact, TSK_DATETIME_START)));
break;
default:
break;
}
}
return s;
}
/**
*
* @param artifact the value of artifact
* @param attributeType the value of TSK_SUBJECT1
*
* @throws TskCoreException
*/
private static String getAttributeDisplayString(final BlackboardArtifact artifact, final ATTRIBUTE_TYPE attributeType) {
try {
BlackboardAttribute attribute = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.fromID(attributeType.getTypeID())));
if (attribute == null) {
return "";
} else {
return attribute.getDisplayString();
}
} catch (TskCoreException tskCoreException) {
logger.log(Level.WARNING, "Error getting attribute value.", tskCoreException);
return "";
}
}
}

View File

@ -37,4 +37,4 @@ MessageContentViewer.directionText.text=direction
MessageContentViewer.ccLabel.text=CC:
MessageContentViewer.showImagesToggleButton.text=Show Images
MessageContentViewer.showImagesToggleButton.hide.text=Hide Images
MessageContentViewer.htmlbodyScrollPane.TabConstraints.tabTitle=HTML
MessageContentViewer.htmlPane.TabConstraints.tabTitle=HTML

View File

@ -3,7 +3,7 @@
<Form version="1.5" maxVersion="1.9" type="org.netbeans.modules.form.forminfo.JPanelFormInfo">
<Properties>
<Property name="minimumSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
<Dimension value="[650, 546]"/>
<Dimension value="null"/>
</Property>
</Properties>
<AuxValues>
@ -21,22 +21,24 @@
<Layout>
<DimensionLayout dim="0">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" alignment="1" attributes="0">
<EmptySpace max="-2" attributes="0"/>
<Component id="envelopePanel" max="32767" attributes="0"/>
<EmptySpace max="-2" attributes="0"/>
<Group type="102" alignment="0" attributes="0">
<EmptySpace min="-2" pref="5" max="-2" attributes="0"/>
<Group type="103" groupAlignment="0" attributes="0">
<Component id="msgbodyTabbedPane" max="32767" attributes="0"/>
<Component id="envelopePanel" max="32767" attributes="0"/>
</Group>
<EmptySpace min="-2" pref="5" max="-2" attributes="0"/>
</Group>
<Component id="msgbodyTabbedPane" alignment="0" max="32767" attributes="0"/>
</Group>
</DimensionLayout>
<DimensionLayout dim="1">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" alignment="0" attributes="0">
<EmptySpace min="-2" pref="5" max="-2" attributes="0"/>
<Component id="envelopePanel" min="-2" max="-2" attributes="0"/>
<EmptySpace max="-2" attributes="0"/>
<Component id="envelopePanel" max="32767" attributes="0"/>
<EmptySpace max="-2" attributes="0"/>
<Component id="msgbodyTabbedPane" min="-2" pref="397" max="-2" attributes="0"/>
<EmptySpace max="-2" attributes="0"/>
<Component id="msgbodyTabbedPane" pref="471" max="32767" attributes="0"/>
<EmptySpace min="0" pref="0" max="-2" attributes="0"/>
</Group>
</Group>
</DimensionLayout>
@ -53,53 +55,46 @@
<DimensionLayout dim="0">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" attributes="0">
<EmptySpace max="-2" attributes="0"/>
<EmptySpace min="-2" pref="5" max="-2" attributes="0"/>
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" attributes="0">
<Group type="103" groupAlignment="0" attributes="0">
<Component id="fromLabel" alignment="0" min="-2" max="-2" attributes="0"/>
<Component id="toLabel" alignment="0" min="-2" max="-2" attributes="0"/>
</Group>
<EmptySpace type="unrelated" max="-2" attributes="0"/>
<Group type="103" groupAlignment="0" attributes="0">
<Component id="fromText" max="32767" attributes="0"/>
<Component id="toText" max="32767" attributes="0"/>
</Group>
<EmptySpace type="unrelated" min="-2" max="-2" attributes="0"/>
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" attributes="0">
<EmptySpace min="-2" pref="8" max="-2" attributes="0"/>
<Component id="datetimeText" min="-2" max="-2" attributes="0"/>
</Group>
<Group type="102" alignment="1" attributes="0">
<Component id="toText" max="32767" attributes="0"/>
<EmptySpace max="-2" attributes="0"/>
<Component id="directionText" min="-2" max="-2" attributes="0"/>
<Component id="directionText" min="-2" pref="66" max="-2" attributes="0"/>
</Group>
<Group type="102" attributes="0">
<Component id="fromText" max="32767" attributes="0"/>
<EmptySpace max="-2" attributes="0"/>
<Component id="datetimeText" min="-2" pref="140" max="-2" attributes="0"/>
</Group>
</Group>
</Group>
<Group type="102" attributes="0">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" attributes="0">
<Component id="ccLabel" min="-2" max="-2" attributes="0"/>
<EmptySpace type="separate" max="-2" attributes="0"/>
<Component id="ccText" min="-2" max="-2" attributes="0"/>
</Group>
<Group type="102" alignment="0" attributes="0">
<Component id="subjectLabel" min="-2" max="-2" attributes="0"/>
<EmptySpace max="-2" attributes="0"/>
<Component id="subjectText" min="-2" pref="400" max="-2" attributes="0"/>
</Group>
</Group>
<EmptySpace min="0" pref="0" max="32767" attributes="0"/>
<Component id="ccLabel" min="-2" max="-2" attributes="0"/>
<EmptySpace min="-2" pref="26" max="-2" attributes="0"/>
<Component id="ccText" max="32767" attributes="0"/>
</Group>
<Group type="102" alignment="0" attributes="0">
<Component id="subjectLabel" min="-2" max="-2" attributes="0"/>
<EmptySpace min="-2" max="-2" attributes="0"/>
<Component id="subjectText" max="32767" attributes="0"/>
</Group>
</Group>
<EmptySpace max="-2" attributes="0"/>
<EmptySpace min="-2" pref="5" max="-2" attributes="0"/>
</Group>
</Group>
</DimensionLayout>
<DimensionLayout dim="1">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" alignment="0" attributes="0">
<EmptySpace max="-2" attributes="0"/>
<EmptySpace min="-2" pref="5" max="-2" attributes="0"/>
<Group type="103" groupAlignment="3" attributes="0">
<Component id="fromLabel" alignment="3" min="-2" max="-2" attributes="0"/>
<Component id="datetimeText" alignment="3" min="-2" max="-2" attributes="0"/>
@ -116,12 +111,12 @@
<Component id="ccLabel" alignment="3" min="-2" max="-2" attributes="0"/>
<Component id="ccText" alignment="3" min="-2" max="-2" attributes="0"/>
</Group>
<EmptySpace type="separate" max="-2" attributes="0"/>
<EmptySpace type="unrelated" max="-2" attributes="0"/>
<Group type="103" groupAlignment="3" attributes="0">
<Component id="subjectLabel" alignment="3" min="-2" max="-2" attributes="0"/>
<Component id="subjectText" alignment="3" min="-2" max="-2" attributes="0"/>
</Group>
<EmptySpace pref="24" max="32767" attributes="0"/>
<EmptySpace min="-2" pref="5" max="-2" attributes="0"/>
</Group>
</Group>
</DimensionLayout>
@ -136,6 +131,7 @@
</Component>
<Component class="javax.swing.JLabel" name="datetimeText">
<Properties>
<Property name="horizontalAlignment" type="int" value="4"/>
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
<ResourceString bundle="org/sleuthkit/autopsy/contentviewers/Bundle.properties" key="MessageContentViewer.datetimeText.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, &quot;{key}&quot;)"/>
</Property>
@ -192,6 +188,7 @@
</Component>
<Component class="javax.swing.JLabel" name="directionText">
<Properties>
<Property name="horizontalAlignment" type="int" value="4"/>
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
<ResourceString bundle="org/sleuthkit/autopsy/contentviewers/Bundle.properties" key="MessageContentViewer.directionText.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, &quot;{key}&quot;)"/>
</Property>
@ -247,81 +244,64 @@
</Component>
</SubComponents>
</Container>
<Container class="javax.swing.JScrollPane" name="htmlbodyScrollPane">
<Container class="javax.swing.JPanel" name="htmlPane">
<Constraints>
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout" value="org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription">
<JTabbedPaneConstraints tabName="HTML">
<Property name="tabTitle" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
<ResourceString bundle="org/sleuthkit/autopsy/contentviewers/Bundle.properties" key="MessageContentViewer.htmlbodyScrollPane.TabConstraints.tabTitle" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, &quot;{key}&quot;)"/>
<ResourceString bundle="org/sleuthkit/autopsy/contentviewers/Bundle.properties" key="MessageContentViewer.htmlPane.TabConstraints.tabTitle" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, &quot;{key}&quot;)"/>
</Property>
</JTabbedPaneConstraints>
</Constraint>
</Constraints>
<Layout class="org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout"/>
<Layout>
<DimensionLayout dim="0">
<Group type="103" groupAlignment="0" attributes="0">
<Component id="jScrollPane2" alignment="0" max="32767" attributes="0"/>
<Group type="102" alignment="1" attributes="0">
<EmptySpace pref="533" max="32767" attributes="0"/>
<Component id="showImagesToggleButton" min="-2" max="-2" attributes="0"/>
<EmptySpace min="-2" pref="3" max="-2" attributes="0"/>
</Group>
</Group>
</DimensionLayout>
<DimensionLayout dim="1">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" alignment="0" attributes="0">
<Component id="showImagesToggleButton" min="-2" max="-2" attributes="0"/>
<EmptySpace min="-2" max="-2" attributes="0"/>
<Component id="jScrollPane2" max="32767" attributes="0"/>
<EmptySpace min="0" pref="0" max="-2" attributes="0"/>
</Group>
</Group>
</DimensionLayout>
</Layout>
<SubComponents>
<Container class="javax.swing.JPanel" name="jPanel2">
<Container class="javax.swing.JScrollPane" name="jScrollPane2">
<AuxValues>
<AuxValue name="autoScrollPane" type="java.lang.Boolean" value="true"/>
</AuxValues>
<Layout>
<DimensionLayout dim="0">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" alignment="1" attributes="0">
<EmptySpace pref="536" max="32767" attributes="0"/>
<Component id="showImagesToggleButton" min="-2" max="-2" attributes="0"/>
<EmptySpace max="-2" attributes="0"/>
</Group>
<Group type="103" rootIndex="1" groupAlignment="0" attributes="0">
<Group type="102" alignment="0" attributes="0">
<EmptySpace max="-2" attributes="0"/>
<Component id="jScrollPane2" pref="623" max="32767" attributes="0"/>
<EmptySpace max="-2" attributes="0"/>
</Group>
</Group>
</Group>
</DimensionLayout>
<DimensionLayout dim="1">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" alignment="0" attributes="0">
<EmptySpace max="-2" attributes="0"/>
<Component id="showImagesToggleButton" min="-2" max="-2" attributes="0"/>
<EmptySpace pref="333" max="32767" attributes="0"/>
</Group>
<Group type="103" rootIndex="1" groupAlignment="0" attributes="0">
<Group type="102" alignment="1" attributes="0">
<EmptySpace min="0" pref="34" max="32767" attributes="0"/>
<Component id="jScrollPane2" min="-2" pref="333" max="-2" attributes="0"/>
</Group>
</Group>
</Group>
</DimensionLayout>
</Layout>
<Layout class="org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout"/>
<SubComponents>
<Container class="javax.swing.JScrollPane" name="jScrollPane2">
<AuxValues>
<AuxValue name="autoScrollPane" type="java.lang.Boolean" value="true"/>
</AuxValues>
<Layout class="org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout"/>
<SubComponents>
<Component class="javax.swing.JTextPane" name="htmlbodyTextPane">
<Properties>
<Property name="editable" type="boolean" value="false"/>
</Properties>
</Component>
</SubComponents>
</Container>
<Component class="javax.swing.JToggleButton" name="showImagesToggleButton">
<Component class="javax.swing.JTextPane" name="htmlbodyTextPane">
<Properties>
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
<ResourceString bundle="org/sleuthkit/autopsy/contentviewers/Bundle.properties" key="MessageContentViewer.showImagesToggleButton.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, &quot;{key}&quot;)"/>
</Property>
<Property name="editable" type="boolean" value="false"/>
</Properties>
<Events>
<EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="showImagesToggleButtonActionPerformed"/>
</Events>
</Component>
</SubComponents>
</Container>
<Component class="javax.swing.JToggleButton" name="showImagesToggleButton">
<Properties>
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
<ResourceString bundle="org/sleuthkit/autopsy/contentviewers/Bundle.properties" key="MessageContentViewer.showImagesToggleButton.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, &quot;{key}&quot;)"/>
</Property>
</Properties>
<Events>
<EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="showImagesToggleButtonActionPerformed"/>
</Events>
</Component>
</SubComponents>
</Container>
<Container class="javax.swing.JScrollPane" name="rtfbodyScrollPane">

View File

@ -20,6 +20,8 @@ package org.sleuthkit.autopsy.contentviewers;
import java.awt.Component;
import java.util.logging.Level;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.openide.nodes.Node;
import org.openide.util.NbBundle;
import org.openide.util.lookup.ServiceProvider;
@ -28,8 +30,6 @@ import org.sleuthkit.autopsy.coreutils.Logger;
import org.sleuthkit.datamodel.BlackboardArtifact;
import org.sleuthkit.datamodel.BlackboardAttribute;
import org.sleuthkit.datamodel.TskCoreException;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
/**
* Shows SMS/MMS/EMail messages
@ -37,16 +37,16 @@ import org.jsoup.nodes.Document;
@ServiceProvider(service = DataContentViewer.class, position = 4)
public class MessageContentViewer extends javax.swing.JPanel implements DataContentViewer {
private static final Logger LOGGER = Logger.getLogger(MessageContentViewer.class.getName());
private static final int HDR_TAB_INDEX = 0;
private static final int TEXT_TAB_INDEX = 1;
private static final int HTML_TAB_INDEX = 2;
private static final int RTF_TAB_INDEX = 3;
private static final long serialVersionUID = 1L;
private BlackboardArtifact artifact; // Artifact currently being displayed
/**
* Creates new form MessageContentViewer
*/
@ -80,20 +80,20 @@ public class MessageContentViewer extends javax.swing.JPanel implements DataCont
headersTextArea = new javax.swing.JTextArea();
textbodyScrollPane = new javax.swing.JScrollPane();
textbodyTextArea = new javax.swing.JTextArea();
htmlbodyScrollPane = new javax.swing.JScrollPane();
jPanel2 = new javax.swing.JPanel();
htmlPane = new javax.swing.JPanel();
jScrollPane2 = new javax.swing.JScrollPane();
htmlbodyTextPane = new javax.swing.JTextPane();
showImagesToggleButton = new javax.swing.JToggleButton();
rtfbodyScrollPane = new javax.swing.JScrollPane();
rtfbodyTextPane = new javax.swing.JTextPane();
setMinimumSize(new java.awt.Dimension(650, 546));
setMinimumSize(null);
envelopePanel.setBackground(new java.awt.Color(204, 204, 204));
org.openide.awt.Mnemonics.setLocalizedText(fromLabel, org.openide.util.NbBundle.getMessage(MessageContentViewer.class, "MessageContentViewer.fromLabel.text")); // NOI18N
datetimeText.setHorizontalAlignment(javax.swing.SwingConstants.RIGHT);
org.openide.awt.Mnemonics.setLocalizedText(datetimeText, org.openide.util.NbBundle.getMessage(MessageContentViewer.class, "MessageContentViewer.datetimeText.text")); // NOI18N
org.openide.awt.Mnemonics.setLocalizedText(fromText, org.openide.util.NbBundle.getMessage(MessageContentViewer.class, "MessageContentViewer.fromText.text")); // NOI18N
@ -110,6 +110,7 @@ public class MessageContentViewer extends javax.swing.JPanel implements DataCont
org.openide.awt.Mnemonics.setLocalizedText(subjectText, org.openide.util.NbBundle.getMessage(MessageContentViewer.class, "MessageContentViewer.subjectText.text")); // NOI18N
directionText.setHorizontalAlignment(javax.swing.SwingConstants.RIGHT);
org.openide.awt.Mnemonics.setLocalizedText(directionText, org.openide.util.NbBundle.getMessage(MessageContentViewer.class, "MessageContentViewer.directionText.text")); // NOI18N
javax.swing.GroupLayout envelopePanelLayout = new javax.swing.GroupLayout(envelopePanel);
@ -117,40 +118,36 @@ public class MessageContentViewer extends javax.swing.JPanel implements DataCont
envelopePanelLayout.setHorizontalGroup(
envelopePanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(envelopePanelLayout.createSequentialGroup()
.addContainerGap()
.addGap(5, 5, 5)
.addGroup(envelopePanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(envelopePanelLayout.createSequentialGroup()
.addGroup(envelopePanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addComponent(fromLabel)
.addComponent(toLabel))
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
.addGroup(envelopePanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addComponent(fromText, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addComponent(toText, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
.addGroup(envelopePanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(envelopePanelLayout.createSequentialGroup()
.addGap(8, 8, 8)
.addComponent(datetimeText))
.addGroup(javax.swing.GroupLayout.Alignment.TRAILING, envelopePanelLayout.createSequentialGroup()
.addComponent(toText, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(directionText))))
.addComponent(directionText, javax.swing.GroupLayout.PREFERRED_SIZE, 66, javax.swing.GroupLayout.PREFERRED_SIZE))
.addGroup(envelopePanelLayout.createSequentialGroup()
.addComponent(fromText, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(datetimeText, javax.swing.GroupLayout.PREFERRED_SIZE, 140, javax.swing.GroupLayout.PREFERRED_SIZE))))
.addGroup(envelopePanelLayout.createSequentialGroup()
.addGroup(envelopePanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(envelopePanelLayout.createSequentialGroup()
.addComponent(ccLabel)
.addGap(18, 18, 18)
.addComponent(ccText))
.addGroup(envelopePanelLayout.createSequentialGroup()
.addComponent(subjectLabel)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(subjectText, javax.swing.GroupLayout.PREFERRED_SIZE, 400, javax.swing.GroupLayout.PREFERRED_SIZE)))
.addGap(0, 0, Short.MAX_VALUE)))
.addContainerGap())
.addComponent(ccLabel)
.addGap(26, 26, 26)
.addComponent(ccText, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
.addGroup(envelopePanelLayout.createSequentialGroup()
.addComponent(subjectLabel)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(subjectText, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)))
.addGap(5, 5, 5))
);
envelopePanelLayout.setVerticalGroup(
envelopePanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(envelopePanelLayout.createSequentialGroup()
.addContainerGap()
.addGap(5, 5, 5)
.addGroup(envelopePanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
.addComponent(fromLabel)
.addComponent(datetimeText)
@ -164,11 +161,11 @@ public class MessageContentViewer extends javax.swing.JPanel implements DataCont
.addGroup(envelopePanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
.addComponent(ccLabel)
.addComponent(ccText))
.addGap(18, 18, 18)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
.addGroup(envelopePanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
.addComponent(subjectLabel)
.addComponent(subjectText))
.addContainerGap(24, Short.MAX_VALUE))
.addGap(5, 5, 5))
);
headersTextArea.setEditable(false);
@ -195,35 +192,26 @@ public class MessageContentViewer extends javax.swing.JPanel implements DataCont
}
});
javax.swing.GroupLayout jPanel2Layout = new javax.swing.GroupLayout(jPanel2);
jPanel2.setLayout(jPanel2Layout);
jPanel2Layout.setHorizontalGroup(
jPanel2Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(javax.swing.GroupLayout.Alignment.TRAILING, jPanel2Layout.createSequentialGroup()
.addContainerGap(536, Short.MAX_VALUE)
javax.swing.GroupLayout htmlPaneLayout = new javax.swing.GroupLayout(htmlPane);
htmlPane.setLayout(htmlPaneLayout);
htmlPaneLayout.setHorizontalGroup(
htmlPaneLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addComponent(jScrollPane2)
.addGroup(javax.swing.GroupLayout.Alignment.TRAILING, htmlPaneLayout.createSequentialGroup()
.addContainerGap(533, Short.MAX_VALUE)
.addComponent(showImagesToggleButton)
.addContainerGap())
.addGroup(jPanel2Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(jPanel2Layout.createSequentialGroup()
.addContainerGap()
.addComponent(jScrollPane2, javax.swing.GroupLayout.DEFAULT_SIZE, 623, Short.MAX_VALUE)
.addContainerGap()))
.addGap(3, 3, 3))
);
jPanel2Layout.setVerticalGroup(
jPanel2Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(jPanel2Layout.createSequentialGroup()
.addContainerGap()
htmlPaneLayout.setVerticalGroup(
htmlPaneLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(htmlPaneLayout.createSequentialGroup()
.addComponent(showImagesToggleButton)
.addContainerGap(333, Short.MAX_VALUE))
.addGroup(jPanel2Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(javax.swing.GroupLayout.Alignment.TRAILING, jPanel2Layout.createSequentialGroup()
.addGap(0, 34, Short.MAX_VALUE)
.addComponent(jScrollPane2, javax.swing.GroupLayout.PREFERRED_SIZE, 333, javax.swing.GroupLayout.PREFERRED_SIZE)))
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(jScrollPane2)
.addGap(0, 0, 0))
);
htmlbodyScrollPane.setViewportView(jPanel2);
msgbodyTabbedPane.addTab(org.openide.util.NbBundle.getMessage(MessageContentViewer.class, "MessageContentViewer.htmlbodyScrollPane.TabConstraints.tabTitle"), htmlbodyScrollPane); // NOI18N
msgbodyTabbedPane.addTab(org.openide.util.NbBundle.getMessage(MessageContentViewer.class, "MessageContentViewer.htmlPane.TabConstraints.tabTitle"), htmlPane); // NOI18N
rtfbodyTextPane.setEditable(false);
rtfbodyScrollPane.setViewportView(rtfbodyTextPane);
@ -234,37 +222,37 @@ public class MessageContentViewer extends javax.swing.JPanel implements DataCont
this.setLayout(layout);
layout.setHorizontalGroup(
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(javax.swing.GroupLayout.Alignment.TRAILING, layout.createSequentialGroup()
.addContainerGap()
.addComponent(envelopePanel, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addContainerGap())
.addComponent(msgbodyTabbedPane)
.addGroup(layout.createSequentialGroup()
.addGap(5, 5, 5)
.addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addComponent(msgbodyTabbedPane)
.addComponent(envelopePanel, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
.addGap(5, 5, 5))
);
layout.setVerticalGroup(
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(layout.createSequentialGroup()
.addContainerGap()
.addComponent(envelopePanel, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addGap(5, 5, 5)
.addComponent(envelopePanel, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(msgbodyTabbedPane, javax.swing.GroupLayout.PREFERRED_SIZE, 397, javax.swing.GroupLayout.PREFERRED_SIZE)
.addContainerGap())
.addComponent(msgbodyTabbedPane, javax.swing.GroupLayout.DEFAULT_SIZE, 471, Short.MAX_VALUE)
.addGap(0, 0, 0))
);
}// </editor-fold>//GEN-END:initComponents
private void showImagesToggleButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_showImagesToggleButtonActionPerformed
try {
BlackboardAttribute attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_EMAIL_CONTENT_HTML));
if (attr != null && !attr.getValueString().isEmpty()) {
if (showImagesToggleButton.isSelected()) {
showImagesToggleButton.setText(org.openide.util.NbBundle.getMessage(MessageContentViewer.class, "MessageContentViewer.showImagesToggleButton.hide.text"));
this.htmlbodyTextPane.setText("<html><body>" + attr.getValueString() + "</body></html>");
}
else {
} else {
showImagesToggleButton.setText(org.openide.util.NbBundle.getMessage(MessageContentViewer.class, "MessageContentViewer.showImagesToggleButton.text"));
this.htmlbodyTextPane.setText("<html><body>" + cleanseHTML(attr.getValueString()) + "</body></html>");
}
}
@ -284,9 +272,8 @@ public class MessageContentViewer extends javax.swing.JPanel implements DataCont
private javax.swing.JLabel fromText;
private javax.swing.JScrollPane headersScrollPane;
private javax.swing.JTextArea headersTextArea;
private javax.swing.JScrollPane htmlbodyScrollPane;
private javax.swing.JPanel htmlPane;
private javax.swing.JTextPane htmlbodyTextPane;
private javax.swing.JPanel jPanel2;
private javax.swing.JScrollPane jScrollPane2;
private javax.swing.JTabbedPane msgbodyTabbedPane;
private javax.swing.JScrollPane rtfbodyScrollPane;
@ -302,27 +289,30 @@ public class MessageContentViewer extends javax.swing.JPanel implements DataCont
private void customizeComponents() {
// do any customizations here
Utilities.configureTextPaneAsHtml(htmlbodyTextPane);
Utilities.configureTextPaneAsRtf(rtfbodyTextPane);
Utilities.configureTextPaneAsHtml(htmlbodyTextPane);
Utilities.configureTextPaneAsRtf(rtfbodyTextPane);
}
@Override
public void setNode(Node node) {
if (node == null) {
return;
}
artifact = node.getLookup().lookup(BlackboardArtifact.class);
if (artifact == null) {
return;
}
if (artifact.getArtifactTypeID() == BlackboardArtifact.ARTIFACT_TYPE.TSK_MESSAGE.getTypeID()) {
displayMsg();
}
else if (artifact.getArtifactTypeID() == BlackboardArtifact.ARTIFACT_TYPE.TSK_EMAIL_MSG.getTypeID()) {
} else if (artifact.getArtifactTypeID() == BlackboardArtifact.ARTIFACT_TYPE.TSK_EMAIL_MSG.getTypeID()) {
displayEmailMsg();
}
}
@Override
@ -352,211 +342,197 @@ public class MessageContentViewer extends javax.swing.JPanel implements DataCont
@Override
public boolean isSupported(Node node) {
BlackboardArtifact artifact = node.getLookup().lookup(BlackboardArtifact.class);
return ( (artifact != null)
BlackboardArtifact artifact = node.getLookup().lookup(BlackboardArtifact.class);
return ((artifact != null)
&& ((artifact.getArtifactTypeID() == BlackboardArtifact.ARTIFACT_TYPE.TSK_EMAIL_MSG.getTypeID())
|| (artifact.getArtifactTypeID() == BlackboardArtifact.ARTIFACT_TYPE.TSK_MESSAGE.getTypeID())));
}
@Override
public int isPreferred(Node node) {
if ( isSupported(node)){
if (isSupported(node)) {
return 6;
}
return 0;
}
private void displayEmailMsg()
{
private void displayEmailMsg() {
directionText.setVisible(false);
showImagesToggleButton.setVisible(false);
showImagesToggleButton.setText("Show Images");
showImagesToggleButton.setSelected(false);
try {
BlackboardAttribute attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_EMAIL_FROM));
this.fromText.setText(attr.getValueString());
attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_EMAIL_TO));
if (attr != null) {
this.toText.setText(attr.getValueString());
this.toText.setText(attr.getValueString());
}
attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_EMAIL_CC));
if (attr != null && !attr.getValueString().isEmpty()) {
this.ccText.setVisible(true);
this.ccText.setText(attr.getValueString());
}
else {
} else {
this.ccText.setVisible(false);
}
attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_SUBJECT));
if (attr != null && !attr.getValueString().isEmpty()) {
this.subjectText.setVisible(true);
this.subjectText.setText(attr.getValueString());
}
else {
} else {
this.subjectText.setVisible(false);
}
attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_DATETIME_RCVD));
if (attr != null && !attr.getDisplayString().isEmpty()) {
this.datetimeText.setVisible(true);
this.datetimeText.setText(attr.getDisplayString());
}
else {
} else {
this.datetimeText.setVisible(false);
}
int selectedTabIndex = -1;
attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_EMAIL_CONTENT_PLAIN));
if (attr != null && !attr.getValueString().isEmpty()) {
this.textbodyTextArea.setVisible(true);
this.textbodyTextArea.setText(attr.getValueString());
msgbodyTabbedPane.setEnabledAt(TEXT_TAB_INDEX, true);
selectedTabIndex = TEXT_TAB_INDEX;
}
else {
} else {
msgbodyTabbedPane.setEnabledAt(TEXT_TAB_INDEX, false);
}
attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_EMAIL_CONTENT_HTML));
if (attr != null && !attr.getValueString().isEmpty()) {
this.showImagesToggleButton.setVisible(true);
this.htmlbodyTextPane.setVisible(true);
this.htmlbodyTextPane.setText("<html><body>" + cleanseHTML(attr.getValueString()) + "</body></html>");
//this.htmlbodyTextPane.setText(cleanseHTML(attr.getValueString()));
msgbodyTabbedPane.setEnabledAt(HTML_TAB_INDEX, true);
selectedTabIndex = HTML_TAB_INDEX;
}
else {
} else {
msgbodyTabbedPane.setEnabledAt(HTML_TAB_INDEX, false);
this.htmlbodyTextPane.setVisible(false);
}
attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_EMAIL_CONTENT_RTF));
if (attr != null && !attr.getValueString().isEmpty()) {
this.rtfbodyTextPane.setVisible(true);
this.rtfbodyTextPane.setText(attr.getValueString());
msgbodyTabbedPane.setEnabledAt(RTF_TAB_INDEX, true);
selectedTabIndex = RTF_TAB_INDEX;
}
else {
} else {
msgbodyTabbedPane.setEnabledAt(RTF_TAB_INDEX, false);
}
attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_HEADERS));
if (attr != null && !attr.getValueString().isEmpty()) {
this.headersTextArea.setVisible(true);
this.headersTextArea.setText(attr.getValueString());
if (selectedTabIndex < 0) {
selectedTabIndex = HDR_TAB_INDEX;
selectedTabIndex = HDR_TAB_INDEX;
}
}
else {
} else {
msgbodyTabbedPane.setEnabledAt(HDR_TAB_INDEX, false);
}
msgbodyTabbedPane.setSelectedIndex(selectedTabIndex);
}
catch (TskCoreException ex) {
} catch (TskCoreException ex) {
LOGGER.log(Level.WARNING, "Failed to get attributes for email message.", ex); //NON-NLS
}
}
private void displayMsg() {
this.ccText.setVisible(false);
this.showImagesToggleButton.setVisible(false);
msgbodyTabbedPane.setEnabledAt(HTML_TAB_INDEX, false);
msgbodyTabbedPane.setEnabledAt(RTF_TAB_INDEX, false);
msgbodyTabbedPane.setEnabledAt(HDR_TAB_INDEX, false);
try {
BlackboardAttribute attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_PHONE_NUMBER_FROM));
if (attr != null) {
this.fromText.setText(attr.getValueString());
}else {
this.fromText.setVisible(false);
} else {
this.fromText.setVisible(false);
}
attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_PHONE_NUMBER_TO));
if (attr != null) {
this.toText.setText(attr.getValueString());
}else {
this.toText.setVisible(false);
this.toText.setText(attr.getValueString());
} else {
this.toText.setVisible(false);
}
attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_DIRECTION));
if (attr != null) {
this.directionText.setText(attr.getValueString());
}else {
this.directionText.setVisible(false);
this.directionText.setText(attr.getValueString());
} else {
this.directionText.setVisible(false);
}
attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_SUBJECT));
if (attr != null && !attr.getValueString().isEmpty()) {
this.subjectText.setVisible(true);
this.subjectText.setText(attr.getValueString());
}
else {
} else {
this.subjectText.setVisible(false);
}
attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_DATETIME));
if (attr != null && !attr.getDisplayString().isEmpty()) {
this.datetimeText.setVisible(true);
this.datetimeText.setText(attr.getDisplayString());
}
else {
} else {
this.datetimeText.setVisible(false);
}
attr = artifact.getAttribute(new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_TEXT));
if (attr != null && !attr.getValueString().isEmpty()) {
this.textbodyTextArea.setVisible(true);
this.textbodyTextArea.setText(attr.getValueString());
msgbodyTabbedPane.setEnabledAt(TEXT_TAB_INDEX, true);
}
else {
} else {
msgbodyTabbedPane.setEnabledAt(TEXT_TAB_INDEX, false);
}
msgbodyTabbedPane.setSelectedIndex(TEXT_TAB_INDEX);
}
catch (TskCoreException ex) {
} catch (TskCoreException ex) {
LOGGER.log(Level.WARNING, "Failed to get attributes for message.", ex); //NON-NLS
}
}
/**
* Cleans out input HTML string
*
* @param htmlInString The HTML string to cleanse
*
* @return The cleansed HTML String
*/
private String cleanseHTML(String htmlInString) {
private String cleanseHTML(String htmlInString) {
Document doc = Jsoup.parse(htmlInString);
// fix all img tags
doc.select("img[src]").forEach((img) -> {
img.attr("src", "");
});
return doc.html();
}
}

View File

@ -20,12 +20,10 @@ package org.sleuthkit.autopsy.corecomponentinterfaces;
import java.beans.PropertyChangeListener;
import org.openide.nodes.Node;
import org.openide.windows.TopComponent;
/**
* The interface for the "bottom right component" window.
*
* @author jantonius
*/
public interface DataContent extends PropertyChangeListener {

View File

@ -22,6 +22,7 @@ import java.awt.Cursor;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import javax.swing.JTabbedPane;
import javax.swing.SwingUtilities;
@ -260,11 +261,7 @@ public class DataResultPanel extends javax.swing.JPanel implements DataResult, C
*/
@Override
public List<DataResultViewer> getViewers() {
List<DataResultViewer> viewers = new ArrayList<>();
resultViewers.forEach((viewer) -> {
viewers.add(viewer);
});
return viewers;
return Collections.unmodifiableList(resultViewers);
}
/**
@ -397,9 +394,7 @@ public class DataResultPanel extends javax.swing.JPanel implements DataResult, C
* @param selectedNodes The nodes to be selected.
*/
public void setSelectedNodes(Node[] selectedNodes) {
this.resultViewers.forEach((viewer) -> {
viewer.setSelectedNodes(selectedNodes);
});
this.resultViewers.forEach((viewer) -> viewer.setSelectedNodes(selectedNodes));
}
/**
@ -517,14 +512,10 @@ public class DataResultPanel extends javax.swing.JPanel implements DataResult, C
explorerManager = null;
}
this.resultViewers.forEach((viewer) -> {
viewer.setNode(null);
});
this.resultViewers.forEach((viewer) -> viewer.setNode(null));
if (!this.isMain) {
this.resultViewers.forEach((viewer) -> {
viewer.clearComponent();
});
this.resultViewers.forEach(DataResultViewer::clearComponent);
this.directoryTablePath.removeAll();
this.directoryTablePath = null;
this.numberMatchLabel.removeAll();
@ -563,9 +554,7 @@ public class DataResultPanel extends javax.swing.JPanel implements DataResult, C
* Pass the selected nodes to all of the result viewers
* sharing this explorer manager.
*/
resultViewers.forEach((viewer) -> {
viewer.setSelectedNodes(selectedNodes);
});
resultViewers.forEach((viewer) -> viewer.setSelectedNodes(selectedNodes));
/*
* Passing null signals that either multiple nodes are

View File

@ -764,7 +764,7 @@ public class DataResultViewerTable extends AbstractDataResultViewer {
Component component = super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, col);
// only override the color if a node is not selected
if (!isSelected) {
if (currentRoot != null && !isSelected) {
Node node = currentRoot.getChildren().getNodeAt(table.convertRowIndexToModel(row));
boolean tagFound = false;
if (node != null) {