mirror of
https://github.com/overcuriousity/autopsy-flatpak.git
synced 2025-07-14 17:06:16 +00:00
abstracted TranslateTextTask
This commit is contained in:
parent
1f7ab40a4d
commit
fe86d86dd2
@ -110,7 +110,7 @@ final class TextTranslatableComponent implements TranslatablePanel.TranslatableC
|
|||||||
this.translated = this.translationService.translate(originalContent);
|
this.translated = this.translationService.translate(originalContent);
|
||||||
} catch (NoServiceProviderException | TranslationException ex) {
|
} catch (NoServiceProviderException | TranslationException ex) {
|
||||||
LOGGER.log(Level.WARNING, "Unable to translate text with translation service", ex);
|
LOGGER.log(Level.WARNING, "Unable to translate text with translation service", ex);
|
||||||
return Bundle.TextTranslatableComponent_setTranslated_onTranslateError();
|
//return Bundle.TextTranslatableComponent_setTranslated_onTranslateError();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -30,7 +30,9 @@ import org.sleuthkit.autopsy.texttranslation.TextTranslationService;
|
|||||||
* A panel for translation with a subcomponent that allows for translation
|
* A panel for translation with a subcomponent that allows for translation
|
||||||
*/
|
*/
|
||||||
final class TranslatablePanel extends JPanel {
|
final class TranslatablePanel extends JPanel {
|
||||||
|
interface ContentSetter {
|
||||||
|
void set(String content) throws Exception;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* an option in drop down of whether or not to translate
|
* an option in drop down of whether or not to translate
|
||||||
|
@ -0,0 +1,160 @@
|
|||||||
|
/*
|
||||||
|
* Autopsy Forensic Browser
|
||||||
|
*
|
||||||
|
* 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.texttranslation.ui;
|
||||||
|
|
||||||
|
import java.awt.ComponentOrientation;
|
||||||
|
import java.awt.Font;
|
||||||
|
import java.util.concurrent.CancellationException;
|
||||||
|
import java.util.concurrent.ExecutionException;
|
||||||
|
import java.util.logging.Level;
|
||||||
|
import javax.swing.SwingUtilities;
|
||||||
|
import javax.swing.SwingWorker;
|
||||||
|
import org.openide.util.NbBundle;
|
||||||
|
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||||
|
import org.sleuthkit.autopsy.coreutils.TextUtil;
|
||||||
|
import org.sleuthkit.autopsy.texttranslation.NoServiceProviderException;
|
||||||
|
import org.sleuthkit.autopsy.texttranslation.TextTranslationService;
|
||||||
|
import org.sleuthkit.autopsy.texttranslation.TranslationException;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* abstract class for translating text and displaying to the user
|
||||||
|
*/
|
||||||
|
public abstract class TranslateTextTask extends SwingWorker<String, Void> {
|
||||||
|
private static final Logger logger = Logger.getLogger(TranslatedTextViewer.class.getName());
|
||||||
|
|
||||||
|
private final boolean translateText;
|
||||||
|
private final String contentDescriptor;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param translateText whether or not to translate text
|
||||||
|
* @param contentDescriptor the content descriptor for the item being translated (used for logging errors)
|
||||||
|
*/
|
||||||
|
public TranslateTextTask(boolean translateText, String fileDescriptor) {
|
||||||
|
this.translateText = translateText;
|
||||||
|
this.contentDescriptor = fileDescriptor;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
protected abstract String retrieveText() throws Exception;
|
||||||
|
|
||||||
|
protected abstract void onTextDisplay(String text, ComponentOrientation orientation, int font);
|
||||||
|
|
||||||
|
@NbBundle.Messages({
|
||||||
|
"TranslatedContentViewer.extractingText=Extracting text, please wait...",
|
||||||
|
"TranslatedContentViewer.translatingText=Translating text, please wait...",
|
||||||
|
"# {0} - exception message", "TranslatedContentViewer.errorExtractingText=An error occurred while extracting the text ({0}).",
|
||||||
|
"TranslatedContentViewer.fileHasNoText=File has no text.",
|
||||||
|
"TranslatedContentViewer.noServiceProvider=The machine translation software was not found.",
|
||||||
|
"# {0} - exception message", "TranslatedContentViewer.translationException=An error occurred while translating the text ({0})."
|
||||||
|
})
|
||||||
|
@Override
|
||||||
|
public String doInBackground() throws InterruptedException {
|
||||||
|
if (this.isCancelled()) {
|
||||||
|
throw new InterruptedException();
|
||||||
|
}
|
||||||
|
|
||||||
|
SwingUtilities.invokeLater(() -> {
|
||||||
|
onTextDisplay(Bundle.TranslatedContentViewer_extractingText(), ComponentOrientation.LEFT_TO_RIGHT, Font.ITALIC);
|
||||||
|
});
|
||||||
|
String fileText;
|
||||||
|
try {
|
||||||
|
fileText = retrieveText();
|
||||||
|
} catch (InterruptedException | CancellationException e) {
|
||||||
|
// bubble up cancellation instead of continuing
|
||||||
|
throw e;
|
||||||
|
} catch (Exception ex) {
|
||||||
|
logger.log(Level.WARNING, "Error extracting text for file " + this.contentDescriptor, ex);
|
||||||
|
return Bundle.TranslatedContentViewer_errorExtractingText(ex.getMessage());
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.isCancelled()) {
|
||||||
|
throw new InterruptedException();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (fileText == null || fileText.isEmpty()) {
|
||||||
|
return Bundle.TranslatedContentViewer_fileHasNoText();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!this.translateText) {
|
||||||
|
return fileText;
|
||||||
|
}
|
||||||
|
|
||||||
|
SwingUtilities.invokeLater(() -> {
|
||||||
|
onTextDisplay(Bundle.TranslatedContentViewer_translatingText(), ComponentOrientation.LEFT_TO_RIGHT, Font.ITALIC);
|
||||||
|
});
|
||||||
|
String translation;
|
||||||
|
try {
|
||||||
|
translation = translate(fileText);
|
||||||
|
} catch (NoServiceProviderException ex) {
|
||||||
|
logger.log(Level.WARNING, "Error translating text for file " + this.contentDescriptor, ex);
|
||||||
|
translation = Bundle.TranslatedContentViewer_noServiceProvider();
|
||||||
|
} catch (TranslationException ex) {
|
||||||
|
logger.log(Level.WARNING, "Error translating text for file " + this.contentDescriptor, ex);
|
||||||
|
translation = Bundle.TranslatedContentViewer_translationException(ex.getMessage());
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.isCancelled()) {
|
||||||
|
throw new InterruptedException();
|
||||||
|
}
|
||||||
|
|
||||||
|
return translation;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void done() {
|
||||||
|
try {
|
||||||
|
String result = get();
|
||||||
|
if (this.isCancelled()) {
|
||||||
|
throw new InterruptedException();
|
||||||
|
}
|
||||||
|
int len = result.length();
|
||||||
|
int maxOrientChars = Math.min(len, 1024);
|
||||||
|
String orientDetectSubstring = result.substring(0, maxOrientChars);
|
||||||
|
ComponentOrientation orientation = TextUtil.getTextDirection(orientDetectSubstring);
|
||||||
|
onTextDisplay(result, orientation, Font.PLAIN);
|
||||||
|
|
||||||
|
} catch (InterruptedException | CancellationException ignored) {
|
||||||
|
// Task cancelled, no error.
|
||||||
|
} catch (ExecutionException ex) {
|
||||||
|
logger.log(Level.WARNING, "Error occurred during background task execution for file " + this.contentDescriptor, ex);
|
||||||
|
onTextDisplay(Bundle.TranslatedContentViewer_translationException(ex.getMessage()), ComponentOrientation.LEFT_TO_RIGHT, Font.ITALIC);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Pass the translation off to the Translation service provider.
|
||||||
|
*
|
||||||
|
* @param input Text to be translated
|
||||||
|
*
|
||||||
|
* @return Translated text or error message
|
||||||
|
*/
|
||||||
|
@NbBundle.Messages({
|
||||||
|
"TranslatedContentViewer.emptyTranslation=The machine translation software did not return any text."
|
||||||
|
})
|
||||||
|
private String translate(String input) throws NoServiceProviderException, TranslationException {
|
||||||
|
TextTranslationService translatorInstance = TextTranslationService.getInstance();
|
||||||
|
String translatedResult = translatorInstance.translate(input);
|
||||||
|
if (translatedResult.isEmpty()) {
|
||||||
|
return Bundle.TranslatedContentViewer_emptyTranslation();
|
||||||
|
}
|
||||||
|
return translatedResult;
|
||||||
|
}
|
||||||
|
}
|
@ -160,112 +160,13 @@ public final class TranslatedTextViewer implements TextViewer {
|
|||||||
/**
|
/**
|
||||||
* Extracts text from a file and optionally translates it.
|
* Extracts text from a file and optionally translates it.
|
||||||
*/
|
*/
|
||||||
private class ExtractAndTranslateTextTask extends SwingWorker<String, Void> {
|
private class ExtractAndTranslateTextTask extends TranslateTextTask {
|
||||||
|
|
||||||
private final AbstractFile file;
|
private final AbstractFile file;
|
||||||
private final boolean translateText;
|
|
||||||
|
|
||||||
private ExtractAndTranslateTextTask(AbstractFile file, boolean translateText) {
|
private ExtractAndTranslateTextTask(AbstractFile file, boolean translateText) {
|
||||||
|
super(translateText, String.format("%s (objId=%d)", file.getName(), file.getId()));
|
||||||
this.file = file;
|
this.file = file;
|
||||||
this.translateText = translateText;
|
|
||||||
}
|
|
||||||
|
|
||||||
@NbBundle.Messages({
|
|
||||||
"TranslatedContentViewer.extractingText=Extracting text, please wait...",
|
|
||||||
"TranslatedContentViewer.translatingText=Translating text, please wait...",
|
|
||||||
"# {0} - exception message", "TranslatedContentViewer.errorExtractingText=An error occurred while extracting the text ({0}).",
|
|
||||||
"TranslatedContentViewer.fileHasNoText=File has no text.",
|
|
||||||
"TranslatedContentViewer.noServiceProvider=The machine translation software was not found.",
|
|
||||||
"# {0} - exception message", "TranslatedContentViewer.translationException=An error occurred while translating the text ({0})."
|
|
||||||
})
|
|
||||||
@Override
|
|
||||||
public String doInBackground() throws InterruptedException {
|
|
||||||
if (this.isCancelled()) {
|
|
||||||
throw new InterruptedException();
|
|
||||||
}
|
|
||||||
|
|
||||||
SwingUtilities.invokeLater(() -> {
|
|
||||||
panel.display(Bundle.TranslatedContentViewer_extractingText(), ComponentOrientation.LEFT_TO_RIGHT, Font.ITALIC);
|
|
||||||
});
|
|
||||||
String fileText;
|
|
||||||
try {
|
|
||||||
fileText = getFileText(file);
|
|
||||||
} catch (IOException | TextExtractor.InitReaderException ex) {
|
|
||||||
logger.log(Level.WARNING, String.format("Error extracting text for file %s (objId=%d)", file.getName(), file.getId()), ex);
|
|
||||||
return Bundle.TranslatedContentViewer_errorExtractingText(ex.getMessage());
|
|
||||||
}
|
|
||||||
|
|
||||||
if (this.isCancelled()) {
|
|
||||||
throw new InterruptedException();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (fileText == null || fileText.isEmpty()) {
|
|
||||||
return Bundle.TranslatedContentViewer_fileHasNoText();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!this.translateText) {
|
|
||||||
return fileText;
|
|
||||||
}
|
|
||||||
|
|
||||||
SwingUtilities.invokeLater(() -> {
|
|
||||||
panel.display(Bundle.TranslatedContentViewer_translatingText(), ComponentOrientation.LEFT_TO_RIGHT, Font.ITALIC);
|
|
||||||
});
|
|
||||||
String translation;
|
|
||||||
try {
|
|
||||||
translation = translate(fileText);
|
|
||||||
} catch (NoServiceProviderException ex) {
|
|
||||||
logger.log(Level.WARNING, String.format("Error translating text for file %s (objId=%d)", file.getName(), file.getId()), ex);
|
|
||||||
translation = Bundle.TranslatedContentViewer_noServiceProvider();
|
|
||||||
} catch (TranslationException ex) {
|
|
||||||
logger.log(Level.WARNING, String.format("Error translating text for file %s (objId=%d)", file.getName(), file.getId()), ex);
|
|
||||||
translation = Bundle.TranslatedContentViewer_translationException(ex.getMessage());
|
|
||||||
}
|
|
||||||
|
|
||||||
if (this.isCancelled()) {
|
|
||||||
throw new InterruptedException();
|
|
||||||
}
|
|
||||||
|
|
||||||
return translation;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void done() {
|
|
||||||
try {
|
|
||||||
String result = get();
|
|
||||||
if (this.isCancelled()) {
|
|
||||||
throw new InterruptedException();
|
|
||||||
}
|
|
||||||
int len = result.length();
|
|
||||||
int maxOrientChars = Math.min(len, 1024);
|
|
||||||
String orientDetectSubstring = result.substring(0, maxOrientChars);
|
|
||||||
ComponentOrientation orientation = TextUtil.getTextDirection(orientDetectSubstring);
|
|
||||||
panel.display(result, orientation, Font.PLAIN);
|
|
||||||
|
|
||||||
} catch (InterruptedException | CancellationException ignored) {
|
|
||||||
// Task cancelled, no error.
|
|
||||||
} catch (ExecutionException ex) {
|
|
||||||
logger.log(Level.WARNING, String.format("Error occurred during background task execution for file %s (objId=%d)", file.getName(), file.getId()), ex);
|
|
||||||
panel.display(Bundle.TranslatedContentViewer_translationException(ex.getMessage()), ComponentOrientation.LEFT_TO_RIGHT, Font.ITALIC);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Pass the translation off to the Translation service provider.
|
|
||||||
*
|
|
||||||
* @param input Text to be translated
|
|
||||||
*
|
|
||||||
* @return Translated text or error message
|
|
||||||
*/
|
|
||||||
@NbBundle.Messages({
|
|
||||||
"TranslatedContentViewer.emptyTranslation=The machine translation software did not return any text."
|
|
||||||
})
|
|
||||||
private String translate(String input) throws NoServiceProviderException, TranslationException {
|
|
||||||
TextTranslationService translatorInstance = TextTranslationService.getInstance();
|
|
||||||
String translatedResult = translatorInstance.translate(input);
|
|
||||||
if (translatedResult.isEmpty()) {
|
|
||||||
return Bundle.TranslatedContentViewer_emptyTranslation();
|
|
||||||
}
|
|
||||||
return translatedResult;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -275,13 +176,9 @@ public final class TranslatedTextViewer implements TextViewer {
|
|||||||
*
|
*
|
||||||
* @return Extracted text
|
* @return Extracted text
|
||||||
*
|
*
|
||||||
* @throws IOException
|
* @throws Exception
|
||||||
* @throws InterruptedException
|
|
||||||
* @throws
|
|
||||||
* org.sleuthkit.autopsy.textextractors.TextExtractor.InitReaderException
|
|
||||||
*/
|
*/
|
||||||
private String getFileText(AbstractFile file) throws IOException,
|
protected String retrieveText() throws Exception {
|
||||||
InterruptedException, TextExtractor.InitReaderException {
|
|
||||||
|
|
||||||
final boolean isImage = file.getMIMEType().toLowerCase().startsWith("image/"); // NON-NLS
|
final boolean isImage = file.getMIMEType().toLowerCase().startsWith("image/"); // NON-NLS
|
||||||
String result;
|
String result;
|
||||||
@ -382,8 +279,15 @@ public final class TranslatedTextViewer implements TextViewer {
|
|||||||
return TextExtractorFactory.getStringsExtractor(file, context).getReader();
|
return TextExtractorFactory.getStringsExtractor(file, context).getReader();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void onTextDisplay(String text, ComponentOrientation orientation, int font) {
|
||||||
|
panel.display(text, orientation, font);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Listens for drop-down selection changes and pushes processing off of the
|
* Listens for drop-down selection changes and pushes processing off of the
|
||||||
* EDT and into a SwingWorker.
|
* EDT and into a SwingWorker.
|
||||||
|
Loading…
x
Reference in New Issue
Block a user