Последняя версия DataExpress 3 beta от 9 октября 2018 года. Скачать. Энциклопедия DX. Форум на Develop-Soft

Загрузка данных в базу по условию

Вопросы, связанные с конструктором приложений баз данных DataExpress.
Аватара пользователя
Гocть
Эксперт
Сообщения: 1130
Зарегистрирован: Пн ноя 27, 2017 8:02 am

Re: Загрузка данных в базу по условию

Сообщение Гocть » Сб июн 02, 2018 4:34 pm

Neko писал(а):"слияние данных"

Думаю близко к теме будет:

Код: Выделить всё

const ImportImage =
'Qk02AwAAAAAAADYAAAAoAAAAEAAAABAAAAABABgAAAAAAAADAADEDgAAxA4AAAAAAAAAAAAAU5hIU'+
'5dHUpdLVJhIUphJUphIUphJUphJUphJUZdIVJhJVJhIVZlJVJlJVZlJUphJU5dKUphJUpdLUphMUZ'+
'dIUphJUphIUphJUphJUphJVJhIVJhIUphIVJhIU5lKU5lKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5h'+
'KU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hK'+
'U5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKibmCvde5vde5ZaJcU5hKU5hKi7qFvde5vNe4Y6JbU5hKU'+
'5hKU5hKU5hKU5hKU5hKXJ1T4u7g////1OXSVZpMbKdk+Pv3////rs+pU5hKU5hKU5hKU5hKU5hKU5'+
'hKU5hKU5hKbKdk9Pn0////rc6o2urZ////1OXSVppNU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5h'+
'KhrZ//v7+////////8PXuY6JbU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKvde5////'+
'////kb6KU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKa6Zj9vr1////////4O3eWpxRU'+
'5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKWJpO3Ora////1ebS8PXu////v9m8VJlLU5hKU5hKU5'+
'hKU5hKU5hKU5hKU5hKU5hKstGu////+fv4a6ZjiLiB////////mMGSU5hKU5hKU5hKU5hKU5hKU5h'+
'KU5hKVZpMgbR6gbR6dKtsU5hKU5hKfLF0gbR6fLF0U5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hK'+
'U5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU'+
'5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5hKU5'+
'hKU5hKU5hKU5hKU5hK';

var MI,D:TMenuItem;
ExcelFileName,TxtReportFile:string;

function SelectFile:string;
var OD:TOpenDialog;
begin
  OD:=TOpenDialog.Create(nil);
  OD.Title:='Выбор файла импорта';
  OD.InitialDir:='';
  OD.Filter:='Excel|*.xls;*.xlsx';
  OD.FilterIndex:=0;
  if OD.Execute then
    Result:=OD.FileName
  else
    Result:='';
    OD.Free;
end;

function CDate(SDate:string):TDateTime;
var S:string;
begin
if SDate='' then exit;
S:=Copy(SDate,9,2)+'.'+Copy(SDate,6,2)+'.'+Copy(SDate,1,4);
if not TryStrToDate(S,result) then exit;
result:=StrToDate(S);
end;

