abort and search
This commit is contained in:
@@ -19,6 +19,7 @@ import {
|
||||
lineFromApi,
|
||||
manifestConfig,
|
||||
TextEditorDialog,
|
||||
ArticleSearchDialog,
|
||||
} from '../../components/manifest';
|
||||
import ManifestPdfDialog from '../../components/manifest/ManifestPdfDialog';
|
||||
import { loadParties } from '../../components/manifest/manifestConfig';
|
||||
@@ -50,6 +51,8 @@ class LieferungNeuPage extends PureComponent {
|
||||
pdfFileName: '',
|
||||
textEditorOpen: false,
|
||||
textEditorAttachment: null,
|
||||
articleSearchDialogOpen: false,
|
||||
articleSearchLine: null,
|
||||
};
|
||||
this._cancelled = false;
|
||||
this.handleRetry = this.handleRetry.bind(this);
|
||||
@@ -65,6 +68,7 @@ class LieferungNeuPage extends PureComponent {
|
||||
this.handlePdfRescan = this.handlePdfRescan.bind(this);
|
||||
this.handlePdfDelete = this.handlePdfDelete.bind(this);
|
||||
this.handleClosePdfDialog = this.handleClosePdfDialog.bind(this);
|
||||
this.handleAbortParse = this.handleAbortParse.bind(this);
|
||||
this.handleAttachmentClick = this.handleAttachmentClick.bind(this);
|
||||
this.handleCloseTextEditor = this.handleCloseTextEditor.bind(this);
|
||||
this.handleSaveTextEditor = this.handleSaveTextEditor.bind(this);
|
||||
@@ -72,6 +76,9 @@ class LieferungNeuPage extends PureComponent {
|
||||
this.ensureAttachmentFile = this.ensureAttachmentFile.bind(this);
|
||||
this.handleSkuBlur = this.handleSkuBlur.bind(this);
|
||||
this.handleCreateArticleForLine = this.handleCreateArticleForLine.bind(this);
|
||||
this.handleOpenArticleSearchForLine = this.handleOpenArticleSearchForLine.bind(this);
|
||||
this.handleCloseArticleSearch = this.handleCloseArticleSearch.bind(this);
|
||||
this.handleAssignArticleForLine = this.handleAssignArticleForLine.bind(this);
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
@@ -106,6 +113,10 @@ class LieferungNeuPage extends PureComponent {
|
||||
|
||||
componentWillUnmount() {
|
||||
this._cancelled = true;
|
||||
if (this._parseAbortController) {
|
||||
this._parseAbortController.abort();
|
||||
this._parseAbortController = null;
|
||||
}
|
||||
if (this._skuDebounceTimers) {
|
||||
Object.values(this._skuDebounceTimers).forEach(clearTimeout);
|
||||
this._skuDebounceTimers = null;
|
||||
@@ -311,6 +322,67 @@ class LieferungNeuPage extends PureComponent {
|
||||
}
|
||||
}
|
||||
|
||||
handleOpenArticleSearchForLine(line) {
|
||||
this.setState({
|
||||
articleSearchDialogOpen: true,
|
||||
articleSearchLine: line,
|
||||
});
|
||||
}
|
||||
|
||||
handleCloseArticleSearch() {
|
||||
this.setState({
|
||||
articleSearchDialogOpen: false,
|
||||
articleSearchLine: null,
|
||||
});
|
||||
}
|
||||
|
||||
async handleAssignArticleForLine(article, line) {
|
||||
const { partyId } = this.state;
|
||||
if (!partyId) {
|
||||
enqueueSnackbar('Bitte wählen Sie zuerst einen Lieferanten aus.', { variant: 'warning' });
|
||||
return;
|
||||
}
|
||||
|
||||
const internalSku = article?.sku;
|
||||
if (!internalSku) {
|
||||
enqueueSnackbar('Artikel hat keine SKU.', { variant: 'error' });
|
||||
return;
|
||||
}
|
||||
|
||||
const supplierSku = line?.sku;
|
||||
|
||||
try {
|
||||
await this.context.article.addSupplier(internalSku, {
|
||||
entityId: partyId,
|
||||
sku: supplierSku || undefined,
|
||||
pu: line?.pu ? Number(line.pu) : undefined,
|
||||
stock: line?.amount ? Number(line.amount) : undefined,
|
||||
netPrice: line?.netprice ? Number(line.netprice) : undefined,
|
||||
taxRate: line?.taxrate ? Number(line.taxrate) : undefined,
|
||||
});
|
||||
|
||||
if (supplierSku) {
|
||||
this.automat.actions.fetchSupplierArticleForSku(supplierSku, line.key);
|
||||
} else {
|
||||
this.automat.actions.fetchSupplierArticles(partyId);
|
||||
}
|
||||
|
||||
enqueueSnackbar(
|
||||
`Lieferant erfolgreich dem Artikel "${internalSku}" zugeordnet.`,
|
||||
{ variant: 'success' },
|
||||
);
|
||||
|
||||
this.setState({
|
||||
articleSearchDialogOpen: false,
|
||||
articleSearchLine: null,
|
||||
});
|
||||
} catch (err) {
|
||||
console.error('Fehler beim Zuordnen des Artikels:', err);
|
||||
notifyError(err);
|
||||
throw err;
|
||||
}
|
||||
}
|
||||
|
||||
handleAddLine() {
|
||||
this.automat.actions.addLineitem();
|
||||
}
|
||||
@@ -451,15 +523,21 @@ class LieferungNeuPage extends PureComponent {
|
||||
}
|
||||
|
||||
async runParse(file) {
|
||||
if (this._parseAbortController) {
|
||||
this._parseAbortController.abort();
|
||||
}
|
||||
const abortController = new AbortController();
|
||||
this._parseAbortController = abortController;
|
||||
|
||||
this.setState({
|
||||
pdfUploading: true,
|
||||
pdfDialogOpen: true,
|
||||
pdfFileName: file.name,
|
||||
pdfDialogData: { streaming: true, messages: [], result: null, error: null },
|
||||
pdfDialogData: { streaming: true, messages: [], result: null, error: null, aborted: false },
|
||||
});
|
||||
|
||||
const appendMessage = (msg) => {
|
||||
if (this._cancelled) return;
|
||||
if (this._cancelled || abortController.signal.aborted) return;
|
||||
this.setState((prev) => ({
|
||||
pdfDialogData: {
|
||||
...prev.pdfDialogData,
|
||||
@@ -472,8 +550,8 @@ class LieferungNeuPage extends PureComponent {
|
||||
const parser = this.context?.delivery?.parseSse;
|
||||
if (!parser) throw new Error('parseSse nicht verfügbar.');
|
||||
|
||||
for await (const { event, data } of parser(file)) {
|
||||
if (this._cancelled) return;
|
||||
for await (const { event, data } of parser(file, { signal: abortController.signal })) {
|
||||
if (this._cancelled || abortController.signal.aborted) return;
|
||||
switch (event) {
|
||||
case 'status':
|
||||
appendMessage({ type: 'status', text: data.message ?? String(data) });
|
||||
@@ -580,6 +658,17 @@ class LieferungNeuPage extends PureComponent {
|
||||
}
|
||||
} catch (err) {
|
||||
if (this._cancelled) return;
|
||||
if (abortController.signal.aborted || err.name === 'AbortError') {
|
||||
this.setState((prev) => ({
|
||||
pdfDialogData: {
|
||||
...prev.pdfDialogData,
|
||||
streaming: false,
|
||||
aborted: true,
|
||||
error: 'Analyse abgebrochen.',
|
||||
},
|
||||
}));
|
||||
return;
|
||||
}
|
||||
this.setState((prev) => ({
|
||||
pdfDialogData: {
|
||||
...prev.pdfDialogData,
|
||||
@@ -588,6 +677,9 @@ class LieferungNeuPage extends PureComponent {
|
||||
},
|
||||
}));
|
||||
} finally {
|
||||
if (this._parseAbortController === abortController) {
|
||||
this._parseAbortController = null;
|
||||
}
|
||||
if (!this._cancelled) {
|
||||
this.setState((prev) => ({
|
||||
pdfUploading: false,
|
||||
@@ -607,8 +699,30 @@ class LieferungNeuPage extends PureComponent {
|
||||
await this.runParse(file);
|
||||
}
|
||||
|
||||
handleAbortParse() {
|
||||
if (this._parseAbortController) {
|
||||
this._parseAbortController.abort();
|
||||
this._parseAbortController = null;
|
||||
}
|
||||
this.setState((prev) => ({
|
||||
pdfUploading: false,
|
||||
pdfDialogData: prev.pdfDialogData
|
||||
? {
|
||||
...prev.pdfDialogData,
|
||||
streaming: false,
|
||||
aborted: true,
|
||||
error: 'Analyse abgebrochen.',
|
||||
}
|
||||
: null,
|
||||
}));
|
||||
}
|
||||
|
||||
handleClosePdfDialog() {
|
||||
this.setState({ pdfDialogOpen: false });
|
||||
if (this._parseAbortController) {
|
||||
this._parseAbortController.abort();
|
||||
this._parseAbortController = null;
|
||||
}
|
||||
this.setState({ pdfDialogOpen: false, pdfUploading: false });
|
||||
}
|
||||
|
||||
async ensureAttachmentFile(attachment) {
|
||||
@@ -929,6 +1043,7 @@ class LieferungNeuPage extends PureComponent {
|
||||
onRemoveLine={this.handleRemoveLine}
|
||||
onSave={() => void this.handleSave()}
|
||||
onCreateArticle={this.handleCreateArticleForLine}
|
||||
onSearchArticle={this.handleOpenArticleSearchForLine}
|
||||
/>
|
||||
</>
|
||||
)}
|
||||
@@ -952,6 +1067,7 @@ class LieferungNeuPage extends PureComponent {
|
||||
filename={pdfFileName}
|
||||
data={pdfDialogData}
|
||||
onClose={this.handleClosePdfDialog}
|
||||
onAbort={this.handleAbortParse}
|
||||
/>
|
||||
<TextEditorDialog
|
||||
open={this.state.textEditorOpen}
|
||||
@@ -961,6 +1077,12 @@ class LieferungNeuPage extends PureComponent {
|
||||
onSave={this.handleSaveTextEditor}
|
||||
onContentLoad={this.handleTextEditorContentLoaded}
|
||||
/>
|
||||
<ArticleSearchDialog
|
||||
open={this.state.articleSearchDialogOpen}
|
||||
line={this.state.articleSearchLine}
|
||||
onClose={this.handleCloseArticleSearch}
|
||||
onAssign={this.handleAssignArticleForLine}
|
||||
/>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user