mirror of
https://github.com/overcuriousity/autopsy-flatpak.git
synced 2025-07-19 11:07:43 +00:00
Merge branch 'develop' of github.com:sleuthkit/autopsy into 6412-updatedDialogs
This commit is contained in:
commit
2b144413c6
@ -53,7 +53,7 @@ public interface CentralRepository {
|
|||||||
case SQLITE:
|
case SQLITE:
|
||||||
return SqliteCentralRepo.getInstance();
|
return SqliteCentralRepo.getInstance();
|
||||||
default:
|
default:
|
||||||
return null;
|
throw new CentralRepoException("Failed to get CentralRepository instance, Central Repositiory is not enabled.");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -329,7 +329,7 @@ public class Persona {
|
|||||||
String deleteSQL = "UPDATE personas SET status_id = " + PersonaStatus.DELETED.status_id + " WHERE id = " + this.id;
|
String deleteSQL = "UPDATE personas SET status_id = " + PersonaStatus.DELETED.status_id + " WHERE id = " + this.id;
|
||||||
CentralRepository cr = CentralRepository.getInstance();
|
CentralRepository cr = CentralRepository.getInstance();
|
||||||
if (cr != null) {
|
if (cr != null) {
|
||||||
cr.executeDeleteSQL(deleteSQL);
|
cr.executeUpdateSQL(deleteSQL);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -121,22 +121,18 @@ public class PersonaAccount {
|
|||||||
/**
|
/**
|
||||||
* Creates an account for the specified Persona.
|
* Creates an account for the specified Persona.
|
||||||
*
|
*
|
||||||
* @param persona Persona for which the account is being added.
|
* @param persona Persona for which the account is being added.
|
||||||
* @param account Account.
|
* @param account Account.
|
||||||
* @param justification Reason for assigning the alias, may be null.
|
* @param justification Reason for assigning the alias, may be null.
|
||||||
* @param confidence Confidence level.
|
* @param confidence Confidence level.
|
||||||
*
|
*
|
||||||
* @return PersonaAccount
|
* @return PersonaAccount
|
||||||
|
*
|
||||||
* @throws CentralRepoException If there is an error in creating the
|
* @throws CentralRepoException If there is an error in creating the
|
||||||
* account.
|
* account.
|
||||||
*/
|
*/
|
||||||
static PersonaAccount addPersonaAccount(Persona persona, CentralRepoAccount account, String justification, Persona.Confidence confidence) throws CentralRepoException {
|
static PersonaAccount addPersonaAccount(Persona persona, CentralRepoAccount account, String justification, Persona.Confidence confidence) throws CentralRepoException {
|
||||||
CentralRepository cr = CentralRepository.getInstance();
|
CentralRepository cr = CentralRepository.getInstance();
|
||||||
|
|
||||||
if(cr == null) {
|
|
||||||
throw new CentralRepoException("Failed to add Persona, Central Repository is not enable");
|
|
||||||
}
|
|
||||||
|
|
||||||
CentralRepoExaminer currentExaminer = cr.getOrInsertExaminer(System.getProperty("user.name"));
|
CentralRepoExaminer currentExaminer = cr.getOrInsertExaminer(System.getProperty("user.name"));
|
||||||
|
|
||||||
Instant instant = Instant.now();
|
Instant instant = Instant.now();
|
||||||
@ -151,7 +147,7 @@ public class PersonaAccount {
|
|||||||
+ currentExaminer.getId()
|
+ currentExaminer.getId()
|
||||||
+ ")";
|
+ ")";
|
||||||
|
|
||||||
CentralRepository.getInstance().executeInsertSQL(insertClause);
|
cr.executeInsertSQL(insertClause);
|
||||||
|
|
||||||
String queryClause = PERSONA_ACCOUNTS_QUERY_CLAUSE
|
String queryClause = PERSONA_ACCOUNTS_QUERY_CLAUSE
|
||||||
+ "WHERE persona_id = " + persona.getId()
|
+ "WHERE persona_id = " + persona.getId()
|
||||||
@ -249,19 +245,13 @@ public class PersonaAccount {
|
|||||||
* persona_account.
|
* persona_account.
|
||||||
*/
|
*/
|
||||||
static Collection<PersonaAccount> getPersonaAccountsForPersona(long personaId) throws CentralRepoException {
|
static Collection<PersonaAccount> getPersonaAccountsForPersona(long personaId) throws CentralRepoException {
|
||||||
CentralRepository cr = CentralRepository.getInstance();
|
String queryClause = PERSONA_ACCOUNTS_QUERY_CLAUSE
|
||||||
|
+ " WHERE persona_accounts.persona_id = " + personaId;
|
||||||
|
|
||||||
if (cr != null) {
|
PersonaAccountsQueryCallback queryCallback = new PersonaAccountsQueryCallback();
|
||||||
String queryClause = PERSONA_ACCOUNTS_QUERY_CLAUSE
|
CentralRepository.getInstance().executeSelectSQL(queryClause, queryCallback);
|
||||||
+ " WHERE persona_accounts.persona_id = " + personaId;
|
|
||||||
|
|
||||||
PersonaAccountsQueryCallback queryCallback = new PersonaAccountsQueryCallback();
|
return queryCallback.getPersonaAccountsList();
|
||||||
cr.executeSelectSQL(queryClause, queryCallback);
|
|
||||||
|
|
||||||
return queryCallback.getPersonaAccountsList();
|
|
||||||
}
|
|
||||||
|
|
||||||
return new ArrayList<>();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -279,16 +269,10 @@ public class PersonaAccount {
|
|||||||
+ " WHERE persona_accounts.account_id = " + accountId
|
+ " WHERE persona_accounts.account_id = " + accountId
|
||||||
+ " AND personas.status_id != " + Persona.PersonaStatus.DELETED.getStatusId();
|
+ " AND personas.status_id != " + Persona.PersonaStatus.DELETED.getStatusId();
|
||||||
|
|
||||||
CentralRepository cr = CentralRepository.getInstance();
|
PersonaAccountsQueryCallback queryCallback = new PersonaAccountsQueryCallback();
|
||||||
|
CentralRepository.getInstance().executeSelectSQL(queryClause, queryCallback);
|
||||||
|
|
||||||
if (cr != null) {
|
return queryCallback.getPersonaAccountsList();
|
||||||
PersonaAccountsQueryCallback queryCallback = new PersonaAccountsQueryCallback();
|
|
||||||
cr.executeSelectSQL(queryClause, queryCallback);
|
|
||||||
|
|
||||||
return queryCallback.getPersonaAccountsList();
|
|
||||||
}
|
|
||||||
|
|
||||||
return new ArrayList<>();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -308,15 +292,10 @@ public class PersonaAccount {
|
|||||||
+ " WHERE LOWER(accounts.account_unique_identifier) LIKE LOWER('%" + accountIdentifierSubstring + "%')"
|
+ " WHERE LOWER(accounts.account_unique_identifier) LIKE LOWER('%" + accountIdentifierSubstring + "%')"
|
||||||
+ " AND personas.status_id != " + Persona.PersonaStatus.DELETED.getStatusId();
|
+ " AND personas.status_id != " + Persona.PersonaStatus.DELETED.getStatusId();
|
||||||
|
|
||||||
CentralRepository cr = CentralRepository.getInstance();
|
PersonaAccountsQueryCallback queryCallback = new PersonaAccountsQueryCallback();
|
||||||
if (cr != null) {
|
CentralRepository.getInstance().executeSelectSQL(queryClause, queryCallback);
|
||||||
PersonaAccountsQueryCallback queryCallback = new PersonaAccountsQueryCallback();
|
|
||||||
cr.executeSelectSQL(queryClause, queryCallback);
|
|
||||||
|
|
||||||
return queryCallback.getPersonaAccountsList();
|
return queryCallback.getPersonaAccountsList();
|
||||||
}
|
|
||||||
|
|
||||||
return new ArrayList<>();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -335,14 +314,10 @@ public class PersonaAccount {
|
|||||||
+ " AND type_name = '" + account.getAccountType().getTypeName() + "' "
|
+ " AND type_name = '" + account.getAccountType().getTypeName() + "' "
|
||||||
+ " AND personas.status_id != " + Persona.PersonaStatus.DELETED.getStatusId();
|
+ " AND personas.status_id != " + Persona.PersonaStatus.DELETED.getStatusId();
|
||||||
|
|
||||||
CentralRepository cr = CentralRepository.getInstance();
|
PersonaAccountsQueryCallback queryCallback = new PersonaAccountsQueryCallback();
|
||||||
if (cr != null) {
|
CentralRepository.getInstance().executeSelectSQL(queryClause, queryCallback);
|
||||||
PersonaAccountsQueryCallback queryCallback = new PersonaAccountsQueryCallback();
|
return queryCallback.getPersonaAccountsList();
|
||||||
cr.executeSelectSQL(queryClause, queryCallback);
|
|
||||||
return queryCallback.getPersonaAccountsList();
|
|
||||||
}
|
|
||||||
|
|
||||||
return new ArrayList<>();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -351,36 +326,24 @@ public class PersonaAccount {
|
|||||||
* @param id row id for the account to be removed
|
* @param id row id for the account to be removed
|
||||||
*
|
*
|
||||||
* @throws CentralRepoException If there is an error in removing the
|
* @throws CentralRepoException If there is an error in removing the
|
||||||
* account.
|
* account.
|
||||||
*/
|
*/
|
||||||
static void removePersonaAccount(long id) throws CentralRepoException {
|
static void removePersonaAccount(long id) throws CentralRepoException {
|
||||||
CentralRepository cr = CentralRepository.getInstance();
|
|
||||||
|
|
||||||
if(cr == null) {
|
|
||||||
throw new CentralRepoException("Failed to remove persona account, Central Repo is not enabled");
|
|
||||||
}
|
|
||||||
|
|
||||||
String deleteClause = " DELETE FROM persona_accounts WHERE id = " + id;
|
String deleteClause = " DELETE FROM persona_accounts WHERE id = " + id;
|
||||||
cr.executeDeleteSQL(deleteClause);
|
CentralRepository.getInstance().executeDeleteSQL(deleteClause);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Modifies the PersonaAccount row by the given id
|
* Modifies the PersonaAccount row by the given id
|
||||||
*
|
*
|
||||||
* @param id row id for the account to be removed
|
* @param id row id for the account to be removed
|
||||||
*
|
*
|
||||||
* @throws CentralRepoException If there is an error in removing the
|
* @throws CentralRepoException If there is an error in removing the
|
||||||
* account.
|
* account.
|
||||||
*/
|
*/
|
||||||
static void modifyPersonaAccount(long id, Persona.Confidence confidence, String justification) throws CentralRepoException {
|
static void modifyPersonaAccount(long id, Persona.Confidence confidence, String justification) throws CentralRepoException {
|
||||||
CentralRepository cr = CentralRepository.getInstance();
|
|
||||||
|
|
||||||
if (cr == null) {
|
|
||||||
throw new CentralRepoException("Failed to modify persona account, Central Repo is not enabled");
|
|
||||||
}
|
|
||||||
|
|
||||||
String updateClause = "UPDATE persona_accounts SET confidence_id = " + confidence.getLevelId() + ", justification = \"" + justification + "\" WHERE id = " + id;
|
String updateClause = "UPDATE persona_accounts SET confidence_id = " + confidence.getLevelId() + ", justification = \"" + justification + "\" WHERE id = " + id;
|
||||||
cr.executeUpdateSQL(updateClause);
|
CentralRepository.getInstance().executeUpdateSQL(updateClause);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -418,28 +381,25 @@ public class PersonaAccount {
|
|||||||
* @param personaId Id of the persona to look for.
|
* @param personaId Id of the persona to look for.
|
||||||
*
|
*
|
||||||
* @return Collection of all accounts associated with the given persona, may
|
* @return Collection of all accounts associated with the given persona, may
|
||||||
* be empty.
|
* be empty.
|
||||||
|
*
|
||||||
* @throws CentralRepoException If there is an error in getting the
|
* @throws CentralRepoException If there is an error in getting the
|
||||||
* accounts.
|
* accounts.
|
||||||
*/
|
*/
|
||||||
static Collection<CentralRepoAccount> getAccountsForPersona(long personaId) throws CentralRepoException {
|
static Collection<CentralRepoAccount> getAccountsForPersona(long personaId) throws CentralRepoException {
|
||||||
CentralRepository cr = CentralRepository.getInstance();
|
|
||||||
|
|
||||||
if (cr != null) {
|
String queryClause = "SELECT account_id, "
|
||||||
String queryClause = "SELECT account_id, "
|
+ " accounts.account_type_id as account_type_id, accounts.account_unique_identifier as account_unique_identifier,"
|
||||||
+ " accounts.account_type_id as account_type_id, accounts.account_unique_identifier as account_unique_identifier,"
|
+ " account_types.type_name as type_name "
|
||||||
+ " account_types.type_name as type_name "
|
+ " FROM persona_accounts "
|
||||||
+ " FROM persona_accounts "
|
+ " JOIN accounts as accounts on persona_accounts.account_id = accounts.id "
|
||||||
+ " JOIN accounts as accounts on persona_accounts.account_id = accounts.id "
|
+ " JOIN account_types as account_types on accounts.account_type_id = account_types.id "
|
||||||
+ " JOIN account_types as account_types on accounts.account_type_id = account_types.id "
|
+ " WHERE persona_accounts.persona_id = " + personaId;
|
||||||
+ " WHERE persona_accounts.persona_id = " + personaId;
|
|
||||||
|
|
||||||
AccountsForPersonaQueryCallback queryCallback = new AccountsForPersonaQueryCallback();
|
AccountsForPersonaQueryCallback queryCallback = new AccountsForPersonaQueryCallback();
|
||||||
cr.executeSelectSQL(queryClause, queryCallback);
|
CentralRepository.getInstance().executeSelectSQL(queryClause, queryCallback);
|
||||||
|
|
||||||
return queryCallback.getAccountsList();
|
return queryCallback.getAccountsList();
|
||||||
}
|
|
||||||
|
|
||||||
return new ArrayList<>();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,15 +1,6 @@
|
|||||||
CTL_OpenPersonaManager=Persona Manager
|
CTL_OpenPersonas=Personas
|
||||||
CTL_PersonaManagerTopComponentAction=Persona Manager
|
CTL_PersonasTopComponentAction=Personas
|
||||||
CTL_PersonaDetailsTopComponent=Persona Details
|
CTL_PersonaDetailsTopComponent=Persona Details
|
||||||
PersonaManagerTopComponent.createBtn.text=New Persona
|
|
||||||
PersonaManagerTopComponent.searchBtn.text=Search
|
|
||||||
PersonaManagerTopComponent.resultsTable.columnModel.title1=Name
|
|
||||||
PersonaManagerTopComponent.resultsTable.columnModel.title0=ID
|
|
||||||
PersonaManagerTopComponent.resultsTable.toolTipText=
|
|
||||||
PersonaManagerTopComponent.searchAccountRadio.text=Account
|
|
||||||
PersonaManagerTopComponent.searchNameRadio.text=Name
|
|
||||||
PersonaManagerTopComponent.searchField.text=
|
|
||||||
PersonaManagerTopComponent.editBtn.text=Edit Persona
|
|
||||||
PersonaDetailsDialog.cancelBtn.text=Cancel
|
PersonaDetailsDialog.cancelBtn.text=Cancel
|
||||||
PersonaDetailsDialog.okBtn.text=OK
|
PersonaDetailsDialog.okBtn.text=OK
|
||||||
PersonaDetailsPanel.casesLbl.text=Cases found in:
|
PersonaDetailsPanel.casesLbl.text=Cases found in:
|
||||||
@ -27,7 +18,6 @@ PersonaDetailsPanel.nameLbl.text=Name:
|
|||||||
AddAliasDialog.accountsLbl.text=Account:
|
AddAliasDialog.accountsLbl.text=Account:
|
||||||
AddAliasDialog.okBtn.text=OK
|
AddAliasDialog.okBtn.text=OK
|
||||||
AddAliasDialog.cancelBtn.text=Cancel
|
AddAliasDialog.cancelBtn.text=Cancel
|
||||||
PersonaManagerTopComponent.deleteBtn.text=Delete Persona
|
|
||||||
PersonaDetailsPanel.casesLbl.text=Cases found in:
|
PersonaDetailsPanel.casesLbl.text=Cases found in:
|
||||||
PersonaDetailsPanel.deleteAliasBtn.text=Delete
|
PersonaDetailsPanel.deleteAliasBtn.text=Delete
|
||||||
PersonaDetailsPanel.addAliasBtn.text=Add
|
PersonaDetailsPanel.addAliasBtn.text=Add
|
||||||
@ -73,3 +63,19 @@ PersonaMetadataDialog.cancelBtn.text=Cancel
|
|||||||
PersonaDetailsPanel.editAccountBtn.text=Edit
|
PersonaDetailsPanel.editAccountBtn.text=Edit
|
||||||
PersonaDetailsPanel.editMetadataBtn.text=Edit
|
PersonaDetailsPanel.editMetadataBtn.text=Edit
|
||||||
PersonaDetailsPanel.editAliasBtn.text=Edit
|
PersonaDetailsPanel.editAliasBtn.text=Edit
|
||||||
|
PersonasTopComponent.searchAccountRadio.text=Account
|
||||||
|
PersonasTopComponent.searchNameRadio.text=Name
|
||||||
|
PersonasTopComponent.searchField.text=
|
||||||
|
PersonasTopComponent.deleteBtn.text=Delete Persona
|
||||||
|
PersonasTopComponent.editBtn.text=Edit Persona
|
||||||
|
PersonasTopComponent.createBtn.text=New Persona
|
||||||
|
PersonasTopComponent.createAccountBtn.text=Create Account
|
||||||
|
PersonasTopComponent.searchBtn.text=Search
|
||||||
|
PersonasTopComponent.resultsTable.columnModel.title1=Name
|
||||||
|
PersonasTopComponent.resultsTable.columnModel.title0=ID
|
||||||
|
PersonasTopComponent.resultsTable.toolTipText=
|
||||||
|
CreatePersonaAccountDialog.cancelBtn.text=Cancel
|
||||||
|
CreatePersonaAccountDialog.typeLbl.text=Type:
|
||||||
|
CreatePersonaAccountDialog.identifierTextField.text=
|
||||||
|
CreatePersonaAccountDialog.identiferLbl.text=Identifier:
|
||||||
|
CreatePersonaAccountDialog.okBtn.text=OK
|
||||||
|
@ -3,10 +3,13 @@ AddMetadataDialog_dup_msg=A metadata entry with this name has already been added
|
|||||||
AddMetadataDialog_dup_Title=Metadata add failure
|
AddMetadataDialog_dup_Title=Metadata add failure
|
||||||
AddMetadataDialog_empty_name_msg=A metadata entry cannot have an empty name or value.
|
AddMetadataDialog_empty_name_msg=A metadata entry cannot have an empty name or value.
|
||||||
AddMetadataDialog_empty_name_Title=Missing field(s)
|
AddMetadataDialog_empty_name_Title=Missing field(s)
|
||||||
CTL_OpenPersonaManager=Persona Manager
|
CreatePersonaAccountDialog.title.text=Create Account
|
||||||
CTL_PersonaManagerTopComponentAction=Persona Manager
|
CreatePersonaAccountDialog_dup_msg=An account with this identifier and type already exists.
|
||||||
|
CreatePersonaAccountDialog_dup_Title=Account creation failure
|
||||||
|
CTL_OpenPersonas=Personas
|
||||||
|
CTL_PersonasTopComponentAction=Personas
|
||||||
CTL_PersonaDetailsTopComponent=Persona Details
|
CTL_PersonaDetailsTopComponent=Persona Details
|
||||||
OpenPersonasAction.displayName=Persona Manager
|
OpenPersonasAction.displayName=Personas
|
||||||
PersonaAccountDialog.title.text=Add Account
|
PersonaAccountDialog.title.text=Add Account
|
||||||
PersonaAccountDialog_dup_msg=This account is already added to the persona.
|
PersonaAccountDialog_dup_msg=This account is already added to the persona.
|
||||||
PersonaAccountDialog_dup_Title=Account add failure
|
PersonaAccountDialog_dup_Title=Account add failure
|
||||||
@ -23,32 +26,11 @@ PersonaAliasDialog_dup_msg=This alias has already been added to this persona.
|
|||||||
PersonaAliasDialog_dup_Title=Alias add failure
|
PersonaAliasDialog_dup_Title=Alias add failure
|
||||||
PersonaAliasDialog_empty_msg=An alias cannot be empty.
|
PersonaAliasDialog_empty_msg=An alias cannot be empty.
|
||||||
PersonaAliasDialog_empty_Title=Empty alias
|
PersonaAliasDialog_empty_Title=Empty alias
|
||||||
|
PersonaDetailsDialog.cancelBtn.text=Cancel
|
||||||
|
PersonaDetailsDialog.okBtn.text=OK
|
||||||
PersonaDetailsDialogCreateTitle=Create Persona
|
PersonaDetailsDialogCreateTitle=Create Persona
|
||||||
PersonaDetailsDialogEditTitle=Edit Persona
|
PersonaDetailsDialogEditTitle=Edit Persona
|
||||||
PersonaDetailsDialogViewTitle=View Persona
|
PersonaDetailsDialogViewTitle=View Persona
|
||||||
PersonaDetailsPanel_CentralRepoErr_msg=Failure to write to Central Repository.
|
|
||||||
PersonaDetailsPanel_CentralRepoErr_Title=Central Repository failure
|
|
||||||
PersonaDetailsPanel_empty_justification_msg=The justification field cannot be empty
|
|
||||||
PersonaDetailsPanel_empty_justification_Title=Empty justification
|
|
||||||
PersonaDetailsPanel_EmptyComment_msg=Persona comment cannot be empty.
|
|
||||||
PersonaDetailsPanel_EmptyComment_Title=Empty persona comment
|
|
||||||
PersonaDetailsPanel_EmptyName_msg=Persona name cannot be empty.
|
|
||||||
PersonaDetailsPanel_EmptyName_Title=Empty persona name
|
|
||||||
PersonaDetailsPanel_load_exception_msg=Failed to load persona.
|
|
||||||
PersonaDetailsPanel_load_exception_Title=Initialization failure
|
|
||||||
PersonaDetailsPanel_NotEnoughAccounts_msg=A persona needs at least one account.
|
|
||||||
PersonaDetailsPanel_NotEnoughAccounts_Title=Missing account
|
|
||||||
PersonaManagerTopComponent.createBtn.text=New Persona
|
|
||||||
PersonaManagerTopComponent.searchBtn.text=Search
|
|
||||||
PersonaManagerTopComponent.resultsTable.columnModel.title1=Name
|
|
||||||
PersonaManagerTopComponent.resultsTable.columnModel.title0=ID
|
|
||||||
PersonaManagerTopComponent.resultsTable.toolTipText=
|
|
||||||
PersonaManagerTopComponent.searchAccountRadio.text=Account
|
|
||||||
PersonaManagerTopComponent.searchNameRadio.text=Name
|
|
||||||
PersonaManagerTopComponent.searchField.text=
|
|
||||||
PersonaManagerTopComponent.editBtn.text=Edit Persona
|
|
||||||
PersonaDetailsDialog.cancelBtn.text=Cancel
|
|
||||||
PersonaDetailsDialog.okBtn.text=OK
|
|
||||||
PersonaDetailsPanel.casesLbl.text=Cases found in:
|
PersonaDetailsPanel.casesLbl.text=Cases found in:
|
||||||
PersonaDetailsPanel.deleteAliasBtn.text=Delete
|
PersonaDetailsPanel.deleteAliasBtn.text=Delete
|
||||||
PersonaDetailsPanel.addAliasBtn.text=Add
|
PersonaDetailsPanel.addAliasBtn.text=Add
|
||||||
@ -64,7 +46,6 @@ PersonaDetailsPanel.nameLbl.text=Name:
|
|||||||
AddAliasDialog.accountsLbl.text=Account:
|
AddAliasDialog.accountsLbl.text=Account:
|
||||||
AddAliasDialog.okBtn.text=OK
|
AddAliasDialog.okBtn.text=OK
|
||||||
AddAliasDialog.cancelBtn.text=Cancel
|
AddAliasDialog.cancelBtn.text=Cancel
|
||||||
PersonaManagerTopComponent.deleteBtn.text=Delete Persona
|
|
||||||
PersonaDetailsPanel.casesLbl.text=Cases found in:
|
PersonaDetailsPanel.casesLbl.text=Cases found in:
|
||||||
PersonaDetailsPanel.deleteAliasBtn.text=Delete
|
PersonaDetailsPanel.deleteAliasBtn.text=Delete
|
||||||
PersonaDetailsPanel.addAliasBtn.text=Add
|
PersonaDetailsPanel.addAliasBtn.text=Add
|
||||||
@ -98,6 +79,18 @@ PersonaAliasDialog.justificationLbl.text=Justification:
|
|||||||
PersonaAliasDialog.aliasTextField.text=
|
PersonaAliasDialog.aliasTextField.text=
|
||||||
PersonaAliasDialog.aliasLbl.text=Alias:
|
PersonaAliasDialog.aliasLbl.text=Alias:
|
||||||
PersonaAliasDialog.okBtn.text_1=OK
|
PersonaAliasDialog.okBtn.text_1=OK
|
||||||
|
PersonaDetailsPanel_CentralRepoErr_msg=Failure to write to Central Repository.
|
||||||
|
PersonaDetailsPanel_CentralRepoErr_Title=Central Repository failure
|
||||||
|
PersonaDetailsPanel_empty_justification_msg=The justification field cannot be empty
|
||||||
|
PersonaDetailsPanel_empty_justification_Title=Empty justification
|
||||||
|
PersonaDetailsPanel_EmptyComment_msg=Persona comment cannot be empty.
|
||||||
|
PersonaDetailsPanel_EmptyComment_Title=Empty persona comment
|
||||||
|
PersonaDetailsPanel_EmptyName_msg=Persona name cannot be empty.
|
||||||
|
PersonaDetailsPanel_EmptyName_Title=Empty persona name
|
||||||
|
PersonaDetailsPanel_load_exception_msg=Failed to load persona.
|
||||||
|
PersonaDetailsPanel_load_exception_Title=Initialization failure
|
||||||
|
PersonaDetailsPanel_NotEnoughAccounts_msg=A persona needs at least one account.
|
||||||
|
PersonaDetailsPanel_NotEnoughAccounts_Title=Missing account
|
||||||
PersonaMetadataDialog.confidenceLbl.text=Confidence:
|
PersonaMetadataDialog.confidenceLbl.text=Confidence:
|
||||||
PersonaMetadataDialog.justificationTextField.text=
|
PersonaMetadataDialog.justificationTextField.text=
|
||||||
PersonaMetadataDialog.justificationLbl.text=Justification:
|
PersonaMetadataDialog.justificationLbl.text=Justification:
|
||||||
@ -110,10 +103,26 @@ PersonaMetadataDialog.cancelBtn.text=Cancel
|
|||||||
PersonaDetailsPanel.editAccountBtn.text=Edit
|
PersonaDetailsPanel.editAccountBtn.text=Edit
|
||||||
PersonaDetailsPanel.editMetadataBtn.text=Edit
|
PersonaDetailsPanel.editMetadataBtn.text=Edit
|
||||||
PersonaDetailsPanel.editAliasBtn.text=Edit
|
PersonaDetailsPanel.editAliasBtn.text=Edit
|
||||||
PMTopComponent_delete_confirmation_msg=Are you sure you want to delete this persona?
|
PersonasTopComponent.searchAccountRadio.text=Account
|
||||||
PMTopComponent_delete_confirmation_Title=Are you sure?
|
PersonasTopComponent.searchNameRadio.text=Name
|
||||||
PMTopComponent_delete_exception_msg=Failed to delete persona.
|
PersonasTopComponent.searchField.text=
|
||||||
PMTopComponent_delete_exception_Title=Delete failure
|
PersonasTopComponent.deleteBtn.text=Delete Persona
|
||||||
PMTopComponent_Name=Persona Manager
|
PersonasTopComponent.editBtn.text=Edit Persona
|
||||||
PMTopComponent_search_exception_msg=Failed to search personas.
|
PersonasTopComponent.createBtn.text=New Persona
|
||||||
PMTopComponent_search_exception_Title=Search failure
|
PersonasTopComponent.createAccountBtn.text=Create Account
|
||||||
|
PersonasTopComponent.searchBtn.text=Search
|
||||||
|
PersonasTopComponent.resultsTable.columnModel.title1=Name
|
||||||
|
PersonasTopComponent.resultsTable.columnModel.title0=ID
|
||||||
|
PersonasTopComponent.resultsTable.toolTipText=
|
||||||
|
CreatePersonaAccountDialog.cancelBtn.text=Cancel
|
||||||
|
CreatePersonaAccountDialog.typeLbl.text=Type:
|
||||||
|
CreatePersonaAccountDialog.identifierTextField.text=
|
||||||
|
CreatePersonaAccountDialog.identiferLbl.text=Identifier:
|
||||||
|
CreatePersonaAccountDialog.okBtn.text=OK
|
||||||
|
PersonasTopComponent_delete_confirmation_msg=Are you sure you want to delete this persona?
|
||||||
|
PersonasTopComponent_delete_confirmation_Title=Are you sure?
|
||||||
|
PersonasTopComponent_delete_exception_msg=Failed to delete persona.
|
||||||
|
PersonasTopComponent_delete_exception_Title=Delete failure
|
||||||
|
PersonasTopComponent_Name=Personas
|
||||||
|
PersonasTopComponent_search_exception_msg=Failed to search personas.
|
||||||
|
PersonasTopComponent_search_exception_Title=Search failure
|
||||||
|
@ -8,3 +8,5 @@ PersonaAliasDialog.cancelBtn.text_1=\u53d6\u308a\u6d88\u3057
|
|||||||
PersonaAliasDialog.okBtn.text_1=OK
|
PersonaAliasDialog.okBtn.text_1=OK
|
||||||
PersonaMetadataDialog.okBtn.text=OK
|
PersonaMetadataDialog.okBtn.text=OK
|
||||||
PersonaMetadataDialog.cancelBtn.text=\u53d6\u308a\u6d88\u3057
|
PersonaMetadataDialog.cancelBtn.text=\u53d6\u308a\u6d88\u3057
|
||||||
|
CreatePersonaAccountDialog.okBtn.text=OK
|
||||||
|
CreatePersonaAccountDialog.cancelBtn.text=\u53d6\u308a\u6d88\u3057
|
||||||
|
@ -0,0 +1,168 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8" ?>
|
||||||
|
|
||||||
|
<Form version="1.5" maxVersion="1.9" type="org.netbeans.modules.form.forminfo.JDialogFormInfo">
|
||||||
|
<Properties>
|
||||||
|
<Property name="defaultCloseOperation" type="int" value="2"/>
|
||||||
|
<Property name="resizable" type="boolean" value="false"/>
|
||||||
|
</Properties>
|
||||||
|
<SyntheticProperties>
|
||||||
|
<SyntheticProperty name="formSizePolicy" type="int" value="1"/>
|
||||||
|
<SyntheticProperty name="generateCenter" type="boolean" value="false"/>
|
||||||
|
</SyntheticProperties>
|
||||||
|
<AuxValues>
|
||||||
|
<AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="1"/>
|
||||||
|
<AuxValue name="FormSettings_autoSetComponentName" type="java.lang.Boolean" value="false"/>
|
||||||
|
<AuxValue name="FormSettings_generateFQN" type="java.lang.Boolean" value="true"/>
|
||||||
|
<AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="true"/>
|
||||||
|
<AuxValue name="FormSettings_i18nAutoMode" type="java.lang.Boolean" value="true"/>
|
||||||
|
<AuxValue name="FormSettings_layoutCodeTarget" type="java.lang.Integer" value="1"/>
|
||||||
|
<AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/>
|
||||||
|
<AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/>
|
||||||
|
<AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/>
|
||||||
|
</AuxValues>
|
||||||
|
|
||||||
|
<Layout>
|
||||||
|
<DimensionLayout dim="0">
|
||||||
|
<Group type="103" groupAlignment="0" attributes="0">
|
||||||
|
<Group type="102" attributes="0">
|
||||||
|
<EmptySpace pref="194" max="32767" attributes="0"/>
|
||||||
|
<Component id="okBtn" linkSize="2" min="-2" max="-2" attributes="0"/>
|
||||||
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
|
<Component id="cancelBtn" linkSize="2" min="-2" max="-2" attributes="0"/>
|
||||||
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
|
</Group>
|
||||||
|
<Component id="settingsPanel" 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 max="-2" attributes="0"/>
|
||||||
|
<Component id="settingsPanel" min="-2" max="-2" attributes="0"/>
|
||||||
|
<EmptySpace min="-2" max="-2" attributes="0"/>
|
||||||
|
<Group type="103" groupAlignment="3" attributes="0">
|
||||||
|
<Component id="okBtn" alignment="3" min="-2" max="-2" attributes="0"/>
|
||||||
|
<Component id="cancelBtn" alignment="3" min="-2" max="-2" attributes="0"/>
|
||||||
|
</Group>
|
||||||
|
<EmptySpace max="32767" attributes="0"/>
|
||||||
|
</Group>
|
||||||
|
</Group>
|
||||||
|
</DimensionLayout>
|
||||||
|
</Layout>
|
||||||
|
<SubComponents>
|
||||||
|
<Container class="javax.swing.JPanel" name="settingsPanel">
|
||||||
|
<Properties>
|
||||||
|
<Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor">
|
||||||
|
<Border info="org.netbeans.modules.form.compat2.border.EtchedBorderInfo">
|
||||||
|
<EtchetBorder/>
|
||||||
|
</Border>
|
||||||
|
</Property>
|
||||||
|
</Properties>
|
||||||
|
|
||||||
|
<Layout>
|
||||||
|
<DimensionLayout dim="0">
|
||||||
|
<Group type="103" groupAlignment="0" attributes="0">
|
||||||
|
<Group type="102" attributes="0">
|
||||||
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
|
<Group type="103" groupAlignment="0" attributes="0">
|
||||||
|
<Group type="102" alignment="0" attributes="0">
|
||||||
|
<Component id="typeLbl" min="-2" max="-2" attributes="0"/>
|
||||||
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
|
<Component id="typeComboBox" max="32767" attributes="0"/>
|
||||||
|
</Group>
|
||||||
|
<Group type="102" alignment="0" attributes="0">
|
||||||
|
<Component id="identiferLbl" min="-2" max="-2" attributes="0"/>
|
||||||
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
|
<Component id="identifierTextField" pref="281" max="32767" attributes="0"/>
|
||||||
|
</Group>
|
||||||
|
</Group>
|
||||||
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
|
</Group>
|
||||||
|
</Group>
|
||||||
|
</DimensionLayout>
|
||||||
|
<DimensionLayout dim="1">
|
||||||
|
<Group type="103" groupAlignment="0" attributes="0">
|
||||||
|
<Group type="102" alignment="0" attributes="0">
|
||||||
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
|
<Group type="103" groupAlignment="3" attributes="0">
|
||||||
|
<Component id="identiferLbl" alignment="3" min="-2" max="-2" attributes="0"/>
|
||||||
|
<Component id="identifierTextField" alignment="3" min="-2" max="-2" attributes="0"/>
|
||||||
|
</Group>
|
||||||
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
|
<Group type="103" groupAlignment="3" attributes="0">
|
||||||
|
<Component id="typeComboBox" alignment="3" min="-2" max="-2" attributes="0"/>
|
||||||
|
<Component id="typeLbl" alignment="3" min="-2" pref="9" max="-2" attributes="0"/>
|
||||||
|
</Group>
|
||||||
|
<EmptySpace max="32767" attributes="0"/>
|
||||||
|
</Group>
|
||||||
|
</Group>
|
||||||
|
</DimensionLayout>
|
||||||
|
</Layout>
|
||||||
|
<SubComponents>
|
||||||
|
<Component class="javax.swing.JLabel" name="identiferLbl">
|
||||||
|
<Properties>
|
||||||
|
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="CreatePersonaAccountDialog.identiferLbl.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
|
</Property>
|
||||||
|
</Properties>
|
||||||
|
</Component>
|
||||||
|
<Component class="javax.swing.JTextField" name="identifierTextField">
|
||||||
|
<Properties>
|
||||||
|
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="CreatePersonaAccountDialog.identifierTextField.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
|
</Property>
|
||||||
|
</Properties>
|
||||||
|
<Events>
|
||||||
|
<EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="identifierTextFieldActionPerformed"/>
|
||||||
|
</Events>
|
||||||
|
</Component>
|
||||||
|
<Component class="javax.swing.JLabel" name="typeLbl">
|
||||||
|
<Properties>
|
||||||
|
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="CreatePersonaAccountDialog.typeLbl.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
|
</Property>
|
||||||
|
</Properties>
|
||||||
|
</Component>
|
||||||
|
<Component class="javax.swing.JComboBox" name="typeComboBox">
|
||||||
|
<Properties>
|
||||||
|
<Property name="model" type="javax.swing.ComboBoxModel" editor="org.netbeans.modules.form.RADConnectionPropertyEditor">
|
||||||
|
<Connection code="new javax.swing.DefaultComboBoxModel<>(getAllAccountTypes())" type="code"/>
|
||||||
|
</Property>
|
||||||
|
</Properties>
|
||||||
|
<AuxValues>
|
||||||
|
<AuxValue name="JavaCodeGenerator_TypeParameters" type="java.lang.String" value="<org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepoAccount.CentralRepoAccountType>"/>
|
||||||
|
</AuxValues>
|
||||||
|
</Component>
|
||||||
|
</SubComponents>
|
||||||
|
</Container>
|
||||||
|
<Component class="javax.swing.JButton" name="cancelBtn">
|
||||||
|
<Properties>
|
||||||
|
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="CreatePersonaAccountDialog.cancelBtn.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
|
</Property>
|
||||||
|
<Property name="maximumSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
|
||||||
|
<Dimension value="[79, 23]"/>
|
||||||
|
</Property>
|
||||||
|
<Property name="minimumSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
|
||||||
|
<Dimension value="[79, 23]"/>
|
||||||
|
</Property>
|
||||||
|
<Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
|
||||||
|
<Dimension value="[79, 23]"/>
|
||||||
|
</Property>
|
||||||
|
</Properties>
|
||||||
|
<Events>
|
||||||
|
<EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="cancelBtnActionPerformed"/>
|
||||||
|
</Events>
|
||||||
|
</Component>
|
||||||
|
<Component class="javax.swing.JButton" name="okBtn">
|
||||||
|
<Properties>
|
||||||
|
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="CreatePersonaAccountDialog.okBtn.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
|
</Property>
|
||||||
|
</Properties>
|
||||||
|
<Events>
|
||||||
|
<EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="okBtnActionPerformed"/>
|
||||||
|
</Events>
|
||||||
|
</Component>
|
||||||
|
</SubComponents>
|
||||||
|
</Form>
|
@ -0,0 +1,270 @@
|
|||||||
|
/*
|
||||||
|
* Central Repository
|
||||||
|
*
|
||||||
|
* Copyright 2020 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.centralrepository.persona;
|
||||||
|
|
||||||
|
import java.awt.Component;
|
||||||
|
import java.io.Serializable;
|
||||||
|
import java.util.Collection;
|
||||||
|
import java.util.logging.Level;
|
||||||
|
import javax.swing.JDialog;
|
||||||
|
import javax.swing.JLabel;
|
||||||
|
import javax.swing.JList;
|
||||||
|
import javax.swing.JOptionPane;
|
||||||
|
import javax.swing.ListCellRenderer;
|
||||||
|
import javax.swing.SwingUtilities;
|
||||||
|
import org.openide.util.NbBundle.Messages;
|
||||||
|
import org.openide.windows.WindowManager;
|
||||||
|
import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepoAccount;
|
||||||
|
import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepoAccount.CentralRepoAccountType;
|
||||||
|
import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepoException;
|
||||||
|
import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepository;
|
||||||
|
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Configuration dialog for creating an account.
|
||||||
|
*/
|
||||||
|
@SuppressWarnings("PMD.SingularField") // UI widgets cause lots of false positives
|
||||||
|
public class CreatePersonaAccountDialog extends JDialog {
|
||||||
|
|
||||||
|
private static final Logger logger = Logger.getLogger(CreatePersonaAccountDialog.class.getName());
|
||||||
|
|
||||||
|
private static final long serialVersionUID = 1L;
|
||||||
|
|
||||||
|
private final TypeChoiceRenderer TYPE_CHOICE_RENDERER = new TypeChoiceRenderer();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates new create account dialog.
|
||||||
|
*/
|
||||||
|
@Messages({"CreatePersonaAccountDialog.title.text=Create Account",})
|
||||||
|
public CreatePersonaAccountDialog(PersonaDetailsPanel pdp) {
|
||||||
|
super(SwingUtilities.windowForComponent(pdp),
|
||||||
|
Bundle.PersonaAccountDialog_title_text(),
|
||||||
|
ModalityType.APPLICATION_MODAL);
|
||||||
|
|
||||||
|
initComponents();
|
||||||
|
typeComboBox.setRenderer(TYPE_CHOICE_RENDERER);
|
||||||
|
display();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This class handles displaying and rendering drop down menu for account
|
||||||
|
* choices.
|
||||||
|
*/
|
||||||
|
private class TypeChoiceRenderer extends JLabel implements ListCellRenderer<CentralRepoAccountType>, Serializable {
|
||||||
|
|
||||||
|
private static final long serialVersionUID = 1L;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Component getListCellRendererComponent(
|
||||||
|
JList<? extends CentralRepoAccountType> list, CentralRepoAccountType value,
|
||||||
|
int index, boolean isSelected, boolean cellHasFocus) {
|
||||||
|
setText(value.getAcctType().getDisplayName());
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private CentralRepoAccountType[] getAllAccountTypes() {
|
||||||
|
Collection<CentralRepoAccountType> allAccountTypes;
|
||||||
|
try {
|
||||||
|
allAccountTypes = CentralRepository.getInstance().getAllAccountTypes();
|
||||||
|
} catch (CentralRepoException e) {
|
||||||
|
logger.log(Level.SEVERE, "Failed to access central repository", e);
|
||||||
|
JOptionPane.showMessageDialog(this,
|
||||||
|
Bundle.PersonaAccountDialog_get_types_exception_Title(),
|
||||||
|
Bundle.PersonaAccountDialog_get_types_exception_msg(),
|
||||||
|
JOptionPane.ERROR_MESSAGE);
|
||||||
|
return new CentralRepoAccountType[0];
|
||||||
|
}
|
||||||
|
return allAccountTypes.toArray(new CentralRepoAccountType[0]);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 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() {
|
||||||
|
|
||||||
|
settingsPanel = new javax.swing.JPanel();
|
||||||
|
identiferLbl = new javax.swing.JLabel();
|
||||||
|
identifierTextField = new javax.swing.JTextField();
|
||||||
|
typeLbl = new javax.swing.JLabel();
|
||||||
|
typeComboBox = new javax.swing.JComboBox<>();
|
||||||
|
cancelBtn = new javax.swing.JButton();
|
||||||
|
okBtn = new javax.swing.JButton();
|
||||||
|
|
||||||
|
setDefaultCloseOperation(javax.swing.WindowConstants.DISPOSE_ON_CLOSE);
|
||||||
|
setResizable(false);
|
||||||
|
|
||||||
|
settingsPanel.setBorder(javax.swing.BorderFactory.createEtchedBorder());
|
||||||
|
|
||||||
|
org.openide.awt.Mnemonics.setLocalizedText(identiferLbl, org.openide.util.NbBundle.getMessage(CreatePersonaAccountDialog.class, "CreatePersonaAccountDialog.identiferLbl.text")); // NOI18N
|
||||||
|
|
||||||
|
identifierTextField.setText(org.openide.util.NbBundle.getMessage(CreatePersonaAccountDialog.class, "CreatePersonaAccountDialog.identifierTextField.text")); // NOI18N
|
||||||
|
identifierTextField.addActionListener(new java.awt.event.ActionListener() {
|
||||||
|
public void actionPerformed(java.awt.event.ActionEvent evt) {
|
||||||
|
identifierTextFieldActionPerformed(evt);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
org.openide.awt.Mnemonics.setLocalizedText(typeLbl, org.openide.util.NbBundle.getMessage(CreatePersonaAccountDialog.class, "CreatePersonaAccountDialog.typeLbl.text")); // NOI18N
|
||||||
|
|
||||||
|
typeComboBox.setModel(new javax.swing.DefaultComboBoxModel<>(getAllAccountTypes()));
|
||||||
|
|
||||||
|
javax.swing.GroupLayout settingsPanelLayout = new javax.swing.GroupLayout(settingsPanel);
|
||||||
|
settingsPanel.setLayout(settingsPanelLayout);
|
||||||
|
settingsPanelLayout.setHorizontalGroup(
|
||||||
|
settingsPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||||
|
.addGroup(settingsPanelLayout.createSequentialGroup()
|
||||||
|
.addContainerGap()
|
||||||
|
.addGroup(settingsPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||||
|
.addGroup(settingsPanelLayout.createSequentialGroup()
|
||||||
|
.addComponent(typeLbl)
|
||||||
|
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||||
|
.addComponent(typeComboBox, 0, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
|
||||||
|
.addGroup(settingsPanelLayout.createSequentialGroup()
|
||||||
|
.addComponent(identiferLbl)
|
||||||
|
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||||
|
.addComponent(identifierTextField, javax.swing.GroupLayout.DEFAULT_SIZE, 281, Short.MAX_VALUE)))
|
||||||
|
.addContainerGap())
|
||||||
|
);
|
||||||
|
settingsPanelLayout.setVerticalGroup(
|
||||||
|
settingsPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||||
|
.addGroup(settingsPanelLayout.createSequentialGroup()
|
||||||
|
.addContainerGap()
|
||||||
|
.addGroup(settingsPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
|
||||||
|
.addComponent(identiferLbl)
|
||||||
|
.addComponent(identifierTextField, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
|
||||||
|
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||||
|
.addGroup(settingsPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
|
||||||
|
.addComponent(typeComboBox, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
|
||||||
|
.addComponent(typeLbl, javax.swing.GroupLayout.PREFERRED_SIZE, 9, javax.swing.GroupLayout.PREFERRED_SIZE))
|
||||||
|
.addContainerGap(javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
|
||||||
|
);
|
||||||
|
|
||||||
|
org.openide.awt.Mnemonics.setLocalizedText(cancelBtn, org.openide.util.NbBundle.getMessage(CreatePersonaAccountDialog.class, "CreatePersonaAccountDialog.cancelBtn.text")); // NOI18N
|
||||||
|
cancelBtn.setMaximumSize(new java.awt.Dimension(79, 23));
|
||||||
|
cancelBtn.setMinimumSize(new java.awt.Dimension(79, 23));
|
||||||
|
cancelBtn.setPreferredSize(new java.awt.Dimension(79, 23));
|
||||||
|
cancelBtn.addActionListener(new java.awt.event.ActionListener() {
|
||||||
|
public void actionPerformed(java.awt.event.ActionEvent evt) {
|
||||||
|
cancelBtnActionPerformed(evt);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
org.openide.awt.Mnemonics.setLocalizedText(okBtn, org.openide.util.NbBundle.getMessage(CreatePersonaAccountDialog.class, "CreatePersonaAccountDialog.okBtn.text")); // NOI18N
|
||||||
|
okBtn.addActionListener(new java.awt.event.ActionListener() {
|
||||||
|
public void actionPerformed(java.awt.event.ActionEvent evt) {
|
||||||
|
okBtnActionPerformed(evt);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
javax.swing.GroupLayout layout = new javax.swing.GroupLayout(getContentPane());
|
||||||
|
getContentPane().setLayout(layout);
|
||||||
|
layout.setHorizontalGroup(
|
||||||
|
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||||
|
.addGroup(layout.createSequentialGroup()
|
||||||
|
.addContainerGap(194, Short.MAX_VALUE)
|
||||||
|
.addComponent(okBtn)
|
||||||
|
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||||
|
.addComponent(cancelBtn, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
|
||||||
|
.addContainerGap())
|
||||||
|
.addComponent(settingsPanel, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
|
||||||
|
);
|
||||||
|
|
||||||
|
layout.linkSize(javax.swing.SwingConstants.HORIZONTAL, new java.awt.Component[] {cancelBtn, okBtn});
|
||||||
|
|
||||||
|
layout.setVerticalGroup(
|
||||||
|
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||||
|
.addGroup(layout.createSequentialGroup()
|
||||||
|
.addContainerGap()
|
||||||
|
.addComponent(settingsPanel, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
|
||||||
|
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||||
|
.addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
|
||||||
|
.addComponent(okBtn)
|
||||||
|
.addComponent(cancelBtn, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
|
||||||
|
.addContainerGap(javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
|
||||||
|
);
|
||||||
|
|
||||||
|
pack();
|
||||||
|
}// </editor-fold>//GEN-END:initComponents
|
||||||
|
|
||||||
|
private void display() {
|
||||||
|
this.setLocationRelativeTo(WindowManager.getDefault().getMainWindow());
|
||||||
|
setVisible(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
private CentralRepoAccount createAccount(CentralRepoAccount.CentralRepoAccountType type, String identifier) {
|
||||||
|
CentralRepoAccount ret = null;
|
||||||
|
try {
|
||||||
|
CentralRepository cr = CentralRepository.getInstance();
|
||||||
|
if (cr != null) {
|
||||||
|
ret = cr.getOrCreateAccount(type, identifier);
|
||||||
|
}
|
||||||
|
} catch (CentralRepoException e) {
|
||||||
|
logger.log(Level.SEVERE, "Failed to access central repository", e);
|
||||||
|
JOptionPane.showMessageDialog(this,
|
||||||
|
Bundle.PersonaAccountDialog_get_types_exception_Title(),
|
||||||
|
Bundle.PersonaAccountDialog_get_types_exception_msg(),
|
||||||
|
JOptionPane.ERROR_MESSAGE);
|
||||||
|
}
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Messages({
|
||||||
|
"CreatePersonaAccountDialog_dup_Title=Account creation failure",
|
||||||
|
"CreatePersonaAccountDialog_dup_msg=An account with this identifier and type already exists.",})
|
||||||
|
private void okBtnActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_okBtnActionPerformed
|
||||||
|
if (identifierTextField.getText().isEmpty()) {
|
||||||
|
JOptionPane.showMessageDialog(this,
|
||||||
|
Bundle.PersonaAccountDialog_identifier_empty_msg(),
|
||||||
|
Bundle.PersonaAccountDialog_identifier_empty_Title(),
|
||||||
|
JOptionPane.ERROR_MESSAGE);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
CentralRepoAccount.CentralRepoAccountType type =
|
||||||
|
(CentralRepoAccount.CentralRepoAccountType) typeComboBox.getSelectedItem();
|
||||||
|
String identifier = identifierTextField.getText();
|
||||||
|
|
||||||
|
if (createAccount(type, identifier) != null) {
|
||||||
|
dispose();
|
||||||
|
}
|
||||||
|
}//GEN-LAST:event_okBtnActionPerformed
|
||||||
|
|
||||||
|
private void cancelBtnActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_cancelBtnActionPerformed
|
||||||
|
dispose();
|
||||||
|
}//GEN-LAST:event_cancelBtnActionPerformed
|
||||||
|
|
||||||
|
private void identifierTextFieldActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_identifierTextFieldActionPerformed
|
||||||
|
// TODO add your handling code here:
|
||||||
|
}//GEN-LAST:event_identifierTextFieldActionPerformed
|
||||||
|
|
||||||
|
// Variables declaration - do not modify//GEN-BEGIN:variables
|
||||||
|
private javax.swing.JButton cancelBtn;
|
||||||
|
private javax.swing.JLabel identiferLbl;
|
||||||
|
private javax.swing.JTextField identifierTextField;
|
||||||
|
private javax.swing.JButton okBtn;
|
||||||
|
private javax.swing.JPanel settingsPanel;
|
||||||
|
private javax.swing.JComboBox<org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepoAccount.CentralRepoAccountType> typeComboBox;
|
||||||
|
private javax.swing.JLabel typeLbl;
|
||||||
|
// End of variables declaration//GEN-END:variables
|
||||||
|
}
|
@ -35,18 +35,18 @@ import org.sleuthkit.autopsy.coreutils.ThreadConfined;
|
|||||||
* An Action that opens the Persona Search window.
|
* An Action that opens the Persona Search window.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@ActionID(category = "Tools", id = "org.sleuthkit.autopsy.centralrepository.persona.OpenPersonaManagerAction")
|
@ActionID(category = "Tools", id = "org.sleuthkit.autopsy.centralrepository.persona.OpenPersonasAction")
|
||||||
@ActionRegistration(displayName = "#CTL_OpenPersonaManager", lazy = false)
|
@ActionRegistration(displayName = "#CTL_OpenPersonas", lazy = false)
|
||||||
@ActionReferences(value = {
|
@ActionReferences(value = {
|
||||||
@ActionReference(path = "Menu/Tools", position = 105)
|
@ActionReference(path = "Menu/Tools", position = 105)
|
||||||
})
|
})
|
||||||
public final class OpenPersonaManagerAction extends CallableSystemAction {
|
public final class OpenPersonasAction extends CallableSystemAction {
|
||||||
|
|
||||||
private static final long serialVersionUID = 1L;
|
private static final long serialVersionUID = 1L;
|
||||||
|
|
||||||
private final JMenuItem menuItem;
|
private final JMenuItem menuItem;
|
||||||
|
|
||||||
public OpenPersonaManagerAction() {
|
public OpenPersonasAction() {
|
||||||
menuItem = super.getMenuPresenter();
|
menuItem = super.getMenuPresenter();
|
||||||
this.setEnabled(CentralRepository.isEnabled());
|
this.setEnabled(CentralRepository.isEnabled());
|
||||||
}
|
}
|
||||||
@ -54,7 +54,7 @@ public final class OpenPersonaManagerAction extends CallableSystemAction {
|
|||||||
@Override
|
@Override
|
||||||
@ThreadConfined(type = ThreadConfined.ThreadType.AWT)
|
@ThreadConfined(type = ThreadConfined.ThreadType.AWT)
|
||||||
public void performAction() {
|
public void performAction() {
|
||||||
final TopComponent topComponent = WindowManager.getDefault().findTopComponent("PersonaManagerTopComponent");
|
final TopComponent topComponent = WindowManager.getDefault().findTopComponent("PersonasTopComponent");
|
||||||
if (topComponent != null) {
|
if (topComponent != null) {
|
||||||
if (topComponent.isOpened() == false) {
|
if (topComponent.isOpened() == false) {
|
||||||
topComponent.open();
|
topComponent.open();
|
||||||
@ -65,7 +65,7 @@ public final class OpenPersonaManagerAction extends CallableSystemAction {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@NbBundle.Messages("OpenPersonasAction.displayName=Persona Manager")
|
@NbBundle.Messages("OpenPersonasAction.displayName=Personas")
|
||||||
public String getName() {
|
public String getName() {
|
||||||
return Bundle.OpenPersonasAction_displayName();
|
return Bundle.OpenPersonasAction_displayName();
|
||||||
}
|
}
|
@ -27,9 +27,7 @@
|
|||||||
</Component>
|
</Component>
|
||||||
</NonVisualComponents>
|
</NonVisualComponents>
|
||||||
<Properties>
|
<Properties>
|
||||||
<Property name="minimumSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
|
<Property name="name" type="java.lang.String" value="" noResource="true"/>
|
||||||
<Dimension value="[400, 400]"/>
|
|
||||||
</Property>
|
|
||||||
</Properties>
|
</Properties>
|
||||||
<AuxValues>
|
<AuxValues>
|
||||||
<AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="1"/>
|
<AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="1"/>
|
||||||
@ -46,7 +44,7 @@
|
|||||||
<Layout>
|
<Layout>
|
||||||
<DimensionLayout dim="0">
|
<DimensionLayout dim="0">
|
||||||
<Group type="103" groupAlignment="0" attributes="0">
|
<Group type="103" groupAlignment="0" attributes="0">
|
||||||
<Component id="jSplitPane1" alignment="0" pref="692" max="32767" attributes="0"/>
|
<Component id="jSplitPane1" alignment="0" pref="794" max="32767" attributes="0"/>
|
||||||
</Group>
|
</Group>
|
||||||
</DimensionLayout>
|
</DimensionLayout>
|
||||||
<DimensionLayout dim="1">
|
<DimensionLayout dim="1">
|
||||||
@ -70,9 +68,10 @@
|
|||||||
<Layout>
|
<Layout>
|
||||||
<DimensionLayout dim="0">
|
<DimensionLayout dim="0">
|
||||||
<Group type="103" groupAlignment="0" attributes="0">
|
<Group type="103" groupAlignment="0" attributes="0">
|
||||||
<Group type="102" attributes="0">
|
<Group type="102" alignment="0" attributes="0">
|
||||||
<EmptySpace max="-2" attributes="0"/>
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
<Group type="103" groupAlignment="0" attributes="0">
|
<Group type="103" groupAlignment="0" attributes="0">
|
||||||
|
<Component id="jSeparator1" max="32767" attributes="0"/>
|
||||||
<Group type="102" alignment="0" attributes="0">
|
<Group type="102" alignment="0" attributes="0">
|
||||||
<Component id="createBtn" min="-2" max="-2" attributes="0"/>
|
<Component id="createBtn" min="-2" max="-2" attributes="0"/>
|
||||||
<EmptySpace max="-2" attributes="0"/>
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
@ -89,6 +88,10 @@
|
|||||||
<EmptySpace max="32767" attributes="0"/>
|
<EmptySpace max="32767" attributes="0"/>
|
||||||
<Component id="searchBtn" min="-2" max="-2" attributes="0"/>
|
<Component id="searchBtn" min="-2" max="-2" attributes="0"/>
|
||||||
</Group>
|
</Group>
|
||||||
|
<Group type="102" alignment="0" attributes="0">
|
||||||
|
<Component id="createAccountBtn" min="-2" max="-2" attributes="0"/>
|
||||||
|
<EmptySpace min="0" pref="0" max="32767" attributes="0"/>
|
||||||
|
</Group>
|
||||||
</Group>
|
</Group>
|
||||||
<EmptySpace max="-2" attributes="0"/>
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
</Group>
|
</Group>
|
||||||
@ -106,7 +109,7 @@
|
|||||||
<Component id="searchBtn" alignment="3" min="-2" max="-2" attributes="0"/>
|
<Component id="searchBtn" alignment="3" min="-2" max="-2" attributes="0"/>
|
||||||
</Group>
|
</Group>
|
||||||
<EmptySpace max="-2" attributes="0"/>
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
<Component id="resultsPane" pref="528" max="32767" attributes="0"/>
|
<Component id="resultsPane" pref="457" max="32767" attributes="0"/>
|
||||||
<EmptySpace max="-2" attributes="0"/>
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
<Group type="103" groupAlignment="3" attributes="0">
|
<Group type="103" groupAlignment="3" attributes="0">
|
||||||
<Component id="editBtn" alignment="3" min="-2" max="-2" attributes="0"/>
|
<Component id="editBtn" alignment="3" min="-2" max="-2" attributes="0"/>
|
||||||
@ -114,6 +117,10 @@
|
|||||||
<Component id="deleteBtn" alignment="3" min="-2" max="-2" attributes="0"/>
|
<Component id="deleteBtn" alignment="3" min="-2" max="-2" attributes="0"/>
|
||||||
</Group>
|
</Group>
|
||||||
<EmptySpace max="-2" attributes="0"/>
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
|
<Component id="jSeparator1" min="-2" pref="4" max="-2" attributes="0"/>
|
||||||
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
|
<Component id="createAccountBtn" min="-2" pref="32" max="-2" attributes="0"/>
|
||||||
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
</Group>
|
</Group>
|
||||||
</Group>
|
</Group>
|
||||||
</DimensionLayout>
|
</DimensionLayout>
|
||||||
@ -122,7 +129,7 @@
|
|||||||
<Component class="javax.swing.JTextField" name="searchField">
|
<Component class="javax.swing.JTextField" name="searchField">
|
||||||
<Properties>
|
<Properties>
|
||||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonaManagerTopComponent.searchField.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonasTopComponent.searchField.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
</Property>
|
</Property>
|
||||||
</Properties>
|
</Properties>
|
||||||
</Component>
|
</Component>
|
||||||
@ -133,7 +140,7 @@
|
|||||||
</Property>
|
</Property>
|
||||||
<Property name="selected" type="boolean" value="true"/>
|
<Property name="selected" type="boolean" value="true"/>
|
||||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonaManagerTopComponent.searchNameRadio.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonasTopComponent.searchNameRadio.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
</Property>
|
</Property>
|
||||||
</Properties>
|
</Properties>
|
||||||
</Component>
|
</Component>
|
||||||
@ -143,7 +150,7 @@
|
|||||||
<ComponentRef name="searchButtonGroup"/>
|
<ComponentRef name="searchButtonGroup"/>
|
||||||
</Property>
|
</Property>
|
||||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonaManagerTopComponent.searchAccountRadio.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonasTopComponent.searchAccountRadio.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
</Property>
|
</Property>
|
||||||
</Properties>
|
</Properties>
|
||||||
</Component>
|
</Component>
|
||||||
@ -157,20 +164,20 @@
|
|||||||
<Component class="javax.swing.JTable" name="resultsTable">
|
<Component class="javax.swing.JTable" name="resultsTable">
|
||||||
<Properties>
|
<Properties>
|
||||||
<Property name="toolTipText" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
<Property name="toolTipText" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonaManagerTopComponent.resultsTable.toolTipText" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonasTopComponent.resultsTable.toolTipText" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
</Property>
|
</Property>
|
||||||
<Property name="columnModel" type="javax.swing.table.TableColumnModel" editor="org.netbeans.modules.form.editors2.TableColumnModelEditor">
|
<Property name="columnModel" type="javax.swing.table.TableColumnModel" editor="org.netbeans.modules.form.editors2.TableColumnModelEditor">
|
||||||
<TableColumnModel selectionModel="0">
|
<TableColumnModel selectionModel="0">
|
||||||
<Column maxWidth="25" minWidth="-1" prefWidth="-1" resizable="true">
|
<Column maxWidth="25" minWidth="-1" prefWidth="-1" resizable="true">
|
||||||
<Title editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
<Title editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonaManagerTopComponent.resultsTable.columnModel.title0" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonasTopComponent.resultsTable.columnModel.title0" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
</Title>
|
</Title>
|
||||||
<Editor/>
|
<Editor/>
|
||||||
<Renderer/>
|
<Renderer/>
|
||||||
</Column>
|
</Column>
|
||||||
<Column maxWidth="-1" minWidth="-1" prefWidth="-1" resizable="true">
|
<Column maxWidth="-1" minWidth="-1" prefWidth="-1" resizable="true">
|
||||||
<Title editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
<Title editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonaManagerTopComponent.resultsTable.columnModel.title1" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonasTopComponent.resultsTable.columnModel.title1" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
</Title>
|
</Title>
|
||||||
<Editor/>
|
<Editor/>
|
||||||
<Renderer/>
|
<Renderer/>
|
||||||
@ -187,36 +194,48 @@
|
|||||||
<Component class="javax.swing.JButton" name="searchBtn">
|
<Component class="javax.swing.JButton" name="searchBtn">
|
||||||
<Properties>
|
<Properties>
|
||||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonaManagerTopComponent.searchBtn.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonasTopComponent.searchBtn.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
</Property>
|
</Property>
|
||||||
</Properties>
|
</Properties>
|
||||||
</Component>
|
</Component>
|
||||||
<Component class="javax.swing.JButton" name="editBtn">
|
<Component class="javax.swing.JButton" name="createAccountBtn">
|
||||||
<Properties>
|
<Properties>
|
||||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonaManagerTopComponent.editBtn.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonasTopComponent.createAccountBtn.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
</Property>
|
|
||||||
<Property name="enabled" type="boolean" value="false"/>
|
|
||||||
</Properties>
|
|
||||||
</Component>
|
|
||||||
<Component class="javax.swing.JButton" name="createBtn">
|
|
||||||
<Properties>
|
|
||||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonaManagerTopComponent.createBtn.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
|
||||||
</Property>
|
</Property>
|
||||||
</Properties>
|
</Properties>
|
||||||
<AuxValues>
|
<AuxValues>
|
||||||
<AuxValue name="generateMnemonicsCode" type="java.lang.Boolean" value="true"/>
|
<AuxValue name="generateMnemonicsCode" type="java.lang.Boolean" value="true"/>
|
||||||
</AuxValues>
|
</AuxValues>
|
||||||
</Component>
|
</Component>
|
||||||
<Component class="javax.swing.JButton" name="deleteBtn">
|
<Component class="javax.swing.JButton" name="createBtn">
|
||||||
<Properties>
|
<Properties>
|
||||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonaManagerTopComponent.deleteBtn.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonasTopComponent.createBtn.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
|
</Property>
|
||||||
|
</Properties>
|
||||||
|
<AuxValues>
|
||||||
|
<AuxValue name="generateMnemonicsCode" type="java.lang.Boolean" value="true"/>
|
||||||
|
</AuxValues>
|
||||||
|
</Component>
|
||||||
|
<Component class="javax.swing.JButton" name="editBtn">
|
||||||
|
<Properties>
|
||||||
|
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonasTopComponent.editBtn.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
</Property>
|
</Property>
|
||||||
<Property name="enabled" type="boolean" value="false"/>
|
<Property name="enabled" type="boolean" value="false"/>
|
||||||
</Properties>
|
</Properties>
|
||||||
</Component>
|
</Component>
|
||||||
|
<Component class="javax.swing.JButton" name="deleteBtn">
|
||||||
|
<Properties>
|
||||||
|
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
|
<ResourceString bundle="org/sleuthkit/autopsy/centralrepository/persona/Bundle.properties" key="PersonasTopComponent.deleteBtn.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
|
</Property>
|
||||||
|
<Property name="enabled" type="boolean" value="false"/>
|
||||||
|
</Properties>
|
||||||
|
</Component>
|
||||||
|
<Component class="javax.swing.JSeparator" name="jSeparator1">
|
||||||
|
</Component>
|
||||||
</SubComponents>
|
</SubComponents>
|
||||||
</Container>
|
</Container>
|
||||||
<Component class="org.sleuthkit.autopsy.centralrepository.persona.PersonaDetailsPanel" name="detailsPanel">
|
<Component class="org.sleuthkit.autopsy.centralrepository.persona.PersonaDetailsPanel" name="detailsPanel">
|
@ -44,27 +44,29 @@ import org.sleuthkit.autopsy.coreutils.Logger;
|
|||||||
* Top component for the Personas tool
|
* Top component for the Personas tool
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
@TopComponent.Description(preferredID = "PersonaManagerTopComponent", persistenceType = TopComponent.PERSISTENCE_NEVER)
|
@TopComponent.Description(preferredID = "PersonasTopComponent", persistenceType = TopComponent.PERSISTENCE_NEVER)
|
||||||
@TopComponent.Registration(mode = "personamanager", openAtStartup = false)
|
@TopComponent.Registration(mode = "personas", openAtStartup = false)
|
||||||
@RetainLocation("personamanager")
|
@RetainLocation("personas")
|
||||||
@SuppressWarnings("PMD.SingularField")
|
@SuppressWarnings("PMD.SingularField")
|
||||||
public final class PersonaManagerTopComponent extends TopComponent {
|
public final class PersonasTopComponent extends TopComponent {
|
||||||
|
|
||||||
|
private static final long serialVersionUID = 1L;
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(PersonaManagerTopComponent.class.getName());
|
private static final Logger logger = Logger.getLogger(PersonasTopComponent.class.getName());
|
||||||
|
|
||||||
private List<Persona> currentResults = null;
|
private List<Persona> currentResults = null;
|
||||||
private Persona selectedPersona = null;
|
private Persona selectedPersona = null;
|
||||||
|
|
||||||
@Messages({
|
@Messages({
|
||||||
"PMTopComponent_Name=Persona Manager",
|
"PersonasTopComponent_Name=Personas",
|
||||||
"PMTopComponent_delete_exception_Title=Delete failure",
|
"PersonasTopComponent_delete_exception_Title=Delete failure",
|
||||||
"PMTopComponent_delete_exception_msg=Failed to delete persona.",
|
"PersonasTopComponent_delete_exception_msg=Failed to delete persona.",
|
||||||
"PMTopComponent_delete_confirmation_Title=Are you sure?",
|
"PersonasTopComponent_delete_confirmation_Title=Are you sure?",
|
||||||
"PMTopComponent_delete_confirmation_msg=Are you sure you want to delete this persona?",
|
"PersonasTopComponent_delete_confirmation_msg=Are you sure you want to delete this persona?",
|
||||||
})
|
})
|
||||||
public PersonaManagerTopComponent() {
|
public PersonasTopComponent() {
|
||||||
initComponents();
|
initComponents();
|
||||||
setName(Bundle.PMTopComponent_Name());
|
setName(Bundle.PersonasTopComponent_Name());
|
||||||
executeSearch();
|
executeSearch();
|
||||||
|
|
||||||
searchBtn.addActionListener(new ActionListener() {
|
searchBtn.addActionListener(new ActionListener() {
|
||||||
@ -77,7 +79,7 @@ public final class PersonaManagerTopComponent extends TopComponent {
|
|||||||
editBtn.addActionListener(new ActionListener() {
|
editBtn.addActionListener(new ActionListener() {
|
||||||
@Override
|
@Override
|
||||||
public void actionPerformed(ActionEvent e) {
|
public void actionPerformed(ActionEvent e) {
|
||||||
new PersonaDetailsDialog(PersonaManagerTopComponent.this,
|
new PersonaDetailsDialog(PersonasTopComponent.this,
|
||||||
PersonaDetailsMode.EDIT, selectedPersona, new CreateEditCallbackImpl());
|
PersonaDetailsMode.EDIT, selectedPersona, new CreateEditCallbackImpl());
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@ -85,7 +87,7 @@ public final class PersonaManagerTopComponent extends TopComponent {
|
|||||||
createBtn.addActionListener(new ActionListener() {
|
createBtn.addActionListener(new ActionListener() {
|
||||||
@Override
|
@Override
|
||||||
public void actionPerformed(ActionEvent e) {
|
public void actionPerformed(ActionEvent e) {
|
||||||
new PersonaDetailsDialog(PersonaManagerTopComponent.this,
|
new PersonaDetailsDialog(PersonasTopComponent.this,
|
||||||
PersonaDetailsMode.CREATE, selectedPersona, new CreateEditCallbackImpl());
|
PersonaDetailsMode.CREATE, selectedPersona, new CreateEditCallbackImpl());
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@ -94,8 +96,8 @@ public final class PersonaManagerTopComponent extends TopComponent {
|
|||||||
@Override
|
@Override
|
||||||
public void actionPerformed(ActionEvent e) {
|
public void actionPerformed(ActionEvent e) {
|
||||||
NotifyDescriptor confirm = new NotifyDescriptor.Confirmation(
|
NotifyDescriptor confirm = new NotifyDescriptor.Confirmation(
|
||||||
Bundle.PMTopComponent_delete_confirmation_msg(),
|
Bundle.PersonasTopComponent_delete_confirmation_msg(),
|
||||||
Bundle.PMTopComponent_delete_confirmation_Title(),
|
Bundle.PersonasTopComponent_delete_confirmation_Title(),
|
||||||
NotifyDescriptor.YES_NO_OPTION);
|
NotifyDescriptor.YES_NO_OPTION);
|
||||||
DialogDisplayer.getDefault().notify(confirm);
|
DialogDisplayer.getDefault().notify(confirm);
|
||||||
if (confirm.getValue().equals(NotifyDescriptor.YES_OPTION)) {
|
if (confirm.getValue().equals(NotifyDescriptor.YES_OPTION)) {
|
||||||
@ -105,9 +107,9 @@ public final class PersonaManagerTopComponent extends TopComponent {
|
|||||||
}
|
}
|
||||||
} catch (CentralRepoException ex) {
|
} catch (CentralRepoException ex) {
|
||||||
logger.log(Level.SEVERE, "Failed to delete persona: " + selectedPersona.getName(), ex);
|
logger.log(Level.SEVERE, "Failed to delete persona: " + selectedPersona.getName(), ex);
|
||||||
JOptionPane.showMessageDialog(PersonaManagerTopComponent.this,
|
JOptionPane.showMessageDialog(PersonasTopComponent.this,
|
||||||
Bundle.PMTopComponent_delete_exception_msg(),
|
Bundle.PersonasTopComponent_delete_exception_msg(),
|
||||||
Bundle.PMTopComponent_delete_exception_Title(),
|
Bundle.PersonasTopComponent_delete_exception_Title(),
|
||||||
JOptionPane.ERROR_MESSAGE);
|
JOptionPane.ERROR_MESSAGE);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@ -132,6 +134,13 @@ public final class PersonaManagerTopComponent extends TopComponent {
|
|||||||
searchAccountRadio.addActionListener((ActionEvent e) -> {
|
searchAccountRadio.addActionListener((ActionEvent e) -> {
|
||||||
searchField.setText("");
|
searchField.setText("");
|
||||||
});
|
});
|
||||||
|
|
||||||
|
createAccountBtn.addActionListener(new ActionListener() {
|
||||||
|
@Override
|
||||||
|
public void actionPerformed(ActionEvent e) {
|
||||||
|
new CreatePersonaAccountDialog(detailsPanel);
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -214,8 +223,8 @@ public final class PersonaManagerTopComponent extends TopComponent {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Messages({
|
@Messages({
|
||||||
"PMTopComponent_search_exception_Title=Search failure",
|
"PersonasTopComponent_search_exception_Title=Search failure",
|
||||||
"PMTopComponent_search_exception_msg=Failed to search personas.",})
|
"PersonasTopComponent_search_exception_msg=Failed to search personas.",})
|
||||||
private void executeSearch() {
|
private void executeSearch() {
|
||||||
Collection<Persona> results;
|
Collection<Persona> results;
|
||||||
try {
|
try {
|
||||||
@ -227,8 +236,8 @@ public final class PersonaManagerTopComponent extends TopComponent {
|
|||||||
} catch (CentralRepoException ex) {
|
} catch (CentralRepoException ex) {
|
||||||
logger.log(Level.SEVERE, "Failed to search personas", ex);
|
logger.log(Level.SEVERE, "Failed to search personas", ex);
|
||||||
JOptionPane.showMessageDialog(this,
|
JOptionPane.showMessageDialog(this,
|
||||||
Bundle.PMTopComponent_search_exception_Title(),
|
Bundle.PersonasTopComponent_search_exception_Title(),
|
||||||
Bundle.PMTopComponent_search_exception_msg(),
|
Bundle.PersonasTopComponent_search_exception_msg(),
|
||||||
JOptionPane.ERROR_MESSAGE);
|
JOptionPane.ERROR_MESSAGE);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@ -262,39 +271,43 @@ public final class PersonaManagerTopComponent extends TopComponent {
|
|||||||
resultsPane = new javax.swing.JScrollPane();
|
resultsPane = new javax.swing.JScrollPane();
|
||||||
resultsTable = new javax.swing.JTable();
|
resultsTable = new javax.swing.JTable();
|
||||||
searchBtn = new javax.swing.JButton();
|
searchBtn = new javax.swing.JButton();
|
||||||
editBtn = new javax.swing.JButton();
|
createAccountBtn = new javax.swing.JButton();
|
||||||
createBtn = new javax.swing.JButton();
|
createBtn = new javax.swing.JButton();
|
||||||
|
editBtn = new javax.swing.JButton();
|
||||||
deleteBtn = new javax.swing.JButton();
|
deleteBtn = new javax.swing.JButton();
|
||||||
|
jSeparator1 = new javax.swing.JSeparator();
|
||||||
detailsPanel = new org.sleuthkit.autopsy.centralrepository.persona.PersonaDetailsPanel();
|
detailsPanel = new org.sleuthkit.autopsy.centralrepository.persona.PersonaDetailsPanel();
|
||||||
|
|
||||||
setMinimumSize(new java.awt.Dimension(400, 400));
|
setName(""); // NOI18N
|
||||||
|
|
||||||
searchField.setText(org.openide.util.NbBundle.getMessage(PersonaManagerTopComponent.class, "PersonaManagerTopComponent.searchField.text")); // NOI18N
|
searchField.setText(org.openide.util.NbBundle.getMessage(PersonasTopComponent.class, "PersonasTopComponent.searchField.text")); // NOI18N
|
||||||
|
|
||||||
searchButtonGroup.add(searchNameRadio);
|
searchButtonGroup.add(searchNameRadio);
|
||||||
searchNameRadio.setSelected(true);
|
searchNameRadio.setSelected(true);
|
||||||
org.openide.awt.Mnemonics.setLocalizedText(searchNameRadio, org.openide.util.NbBundle.getMessage(PersonaManagerTopComponent.class, "PersonaManagerTopComponent.searchNameRadio.text")); // NOI18N
|
org.openide.awt.Mnemonics.setLocalizedText(searchNameRadio, org.openide.util.NbBundle.getMessage(PersonasTopComponent.class, "PersonasTopComponent.searchNameRadio.text")); // NOI18N
|
||||||
|
|
||||||
searchButtonGroup.add(searchAccountRadio);
|
searchButtonGroup.add(searchAccountRadio);
|
||||||
org.openide.awt.Mnemonics.setLocalizedText(searchAccountRadio, org.openide.util.NbBundle.getMessage(PersonaManagerTopComponent.class, "PersonaManagerTopComponent.searchAccountRadio.text")); // NOI18N
|
org.openide.awt.Mnemonics.setLocalizedText(searchAccountRadio, org.openide.util.NbBundle.getMessage(PersonasTopComponent.class, "PersonasTopComponent.searchAccountRadio.text")); // NOI18N
|
||||||
|
|
||||||
resultsTable.setToolTipText(org.openide.util.NbBundle.getMessage(PersonaManagerTopComponent.class, "PersonaManagerTopComponent.resultsTable.toolTipText")); // NOI18N
|
resultsTable.setToolTipText(org.openide.util.NbBundle.getMessage(PersonasTopComponent.class, "PersonasTopComponent.resultsTable.toolTipText")); // NOI18N
|
||||||
resultsTable.getTableHeader().setReorderingAllowed(false);
|
resultsTable.getTableHeader().setReorderingAllowed(false);
|
||||||
resultsPane.setViewportView(resultsTable);
|
resultsPane.setViewportView(resultsTable);
|
||||||
if (resultsTable.getColumnModel().getColumnCount() > 0) {
|
if (resultsTable.getColumnModel().getColumnCount() > 0) {
|
||||||
resultsTable.getColumnModel().getColumn(0).setMaxWidth(25);
|
resultsTable.getColumnModel().getColumn(0).setMaxWidth(25);
|
||||||
resultsTable.getColumnModel().getColumn(0).setHeaderValue(org.openide.util.NbBundle.getMessage(PersonaManagerTopComponent.class, "PersonaManagerTopComponent.resultsTable.columnModel.title0")); // NOI18N
|
resultsTable.getColumnModel().getColumn(0).setHeaderValue(org.openide.util.NbBundle.getMessage(PersonasTopComponent.class, "PersonasTopComponent.resultsTable.columnModel.title0")); // NOI18N
|
||||||
resultsTable.getColumnModel().getColumn(1).setHeaderValue(org.openide.util.NbBundle.getMessage(PersonaManagerTopComponent.class, "PersonaManagerTopComponent.resultsTable.columnModel.title1")); // NOI18N
|
resultsTable.getColumnModel().getColumn(1).setHeaderValue(org.openide.util.NbBundle.getMessage(PersonasTopComponent.class, "PersonasTopComponent.resultsTable.columnModel.title1")); // NOI18N
|
||||||
}
|
}
|
||||||
|
|
||||||
org.openide.awt.Mnemonics.setLocalizedText(searchBtn, org.openide.util.NbBundle.getMessage(PersonaManagerTopComponent.class, "PersonaManagerTopComponent.searchBtn.text")); // NOI18N
|
org.openide.awt.Mnemonics.setLocalizedText(searchBtn, org.openide.util.NbBundle.getMessage(PersonasTopComponent.class, "PersonasTopComponent.searchBtn.text")); // NOI18N
|
||||||
|
|
||||||
org.openide.awt.Mnemonics.setLocalizedText(editBtn, org.openide.util.NbBundle.getMessage(PersonaManagerTopComponent.class, "PersonaManagerTopComponent.editBtn.text")); // NOI18N
|
org.openide.awt.Mnemonics.setLocalizedText(createAccountBtn, org.openide.util.NbBundle.getMessage(PersonasTopComponent.class, "PersonasTopComponent.createAccountBtn.text")); // NOI18N
|
||||||
|
|
||||||
|
org.openide.awt.Mnemonics.setLocalizedText(createBtn, org.openide.util.NbBundle.getMessage(PersonasTopComponent.class, "PersonasTopComponent.createBtn.text")); // NOI18N
|
||||||
|
|
||||||
|
org.openide.awt.Mnemonics.setLocalizedText(editBtn, org.openide.util.NbBundle.getMessage(PersonasTopComponent.class, "PersonasTopComponent.editBtn.text")); // NOI18N
|
||||||
editBtn.setEnabled(false);
|
editBtn.setEnabled(false);
|
||||||
|
|
||||||
org.openide.awt.Mnemonics.setLocalizedText(createBtn, org.openide.util.NbBundle.getMessage(PersonaManagerTopComponent.class, "PersonaManagerTopComponent.createBtn.text")); // NOI18N
|
org.openide.awt.Mnemonics.setLocalizedText(deleteBtn, org.openide.util.NbBundle.getMessage(PersonasTopComponent.class, "PersonasTopComponent.deleteBtn.text")); // NOI18N
|
||||||
|
|
||||||
org.openide.awt.Mnemonics.setLocalizedText(deleteBtn, org.openide.util.NbBundle.getMessage(PersonaManagerTopComponent.class, "PersonaManagerTopComponent.deleteBtn.text")); // NOI18N
|
|
||||||
deleteBtn.setEnabled(false);
|
deleteBtn.setEnabled(false);
|
||||||
|
|
||||||
javax.swing.GroupLayout searchPanelLayout = new javax.swing.GroupLayout(searchPanel);
|
javax.swing.GroupLayout searchPanelLayout = new javax.swing.GroupLayout(searchPanel);
|
||||||
@ -304,6 +317,7 @@ public final class PersonaManagerTopComponent extends TopComponent {
|
|||||||
.addGroup(searchPanelLayout.createSequentialGroup()
|
.addGroup(searchPanelLayout.createSequentialGroup()
|
||||||
.addContainerGap()
|
.addContainerGap()
|
||||||
.addGroup(searchPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
.addGroup(searchPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||||
|
.addComponent(jSeparator1)
|
||||||
.addGroup(searchPanelLayout.createSequentialGroup()
|
.addGroup(searchPanelLayout.createSequentialGroup()
|
||||||
.addComponent(createBtn)
|
.addComponent(createBtn)
|
||||||
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||||
@ -317,7 +331,10 @@ public final class PersonaManagerTopComponent extends TopComponent {
|
|||||||
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||||
.addComponent(searchAccountRadio)
|
.addComponent(searchAccountRadio)
|
||||||
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
|
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
|
||||||
.addComponent(searchBtn)))
|
.addComponent(searchBtn))
|
||||||
|
.addGroup(searchPanelLayout.createSequentialGroup()
|
||||||
|
.addComponent(createAccountBtn)
|
||||||
|
.addGap(0, 0, Short.MAX_VALUE)))
|
||||||
.addContainerGap())
|
.addContainerGap())
|
||||||
);
|
);
|
||||||
searchPanelLayout.setVerticalGroup(
|
searchPanelLayout.setVerticalGroup(
|
||||||
@ -331,12 +348,16 @@ public final class PersonaManagerTopComponent extends TopComponent {
|
|||||||
.addComponent(searchAccountRadio)
|
.addComponent(searchAccountRadio)
|
||||||
.addComponent(searchBtn))
|
.addComponent(searchBtn))
|
||||||
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||||
.addComponent(resultsPane, javax.swing.GroupLayout.DEFAULT_SIZE, 528, Short.MAX_VALUE)
|
.addComponent(resultsPane, javax.swing.GroupLayout.DEFAULT_SIZE, 457, Short.MAX_VALUE)
|
||||||
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||||
.addGroup(searchPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
|
.addGroup(searchPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
|
||||||
.addComponent(editBtn)
|
.addComponent(editBtn)
|
||||||
.addComponent(createBtn)
|
.addComponent(createBtn)
|
||||||
.addComponent(deleteBtn))
|
.addComponent(deleteBtn))
|
||||||
|
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||||
|
.addComponent(jSeparator1, javax.swing.GroupLayout.PREFERRED_SIZE, 4, javax.swing.GroupLayout.PREFERRED_SIZE)
|
||||||
|
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
|
||||||
|
.addComponent(createAccountBtn, javax.swing.GroupLayout.PREFERRED_SIZE, 32, javax.swing.GroupLayout.PREFERRED_SIZE)
|
||||||
.addContainerGap())
|
.addContainerGap())
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -347,7 +368,7 @@ public final class PersonaManagerTopComponent extends TopComponent {
|
|||||||
this.setLayout(layout);
|
this.setLayout(layout);
|
||||||
layout.setHorizontalGroup(
|
layout.setHorizontalGroup(
|
||||||
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||||
.addComponent(jSplitPane1, javax.swing.GroupLayout.DEFAULT_SIZE, 692, Short.MAX_VALUE)
|
.addComponent(jSplitPane1, javax.swing.GroupLayout.DEFAULT_SIZE, 794, Short.MAX_VALUE)
|
||||||
);
|
);
|
||||||
layout.setVerticalGroup(
|
layout.setVerticalGroup(
|
||||||
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||||
@ -356,10 +377,12 @@ public final class PersonaManagerTopComponent extends TopComponent {
|
|||||||
}// </editor-fold>//GEN-END:initComponents
|
}// </editor-fold>//GEN-END:initComponents
|
||||||
|
|
||||||
// Variables declaration - do not modify//GEN-BEGIN:variables
|
// Variables declaration - do not modify//GEN-BEGIN:variables
|
||||||
|
private javax.swing.JButton createAccountBtn;
|
||||||
private javax.swing.JButton createBtn;
|
private javax.swing.JButton createBtn;
|
||||||
private javax.swing.JButton deleteBtn;
|
private javax.swing.JButton deleteBtn;
|
||||||
private org.sleuthkit.autopsy.centralrepository.persona.PersonaDetailsPanel detailsPanel;
|
private org.sleuthkit.autopsy.centralrepository.persona.PersonaDetailsPanel detailsPanel;
|
||||||
private javax.swing.JButton editBtn;
|
private javax.swing.JButton editBtn;
|
||||||
|
private javax.swing.JSeparator jSeparator1;
|
||||||
private javax.swing.JSplitPane jSplitPane1;
|
private javax.swing.JSplitPane jSplitPane1;
|
||||||
private javax.swing.JScrollPane resultsPane;
|
private javax.swing.JScrollPane resultsPane;
|
||||||
private javax.swing.JTable resultsTable;
|
private javax.swing.JTable resultsTable;
|
@ -981,4 +981,3 @@ CallLogArtifactViewer.localAccountPersonaNameLabel.text=jLabel1
|
|||||||
CallLogArtifactViewer.localAccountPersonaButton.text=jButton1
|
CallLogArtifactViewer.localAccountPersonaButton.text=jButton1
|
||||||
ContactArtifactViewer.personasLabel.text=Personas
|
ContactArtifactViewer.personasLabel.text=Personas
|
||||||
MessageArtifactViewer.accountsTab.TabConstraints.tabTitle=Accounts
|
MessageArtifactViewer.accountsTab.TabConstraints.tabTitle=Accounts
|
||||||
ContactArtifactViewer.contactImage.text=
|
|
||||||
|
@ -35,15 +35,23 @@ AnnotationsContentViewer.title=Annotations
|
|||||||
AnnotationsContentViewer.toolTip=Displays tags and comments associated with the selected content.
|
AnnotationsContentViewer.toolTip=Displays tags and comments associated with the selected content.
|
||||||
ApplicationContentViewer.title=Application
|
ApplicationContentViewer.title=Application
|
||||||
ApplicationContentViewer.toolTip=Displays file contents.
|
ApplicationContentViewer.toolTip=Displays file contents.
|
||||||
CallLogArtifactViewer_crdisbaled_persona_button_text=Create
|
CallLogArtifactViewer_heading_metadata=Metadata
|
||||||
CallLogArtifactViewer_crdisbaled_persona_label=Unknown
|
CallLogArtifactViewer_heading_parties=Parties
|
||||||
CallLogArtifactViewer_number_from=From
|
CallLogArtifactViewer_heading_Source=Source
|
||||||
CallLogArtifactViewer_number_to=To
|
CallLogArtifactViewer_label_datasource=Data Source
|
||||||
CallLogArtifactViewer_persona_button_new=Create
|
CallLogArtifactViewer_label_date=Date
|
||||||
CallLogArtifactViewer_persona_button_view=View
|
CallLogArtifactViewer_label_direction=Direction
|
||||||
CallLogArtifactViewer_persona_label=\ Persona
|
CallLogArtifactViewer_label_duration=Duration
|
||||||
CallLogArtifactViewer_persona_searching=Searching...
|
CallLogArtifactViewer_label_from=From
|
||||||
CallLogArtifactViewer_persona_text_none=None Found
|
CallLogArtifactViewer_label_to=To
|
||||||
|
CallLogArtifactViewer_suffix_local=(Local)
|
||||||
|
CallLogArtifactViewer_value_unknown=Unknown
|
||||||
|
CommunicationArtifactViewerHelper_menuitem_copy=Copy
|
||||||
|
CommunicationArtifactViewerHelper_persona_button_create=Create
|
||||||
|
CommunicationArtifactViewerHelper_persona_button_view=View
|
||||||
|
CommunicationArtifactViewerHelper_persona_label=Persona:
|
||||||
|
CommunicationArtifactViewerHelper_persona_searching=Searching...
|
||||||
|
CommunicationArtifactViewerHelper_persona_unknown=Unknown
|
||||||
ContactArtifactViewer_missing_account_label=Missing Account:
|
ContactArtifactViewer_missing_account_label=Missing Account:
|
||||||
ContactArtifactViewer_persona_account_justification=Account found in Contact artifact
|
ContactArtifactViewer_persona_account_justification=Account found in Contact artifact
|
||||||
ContactArtifactViewer_persona_button_new=Create
|
ContactArtifactViewer_persona_button_new=Create
|
||||||
|
@ -35,6 +35,7 @@ import org.apache.commons.lang3.ObjectUtils;
|
|||||||
import org.apache.commons.lang3.StringUtils;
|
import org.apache.commons.lang3.StringUtils;
|
||||||
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.centralrepository.datamodel.CentralRepository;
|
||||||
import org.sleuthkit.autopsy.coreutils.Logger;
|
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||||
import org.sleuthkit.datamodel.BlackboardArtifact;
|
import org.sleuthkit.datamodel.BlackboardArtifact;
|
||||||
import org.sleuthkit.datamodel.BlackboardAttribute;
|
import org.sleuthkit.datamodel.BlackboardAttribute;
|
||||||
@ -66,8 +67,8 @@ public class CallLogArtifactViewer extends javax.swing.JPanel implements Artifac
|
|||||||
|
|
||||||
private GridBagLayout m_gridBagLayout = new GridBagLayout();
|
private GridBagLayout m_gridBagLayout = new GridBagLayout();
|
||||||
private GridBagConstraints m_constraints = new GridBagConstraints();
|
private GridBagConstraints m_constraints = new GridBagConstraints();
|
||||||
|
|
||||||
private final List<PersonaSearchAndDisplayTask> personaSearchtasks = new ArrayList<>();
|
private PersonaAccountFetcher currentAccountFetcher = null;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Creates new form CallLogArtifactViewer.
|
* Creates new form CallLogArtifactViewer.
|
||||||
@ -92,6 +93,10 @@ public class CallLogArtifactViewer extends javax.swing.JPanel implements Artifac
|
|||||||
public void setArtifact(BlackboardArtifact artifact) {
|
public void setArtifact(BlackboardArtifact artifact) {
|
||||||
resetComponent();
|
resetComponent();
|
||||||
|
|
||||||
|
if (artifact == null) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
CallLogViewData callLogViewData = null;
|
CallLogViewData callLogViewData = null;
|
||||||
try {
|
try {
|
||||||
callLogViewData = getCallLogViewData(artifact);
|
callLogViewData = getCallLogViewData(artifact);
|
||||||
@ -101,11 +106,16 @@ public class CallLogArtifactViewer extends javax.swing.JPanel implements Artifac
|
|||||||
|
|
||||||
// update the view with the call log data
|
// update the view with the call log data
|
||||||
if (callLogViewData != null) {
|
if (callLogViewData != null) {
|
||||||
updateView(callLogViewData);
|
List<AccountPersonaSearcherData> personaSearchDataList = updateView(callLogViewData);
|
||||||
|
if(!personaSearchDataList.isEmpty()) {
|
||||||
|
currentAccountFetcher = new PersonaAccountFetcher(artifact, personaSearchDataList, this);
|
||||||
|
currentAccountFetcher.execute();
|
||||||
|
} else {
|
||||||
|
currentAccountFetcher = null;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
// repaint
|
// repaint
|
||||||
this.revalidate();
|
this.revalidate();
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -281,6 +291,8 @@ public class CallLogArtifactViewer extends javax.swing.JPanel implements Artifac
|
|||||||
* Update the viewer with the call log data.
|
* Update the viewer with the call log data.
|
||||||
*
|
*
|
||||||
* @param callLogViewData Call log data to update the view with.
|
* @param callLogViewData Call log data to update the view with.
|
||||||
|
*
|
||||||
|
* @return List of AccountPersonaSearcherData objects.
|
||||||
*/
|
*/
|
||||||
@NbBundle.Messages({
|
@NbBundle.Messages({
|
||||||
"CallLogArtifactViewer_heading_parties=Parties",
|
"CallLogArtifactViewer_heading_parties=Parties",
|
||||||
@ -288,10 +300,11 @@ public class CallLogArtifactViewer extends javax.swing.JPanel implements Artifac
|
|||||||
"CallLogArtifactViewer_label_from=From",
|
"CallLogArtifactViewer_label_from=From",
|
||||||
"CallLogArtifactViewer_label_to=To"
|
"CallLogArtifactViewer_label_to=To"
|
||||||
})
|
})
|
||||||
private void updateView(CallLogViewData callLogViewData) {
|
private List<AccountPersonaSearcherData> updateView(CallLogViewData callLogViewData) {
|
||||||
|
|
||||||
CommunicationArtifactViewerHelper.addHeader(this, m_gridBagLayout, this.m_constraints, Bundle.CallLogArtifactViewer_heading_parties());
|
CommunicationArtifactViewerHelper.addHeader(this, m_gridBagLayout, this.m_constraints, Bundle.CallLogArtifactViewer_heading_parties());
|
||||||
|
|
||||||
|
List<AccountPersonaSearcherData> dataList = new ArrayList<>();
|
||||||
// Display From address
|
// Display From address
|
||||||
CommunicationArtifactViewerHelper.addKey(this, m_gridBagLayout, this.m_constraints, Bundle.CallLogArtifactViewer_label_from());
|
CommunicationArtifactViewerHelper.addKey(this, m_gridBagLayout, this.m_constraints, Bundle.CallLogArtifactViewer_label_from());
|
||||||
|
|
||||||
@ -301,10 +314,7 @@ public class CallLogArtifactViewer extends javax.swing.JPanel implements Artifac
|
|||||||
CommunicationArtifactViewerHelper.addValue(this, m_gridBagLayout, this.m_constraints, accountDisplayString);
|
CommunicationArtifactViewerHelper.addValue(this, m_gridBagLayout, this.m_constraints, accountDisplayString);
|
||||||
|
|
||||||
// show persona
|
// show persona
|
||||||
Optional<PersonaSearchAndDisplayTask> task = CommunicationArtifactViewerHelper.addPersonaRow(this, m_gridBagLayout, this.m_constraints, callLogViewData.getFromAccount());
|
dataList.addAll( CommunicationArtifactViewerHelper.addPersonaRow(this, m_gridBagLayout, this.m_constraints, callLogViewData.getFromAccount()));
|
||||||
if (task.isPresent()) {
|
|
||||||
personaSearchtasks.add(task.get());
|
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
CommunicationArtifactViewerHelper.addValue(this, m_gridBagLayout, this.m_constraints, Bundle.CallLogArtifactViewer_value_unknown());
|
CommunicationArtifactViewerHelper.addValue(this, m_gridBagLayout, this.m_constraints, Bundle.CallLogArtifactViewer_value_unknown());
|
||||||
}
|
}
|
||||||
@ -315,10 +325,8 @@ public class CallLogArtifactViewer extends javax.swing.JPanel implements Artifac
|
|||||||
String accountDisplayString = getAccountDisplayString(callLogViewData.getToAccount(), callLogViewData);
|
String accountDisplayString = getAccountDisplayString(callLogViewData.getToAccount(), callLogViewData);
|
||||||
CommunicationArtifactViewerHelper.addValue(this, m_gridBagLayout, this.m_constraints, accountDisplayString);
|
CommunicationArtifactViewerHelper.addValue(this, m_gridBagLayout, this.m_constraints, accountDisplayString);
|
||||||
|
|
||||||
Optional<PersonaSearchAndDisplayTask> task = CommunicationArtifactViewerHelper.addPersonaRow(this, m_gridBagLayout, this.m_constraints, callLogViewData.getToAccount());
|
dataList.addAll( CommunicationArtifactViewerHelper.addPersonaRow(this, m_gridBagLayout, this.m_constraints, callLogViewData.getToAccount()));
|
||||||
if (task.isPresent()) {
|
|
||||||
personaSearchtasks.add(task.get());
|
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
CommunicationArtifactViewerHelper.addValue(this, m_gridBagLayout, this.m_constraints, Bundle.CallLogArtifactViewer_value_unknown());
|
CommunicationArtifactViewerHelper.addValue(this, m_gridBagLayout, this.m_constraints, Bundle.CallLogArtifactViewer_value_unknown());
|
||||||
}
|
}
|
||||||
@ -328,20 +336,26 @@ public class CallLogArtifactViewer extends javax.swing.JPanel implements Artifac
|
|||||||
CommunicationArtifactViewerHelper.addKey(this, m_gridBagLayout, this.m_constraints, Bundle.CallLogArtifactViewer_label_to());
|
CommunicationArtifactViewerHelper.addKey(this, m_gridBagLayout, this.m_constraints, Bundle.CallLogArtifactViewer_label_to());
|
||||||
CommunicationArtifactViewerHelper.addValue(this, m_gridBagLayout, this.m_constraints, otherParty);
|
CommunicationArtifactViewerHelper.addValue(this, m_gridBagLayout, this.m_constraints, otherParty);
|
||||||
|
|
||||||
Optional<PersonaSearchAndDisplayTask> task = CommunicationArtifactViewerHelper.addPersonaRow(this, m_gridBagLayout, this.m_constraints, otherParty);
|
dataList.addAll( CommunicationArtifactViewerHelper.addPersonaRow(this, m_gridBagLayout, this.m_constraints, otherParty));
|
||||||
if (task.isPresent()) {
|
|
||||||
personaSearchtasks.add(task.get());
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
updateMetadataView(callLogViewData);
|
updateMetadataView(callLogViewData);
|
||||||
|
|
||||||
|
updateOtherAttributesView(callLogViewData);
|
||||||
|
|
||||||
updateSourceView(callLogViewData);
|
updateSourceView(callLogViewData);
|
||||||
|
|
||||||
|
if (CentralRepository.isEnabled() == false) {
|
||||||
|
showCRDisabledMessage();
|
||||||
|
}
|
||||||
|
|
||||||
CommunicationArtifactViewerHelper.addPageEndGlue(this, m_gridBagLayout, this.m_constraints);
|
CommunicationArtifactViewerHelper.addPageEndGlue(this, m_gridBagLayout, this.m_constraints);
|
||||||
|
|
||||||
this.setLayout(m_gridBagLayout);
|
this.setLayout(m_gridBagLayout);
|
||||||
this.revalidate();
|
this.revalidate();
|
||||||
this.repaint();
|
this.repaint();
|
||||||
|
|
||||||
|
return dataList;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -392,6 +406,37 @@ public class CallLogArtifactViewer extends javax.swing.JPanel implements Artifac
|
|||||||
CommunicationArtifactViewerHelper.addValue(this, m_gridBagLayout, this.m_constraints, callLogViewData.getDataSourceName());
|
CommunicationArtifactViewerHelper.addValue(this, m_gridBagLayout, this.m_constraints, callLogViewData.getDataSourceName());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update the other attributes section.
|
||||||
|
*
|
||||||
|
* @param callLogViewData Call log data.
|
||||||
|
*/
|
||||||
|
@NbBundle.Messages({
|
||||||
|
"CallLogArtifactViewer_heading_others=Other Attributes"
|
||||||
|
})
|
||||||
|
private void updateOtherAttributesView(CallLogViewData callLogViewData) {
|
||||||
|
|
||||||
|
if (callLogViewData.getOtherAttributes().isEmpty()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
CommunicationArtifactViewerHelper.addHeader(this, m_gridBagLayout, this.m_constraints, Bundle.CallLogArtifactViewer_heading_others());
|
||||||
|
|
||||||
|
for (Map.Entry<String, String> entry : callLogViewData.getOtherAttributes().entrySet()) {
|
||||||
|
CommunicationArtifactViewerHelper.addKey(this, m_gridBagLayout, this.m_constraints, entry.getKey());
|
||||||
|
CommunicationArtifactViewerHelper.addValue(this, m_gridBagLayout, this.m_constraints, entry.getValue());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@NbBundle.Messages({
|
||||||
|
"CalllogArtifactViewer_cr_disabled_message=Enable Central Repository to view, create and edit personas."
|
||||||
|
})
|
||||||
|
private void showCRDisabledMessage() {
|
||||||
|
CommunicationArtifactViewerHelper.addBlankLine(this, m_gridBagLayout, m_constraints);
|
||||||
|
m_constraints.gridy++;
|
||||||
|
CommunicationArtifactViewerHelper.addMessageRow(this, m_gridBagLayout, m_constraints, Bundle.ContactArtifactViewer_cr_disabled_message());
|
||||||
|
m_constraints.gridy++;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns display string for a account. Checks if the given account is the
|
* Returns display string for a account. Checks if the given account is the
|
||||||
* local account, if it is known. If it is, it appends a "(Local)" suffix to
|
* local account, if it is known. If it is, it appends a "(Local)" suffix to
|
||||||
@ -419,7 +464,9 @@ public class CallLogArtifactViewer extends javax.swing.JPanel implements Artifac
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean isSupported(BlackboardArtifact artifact) {
|
public boolean isSupported(BlackboardArtifact artifact) {
|
||||||
return artifact.getArtifactTypeID() == BlackboardArtifact.ARTIFACT_TYPE.TSK_CALLLOG.getTypeID();
|
|
||||||
|
return (artifact != null)
|
||||||
|
&& (artifact.getArtifactTypeID() == BlackboardArtifact.ARTIFACT_TYPE.TSK_CALLLOG.getTypeID());
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -428,8 +475,10 @@ public class CallLogArtifactViewer extends javax.swing.JPanel implements Artifac
|
|||||||
private void resetComponent() {
|
private void resetComponent() {
|
||||||
|
|
||||||
// cancel any outstanding persona searching threads.
|
// cancel any outstanding persona searching threads.
|
||||||
personaSearchtasks.forEach(task -> task.cancel(Boolean.TRUE));
|
if(currentAccountFetcher != null && !currentAccountFetcher.isDone()) {
|
||||||
personaSearchtasks.clear();
|
currentAccountFetcher.cancel(true);
|
||||||
|
currentAccountFetcher = null;
|
||||||
|
}
|
||||||
|
|
||||||
// clear the panel
|
// clear the panel
|
||||||
this.removeAll();
|
this.removeAll();
|
||||||
@ -441,9 +490,9 @@ public class CallLogArtifactViewer extends javax.swing.JPanel implements Artifac
|
|||||||
m_constraints.anchor = GridBagConstraints.FIRST_LINE_START;
|
m_constraints.anchor = GridBagConstraints.FIRST_LINE_START;
|
||||||
m_constraints.gridy = 0;
|
m_constraints.gridy = 0;
|
||||||
m_constraints.gridx = 0;
|
m_constraints.gridx = 0;
|
||||||
m_constraints.weighty = 0.05;
|
m_constraints.weighty = 0.0;
|
||||||
m_constraints.weightx = 0.05;
|
m_constraints.weightx = 0.0; // keep components fixed horizontally.
|
||||||
m_constraints.insets = new java.awt.Insets(0, 0, 0, 0);
|
m_constraints.insets = new java.awt.Insets(0, CommunicationArtifactViewerHelper.LEFT_INSET, 0, 0);
|
||||||
m_constraints.fill = GridBagConstraints.NONE;
|
m_constraints.fill = GridBagConstraints.NONE;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -27,12 +27,14 @@ import java.awt.Toolkit;
|
|||||||
import java.awt.datatransfer.StringSelection;
|
import java.awt.datatransfer.StringSelection;
|
||||||
import java.awt.event.ActionEvent;
|
import java.awt.event.ActionEvent;
|
||||||
import java.awt.event.ActionListener;
|
import java.awt.event.ActionListener;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
import javax.swing.JLabel;
|
import javax.swing.JLabel;
|
||||||
import javax.swing.JMenuItem;
|
import javax.swing.JMenuItem;
|
||||||
|
import javax.swing.JComponent;
|
||||||
import javax.swing.JPanel;
|
import javax.swing.JPanel;
|
||||||
import javax.swing.JPopupMenu;
|
import javax.swing.JPopupMenu;
|
||||||
import javax.swing.SwingUtilities;
|
import javax.swing.SwingUtilities;
|
||||||
import java.util.Optional;
|
|
||||||
import org.openide.util.NbBundle;
|
import org.openide.util.NbBundle;
|
||||||
import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepository;
|
import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepository;
|
||||||
|
|
||||||
@ -41,20 +43,20 @@ import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepository;
|
|||||||
* A class to help display a communication artifact in a panel using a
|
* A class to help display a communication artifact in a panel using a
|
||||||
* gridbaglayout.
|
* gridbaglayout.
|
||||||
*/
|
*/
|
||||||
public final class CommunicationArtifactViewerHelper {
|
final class CommunicationArtifactViewerHelper {
|
||||||
|
|
||||||
// Number of columns in the gridbag layout.
|
// Number of columns in the gridbag layout.
|
||||||
private final static int MAX_COLS = 4;
|
private final static int MAX_COLS = 4;
|
||||||
|
|
||||||
private final static int LEFT_INDENT = 12;
|
final static int LEFT_INSET = 12;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Empty private constructor
|
* Empty private constructor
|
||||||
*/
|
*/
|
||||||
private CommunicationArtifactViewerHelper() {
|
private CommunicationArtifactViewerHelper() {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Adds a new heading to the panel.
|
* Adds a new heading to the panel.
|
||||||
*
|
*
|
||||||
@ -62,8 +64,15 @@ public final class CommunicationArtifactViewerHelper {
|
|||||||
* @param gridbagLayout Layout to use.
|
* @param gridbagLayout Layout to use.
|
||||||
* @param constraints Constrains to use.
|
* @param constraints Constrains to use.
|
||||||
* @param headerString Heading string to display.
|
* @param headerString Heading string to display.
|
||||||
|
*
|
||||||
|
* @return JLabel Heading label added.
|
||||||
*/
|
*/
|
||||||
static void addHeader(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints, String headerString) {
|
static JLabel addHeader(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints, String headerString) {
|
||||||
|
|
||||||
|
Insets savedInsets = constraints.insets;
|
||||||
|
|
||||||
|
// create label for heading
|
||||||
|
javax.swing.JLabel headingLabel = new javax.swing.JLabel();
|
||||||
|
|
||||||
// add a blank line before the start of new section, unless it's
|
// add a blank line before the start of new section, unless it's
|
||||||
// the first section
|
// the first section
|
||||||
@ -75,9 +84,9 @@ public final class CommunicationArtifactViewerHelper {
|
|||||||
|
|
||||||
// let the header span all of the row
|
// let the header span all of the row
|
||||||
constraints.gridwidth = MAX_COLS;
|
constraints.gridwidth = MAX_COLS;
|
||||||
|
constraints.insets = new Insets(0, 0, 0, 0); // No inset for header
|
||||||
|
|
||||||
// create label for heading
|
// set text
|
||||||
javax.swing.JLabel headingLabel = new javax.swing.JLabel();
|
|
||||||
headingLabel.setText(headerString);
|
headingLabel.setText(headerString);
|
||||||
|
|
||||||
// make it large and bold
|
// make it large and bold
|
||||||
@ -92,6 +101,28 @@ public final class CommunicationArtifactViewerHelper {
|
|||||||
|
|
||||||
// add line end glue
|
// add line end glue
|
||||||
addLineEndGlue(panel, gridbagLayout, constraints);
|
addLineEndGlue(panel, gridbagLayout, constraints);
|
||||||
|
|
||||||
|
//restore insets
|
||||||
|
constraints.insets = savedInsets;
|
||||||
|
|
||||||
|
return headingLabel;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Adds the given component to the panel.
|
||||||
|
*
|
||||||
|
* Caller must know what it's doing and set up all the constraints properly.
|
||||||
|
*
|
||||||
|
* @param panel Panel to update.
|
||||||
|
* @param gridbagLayout Layout to use.
|
||||||
|
* @param constraints Constrains to use.
|
||||||
|
* @param component Component to add.
|
||||||
|
*/
|
||||||
|
static void addComponent(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints, JComponent component) {
|
||||||
|
|
||||||
|
// add to panel
|
||||||
|
gridbagLayout.setConstraints(component, constraints);
|
||||||
|
panel.add(component);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -102,7 +133,7 @@ public final class CommunicationArtifactViewerHelper {
|
|||||||
* @param gridbagLayout Layout to use.
|
* @param gridbagLayout Layout to use.
|
||||||
* @param constraints Constrains to use.
|
* @param constraints Constrains to use.
|
||||||
*/
|
*/
|
||||||
private static void addLineEndGlue(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints) {
|
static void addLineEndGlue(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints) {
|
||||||
// Place the filler just past the last column.
|
// Place the filler just past the last column.
|
||||||
constraints.gridx = MAX_COLS;
|
constraints.gridx = MAX_COLS;
|
||||||
|
|
||||||
@ -155,7 +186,7 @@ public final class CommunicationArtifactViewerHelper {
|
|||||||
* @param gridbagLayout Layout to use.
|
* @param gridbagLayout Layout to use.
|
||||||
* @param constraints Constrains to use.
|
* @param constraints Constrains to use.
|
||||||
*/
|
*/
|
||||||
private static void addBlankLine(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints) {
|
static void addBlankLine(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints) {
|
||||||
constraints.gridy++;
|
constraints.gridy++;
|
||||||
constraints.gridx = 0;
|
constraints.gridx = 0;
|
||||||
|
|
||||||
@ -167,54 +198,85 @@ public final class CommunicationArtifactViewerHelper {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Adds a label/key to the panel.
|
* Adds a label/key to the panel at col 0.
|
||||||
*
|
*
|
||||||
* @param panel Panel to update.
|
* @param panel Panel to update.
|
||||||
* @param gridbagLayout Layout to use.
|
* @param gridbagLayout Layout to use.
|
||||||
* @param constraints Constrains to use.
|
* @param constraints Constrains to use.
|
||||||
* @param keyString Key name to display.
|
* @param keyString Key name to display.
|
||||||
|
*
|
||||||
|
* @return Label added.
|
||||||
*/
|
*/
|
||||||
static void addKey(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints, String keyString) {
|
static JLabel addKey(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints, String keyString) {
|
||||||
|
return addKeyAtCol(panel, gridbagLayout, constraints, keyString, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Adds a label/key to the panel at specified column.
|
||||||
|
*
|
||||||
|
* @param panel Panel to update.
|
||||||
|
* @param gridbagLayout Layout to use.
|
||||||
|
* @param constraints Constrains to use.
|
||||||
|
* @param keyString Key name to display.
|
||||||
|
* @param gridx column index, must be less than MAX_COLS - 1.
|
||||||
|
*
|
||||||
|
* @return Label added.
|
||||||
|
*/
|
||||||
|
static JLabel addKeyAtCol(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints, String keyString, int gridx) {
|
||||||
|
|
||||||
|
// create label
|
||||||
|
javax.swing.JLabel keyLabel = new javax.swing.JLabel();
|
||||||
|
|
||||||
constraints.gridy++;
|
constraints.gridy++;
|
||||||
constraints.gridx = 0;
|
constraints.gridx = gridx < MAX_COLS - 1 ? gridx : MAX_COLS - 2;
|
||||||
|
|
||||||
Insets savedInsets = constraints.insets;
|
// set text
|
||||||
|
|
||||||
// Set inset to indent in
|
|
||||||
constraints.insets = new java.awt.Insets(0, LEFT_INDENT, 0, 0);
|
|
||||||
|
|
||||||
// create label,
|
|
||||||
javax.swing.JLabel keyLabel = new javax.swing.JLabel();
|
|
||||||
keyLabel.setText(keyString + ": ");
|
keyLabel.setText(keyString + ": ");
|
||||||
|
|
||||||
// add to panel
|
// add to panel
|
||||||
gridbagLayout.setConstraints(keyLabel, constraints);
|
gridbagLayout.setConstraints(keyLabel, constraints);
|
||||||
panel.add(keyLabel);
|
panel.add(keyLabel);
|
||||||
|
|
||||||
// restore inset
|
return keyLabel;
|
||||||
constraints.insets = savedInsets;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Adds a value string to the panel.
|
* Adds a value string to the panel at col 1.
|
||||||
*
|
*
|
||||||
* @param panel Panel to update.
|
* @param panel Panel to update.
|
||||||
* @param gridbagLayout Layout to use.
|
* @param gridbagLayout Layout to use.
|
||||||
* @param constraints Constrains to use.
|
* @param constraints Constrains to use.
|
||||||
* @param keyString Value string to display.
|
* @param keyString Value string to display.
|
||||||
|
*
|
||||||
|
* @return Label added.
|
||||||
*/
|
*/
|
||||||
static void addValue(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints, String valueString) {
|
static JLabel addValue(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints, String valueString) {
|
||||||
|
return addValueAtCol(panel, gridbagLayout, constraints, valueString, 1);
|
||||||
|
}
|
||||||
|
|
||||||
constraints.gridx = 1;
|
/**
|
||||||
|
* Adds a value string to the panel at specified column.
|
||||||
|
*
|
||||||
|
* @param panel Panel to update.
|
||||||
|
* @param gridbagLayout Layout to use.
|
||||||
|
* @param constraints Constrains to use.
|
||||||
|
* @param keyString Value string to display.
|
||||||
|
* @param gridx Column index, must be less than MAX_COLS;
|
||||||
|
*
|
||||||
|
* @return Label added.
|
||||||
|
*/
|
||||||
|
static JLabel addValueAtCol(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints, String valueString, int gridx) {
|
||||||
|
// create label,
|
||||||
|
javax.swing.JLabel valueField = new javax.swing.JLabel();
|
||||||
|
|
||||||
|
constraints.gridx = gridx < MAX_COLS ? gridx : MAX_COLS - 1;
|
||||||
|
|
||||||
int savedGridwidth = constraints.gridwidth;
|
int savedGridwidth = constraints.gridwidth;
|
||||||
|
|
||||||
// let the value span 2 cols
|
// let the value span 2 cols
|
||||||
constraints.gridwidth = 2;
|
constraints.gridwidth = 2;
|
||||||
|
|
||||||
// create label,
|
// set text
|
||||||
javax.swing.JLabel valueField = new javax.swing.JLabel();
|
|
||||||
valueField.setText(valueString);
|
valueField.setText(valueString);
|
||||||
|
|
||||||
// attach a right click menu with Copy option
|
// attach a right click menu with Copy option
|
||||||
@ -234,6 +296,63 @@ public final class CommunicationArtifactViewerHelper {
|
|||||||
|
|
||||||
// end the line
|
// end the line
|
||||||
addLineEndGlue(panel, gridbagLayout, constraints);
|
addLineEndGlue(panel, gridbagLayout, constraints);
|
||||||
|
|
||||||
|
return valueField;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Displays a message string, starting at column 0, and spanning the entire
|
||||||
|
* row.
|
||||||
|
*
|
||||||
|
* @param panel Panel to show.
|
||||||
|
* @param gridbagLayout Layout to use.
|
||||||
|
* @param constraints Constraints to use.
|
||||||
|
*
|
||||||
|
* @param messageString Message to display.
|
||||||
|
*
|
||||||
|
* @return Label for message added.
|
||||||
|
*/
|
||||||
|
static JLabel addMessageRow(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints, String messageString) {
|
||||||
|
return addMessageRow(panel, gridbagLayout, constraints, messageString, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Displays a message string, starting at specified column, and spanning the
|
||||||
|
* entire row.
|
||||||
|
*
|
||||||
|
* @param panel Panel to show.
|
||||||
|
* @param gridbagLayout Layout to use.
|
||||||
|
* @param constraints Constraints to use.
|
||||||
|
*
|
||||||
|
* @param messageString Message to display.
|
||||||
|
*
|
||||||
|
* @return Label for message added.
|
||||||
|
*/
|
||||||
|
static JLabel addMessageRow(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints, String messageString, int gridx) {
|
||||||
|
|
||||||
|
// create label
|
||||||
|
javax.swing.JLabel messageLabel = new javax.swing.JLabel();
|
||||||
|
|
||||||
|
constraints.gridy++;
|
||||||
|
constraints.gridx = gridx < MAX_COLS - 1 ? gridx : MAX_COLS - 2;
|
||||||
|
|
||||||
|
int savedGridwidth = constraints.gridwidth;
|
||||||
|
|
||||||
|
constraints.gridwidth = 3;
|
||||||
|
|
||||||
|
// set text
|
||||||
|
messageLabel.setText(messageString);
|
||||||
|
|
||||||
|
// add to panel
|
||||||
|
gridbagLayout.setConstraints(messageLabel, constraints);
|
||||||
|
panel.add(messageLabel);
|
||||||
|
|
||||||
|
addLineEndGlue(panel, gridbagLayout, constraints);
|
||||||
|
|
||||||
|
// restore constraints
|
||||||
|
constraints.gridwidth = savedGridwidth;
|
||||||
|
|
||||||
|
return messageLabel;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -250,8 +369,7 @@ public final class CommunicationArtifactViewerHelper {
|
|||||||
* @param constraints Constrains to use.
|
* @param constraints Constrains to use.
|
||||||
* @param accountIdentifier Account identifier to search the persona.
|
* @param accountIdentifier Account identifier to search the persona.
|
||||||
*
|
*
|
||||||
* @return Optional PersonaSearchAndDisplayTask started to search for
|
* @return List of AccountPersonaSearcherData objects.
|
||||||
* persona.
|
|
||||||
*/
|
*/
|
||||||
@NbBundle.Messages({
|
@NbBundle.Messages({
|
||||||
"CommunicationArtifactViewerHelper_persona_label=Persona: ",
|
"CommunicationArtifactViewerHelper_persona_label=Persona: ",
|
||||||
@ -260,17 +378,17 @@ public final class CommunicationArtifactViewerHelper {
|
|||||||
"CommunicationArtifactViewerHelper_persona_button_view=View",
|
"CommunicationArtifactViewerHelper_persona_button_view=View",
|
||||||
"CommunicationArtifactViewerHelper_persona_button_create=Create"
|
"CommunicationArtifactViewerHelper_persona_button_create=Create"
|
||||||
})
|
})
|
||||||
static Optional<PersonaSearchAndDisplayTask> addPersonaRow(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints, String accountIdentifier) {
|
|
||||||
|
static List<AccountPersonaSearcherData> addPersonaRow(JPanel panel, GridBagLayout gridbagLayout, GridBagConstraints constraints, String accountIdentifier) {
|
||||||
PersonaSearchAndDisplayTask personaTask = null;
|
List<AccountPersonaSearcherData> dataList = new ArrayList<>();
|
||||||
|
|
||||||
constraints.gridy++;
|
constraints.gridy++;
|
||||||
constraints.gridx = 1;
|
constraints.gridx = 1;
|
||||||
|
|
||||||
Insets savedInsets = constraints.insets;
|
Insets savedInsets = constraints.insets;
|
||||||
|
|
||||||
// Indent in
|
// extra Indent in
|
||||||
constraints.insets = new java.awt.Insets(0, LEFT_INDENT, 0, 0);
|
constraints.insets = new java.awt.Insets(0, 2 * LEFT_INSET, 0, 0);
|
||||||
|
|
||||||
// create label
|
// create label
|
||||||
javax.swing.JLabel personaLabel = new javax.swing.JLabel();
|
javax.swing.JLabel personaLabel = new javax.swing.JLabel();
|
||||||
@ -293,23 +411,22 @@ public final class CommunicationArtifactViewerHelper {
|
|||||||
// Place a button as place holder. It will be enabled when persona is available.
|
// Place a button as place holder. It will be enabled when persona is available.
|
||||||
javax.swing.JButton personaButton = new javax.swing.JButton();
|
javax.swing.JButton personaButton = new javax.swing.JButton();
|
||||||
personaButton.setText(Bundle.CommunicationArtifactViewerHelper_persona_button_view());
|
personaButton.setText(Bundle.CommunicationArtifactViewerHelper_persona_button_view());
|
||||||
|
personaButton.setMargin(new Insets(0, 5, 0, 5));
|
||||||
personaButton.setEnabled(false);
|
personaButton.setEnabled(false);
|
||||||
|
|
||||||
|
|
||||||
gridbagLayout.setConstraints(personaButton, constraints);
|
gridbagLayout.setConstraints(personaButton, constraints);
|
||||||
panel.add(personaButton);
|
panel.add(personaButton);
|
||||||
|
|
||||||
if (CentralRepository.isEnabled()) {
|
if (CentralRepository.isEnabled()) {
|
||||||
// kick off a task to find the persona for this account
|
// kick off a task to find the persona for this account
|
||||||
personaTask = new PersonaSearchAndDisplayTask(panel, new AccountPersonaSearcherData(accountIdentifier, personaLabel, personaButton));
|
dataList.add(new AccountPersonaSearcherData(accountIdentifier, personaLabel, personaButton));
|
||||||
personaTask.execute();
|
|
||||||
} else {
|
} else {
|
||||||
personaLabel.setEnabled(false);
|
personaLabel.setEnabled(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
addLineEndGlue(panel, gridbagLayout, constraints);
|
addLineEndGlue(panel, gridbagLayout, constraints);
|
||||||
|
|
||||||
return Optional.ofNullable(personaTask);
|
return dataList;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -1,6 +1,9 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8" ?>
|
<?xml version="1.0" encoding="UTF-8" ?>
|
||||||
|
|
||||||
<Form version="1.5" maxVersion="1.9" type="org.netbeans.modules.form.forminfo.JPanelFormInfo">
|
<Form version="1.4" maxVersion="1.9" type="org.netbeans.modules.form.forminfo.JPanelFormInfo">
|
||||||
|
<Properties>
|
||||||
|
<Property name="toolTipText" type="java.lang.String" value="" noResource="true"/>
|
||||||
|
</Properties>
|
||||||
<AuxValues>
|
<AuxValues>
|
||||||
<AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="1"/>
|
<AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="1"/>
|
||||||
<AuxValue name="FormSettings_autoSetComponentName" type="java.lang.Boolean" value="false"/>
|
<AuxValue name="FormSettings_autoSetComponentName" type="java.lang.Boolean" value="false"/>
|
||||||
@ -11,217 +14,8 @@
|
|||||||
<AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/>
|
<AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/>
|
||||||
<AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/>
|
<AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/>
|
||||||
<AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/>
|
<AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/>
|
||||||
<AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,-57,0,0,2,31"/>
|
<AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/>
|
||||||
</AuxValues>
|
</AuxValues>
|
||||||
|
|
||||||
<Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/>
|
<Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/>
|
||||||
<SubComponents>
|
|
||||||
<Container class="javax.swing.JPanel" name="namePanel">
|
|
||||||
<Constraints>
|
|
||||||
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription">
|
|
||||||
<GridBagConstraints gridX="0" gridY="1" gridWidth="5" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="6" insetsLeft="19" insetsBottom="0" insetsRight="0" anchor="18" weightX="1.0" weightY="0.0"/>
|
|
||||||
</Constraint>
|
|
||||||
</Constraints>
|
|
||||||
|
|
||||||
<Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/>
|
|
||||||
<SubComponents>
|
|
||||||
<Component class="javax.swing.JLabel" name="contactNameLabel">
|
|
||||||
<Properties>
|
|
||||||
<Property name="font" type="java.awt.Font" editor="org.netbeans.modules.form.editors2.FontEditor">
|
|
||||||
<FontInfo relative="true">
|
|
||||||
<Font bold="true" component="contactNameLabel" italic="true" property="font" relativeSize="true" size="6"/>
|
|
||||||
</FontInfo>
|
|
||||||
</Property>
|
|
||||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/contentviewers/Bundle.properties" key="ContactArtifactViewer.contactNameLabel.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
|
||||||
</Property>
|
|
||||||
</Properties>
|
|
||||||
<Constraints>
|
|
||||||
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription">
|
|
||||||
<GridBagConstraints gridX="0" gridY="0" gridWidth="1" gridHeight="1" fill="2" ipadX="111" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="18" weightX="1.0" weightY="0.0"/>
|
|
||||||
</Constraint>
|
|
||||||
</Constraints>
|
|
||||||
</Component>
|
|
||||||
</SubComponents>
|
|
||||||
</Container>
|
|
||||||
<Component class="javax.swing.JLabel" name="phonesLabel">
|
|
||||||
<Properties>
|
|
||||||
<Property name="font" type="java.awt.Font" editor="org.netbeans.modules.form.editors2.FontEditor">
|
|
||||||
<FontInfo relative="true">
|
|
||||||
<Font bold="true" component="phonesLabel" property="font" relativeSize="true" size="2"/>
|
|
||||||
</FontInfo>
|
|
||||||
</Property>
|
|
||||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/contentviewers/Bundle.properties" key="ContactArtifactViewer.phonesLabel.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
|
||||||
</Property>
|
|
||||||
</Properties>
|
|
||||||
<Constraints>
|
|
||||||
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription">
|
|
||||||
<GridBagConstraints gridX="0" gridY="2" gridWidth="3" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="6" insetsLeft="19" insetsBottom="0" insetsRight="0" anchor="18" weightX="0.0" weightY="0.0"/>
|
|
||||||
</Constraint>
|
|
||||||
</Constraints>
|
|
||||||
</Component>
|
|
||||||
<Container class="javax.swing.JPanel" name="phoneNumbersPanel">
|
|
||||||
<Constraints>
|
|
||||||
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription">
|
|
||||||
<GridBagConstraints gridX="0" gridY="3" gridWidth="4" gridHeight="1" fill="3" ipadX="0" ipadY="0" insetsTop="6" insetsLeft="19" insetsBottom="0" insetsRight="0" anchor="18" weightX="0.0" weightY="0.0"/>
|
|
||||||
</Constraint>
|
|
||||||
</Constraints>
|
|
||||||
|
|
||||||
<Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/>
|
|
||||||
</Container>
|
|
||||||
<Component class="javax.swing.JLabel" name="emailsLabel">
|
|
||||||
<Properties>
|
|
||||||
<Property name="font" type="java.awt.Font" editor="org.netbeans.modules.form.editors2.FontEditor">
|
|
||||||
<FontInfo relative="true">
|
|
||||||
<Font bold="true" component="emailsLabel" property="font" relativeSize="true" size="2"/>
|
|
||||||
</FontInfo>
|
|
||||||
</Property>
|
|
||||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/contentviewers/Bundle.properties" key="ContactArtifactViewer.emailsLabel.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
|
||||||
</Property>
|
|
||||||
</Properties>
|
|
||||||
<Constraints>
|
|
||||||
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription">
|
|
||||||
<GridBagConstraints gridX="0" gridY="4" gridWidth="2" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="6" insetsLeft="19" insetsBottom="0" insetsRight="0" anchor="18" weightX="0.0" weightY="0.0"/>
|
|
||||||
</Constraint>
|
|
||||||
</Constraints>
|
|
||||||
</Component>
|
|
||||||
<Container class="javax.swing.JPanel" name="emailsPanel">
|
|
||||||
<Constraints>
|
|
||||||
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription">
|
|
||||||
<GridBagConstraints gridX="0" gridY="5" gridWidth="4" gridHeight="1" fill="3" ipadX="0" ipadY="0" insetsTop="6" insetsLeft="19" insetsBottom="0" insetsRight="0" anchor="18" weightX="0.0" weightY="0.0"/>
|
|
||||||
</Constraint>
|
|
||||||
</Constraints>
|
|
||||||
|
|
||||||
<Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/>
|
|
||||||
</Container>
|
|
||||||
<Component class="javax.swing.JLabel" name="othersLabel">
|
|
||||||
<Properties>
|
|
||||||
<Property name="font" type="java.awt.Font" editor="org.netbeans.modules.form.editors2.FontEditor">
|
|
||||||
<FontInfo relative="true">
|
|
||||||
<Font bold="true" component="othersLabel" property="font" relativeSize="true" size="2"/>
|
|
||||||
</FontInfo>
|
|
||||||
</Property>
|
|
||||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/contentviewers/Bundle.properties" key="ContactArtifactViewer.othersLabel.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
|
||||||
</Property>
|
|
||||||
</Properties>
|
|
||||||
<Constraints>
|
|
||||||
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription">
|
|
||||||
<GridBagConstraints gridX="0" gridY="6" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="6" insetsLeft="19" insetsBottom="0" insetsRight="0" anchor="18" weightX="0.0" weightY="0.0"/>
|
|
||||||
</Constraint>
|
|
||||||
</Constraints>
|
|
||||||
</Component>
|
|
||||||
<Container class="javax.swing.JPanel" name="otherAttrsPanel">
|
|
||||||
<Constraints>
|
|
||||||
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription">
|
|
||||||
<GridBagConstraints gridX="0" gridY="7" gridWidth="4" gridHeight="1" fill="3" ipadX="0" ipadY="0" insetsTop="6" insetsLeft="19" insetsBottom="0" insetsRight="0" anchor="18" weightX="0.0" weightY="0.0"/>
|
|
||||||
</Constraint>
|
|
||||||
</Constraints>
|
|
||||||
|
|
||||||
<Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/>
|
|
||||||
</Container>
|
|
||||||
<Component class="javax.swing.Box$Filler" name="interPanelfiller">
|
|
||||||
<Properties>
|
|
||||||
<Property name="maximumSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
|
|
||||||
<Dimension value="[0, 32767]"/>
|
|
||||||
</Property>
|
|
||||||
</Properties>
|
|
||||||
<AuxValues>
|
|
||||||
<AuxValue name="JavaCodeGenerator_VariableLocal" type="java.lang.Boolean" value="true"/>
|
|
||||||
<AuxValue name="JavaCodeGenerator_VariableModifier" type="java.lang.Integer" value="0"/>
|
|
||||||
<AuxValue name="classDetails" type="java.lang.String" value="Box.Filler.VerticalGlue"/>
|
|
||||||
</AuxValues>
|
|
||||||
<Constraints>
|
|
||||||
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription">
|
|
||||||
<GridBagConstraints gridX="0" gridY="8" gridWidth="1" gridHeight="2" fill="3" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.1"/>
|
|
||||||
</Constraint>
|
|
||||||
</Constraints>
|
|
||||||
</Component>
|
|
||||||
<Component class="javax.swing.JLabel" name="personasLabel">
|
|
||||||
<Properties>
|
|
||||||
<Property name="font" type="java.awt.Font" editor="org.netbeans.modules.form.editors2.FontEditor">
|
|
||||||
<FontInfo relative="true">
|
|
||||||
<Font bold="true" component="personasLabel" property="font" relativeSize="true" size="2"/>
|
|
||||||
</FontInfo>
|
|
||||||
</Property>
|
|
||||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/contentviewers/Bundle.properties" key="ContactArtifactViewer.personasLabel.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
|
||||||
</Property>
|
|
||||||
<Property name="maximumSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
|
|
||||||
<Dimension value="[90, 19]"/>
|
|
||||||
</Property>
|
|
||||||
<Property name="minimumSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
|
|
||||||
<Dimension value="[90, 19]"/>
|
|
||||||
</Property>
|
|
||||||
<Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
|
|
||||||
<Dimension value="[90, 19]"/>
|
|
||||||
</Property>
|
|
||||||
</Properties>
|
|
||||||
<Constraints>
|
|
||||||
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription">
|
|
||||||
<GridBagConstraints gridX="0" gridY="9" gridWidth="3" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="6" insetsLeft="19" insetsBottom="0" insetsRight="0" anchor="18" weightX="0.0" weightY="0.0"/>
|
|
||||||
</Constraint>
|
|
||||||
</Constraints>
|
|
||||||
</Component>
|
|
||||||
<Container class="javax.swing.JPanel" name="personasPanel">
|
|
||||||
<Constraints>
|
|
||||||
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription">
|
|
||||||
<GridBagConstraints gridX="0" gridY="10" gridWidth="4" gridHeight="1" fill="3" ipadX="0" ipadY="0" insetsTop="6" insetsLeft="19" insetsBottom="0" insetsRight="0" anchor="18" weightX="0.0" weightY="0.0"/>
|
|
||||||
</Constraint>
|
|
||||||
</Constraints>
|
|
||||||
|
|
||||||
<Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/>
|
|
||||||
</Container>
|
|
||||||
<Component class="javax.swing.Box$Filler" name="bottomFiller">
|
|
||||||
<Properties>
|
|
||||||
<Property name="maximumSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
|
|
||||||
<Dimension value="[0, 32767]"/>
|
|
||||||
</Property>
|
|
||||||
</Properties>
|
|
||||||
<AuxValues>
|
|
||||||
<AuxValue name="JavaCodeGenerator_VariableLocal" type="java.lang.Boolean" value="true"/>
|
|
||||||
<AuxValue name="JavaCodeGenerator_VariableModifier" type="java.lang.Integer" value="0"/>
|
|
||||||
<AuxValue name="classDetails" type="java.lang.String" value="Box.Filler.VerticalGlue"/>
|
|
||||||
</AuxValues>
|
|
||||||
<Constraints>
|
|
||||||
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription">
|
|
||||||
<GridBagConstraints gridX="0" gridY="11" gridWidth="4" gridHeight="1" fill="1" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="1.0"/>
|
|
||||||
</Constraint>
|
|
||||||
</Constraints>
|
|
||||||
</Component>
|
|
||||||
<Component class="javax.swing.Box$Filler" name="rightFiller">
|
|
||||||
<Properties>
|
|
||||||
<Property name="maximumSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
|
|
||||||
<Dimension value="[32767, 0]"/>
|
|
||||||
</Property>
|
|
||||||
</Properties>
|
|
||||||
<AuxValues>
|
|
||||||
<AuxValue name="JavaCodeGenerator_VariableLocal" type="java.lang.Boolean" value="true"/>
|
|
||||||
<AuxValue name="JavaCodeGenerator_VariableModifier" type="java.lang.Integer" value="0"/>
|
|
||||||
<AuxValue name="classDetails" type="java.lang.String" value="Box.Filler.HorizontalGlue"/>
|
|
||||||
</AuxValues>
|
|
||||||
<Constraints>
|
|
||||||
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription">
|
|
||||||
<GridBagConstraints gridX="4" gridY="3" gridWidth="1" gridHeight="8" fill="1" ipadX="2" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="1.0" weightY="0.0"/>
|
|
||||||
</Constraint>
|
|
||||||
</Constraints>
|
|
||||||
</Component>
|
|
||||||
<Component class="javax.swing.JLabel" name="contactImage">
|
|
||||||
<Properties>
|
|
||||||
<Property name="icon" type="javax.swing.Icon" editor="org.netbeans.modules.form.editors2.IconEditor">
|
|
||||||
<Image iconType="3" name="/org/sleuthkit/autopsy/images/defaultContact.png"/>
|
|
||||||
</Property>
|
|
||||||
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
|
||||||
<ResourceString bundle="org/sleuthkit/autopsy/contentviewers/Bundle.properties" key="ContactArtifactViewer.contactImage.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
|
||||||
</Property>
|
|
||||||
</Properties>
|
|
||||||
<Constraints>
|
|
||||||
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription">
|
|
||||||
<GridBagConstraints gridX="0" gridY="0" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="6" insetsLeft="19" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/>
|
|
||||||
</Constraint>
|
|
||||||
</Constraints>
|
|
||||||
</Component>
|
|
||||||
</SubComponents>
|
|
||||||
</Form>
|
</Form>
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -1,4 +1,4 @@
|
|||||||
/**
|
/*
|
||||||
* Autopsy Forensic Browser
|
* Autopsy Forensic Browser
|
||||||
*
|
*
|
||||||
* Copyright 2020 Basis Technology Corp.
|
* Copyright 2020 Basis Technology Corp.
|
||||||
@ -22,116 +22,138 @@ import java.awt.Component;
|
|||||||
import java.awt.event.ActionListener;
|
import java.awt.event.ActionListener;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
import java.util.concurrent.CancellationException;
|
import java.util.concurrent.CancellationException;
|
||||||
import java.util.concurrent.ExecutionException;
|
import java.util.concurrent.ExecutionException;
|
||||||
import java.util.logging.Level;
|
import java.util.logging.Level;
|
||||||
import java.util.stream.Collectors;
|
|
||||||
import javax.swing.JButton;
|
import javax.swing.JButton;
|
||||||
import javax.swing.SwingWorker;
|
import javax.swing.SwingWorker;
|
||||||
import org.openide.util.NbBundle;
|
import org.sleuthkit.autopsy.casemodule.Case;
|
||||||
import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepoAccount;
|
|
||||||
import org.sleuthkit.autopsy.centralrepository.datamodel.CentralRepository;
|
|
||||||
import org.sleuthkit.autopsy.centralrepository.datamodel.Persona;
|
import org.sleuthkit.autopsy.centralrepository.datamodel.Persona;
|
||||||
import org.sleuthkit.autopsy.centralrepository.datamodel.PersonaAccount;
|
import org.sleuthkit.autopsy.centralrepository.datamodel.PersonaAccount;
|
||||||
import org.sleuthkit.autopsy.centralrepository.persona.PersonaDetailsDialog;
|
import org.sleuthkit.autopsy.centralrepository.persona.PersonaDetailsDialog;
|
||||||
import org.sleuthkit.autopsy.centralrepository.persona.PersonaDetailsDialogCallback;
|
import org.sleuthkit.autopsy.centralrepository.persona.PersonaDetailsDialogCallback;
|
||||||
import org.sleuthkit.autopsy.centralrepository.persona.PersonaDetailsMode;
|
import org.sleuthkit.autopsy.centralrepository.persona.PersonaDetailsMode;
|
||||||
import org.sleuthkit.autopsy.coreutils.Logger;
|
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||||
|
import org.sleuthkit.datamodel.Account;
|
||||||
|
import org.sleuthkit.datamodel.BlackboardArtifact;
|
||||||
|
import org.sleuthkit.datamodel.CommunicationsManager;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Background task to search for a persona for a given account.
|
* SwingWorker for fetching and updating Persona controls.
|
||||||
*
|
*/
|
||||||
* When the search is complete, it updates the UI components
|
class PersonaAccountFetcher extends SwingWorker<Map<String, Collection<Persona>>, Void> {
|
||||||
* for the persona appropriately.
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
@NbBundle.Messages({
|
private final static Logger logger = Logger.getLogger(PersonaAccountFetcher.class.getName());
|
||||||
"# {0} - Persona count",
|
|
||||||
"PersonaDisplayTask_persona_count_suffix=(1 of {0})"
|
|
||||||
})
|
|
||||||
class PersonaSearchAndDisplayTask extends SwingWorker<Collection<Persona>, Void> {
|
|
||||||
|
|
||||||
private final static Logger logger = Logger.getLogger(PersonaSearchAndDisplayTask.class.getName());
|
private final BlackboardArtifact artifact;
|
||||||
|
private final List<AccountPersonaSearcherData> personaSearchDataList;
|
||||||
private final Component parentComponent;
|
private final Component parentComponent;
|
||||||
private final AccountPersonaSearcherData personaSearcherData;
|
|
||||||
|
|
||||||
PersonaSearchAndDisplayTask(Component parentComponent, AccountPersonaSearcherData personaSearcherData) {
|
/**
|
||||||
this.parentComponent = parentComponent;
|
* Construct the SwingWorker.
|
||||||
this.personaSearcherData = personaSearcherData;
|
*
|
||||||
}
|
* @param artifact The artifact to search account for.
|
||||||
|
* @param personaSearchDataList List of PersonaSerarcherData objects.
|
||||||
|
* @param parentComponent The parent panel.
|
||||||
|
*/
|
||||||
|
PersonaAccountFetcher(BlackboardArtifact artifact, List<AccountPersonaSearcherData> personaSearchDataList, Component parentComponent) {
|
||||||
|
this.artifact = artifact;
|
||||||
|
this.personaSearchDataList = personaSearchDataList;
|
||||||
|
this.parentComponent = parentComponent;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected Collection<Persona> doInBackground() throws Exception {
|
protected Map<String, Collection<Persona>> doInBackground() throws Exception {
|
||||||
|
Map<String, Collection<Persona>> accountMap = new HashMap<>();
|
||||||
|
|
||||||
Collection<Persona> personas = new ArrayList<>();
|
CommunicationsManager commManager = Case.getCurrentCase().getSleuthkitCase().getCommunicationsManager();
|
||||||
|
|
||||||
if (CentralRepository.isEnabled()) {
|
List<Account> relatedAccountList = commManager.getAccountsRelatedToArtifact(artifact);
|
||||||
Collection<CentralRepoAccount> accountCandidates
|
|
||||||
= CentralRepoAccount.getAccountsWithIdentifier(personaSearcherData.getAccountIdentifer());
|
|
||||||
|
|
||||||
if (accountCandidates.isEmpty() == false) {
|
for (Account account : relatedAccountList) {
|
||||||
CentralRepoAccount account = accountCandidates.iterator().next();
|
|
||||||
|
|
||||||
// get personas for the account
|
if (isCancelled()) {
|
||||||
Collection<PersonaAccount> personaAccountsList = PersonaAccount.getPersonaAccountsForAccount(account.getId());
|
return new HashMap<>();
|
||||||
personas = personaAccountsList.stream().map(PersonaAccount::getPersona)
|
|
||||||
.collect(Collectors.toList());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return personas;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void done() {
|
|
||||||
Collection<Persona> personas;
|
|
||||||
try {
|
|
||||||
personas = super.get();
|
|
||||||
|
|
||||||
if (this.isCancelled()) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
//Update the Persona label and button based on the search result
|
|
||||||
String personaLabelText = Bundle.CommunicationArtifactViewerHelper_persona_label();
|
|
||||||
String personaButtonText;
|
|
||||||
ActionListener buttonActionListener;
|
|
||||||
|
|
||||||
if (personas.isEmpty()) {
|
|
||||||
// No persona found
|
|
||||||
personaLabelText += Bundle.CommunicationArtifactViewerHelper_persona_unknown();
|
|
||||||
|
|
||||||
// show a 'Create' button
|
|
||||||
personaButtonText = Bundle.CommunicationArtifactViewerHelper_persona_button_create();
|
|
||||||
buttonActionListener = new CreatePersonaButtonListener(parentComponent, personaSearcherData);
|
|
||||||
} else {
|
|
||||||
Persona persona = personas.iterator().next();
|
|
||||||
personaLabelText += persona.getName();
|
|
||||||
if (personas.size() > 1) {
|
|
||||||
personaLabelText += Bundle.PersonaDisplayTask_persona_count_suffix(Integer.toString(personas.size()));
|
|
||||||
}
|
|
||||||
// Show a 'View' button
|
|
||||||
personaButtonText = Bundle.CommunicationArtifactViewerHelper_persona_button_view();
|
|
||||||
buttonActionListener = new ViewPersonaButtonListener(parentComponent, persona);
|
|
||||||
}
|
|
||||||
|
|
||||||
personaSearcherData.getPersonaNameLabel().setText(personaLabelText);
|
|
||||||
personaSearcherData.getPersonaActionButton().setText(personaButtonText);
|
|
||||||
personaSearcherData.getPersonaActionButton().setEnabled(true);
|
|
||||||
|
|
||||||
// set button action
|
|
||||||
personaSearcherData.getPersonaActionButton().addActionListener(buttonActionListener);
|
|
||||||
} catch (CancellationException ex) {
|
|
||||||
logger.log(Level.INFO, "Persona searching was canceled."); //NON-NLS
|
|
||||||
} catch (InterruptedException ex) {
|
|
||||||
logger.log(Level.INFO, "Persona searching was interrupted."); //NON-NLS
|
|
||||||
} catch (ExecutionException ex) {
|
|
||||||
logger.log(Level.SEVERE, "Fatal error during Persona search.", ex); //NON-NLS
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Collection<PersonaAccount> personaAccountList = PersonaAccount.getPersonaAccountsForAccount(account);
|
||||||
|
Collection<Persona> personaList = new ArrayList<>();
|
||||||
|
for (PersonaAccount pAccount : personaAccountList) {
|
||||||
|
personaList.add(pAccount.getPersona());
|
||||||
|
}
|
||||||
|
|
||||||
|
accountMap.put(account.getTypeSpecificID(), personaList);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return accountMap;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void done() {
|
||||||
|
if (isCancelled()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
Map<String, Collection<Persona>> accountMap = get();
|
||||||
|
|
||||||
|
for (AccountPersonaSearcherData searcherData : personaSearchDataList) {
|
||||||
|
Collection<Persona> persona = accountMap.get(searcherData.getAccountIdentifer());
|
||||||
|
updatePersonaControls(searcherData, persona);
|
||||||
|
}
|
||||||
|
|
||||||
|
} catch (CancellationException ex) {
|
||||||
|
logger.log(Level.INFO, "Persona searching was canceled."); //NON-NLS
|
||||||
|
} catch (InterruptedException ex) {
|
||||||
|
logger.log(Level.INFO, "Persona searching was interrupted."); //NON-NLS
|
||||||
|
} catch (ExecutionException ex) {
|
||||||
|
logger.log(Level.SEVERE, "Fatal error during Persona search.", ex); //NON-NLS
|
||||||
|
}
|
||||||
|
|
||||||
|
parentComponent.repaint();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update the Persona gui controls.
|
||||||
|
*
|
||||||
|
* @param personaSearcherData The data objects with persona controls
|
||||||
|
* @param personas Collection of persona objects
|
||||||
|
*/
|
||||||
|
private void updatePersonaControls(AccountPersonaSearcherData personaSearcherData, Collection<Persona> personas) {
|
||||||
|
//Update the Persona label and button based on the search result
|
||||||
|
String personaLabelText = Bundle.CommunicationArtifactViewerHelper_persona_label();
|
||||||
|
String personaButtonText;
|
||||||
|
ActionListener buttonActionListener;
|
||||||
|
|
||||||
|
if (personas == null || personas.isEmpty()) {
|
||||||
|
// No persona found
|
||||||
|
personaLabelText += Bundle.CommunicationArtifactViewerHelper_persona_unknown();
|
||||||
|
|
||||||
|
// show a 'Create' button
|
||||||
|
personaButtonText = Bundle.CommunicationArtifactViewerHelper_persona_button_create();
|
||||||
|
buttonActionListener = new CreatePersonaButtonListener(parentComponent, personaSearcherData);
|
||||||
|
} else {
|
||||||
|
Persona persona = personas.iterator().next();
|
||||||
|
personaLabelText += persona.getName();
|
||||||
|
if (personas.size() > 1) {
|
||||||
|
personaLabelText += Bundle.PersonaDisplayTask_persona_count_suffix(Integer.toString(personas.size()));
|
||||||
|
}
|
||||||
|
// Show a 'View' button
|
||||||
|
personaButtonText = Bundle.CommunicationArtifactViewerHelper_persona_button_view();
|
||||||
|
buttonActionListener = new ViewPersonaButtonListener(parentComponent, persona);
|
||||||
|
}
|
||||||
|
|
||||||
|
personaSearcherData.getPersonaNameLabel().setText(personaLabelText);
|
||||||
|
personaSearcherData.getPersonaActionButton().setText(personaButtonText);
|
||||||
|
personaSearcherData.getPersonaActionButton().setEnabled(true);
|
||||||
|
|
||||||
|
// set button action
|
||||||
|
personaSearcherData.getPersonaActionButton().addActionListener(buttonActionListener);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Action listener for Create persona button.
|
* Action listener for Create persona button.
|
||||||
*/
|
*/
|
||||||
@ -177,7 +199,7 @@ class PersonaSearchAndDisplayTask extends SwingWorker<Collection<Persona>, Void>
|
|||||||
* Callback method for the create mode of the PersonaDetailsDialog
|
* Callback method for the create mode of the PersonaDetailsDialog
|
||||||
*/
|
*/
|
||||||
class PersonaCreateCallbackImpl implements PersonaDetailsDialogCallback {
|
class PersonaCreateCallbackImpl implements PersonaDetailsDialogCallback {
|
||||||
|
|
||||||
private final Component parentComponent;
|
private final Component parentComponent;
|
||||||
private final AccountPersonaSearcherData personaSearcherData;
|
private final AccountPersonaSearcherData personaSearcherData;
|
||||||
|
|
||||||
@ -217,4 +239,5 @@ class PersonaSearchAndDisplayTask extends SwingWorker<Collection<Persona>, Void>
|
|||||||
// nothing to do
|
// nothing to do
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
@ -290,6 +290,62 @@ public final class ContentUtils {
|
|||||||
return totalRead;
|
return totalRead;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Reads all the data from any content object and writes (extracts) it to a
|
||||||
|
* file, using a cancellation check instead of a Future object method.
|
||||||
|
*
|
||||||
|
* @param content Any content object.
|
||||||
|
* @param outputFile Will be created if it doesn't exist, and overwritten
|
||||||
|
* if it does
|
||||||
|
* @param cancelCheck A function used to check if the file write process
|
||||||
|
* should be terminated.
|
||||||
|
* @param startingOffset the starting offset to start reading the file
|
||||||
|
* @param endingOffset the ending offset to read of the file to write
|
||||||
|
*
|
||||||
|
* @return number of bytes extracted
|
||||||
|
*
|
||||||
|
* @throws IOException if file could not be written
|
||||||
|
*/
|
||||||
|
public static long writeToFile(Content content, java.io.File outputFile,
|
||||||
|
Supplier<Boolean> cancelCheck, long startingOffset, long endingOffset) throws IOException {
|
||||||
|
|
||||||
|
InputStream in = new ReadContentInputStream(content);
|
||||||
|
long totalRead = 0;
|
||||||
|
try (FileOutputStream out = new FileOutputStream(outputFile, false)) {
|
||||||
|
long offsetSkipped = in.skip(startingOffset);
|
||||||
|
if (offsetSkipped != startingOffset) {
|
||||||
|
in.close();
|
||||||
|
throw new IOException(String.format("Skipping file to starting offset {0} was not successful only skipped to offset {1}.", startingOffset, offsetSkipped));
|
||||||
|
}
|
||||||
|
byte[] buffer = new byte[TO_FILE_BUFFER_SIZE];
|
||||||
|
int len = in.read(buffer);
|
||||||
|
long writeFileLength = endingOffset - startingOffset;
|
||||||
|
writeFileLength = writeFileLength - TO_FILE_BUFFER_SIZE;
|
||||||
|
while (len != -1 && writeFileLength != 0) {
|
||||||
|
out.write(buffer, 0, len);
|
||||||
|
totalRead += len;
|
||||||
|
if (cancelCheck.get()) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (writeFileLength > TO_FILE_BUFFER_SIZE) {
|
||||||
|
len = in.read(buffer);
|
||||||
|
writeFileLength = writeFileLength - TO_FILE_BUFFER_SIZE;
|
||||||
|
} else {
|
||||||
|
int writeLength = (int)writeFileLength;
|
||||||
|
byte[] lastBuffer = new byte[writeLength];
|
||||||
|
len = in.read(lastBuffer);
|
||||||
|
out.write(lastBuffer, 0, len);
|
||||||
|
totalRead += len;
|
||||||
|
writeFileLength = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
} finally {
|
||||||
|
in.close();
|
||||||
|
}
|
||||||
|
return totalRead;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Helper to ignore the '.' and '..' directories
|
* Helper to ignore the '.' and '..' directories
|
||||||
*
|
*
|
||||||
|
@ -777,10 +777,6 @@ public class TimeLineController {
|
|||||||
case CONTENT_TAG_DELETED:
|
case CONTENT_TAG_DELETED:
|
||||||
future = executor.submit(() -> filteredEvents.handleContentTagDeleted((ContentTagDeletedEvent) evt));
|
future = executor.submit(() -> filteredEvents.handleContentTagDeleted((ContentTagDeletedEvent) evt));
|
||||||
break;
|
break;
|
||||||
case CURRENT_CASE:
|
|
||||||
//close timeline on case changes.
|
|
||||||
SwingUtilities.invokeLater(TimeLineController.this::shutDownTimeLine);
|
|
||||||
break;
|
|
||||||
case DATA_SOURCE_ADDED:
|
case DATA_SOURCE_ADDED:
|
||||||
future = executor.submit(() -> {
|
future = executor.submit(() -> {
|
||||||
filteredEvents.handleDataSourceAdded();
|
filteredEvents.handleDataSourceAdded();
|
||||||
|
@ -86,19 +86,13 @@ public class TimeLineModule {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void propertyChange(PropertyChangeEvent evt) {
|
public void propertyChange(PropertyChangeEvent evt) {
|
||||||
try {
|
|
||||||
getController().handleCaseEvent(evt);
|
|
||||||
} catch (NoCurrentCaseException ex) {
|
|
||||||
// ignore
|
|
||||||
return;
|
|
||||||
} catch (TskCoreException ex) {
|
|
||||||
MessageNotifyUtil.Message.error("Error creating timeline controller.");
|
|
||||||
logger.log(Level.SEVERE, "Error creating timeline controller", ex);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (Case.Events.valueOf(evt.getPropertyName()).equals(CURRENT_CASE)) {
|
if (Case.Events.valueOf(evt.getPropertyName()).equals(CURRENT_CASE)) {
|
||||||
// we care only about case closing here
|
|
||||||
if (evt.getNewValue() == null) {
|
if (evt.getNewValue() == null) {
|
||||||
|
/*
|
||||||
|
* Current case is closing, shut down the timeline top
|
||||||
|
* component and set the pre case singleton controller
|
||||||
|
* reference to null.
|
||||||
|
*/
|
||||||
synchronized (controllerLock) {
|
synchronized (controllerLock) {
|
||||||
if (controller != null) {
|
if (controller != null) {
|
||||||
SwingUtilities.invokeLater(controller::shutDownTimeLine);
|
SwingUtilities.invokeLater(controller::shutDownTimeLine);
|
||||||
@ -106,6 +100,13 @@ public class TimeLineModule {
|
|||||||
controller = null;
|
controller = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
try {
|
||||||
|
getController().handleCaseEvent(evt);
|
||||||
|
} catch (NoCurrentCaseException ignored) {
|
||||||
|
} catch (TskCoreException ex) {
|
||||||
|
logger.log(Level.SEVERE, "Error handling application event", ex);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -55,6 +55,7 @@ ExtractOs.windowsVolume.label=OS Drive (Windows)
|
|||||||
ExtractOs.yellowDogLinuxOs.label=Linux (Yellow Dog)
|
ExtractOs.yellowDogLinuxOs.label=Linux (Yellow Dog)
|
||||||
ExtractOs.yellowDogLinuxVolume.label=OS Drive (Linux Yellow Dog)
|
ExtractOs.yellowDogLinuxVolume.label=OS Drive (Linux Yellow Dog)
|
||||||
ExtractOS_progressMessage=Checking for OS
|
ExtractOS_progressMessage=Checking for OS
|
||||||
|
ExtractPrefetch_module_name=Windows Prefetch Extractor
|
||||||
ExtractRecycleBin_module_name=Recycle Bin
|
ExtractRecycleBin_module_name=Recycle Bin
|
||||||
ExtractSafari_Error_Getting_History=An error occurred while processing Safari history files.
|
ExtractSafari_Error_Getting_History=An error occurred while processing Safari history files.
|
||||||
ExtractSafari_Error_Parsing_Bookmark=An error occured while processing Safari Bookmark files
|
ExtractSafari_Error_Parsing_Bookmark=An error occured while processing Safari Bookmark files
|
||||||
|
@ -0,0 +1,388 @@
|
|||||||
|
/*
|
||||||
|
*
|
||||||
|
* Autopsy Forensic Browser
|
||||||
|
*
|
||||||
|
* Copyright 2020 Basis Technology Corp.
|
||||||
|
*
|
||||||
|
*
|
||||||
|
* 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.recentactivity;
|
||||||
|
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.FileNotFoundException;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.nio.file.Path;
|
||||||
|
import java.nio.file.Paths;
|
||||||
|
import java.sql.ResultSet;
|
||||||
|
import java.sql.SQLException;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.Arrays;
|
||||||
|
import java.util.Collection;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.logging.Level;
|
||||||
|
import org.openide.modules.InstalledFileLocator;
|
||||||
|
import org.openide.util.NbBundle.Messages;
|
||||||
|
import org.sleuthkit.autopsy.casemodule.Case;
|
||||||
|
import org.sleuthkit.autopsy.casemodule.services.FileManager;
|
||||||
|
import org.sleuthkit.autopsy.coreutils.ExecUtil;
|
||||||
|
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||||
|
import org.sleuthkit.autopsy.coreutils.PlatformUtil;
|
||||||
|
import org.sleuthkit.autopsy.coreutils.SQLiteDBConnect;
|
||||||
|
import org.sleuthkit.autopsy.datamodel.ContentUtils;
|
||||||
|
import org.sleuthkit.autopsy.ingest.DataSourceIngestModuleProcessTerminator;
|
||||||
|
import org.sleuthkit.autopsy.ingest.DataSourceIngestModuleProgress;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestJobContext;
|
||||||
|
import org.sleuthkit.datamodel.AbstractFile;
|
||||||
|
import org.sleuthkit.datamodel.Blackboard;
|
||||||
|
import org.sleuthkit.datamodel.BlackboardArtifact;
|
||||||
|
import static org.sleuthkit.datamodel.BlackboardArtifact.ARTIFACT_TYPE.TSK_ASSOCIATED_OBJECT;
|
||||||
|
import org.sleuthkit.datamodel.BlackboardAttribute;
|
||||||
|
import static org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE.TSK_ASSOCIATED_ARTIFACT;
|
||||||
|
import org.sleuthkit.datamodel.Content;
|
||||||
|
import org.sleuthkit.datamodel.TskCoreException;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Extract the Prefetch Files and process them thru an External program. The data will then be added to the
|
||||||
|
* TSK_PROG_RUN artifact. Associated artifacts will be created if possible.
|
||||||
|
*/
|
||||||
|
final class ExtractPrefetch extends Extract {
|
||||||
|
|
||||||
|
private static final Logger logger = Logger.getLogger(ExtractPrefetch.class.getName());
|
||||||
|
|
||||||
|
private IngestJobContext context;
|
||||||
|
|
||||||
|
|
||||||
|
private static final String MODULE_NAME = "extractPREFETCH"; //NON-NLS
|
||||||
|
|
||||||
|
private static final String PREFETCH_TSK_COMMENT = "Prefetch File";
|
||||||
|
private static final String PREFETCH_FILE_LOCATION = "/Windows/Prefetch";
|
||||||
|
private static final String PREFETCH_TOOL_FOLDER = "markmckinnon"; //NON-NLS
|
||||||
|
private static final String PREFETCH_TOOL_NAME_WINDOWS_64 = "parse_prefetch_x64.exe"; //NON-NLS
|
||||||
|
private static final String PREFETCH_TOOL_NAME_WINDOWS_32 = "parse_prefetch_x32.exe"; //NON-NLS
|
||||||
|
private static final String PREFETCH_TOOL_NAME_MACOS = "parse_prefetch_macos"; //NON-NLS
|
||||||
|
private static final String PREFETCH_TOOL_NAME_LINUX = "parse_prefetch_linux"; //NON-NLS
|
||||||
|
private static final String PREFETCH_OUTPUT_FILE_NAME = "Output.txt"; //NON-NLS
|
||||||
|
private static final String PREFETCH_ERROR_FILE_NAME = "Error.txt"; //NON-NLS
|
||||||
|
private static final String PREFETCH_PARSER_DB_FILE = "Autopsy_PF_DB.db3"; //NON-NLS
|
||||||
|
private static final String PREFETCH_DIR_NAME = "prefetch"; //NON-NLS
|
||||||
|
|
||||||
|
@Messages({
|
||||||
|
"ExtractPrefetch_module_name=Windows Prefetch Extractor"
|
||||||
|
})
|
||||||
|
ExtractPrefetch() {
|
||||||
|
this.moduleName = Bundle.ExtractPrefetch_module_name();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
void process(Content dataSource, IngestJobContext context, DataSourceIngestModuleProgress progressBar) {
|
||||||
|
|
||||||
|
this.context = context;
|
||||||
|
|
||||||
|
String modOutPath = Case.getCurrentCase().getModuleDirectory() + File.separator + PREFETCH_DIR_NAME;
|
||||||
|
File dir = new File(modOutPath);
|
||||||
|
if (dir.exists() == false) {
|
||||||
|
boolean dirMade = dir.mkdirs();
|
||||||
|
if (!dirMade) {
|
||||||
|
logger.log(Level.SEVERE, "Error creating directory to store prefetch output database"); //NON-NLS
|
||||||
|
return; //If we cannot create the directory then we need to exit
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
extractPrefetchFiles(dataSource);
|
||||||
|
|
||||||
|
final String prefetchDumper = getPathForPrefetchDumper();
|
||||||
|
if (prefetchDumper == null) {
|
||||||
|
logger.log(Level.SEVERE, "Error finding parse_prefetch program"); //NON-NLS
|
||||||
|
return; //If we cannot find the parse_prefetch program we cannot proceed
|
||||||
|
}
|
||||||
|
|
||||||
|
if (context.dataSourceIngestIsCancelled()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
String modOutFile = modOutPath + File.separator + PREFETCH_PARSER_DB_FILE;
|
||||||
|
try {
|
||||||
|
String tempDirPath = RAImageIngestModule.getRATempPath(Case.getCurrentCase(), PREFETCH_DIR_NAME );
|
||||||
|
parsePrefetchFiles(prefetchDumper, tempDirPath, modOutFile, modOutPath);
|
||||||
|
createAppExecArtifacts(modOutFile, dataSource);
|
||||||
|
} catch (IOException ex) {
|
||||||
|
logger.log(Level.WARNING, "Error runing parse_prefetch or creating artifacts.", ex); //NON-NLS
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Extract prefetch file to temp directory to process. Checks to make sure that the prefetch files only
|
||||||
|
* come from the /Windows/Prefetch directory
|
||||||
|
*
|
||||||
|
* @param dataSource - datasource to search for prefetch files
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
void extractPrefetchFiles(Content dataSource) {
|
||||||
|
List<AbstractFile> pFiles;
|
||||||
|
|
||||||
|
FileManager fileManager = Case.getCurrentCase().getServices().getFileManager();
|
||||||
|
|
||||||
|
try {
|
||||||
|
pFiles = fileManager.findFiles(dataSource, "%.pf"); //NON-NLS
|
||||||
|
} catch (TskCoreException ex) {
|
||||||
|
logger.log(Level.WARNING, "Unable to find prefetch files.", ex); //NON-NLS
|
||||||
|
return; // No need to continue
|
||||||
|
}
|
||||||
|
|
||||||
|
for (AbstractFile pFile : pFiles) {
|
||||||
|
|
||||||
|
if (context.dataSourceIngestIsCancelled()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
String prefetchFile = RAImageIngestModule.getRATempPath(Case.getCurrentCase(), PREFETCH_DIR_NAME) + File.separator + pFile.getName();
|
||||||
|
if (pFile.getParentPath().contains(PREFETCH_FILE_LOCATION)) {
|
||||||
|
try {
|
||||||
|
ContentUtils.writeToFile(pFile, new File(prefetchFile));
|
||||||
|
} catch (IOException ex) {
|
||||||
|
logger.log(Level.WARNING, String.format("Unable to write %s to temp directory. File name: %s", pFile.getName(), prefetchFile), ex); //NON-NLS
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Run the export parse_prefetch program against the prefetch files
|
||||||
|
*
|
||||||
|
* @param prefetchExePath - Path to the Executable to run
|
||||||
|
* @param prefetchDir - Directory where the prefetch files reside to be processed.
|
||||||
|
* @param tempOutFile - Output database file name and path.
|
||||||
|
* @param tempOutPath - Directory to store the output and error files.
|
||||||
|
*
|
||||||
|
* @throws FileNotFoundException
|
||||||
|
* @throws IOException
|
||||||
|
*/
|
||||||
|
void parsePrefetchFiles(String prefetchExePath, String prefetchDir, String tempOutFile, String tempOutPath) throws FileNotFoundException, IOException {
|
||||||
|
final Path outputFilePath = Paths.get(tempOutPath, PREFETCH_OUTPUT_FILE_NAME);
|
||||||
|
final Path errFilePath = Paths.get(tempOutPath, PREFETCH_ERROR_FILE_NAME);
|
||||||
|
|
||||||
|
List<String> commandLine = new ArrayList<>();
|
||||||
|
commandLine.add(prefetchExePath);
|
||||||
|
commandLine.add(prefetchDir); //NON-NLS
|
||||||
|
commandLine.add(tempOutFile);
|
||||||
|
|
||||||
|
ProcessBuilder processBuilder = new ProcessBuilder(commandLine);
|
||||||
|
processBuilder.redirectOutput(outputFilePath.toFile());
|
||||||
|
processBuilder.redirectError(errFilePath.toFile());
|
||||||
|
|
||||||
|
ExecUtil.execute(processBuilder, new DataSourceIngestModuleProcessTerminator(context));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the path and executable for the parse_prefetch program. Checks for specific version of OS to
|
||||||
|
* get proper executable.
|
||||||
|
*
|
||||||
|
* @return - path and executable to run.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
private String getPathForPrefetchDumper() {
|
||||||
|
Path path = null;
|
||||||
|
if (PlatformUtil.isWindowsOS()) {
|
||||||
|
if (PlatformUtil.is64BitOS()) {
|
||||||
|
path = Paths.get(PREFETCH_TOOL_FOLDER, PREFETCH_TOOL_NAME_WINDOWS_64);
|
||||||
|
} else {
|
||||||
|
path = Paths.get(PREFETCH_TOOL_FOLDER, PREFETCH_TOOL_NAME_WINDOWS_32);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if ("Linux".equals(PlatformUtil.getOSName())) {
|
||||||
|
path = Paths.get(PREFETCH_TOOL_FOLDER, PREFETCH_TOOL_NAME_LINUX);
|
||||||
|
} else {
|
||||||
|
path = Paths.get(PREFETCH_TOOL_FOLDER, PREFETCH_TOOL_NAME_MACOS);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
File prefetchToolFile = InstalledFileLocator.getDefault().locate(path.toString(),
|
||||||
|
ExtractPrefetch.class.getPackage().getName(), false);
|
||||||
|
if (prefetchToolFile != null) {
|
||||||
|
return prefetchToolFile.getAbsolutePath();
|
||||||
|
}
|
||||||
|
|
||||||
|
return null;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the artifacts from external run of the parse_prefetch program
|
||||||
|
*
|
||||||
|
* @param prefetchDb - Database file to read from running the parse_prefetch program.
|
||||||
|
* @param dataSource - The datasource to search in
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
private void createAppExecArtifacts(String prefetchDb, Content dataSource) {
|
||||||
|
List<BlackboardArtifact> blkBrdArtList = new ArrayList<>();
|
||||||
|
|
||||||
|
String sqlStatement = "SELECT prefetch_File_Name, actual_File_Name, file_path, Number_time_file_run, Embeded_date_Time_Unix_1, " +
|
||||||
|
" Embeded_date_Time_Unix_2, Embeded_date_Time_Unix_3, Embeded_date_Time_Unix_4, Embeded_date_Time_Unix_5," +
|
||||||
|
" Embeded_date_Time_Unix_6, Embeded_date_Time_Unix_7, Embeded_date_Time_Unix_8 " +
|
||||||
|
" FROM prefetch_file_info;"; //NON-NLS
|
||||||
|
|
||||||
|
try (SQLiteDBConnect tempdbconnect = new SQLiteDBConnect("org.sqlite.JDBC", "jdbc:sqlite:" + prefetchDb); //NON-NLS
|
||||||
|
ResultSet resultSet = tempdbconnect.executeQry(sqlStatement)) {
|
||||||
|
|
||||||
|
while (resultSet.next()) {
|
||||||
|
|
||||||
|
if (context.dataSourceIngestIsCancelled()) {
|
||||||
|
logger.log(Level.INFO, "Cancelled Prefetch Artifact Creation."); //NON-NLS
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
String prefetchFileName = resultSet.getString("prefetch_File_Name");
|
||||||
|
String applicationName = resultSet.getString("actual_File_Name"); //NON-NLS
|
||||||
|
List<Long> executionTimes = new ArrayList<>();
|
||||||
|
executionTimes.add(Long.valueOf(resultSet.getInt("Embeded_date_Time_Unix_1")));
|
||||||
|
executionTimes.add(Long.valueOf(resultSet.getInt("Embeded_date_Time_Unix_2")));
|
||||||
|
executionTimes.add(Long.valueOf(resultSet.getInt("Embeded_date_Time_Unix_3")));
|
||||||
|
executionTimes.add(Long.valueOf(resultSet.getInt("Embeded_date_Time_Unix_4")));
|
||||||
|
executionTimes.add(Long.valueOf(resultSet.getInt("Embeded_date_Time_Unix_5")));
|
||||||
|
executionTimes.add(Long.valueOf(resultSet.getInt("Embeded_date_Time_Unix_6")));
|
||||||
|
executionTimes.add(Long.valueOf(resultSet.getInt("Embeded_date_Time_Unix_7")));
|
||||||
|
executionTimes.add(Long.valueOf(resultSet.getInt("Embeded_date_Time_Unix_8")));
|
||||||
|
String timesProgramRun = resultSet.getString("Number_time_file_run");
|
||||||
|
String filePath = resultSet.getString("file_path");
|
||||||
|
|
||||||
|
AbstractFile pfAbstractFile = getAbstractFile(prefetchFileName, PREFETCH_FILE_LOCATION, dataSource);
|
||||||
|
|
||||||
|
List<Long> prefetchExecutionTimes = findNonZeroExecutionTimes(executionTimes);
|
||||||
|
|
||||||
|
if (pfAbstractFile != null) {
|
||||||
|
for (Long executionTime : prefetchExecutionTimes) {
|
||||||
|
|
||||||
|
// only add prefetch file entries that have an actual date associated with them
|
||||||
|
Collection<BlackboardAttribute> blkBrdAttributes = Arrays.asList(
|
||||||
|
new BlackboardAttribute(
|
||||||
|
BlackboardAttribute.ATTRIBUTE_TYPE.TSK_PROG_NAME, getName(),
|
||||||
|
applicationName),//NON-NLS
|
||||||
|
new BlackboardAttribute(
|
||||||
|
BlackboardAttribute.ATTRIBUTE_TYPE.TSK_DATETIME, getName(),
|
||||||
|
executionTime),
|
||||||
|
new BlackboardAttribute(
|
||||||
|
BlackboardAttribute.ATTRIBUTE_TYPE.TSK_COUNT, getName(), Integer.valueOf(timesProgramRun)),
|
||||||
|
new BlackboardAttribute(
|
||||||
|
BlackboardAttribute.ATTRIBUTE_TYPE.TSK_COMMENT, getName(), PREFETCH_TSK_COMMENT));
|
||||||
|
|
||||||
|
try {
|
||||||
|
BlackboardArtifact blkBrdArt = pfAbstractFile.newArtifact(BlackboardArtifact.ARTIFACT_TYPE.TSK_PROG_RUN);
|
||||||
|
blkBrdArt.addAttributes(blkBrdAttributes);
|
||||||
|
blkBrdArtList.add(blkBrdArt);
|
||||||
|
BlackboardArtifact associatedBbArtifact = createAssociatedArtifact(applicationName.toLowerCase(), filePath, blkBrdArt, dataSource);
|
||||||
|
if (associatedBbArtifact != null) {
|
||||||
|
blkBrdArtList.add(associatedBbArtifact);
|
||||||
|
}
|
||||||
|
} catch (TskCoreException ex) {
|
||||||
|
logger.log(Level.SEVERE, "Exception Adding Artifact.", ex);//NON-NLS
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
logger.log(Level.SEVERE, "File has a null value " + prefetchFileName);//NON-NLS
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
} catch (SQLException ex) {
|
||||||
|
logger.log(Level.SEVERE, "Error while trying to read into a sqlite db.", ex);//NON-NLS
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!blkBrdArtList.isEmpty()) {
|
||||||
|
try {
|
||||||
|
blackboard.postArtifacts(blkBrdArtList, MODULE_NAME);
|
||||||
|
} catch (Blackboard.BlackboardException ex) {
|
||||||
|
logger.log(Level.SEVERE, "Error Posting Artifact.", ex);//NON-NLS
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Cycle thru the execution times list and only return a new list of times that are greater than zero.
|
||||||
|
*
|
||||||
|
* @param executionTimes - list of prefetch execution times 8 possible timestamps
|
||||||
|
*
|
||||||
|
* @return List of timestamps that are greater than zero
|
||||||
|
*/
|
||||||
|
|
||||||
|
private List<Long> findNonZeroExecutionTimes(List<Long> executionTimes) {
|
||||||
|
List<Long> prefetchExecutionTimes = new ArrayList<>();
|
||||||
|
for (Long executionTime : executionTimes) { // only add prefetch file entries that have an actual date associated with them
|
||||||
|
if (executionTime > 0) {
|
||||||
|
prefetchExecutionTimes.add(executionTime);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return prefetchExecutionTimes;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* Create associated artifacts using file path name and the artifact it associates with
|
||||||
|
*
|
||||||
|
* @param fileName the filename to search for
|
||||||
|
* @param filePathName file and path of object being associated with
|
||||||
|
* @param bba blackboard artifact to associate with
|
||||||
|
* @param dataSource - The datasource to search in
|
||||||
|
*
|
||||||
|
* @returnv BlackboardArtifact or a null value
|
||||||
|
*/
|
||||||
|
private BlackboardArtifact createAssociatedArtifact(String fileName, String filePathName, BlackboardArtifact bba, Content dataSource) {
|
||||||
|
AbstractFile sourceFile = getAbstractFile(fileName, filePathName, dataSource);
|
||||||
|
if (sourceFile != null) {
|
||||||
|
Collection<BlackboardAttribute> bbattributes2 = new ArrayList<>();
|
||||||
|
bbattributes2.addAll(Arrays.asList(
|
||||||
|
new BlackboardAttribute(TSK_ASSOCIATED_ARTIFACT, this.getName(),
|
||||||
|
bba.getArtifactID())));
|
||||||
|
|
||||||
|
BlackboardArtifact associatedObjectBba = createArtifactWithAttributes(TSK_ASSOCIATED_OBJECT, sourceFile, bbattributes2);
|
||||||
|
if (associatedObjectBba != null) {
|
||||||
|
return associatedObjectBba;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the abstract file for the prefetch file.
|
||||||
|
*
|
||||||
|
* @param fileName - File name of the prefetch file to find.
|
||||||
|
* @param filePath - Path where the prefetch file is located.
|
||||||
|
* @param dataSource - The datasource to search in
|
||||||
|
*
|
||||||
|
* @return Abstract file of the prefetch file.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
AbstractFile getAbstractFile(String fileName, String filePath, Content dataSource) {
|
||||||
|
List<AbstractFile> files;
|
||||||
|
|
||||||
|
FileManager fileManager = Case.getCurrentCase().getServices().getFileManager();
|
||||||
|
|
||||||
|
try {
|
||||||
|
files = fileManager.findFiles(dataSource, fileName, filePath); //NON-NLS
|
||||||
|
} catch (TskCoreException ex) {
|
||||||
|
logger.log(Level.WARNING, "Unable to find prefetch files.", ex); //NON-NLS
|
||||||
|
return null; // No need to continue
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!files.isEmpty()) {
|
||||||
|
return files.get(0);
|
||||||
|
} else {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -79,6 +79,7 @@ public final class RAImageIngestModule implements DataSourceIngestModule {
|
|||||||
Extract zoneInfo = new ExtractZoneIdentifier();
|
Extract zoneInfo = new ExtractZoneIdentifier();
|
||||||
Extract recycleBin = new ExtractRecycleBin();
|
Extract recycleBin = new ExtractRecycleBin();
|
||||||
Extract sru = new ExtractSru();
|
Extract sru = new ExtractSru();
|
||||||
|
Extract prefetch = new ExtractPrefetch();
|
||||||
|
|
||||||
extractors.add(chrome);
|
extractors.add(chrome);
|
||||||
extractors.add(firefox);
|
extractors.add(firefox);
|
||||||
@ -93,6 +94,7 @@ public final class RAImageIngestModule implements DataSourceIngestModule {
|
|||||||
extractors.add(zoneInfo); // this needs to run after the web browser modules
|
extractors.add(zoneInfo); // this needs to run after the web browser modules
|
||||||
extractors.add(recycleBin); // this needs to run after ExtractRegistry and ExtractOS
|
extractors.add(recycleBin); // this needs to run after ExtractRegistry and ExtractOS
|
||||||
extractors.add(sru);
|
extractors.add(sru);
|
||||||
|
extractors.add(prefetch);
|
||||||
|
|
||||||
browserExtractors.add(chrome);
|
browserExtractors.add(chrome);
|
||||||
browserExtractors.add(firefox);
|
browserExtractors.add(firefox);
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
#Updated by build script
|
#Updated by build script
|
||||||
#Fri, 12 Jun 2020 14:50:38 -0400
|
#Fri, 19 Jun 2020 10:14:47 -0400
|
||||||
LBL_splash_window_title=Starting Autopsy
|
LBL_splash_window_title=Starting Autopsy
|
||||||
SPLASH_HEIGHT=314
|
SPLASH_HEIGHT=314
|
||||||
SPLASH_WIDTH=538
|
SPLASH_WIDTH=538
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
#Updated by build script
|
#Updated by build script
|
||||||
#Fri, 12 Jun 2020 14:50:38 -0400
|
#Fri, 19 Jun 2020 10:14:47 -0400
|
||||||
CTL_MainWindow_Title=Autopsy 4.15.0
|
CTL_MainWindow_Title=Autopsy 4.15.0
|
||||||
CTL_MainWindow_Title_No_Project=Autopsy 4.15.0
|
CTL_MainWindow_Title_No_Project=Autopsy 4.15.0
|
||||||
|
BIN
thirdparty/markmckinnon/parse_prefetch_linux
vendored
Normal file
BIN
thirdparty/markmckinnon/parse_prefetch_linux
vendored
Normal file
Binary file not shown.
BIN
thirdparty/markmckinnon/parse_prefetch_macos
vendored
Normal file
BIN
thirdparty/markmckinnon/parse_prefetch_macos
vendored
Normal file
Binary file not shown.
BIN
thirdparty/markmckinnon/parse_prefetch_x64.exe
vendored
Normal file
BIN
thirdparty/markmckinnon/parse_prefetch_x64.exe
vendored
Normal file
Binary file not shown.
BIN
thirdparty/markmckinnon/parse_prefetch_x86.exe
vendored
Normal file
BIN
thirdparty/markmckinnon/parse_prefetch_x86.exe
vendored
Normal file
Binary file not shown.
@ -6,6 +6,15 @@
|
|||||||
<code-name-base>org.sleuthkit.autopsy.thunderbirdparser</code-name-base>
|
<code-name-base>org.sleuthkit.autopsy.thunderbirdparser</code-name-base>
|
||||||
<suite-component/>
|
<suite-component/>
|
||||||
<module-dependencies>
|
<module-dependencies>
|
||||||
|
<dependency>
|
||||||
|
<code-name-base>org.netbeans.api.progress</code-name-base>
|
||||||
|
<build-prerequisite/>
|
||||||
|
<compile-dependency/>
|
||||||
|
<run-dependency>
|
||||||
|
<release-version>1</release-version>
|
||||||
|
<specification-version>1.47.1</specification-version>
|
||||||
|
</run-dependency>
|
||||||
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<code-name-base>org.openide.util</code-name-base>
|
<code-name-base>org.openide.util</code-name-base>
|
||||||
<build-prerequisite/>
|
<build-prerequisite/>
|
||||||
|
@ -54,6 +54,7 @@ import org.sleuthkit.datamodel.BlackboardArtifact;
|
|||||||
import org.sleuthkit.datamodel.BlackboardAttribute;
|
import org.sleuthkit.datamodel.BlackboardAttribute;
|
||||||
import org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE;
|
import org.sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE;
|
||||||
import org.sleuthkit.datamodel.DerivedFile;
|
import org.sleuthkit.datamodel.DerivedFile;
|
||||||
|
import org.sleuthkit.datamodel.ReadContentInputStream;
|
||||||
import org.sleuthkit.datamodel.Relationship;
|
import org.sleuthkit.datamodel.Relationship;
|
||||||
import org.sleuthkit.datamodel.TskCoreException;
|
import org.sleuthkit.datamodel.TskCoreException;
|
||||||
import org.sleuthkit.datamodel.TskData;
|
import org.sleuthkit.datamodel.TskData;
|
||||||
@ -76,6 +77,7 @@ public final class ThunderbirdMboxFileIngestModule implements FileIngestModule {
|
|||||||
private Blackboard blackboard;
|
private Blackboard blackboard;
|
||||||
private CommunicationArtifactsHelper communicationArtifactsHelper;
|
private CommunicationArtifactsHelper communicationArtifactsHelper;
|
||||||
|
|
||||||
|
private static final int MBOX_SIZE_TO_SPLIT = 1048576000;
|
||||||
private Case currentCase;
|
private Case currentCase;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -309,12 +311,75 @@ public final class ThunderbirdMboxFileIngestModule implements FileIngestModule {
|
|||||||
return ProcessResult.OK;
|
return ProcessResult.OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
if (abstractFile.getSize() < MBOX_SIZE_TO_SPLIT) {
|
||||||
ContentUtils.writeToFile(abstractFile, file, context::fileIngestIsCancelled);
|
|
||||||
} catch (IOException ex) {
|
try {
|
||||||
logger.log(Level.WARNING, "Failed writing mbox file to disk.", ex); //NON-NLS
|
ContentUtils.writeToFile(abstractFile, file, context::fileIngestIsCancelled);
|
||||||
return ProcessResult.OK;
|
} catch (IOException ex) {
|
||||||
|
logger.log(Level.WARNING, "Failed writing mbox file to disk.", ex); //NON-NLS
|
||||||
|
return ProcessResult.OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
processMboxFile(file, abstractFile, emailFolder);
|
||||||
|
|
||||||
|
if (file.delete() == false) {
|
||||||
|
logger.log(Level.INFO, "Failed to delete temp file: {0}", file.getName()); //NON-NLS
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
|
||||||
|
List<Long> mboxSplitOffsets = new ArrayList<>();
|
||||||
|
try{
|
||||||
|
mboxSplitOffsets = findMboxSplitOffset(abstractFile, file);
|
||||||
|
} catch (IOException ex) {
|
||||||
|
logger.log(Level.WARNING, String.format("Failed finding split offsets for mbox file {0}.", fileName), ex); //NON-NLS
|
||||||
|
return ProcessResult.OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
long startingOffset = 0;
|
||||||
|
for (Long mboxSplitOffset : mboxSplitOffsets) {
|
||||||
|
File splitFile = new File(fileName + "-" + mboxSplitOffset);
|
||||||
|
try {
|
||||||
|
ContentUtils.writeToFile(abstractFile, splitFile, context::fileIngestIsCancelled, startingOffset, mboxSplitOffset);
|
||||||
|
} catch (IOException ex) {
|
||||||
|
logger.log(Level.WARNING, "Failed writing split mbox file to disk.", ex); //NON-NLS
|
||||||
|
return ProcessResult.OK;
|
||||||
|
}
|
||||||
|
processMboxFile(splitFile, abstractFile, emailFolder);
|
||||||
|
startingOffset = mboxSplitOffset;
|
||||||
|
if (splitFile.delete() == false) {
|
||||||
|
logger.log(Level.INFO, "Failed to delete temp file: {0}", splitFile); //NON-NLS
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return ProcessResult.OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
private List<Long> findMboxSplitOffset(AbstractFile abstractFile, File file) throws IOException {
|
||||||
|
|
||||||
|
List<Long> mboxSplitOffset = new ArrayList<>();
|
||||||
|
|
||||||
|
byte[] buffer = new byte[7];
|
||||||
|
ReadContentInputStream in = new ReadContentInputStream(abstractFile);
|
||||||
|
in.skip(MBOX_SIZE_TO_SPLIT);
|
||||||
|
int len = in.read(buffer);
|
||||||
|
while (len != -1) {
|
||||||
|
len = in.read(buffer);
|
||||||
|
if (buffer[0] == 13 && buffer[1] == 10 && buffer[2] == 70 && buffer[3] == 114 &&
|
||||||
|
buffer[4] == 111 && buffer[5] == 109 && buffer[6] == 32) {
|
||||||
|
mboxSplitOffset.add(in.getCurPosition() - 5 );
|
||||||
|
in.skip(MBOX_SIZE_TO_SPLIT);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return mboxSplitOffset;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private void processMboxFile(File file, AbstractFile abstractFile, String emailFolder) {
|
||||||
|
|
||||||
|
|
||||||
MboxParser emailIterator = MboxParser.getEmailIterator( emailFolder, file, abstractFile.getId());
|
MboxParser emailIterator = MboxParser.getEmailIterator( emailFolder, file, abstractFile.getId());
|
||||||
List<EmailMessage> emails = new ArrayList<>();
|
List<EmailMessage> emails = new ArrayList<>();
|
||||||
@ -325,7 +390,7 @@ public final class ThunderbirdMboxFileIngestModule implements FileIngestModule {
|
|||||||
emails.add(emailMessage);
|
emails.add(emailMessage);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
String errors = emailIterator.getErrors();
|
String errors = emailIterator.getErrors();
|
||||||
if (!errors.isEmpty()) {
|
if (!errors.isEmpty()) {
|
||||||
postErrorMessage(
|
postErrorMessage(
|
||||||
@ -335,11 +400,6 @@ public final class ThunderbirdMboxFileIngestModule implements FileIngestModule {
|
|||||||
}
|
}
|
||||||
processEmails(emails, MboxParser.getEmailIterator( emailFolder, file, abstractFile.getId()), abstractFile);
|
processEmails(emails, MboxParser.getEmailIterator( emailFolder, file, abstractFile.getId()), abstractFile);
|
||||||
|
|
||||||
if (file.delete() == false) {
|
|
||||||
logger.log(Level.INFO, "Failed to delete temp file: {0}", file.getName()); //NON-NLS
|
|
||||||
}
|
|
||||||
|
|
||||||
return ProcessResult.OK;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -755,4 +815,5 @@ public final class ThunderbirdMboxFileIngestModule implements FileIngestModule {
|
|||||||
public void shutDown() {
|
public void shutDown() {
|
||||||
// nothing to shut down
|
// nothing to shut down
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user