function DateMagExists(Dt:TDateTime;Mag:string):boolean;
begin
if EvalExpr(
'DBCOUNT("Продажа", "[!Дата]='''+DateToStr(Dt)+
''' & [!Отдел|Отдел]='''+Mag+'''")',Self) > 0
then
Result:=true else Result:=false;
end;

type
TTitle = record
Magazin:string;
DataS:TDateTime;
DataPo:TDateTime;
end;

function GetTitle(s:string):TTitle;
var SL:TStrings;
i:integer;
T:TTitle;
begin
SL:=TStringList.Create;

S:=StringReplace(S,'Отчет по продажам за период c:',';',[]);
S:=StringReplace(S,'по:',';',[]);
S:=StringReplace(S,'в магазине',';',[]);


SplitStr(Trim(S),';',SL)
  for i:=0 to SL.Count-1 do
  begin
    if Trim(SL[i])='' then
    SL.Delete(i);
    SL[i]:=Trim(SL[i]);
  end;
T.Magazin:=StringReplace(SL[2],'"','',[rfReplaceAll]); //string;
T.DataS:=CDate(SL[0]);
T.DataPo:=CDate(SL[1]);
result:=T;
SL.Free;
end;

{


███████████████████████████████
█─██─█─███─█────█────█────█───█
█─██─█──█──█─██─█─██─█─██─██─██
█─█──█─█─█─█─██─█─██─█────██─██
█──█─█─███─█─██─█─██─█─█████─██
█─██─█─███─█─██─█────█─█████─██
███████████████████████████████

}

procedure LoadXlsx(Sheet:variant);
 var i,j,k,m:integer;
 Title, DataProdazhi, Magazin, Kassir,
 Tip, Kod, Cena, SkidkaProc, KolVo, Stoimost,
 VidOplaty:variant;
 PFm,TFm:TdxForm;
 TFloat:extended;
 //DMAE:boolean;
 S
 //,MAG
 ,FIO
 :string;
 DataSet,SLParent,SLChild,SLParentFields,SLChildFields,ImportReport:TStringList;

begin

DataSet:=TStringList.Create;
SLParent:=TStringList.Create;
SLChild:=TStringList.Create;
SLParentFields:=TStringList.Create;
SLChildFields:=TStringList.Create;
ImportReport:=TStringList.Create;

 PFm:=TdxForm.Create('Продажа');
 TFm:=PFm.Forms['Проданный товар'];
//debug(#13#10+#13#10)
ImportReport.Add('====== Импорт продаж из xlsx ======='+#13#10);
ImportReport.Add('Начало импорта: '+DateToStr(Now)+'_'+TimeToStr(Now));
ImportReport.Add('Импортируемый файл: '+ExcelFileName+#13#10);

  try
    if Sheet.Cells(2,2).value<>'Дата' then RaiseException(erCustomError,'Дата');
    if Sheet.Cells(2,5).value<>'Кассир' then RaiseException(erCustomError,'Кассир');
    if Sheet.Cells(2,6).value<>'Тип' then RaiseException(erCustomError,'Тип');
    if Sheet.Cells(2,7).value<>'Код' then RaiseException(erCustomError,'Код');
    if Sheet.Cells(2,9).value<>'Цена' then RaiseException(erCustomError,'Цена');
    if Sheet.Cells(2,11).value<>'Скидка(%)' then RaiseException(erCustomError,'Скидка(%)');
    if Sheet.Cells(2,13).value<>'Кол-во' then RaiseException(erCustomError,'Кол-во');
    if Sheet.Cells(2,14).value<>'Стоимость' then RaiseException(erCustomError,'Стоимость');
    if Sheet.Cells(2,15).value<>'Вид оплаты' then RaiseException(erCustomError,'Вид оплаты');
  except;
    ImportReport.Add('Импорт прерван. Обнаружены ошибки:'+#13#10+
    'Колонка "'+ExceptionParam+'" не найдена');
    PFm.Free;
    exit;
  end;

  Title:=Sheet.Cells(1,1).value; // текст заголовка

ImportReport.Add('Магазин: "'+GetTitle(Title).Magazin+'"');
ImportReport.Add('Начало периода: '+DateToStr(GetTitle(Title).DataS));
ImportReport.Add('Конец периода: '+DateToStr(GetTitle(Title).DataPo)+#13#10);

  for i:=3 to Sheet.UsedRange.Rows.Count() do
  begin
  try

    DataProdazhi:=CDate(Sheet.Cells(i,2).value); // родитель
    Magazin:=GetTitle(Title).Magazin; // родитель
    Kassir:=Sheet.Cells(i,5).value; // родитель

    Tip:=Sheet.Cells(i,6).value; // дочка (Оплата (не возврат)
    Kod:=Sheet.Cells(i,7).value; // дочка
    Cena:=Sheet.Cells(i,9).value; // дочка
    SkidkaProc:=Sheet.Cells(i,11).value; // дочка
    KolVo:=Sheet.Cells(i,13).value; // дочка
    Stoimost:=Sheet.Cells(i,14).value; // дочка
    VidOplaty:=Sheet.Cells(i,15).value; // дочка

    if Length(Kod)=0 then
    Continue;

    if Pos(DateToStr(DataProdazhi)+'&'+Magazin,DataSet.CommaText)>0 then // дата во всем обработанном списке
        for j:=0 to DataSet.Count-1 do  // если нашли такую же дату - перебираем сформированный лист (ищем конкретную строку)
        begin
        if Pos(DateToStr(DataProdazhi)+'&'+Magazin,DataSet[j])>0 then // уже найдена такая дата в текущей найденной строке листа
          begin
                S:=DataSet[j]     +';'+
                VarToStr(Tip)+'&'+ // добавляем дочернюю запись в существующий набор найденной строки
                VarToStr(Kod)+'&'+
                VarToStr(Cena)+'&'+
                VarToStr(SkidkaProc)+'&'+
                VarToStr(KolVo)+'&'+
                VarToStr(Stoimost)+'&'+
                VarToStr(VidOplaty);
            DataSet.Delete(j);
            DataSet.Insert(j, S);
            Break;
          end;
        end
        else                               // иначе - родитель + таблица
        DataSet.Add(VarToStr(DataProdazhi)+'&'+
                VarToStr(Magazin)+'&'+
                VarToStr(Kassir)+'#'+

                VarToStr(Tip)+'&'+ // добавляем дочернюю запись в существующий набор найденной строки
                VarToStr(Kod)+'&'+
                VarToStr(Cena)+'&'+
                VarToStr(SkidkaProc)+'&'+
                VarToStr(KolVo)+'&'+
                VarToStr(Stoimost)+'&'+
                VarToStr(VidOplaty));
    except;
    //  PFm.cancel;
     // break;
     finally;
    end;
  end;

for k:=0 to DataSet.Count-1 do
begin

SplitStr(DataSet[k],'#',SLParent);
SplitStr(SLParent[0],'&',SLParentFields);

PFm.OpenRecords('[!Дата]='''+SLParentFields[0]+
''' & [!Отдел|Отдел]='''+SLParentFields[1]+'''',false);

if PFm.REcordCount=0 then
  begin

    PFm.Append;

    PFm['Дата']:=StrToDate(SLParentFields[0]);

    PFm['Отдел']:=EvalExpr('DBGETID("Отделы", "[!Отдел]='''+SLParentFields[1]+'''")',nil);

    if PFm['Отдел'] =null then
    begin
    ImportReport.Add('ОШИБКА! Магазин "'+SLParentFields[1]+'" не найден в справочнике "'+
    dxLookupComboBox2.SourceFormName+'". Импорт прерван.')
    exit;
    end;

    FIO:=StringReplace(SLParentFields[2],' ',';',[rfReplaceAll]);

    PFm['Продавец']:=EvalExpr('DBGETID("Сотрудники", "[!ФИО]==INDEXOF(0,'''
    +FIO+''') & [!ФИО]==INDEXOF(1,'''+FIO+''')")',nil);
    if PFm['Продавец']=null then
    ImportReport.Add('ОШИБКА! Сотрудник "'+SLParentFields[2]+'" не найден в справочнике "Сотрудники"');


   TFm.MoveFirst;
   SplitStr(SLParent[1],';',SLChild)

  for m:=0 to SLChild.Count-1 do
  begin
   SplitStr(SLChild[m],'&',SLChildFields);

      if SLChildFields[0]<>'Оплата' then
        begin
        ImportReport.Add('Товар с кодом '+SLChildFields[1]+
        ' в документ продажи от '+SLParentFields[0]+
        ' НЕ импортирован. Статус: '+SLChildFields[0]);
        Continue;
        end;

   TFm.Append;
     TFm['Товар']:=
     EvalExpr('DBGETID("Справочник товаров", "[!Артикул]='''+SLChildFields[1]+'''")',nil);
     if TFm['Товар']=null then
       begin
       ImportReport.Add('ОШИБКА! Товар с кодом '+SLChildFields[1]+' не найден в справочнике товаров. Пропущен.');
       Continue;
       end;
     if TryStrToFloat(SLChildFields[3],TFloat) then
     TFm['Скидка']:=StrToFloat(SLChildFields[3]);
     if TryStrToFloat(SLChildFields[4],TFloat) then
     TFm['Количество']:=SLChildFields[4];
     if SLChildFields[6]<>'Наличные' then
     TFm['Терминал']:=1;
     TFm.Post;
  end;
    PFm.Post;
    PFm.Close;
    ImportReport.Add('Добавлена продажа от '+SLParentFields[0])
  end
else
begin
ImportReport.Add('Продажа от '+SLParentFields[0]+': дубликат не импортирован.')
PFm.Close;
Continue;
end;
end;

DataSet.Free;
SLParent.Free;
SLChild.Free;
SLParentFields.Free;
SLChildFields.Free;
PFm.Free;
Self.Refresh;
ImportReport.Add(#13#10+'========== Импорт завершен ========='+#13#10);

TxtReportFile:=ExtractFilePath(ExcelFileName)+
'Отчет импорта '+DateToStr(Now)+
'_'+StringReplace(TimeToStr(Now),':','-',[rfReplaceAll])+
'_'+ExtractFileName(ExcelFileName)+'.txt';

ImportReport.Add('Отчет импорта сохранен в файл:'+#13#10+TxtReportFile+#13#10);

//debug(ImportReport.Text);

ImportReport.SaveToFile(TxtReportFile);
ShellExecute('','notepad','"'+TxtReportFile+'"','',5);

ImportReport.Free;
end;

{█████████████████████████████████ E N D ██████████████████████████████████████}


procedure ImportFromExcel(Sender:TObject);
  var
  Excel,WorkBook: Variant;
begin
  ExcelFileName:=SelectFile;
  if
    (ExcelFileName='') or
    ((ExtractFileExt(ExcelFileName)<>'.xls') and
    (ExtractFileExt(ExcelFileName)<>'.xlsx'))
  then
    exit;

begin
  Excel:= CreateOleObject('Excel.Application');
  try
    if FileExists(ExcelFileName) then
      begin
        WorkBook := Excel.WorkBooks.Open(ExcelFileName);
        LoadXlsx(WorkBook.ActiveSheet);
      end
    else
      begin
        Debug('Файл "'+ExcelFileName+'" не найден');
        Excel.Quit;
        Exit;
      end;
    Excel.Visible := false;
    Excel.quit;
  except
    Excel.quit;
    debug(ExceptionParam);
  finally
    Excel:=Unassigned;
    WorkBook:=Unassigned;
  end;
end;


end;

procedure CreateMenuItem(Sender:TObject);
var IStr:TStringStream;
begin
 MI:=TMenuItem.Create(Self.Grid.PopupMenu);
 MI.Caption:='Импорт продаж из *.xlsx';
 D:=TMenuItem.Create(Self.Grid.PopupMenu);
 D.Caption:='-';
 IStr:=TStringStream.Create(DecodeBase64(VarToStr(ImportImage),true));
 IStr.Position := 0;
 MI.Bitmap.LoadFromStream(IStr);
 MI.OnClick:=@ImportFromExcel;
 IStr.free;
 Self.Grid.PopupMenu.Items.Add(D);
 Self.Grid.PopupMenu.Items.Add(Mi);
end;

procedure DeleteMenuItem(Sender:TObject);
begin FreeObj(Mi); end;

procedure Form_Create;
begin
  CreateMenuItem(nil);
end;

procedure Form_Destroy;
begin
  DeleteMenuItem(nil)
end;

Импорт двухмерной таблицы с делением на родителя и подчинённые данные. Допиливайте (ну или меня можно попросить допилить под ваши нужды ;) ).
Фрилансер. Разработка на заказ. Консультирование.