15.05.2019, 17:54 | #1 |
Administrator
|
D365FO: Пример импорта из (экспорта в) Excel
Добрый день! В связи с увеличившимися просьбами как на курсах, на и на форуме - хочу выложить простейший пример импорта из Excel.
В примере производится импорт из Excel, затем полученные значения записываются в новый Excel-файл и сохраняются. Для загрузки файла используется класс FileUploadBuild. Для сохранения - DocuFileSave Выгрузка производится в той же сессии, что и загрузка - иначе не получается скачать экспортируемый файл (canRunInNewSession = false) X++: // VSUH, Пример импорта из файла Excel / экспорта в файл Excel class Tutorial_ExcelImportExport extends RunBaseBatch { private DialogRunbase dialog; private FileUploadBuild dialogFileUpload; private const FormControlName fileUploadControlName = "FileName"; protected Filename uploadFileName; protected URL uploadFileURL; protected SharedServiceUnitFileID uploadFileID; #define.CurrentVersion(1) #localmacro.CurrentList uploadFileName, uploadFileURL, uploadFileID #endmacro #File public Object dialog() { FormBuildControl formBuildControl; DialogGroup dialogGroup; ; dialog = super(); dialogGroup = dialog.addGroup(this.labelGroupControl()); formBuildControl = dialog.formBuildDesign().control(dialogGroup.name()); dialogFileUpload = formBuildControl.addControlEx(classstr(FileUpload), fileUploadControlName); dialogFileUpload.fileTypesAccepted(#xls + ',' + #xlsx); dialogFileUpload.fileNameLabel(this.labelUploadControl()); return dialog; } public boolean getFromDialog() { boolean ret; ret = super(); FileUpload fileUploadControl = dialog.formRun().control(dialog.formRun().controlId(fileUploadControlName)); FileUploadTemporaryStorageResult fileUploadResult = fileUploadControl.getFileUploadResult(); if (fileUploadResult != null && fileUploadResult.getUploadStatus()) { uploadFileURL = fileUploadResult.getDownloadUrl(); uploadFileName = fileUploadResult.getFileName(); uploadFileID = fileUploadResult.getFileId(); } return ret; } private void deleteFile(SharedServiceUnitFileID _fileId) { FileUploadTemporaryStorageResult result = new FileUploadTemporaryStorageResult('', '', true, '', '', _fileId); result.deleteResult(); } public void run() { System.IO.Stream stream; OfficeOpenXml.ExcelPackage package, packageOut; OfficeOpenXml.ExcelWorksheet worksheet, worksheetOut; Counter rowCount, columnCount; anytype value; DocuFileSaveResult saveResult; System.IO.MemoryStream streamOut = new System.IO.MemoryStream(); FilePath filePath; Filename fileName, fileNameLog; Filename fileExt; ; try { stream = File::UseFileFromURL(uploadFileURL); package = new OfficeOpenXml.ExcelPackage(stream); if (!package) { throw Exception::Error; } worksheet = package.get_workbook().get_worksheets().get_Item(this.worksheetNum()); rowCount = worksheet.get_Dimension().get_End().get_Row(); columnCount = worksheet.get_Dimension().get_End().get_Column(); packageOut = new OfficeOpenXml.ExcelPackage(streamOut); var worksheetsOut = packageOut.get_Workbook().get_Worksheets(); [filePath, fileName, fileExt] = fileNameSplit(uploadFileName); fileNameLog = filename + this.labelLogFileSuffix(); worksheetOut = worksheetsOut.Add(worksheet.Name); for (int i = 1; i <= rowcount; i++) { for (int j = 1; j <= columnCount; j++) { value = worksheet.get_cells().get_Item(i, j).get_Value(); worksheetOut.get_cells().get_Item(i, j).set_Value(value); } } packageOut.Save(); saveResult = DocuFileSave::promptForSaveLocation(fileNameLog, fileExt, null, this.labelReportResult()); DocuFileSave::processSaveResult(streamOut, saveResult); packageOut.Dispose(); package.Dispose(); this.deleteFile(uploadFileID); } catch { if (package) { packageOut.Save(); saveResult = DocuFileSave::promptForSaveLocation(fileNameLog, fileExt, null, this.labelReportResult()); DocuFileSave::processSaveResult(streamOut, saveResult); packageOut.Dispose(); package.Dispose(); this.deleteFile(uploadFileID); error(strfmt("@SYS63093", uploadFileName)); } else { error(strfmt("@SYS345194", uploadFileName)); } } } protected boolean canRunInNewSession() { return false; } public container pack() { return [#CurrentVersion, #CurrentList]; } public boolean unpack(container _packedClass) { Version version = RunBase::getVersion(_packedClass); switch (version) { case #CurrentVersion: [version, #CurrentList] = _packedClass; break; default: return false; } return true; } // Номер листа в Excel, с которого производится загрузка protected Integer worksheetNum() { return 1; } // Название группы полей в диалоге импорта protected Description labelGroupControl() { return "@SYS54759"; } // Суффикс файла-лога, добавляемый к исходному названию файла protected Description labelLogFileSuffix() { return "@SYS2515"; } // Название контрола, в котором выбирается файл для отправки на сервер protected Description labelUploadControl() { return "@SYS4820"; } // Название результирующего отчета о результатах загрузки protected Description labelReportResult() { return "@SYS30597"; } public static server Tutorial_ExcelImportExport construct() { return new Tutorial_ExcelImportExport(); } public static ClassDescription description() { return "@GLS105893"; } public static void main(Args _args) { Tutorial_ExcelImportExport import; ; import = Tutorial_ExcelImportExport::construct(); if (import.prompt()) { import.runOperation(); } } } В нем необходимо нажать кнопку Обзор, выбрать файл и нажать кнопку Отправить. Если все прошло успешно, то можно жать ОК. Класс начнет работать и перекладывать содержимое из одного файла в другой. По завершении перекладки - система предложит сохранить новый файл Здесь можно нажать кнопку загрузить и файл будет скачан браузером в папку Загрузки (ну или будет выдан запрос, куда его сохранять - в зависимости от настроек браузера) Проверялось на PU10 и далее (на PU25 работает)
__________________
Возможно сделать все. Вопрос времени Последний раз редактировалось sukhanchik; 15.05.2019 в 20:02. |
|
|
За это сообщение автора поблагодарили: Oz (2), trud (10), raz (5), AlexeyS (5), AvrDen (1), IvanS (1), raniel (1), Dreadlock (4), pedrozzz (3), Vovan911 (1). |
03.07.2019, 16:19 | #2 |
Участник
|
В продолжении темы импорта из Excel.
Выложил классы обертки которые несколько упрощают импорт https://github.com/TrudAX/XppTools#-...-and-csv-files. Плюс расширил тулзу для генерации RunBase, чтобы она генерировала шаблонный код с использованием этих классов https://github.com/TrudAX/TRUDUtilsD...-class-builder |
|
|
За это сообщение автора поблагодарили: raz (1), sukhanchik (10), AvrDen (1). |
|
|