Android cep telefonunda veritabanını bulamıyorum

Delphi'de kod yazma ile ilgili sorularınızı bu foruma yazabilirsiniz.
Cevapla
lazanya61
Üye
Mesajlar: 4
Kayıt: 17 Oca 2021 02:45

Android cep telefonunda veritabanını bulamıyorum

Mesaj gönderen lazanya61 »

Merhaba. Bir proje üzerinde çalışıyorum. Şimdi veritabanında 2 adet tablom var. Bunlara Redmi 10 da deniyorum ve kayıt yapıyor. 3. bir tablo ekledim, ama 3. tabloya veri kaydedemedim bir türlü. Veritabanını telefonda bulup 3. tabloyu oluşturmuş mu diye bakmam lazım. Ayrıca ileride veritabanın yedeğini almam gerekecek. Program android\data altında com.embarcadero.takip klasöre kurulmuş. sınıflar ve öğrenciler tablosuna veri kaydedildiğine göre takip.db olması lazım. Ama nerede?
__________
var
DatabasePath: string;
FileStream: TFileStream;
begin
DatabasePath := TPath.Combine(TPath.GetDocumentsPath, 'takip.db');

if not TFile.Exists(DatabasePath) then
begin
FileStream := TFileStream.Create(DatabasePath, fmCreate);
FileStream.Free;
end;

Form1.FDConnection1.Params.Database := DatabasePath;
Form1.FDConnection1.Params.DriverID := 'SQLite';
Form1.FDConnection1.Connected := True;

end;
_________________________

FDConnection1.ExecSQL('CREATE TABLE IF NOT EXISTS siniflar (' +
'id INTEGER PRIMARY KEY AUTOINCREMENT,' +
'sinif_adi TEXT NOT NULL);');

FDConnection1.ExecSQL(
'CREATE TABLE IF NOT EXISTS ogrenciler (' +
'ogrenci_no INTEGER PRIMARY KEY,' +
'ogrenci_adi TEXT NOT NULL,' +
'sinif_id INTEGER,' +
'FOREIGN KEY(sinif_id) REFERENCES siniflar(id)' +
');'
);
______
ertank
Kıdemli Üye
Mesajlar: 1716
Kayıt: 12 Eyl 2015 12:45

Re: Android cep telefonunda veritabanını bulamıyorum

Mesaj gönderen ertank »

TPath.GetDocumentsPath Android cihazlarda

Kod: Tümünü seç

/data/data/<application ID>/files 
dizini altına kayıt ediyor yardım dökümanını okuduğumuz zaman.

Tavsiyem testlerinizi yapmak için uygulamanıza dosya yazma izini verip TPath.GetSharedDocumentsPath içine kaydedin veritabanınızı. Bu durumda

Kod: Tümünü seç

/storage/emulated/0/Documents
dizinine kayıt ediyor olacaksınız. Bu da Android cihazın Dosyalar kısmıdır. Buraya kolaylıkla erişim sağlayabilirsiniz.

Paylaştığınız kodlardan kullandığınız veritabanını anlayamadım. Ancak çoğu veritabanı için boş veirtabanı oluşturma imkanı vardır. Siz kendiniz sıfır byte uzunluğunda dosya oluşturmaya çalışıyorsunuz gibi okuyorum kodları. Özel bir sebebi yoksa bunu yapmamalısınız.

Her veritabanının kendi dosya formatı vardır. Bunu veritabanı motoru bilir.

- SQLite3 kendi veritabanı oluşturur.
- MemoryTable çoğunlukla kendi formatında kayıt eder ve okur.
- FirebirdSQL / Interbase kendi veritabanı dosyasını oluşturur.

Kullanıdğınız veritabanının boş veritabanı oluşturmayı nasıl yaptığını öğrenip ardından bunu FireDAC ile nasıl yapabileceğinizi öğrenmelisiniz.
lazanya61
Üye
Mesajlar: 4
Kayıt: 17 Oca 2021 02:45

Re: Android cep telefonunda veritabanını bulamıyorum

Mesaj gönderen lazanya61 »

sayın hocam progamımı şöyle özetleyebilirim. iki adet formum var. 1. formda sınıflar(llistbox1) ve üzerine tıklanınca ogrenciler (listbox2) var. sınıf kaydet ve öğrenci kaydet telefon üzerinde kaydediliyor.

1. forma ait kodlarım şöyle;
unit Unit1;

Kod: Tümünü seç

interface

uses
  System.SysUtils, System.Types, System.UITypes, System.Classes, System.Variants,
  FMX.Types, FMX.Controls, FMX.Forms, FMX.Graphics, FMX.Dialogs,
  FireDAC.Stan.Intf, FireDAC.Stan.Option, FireDAC.Stan.Error, FireDAC.UI.Intf,
  FireDAC.Phys.Intf, FireDAC.Stan.Def, FireDAC.Stan.Pool, FireDAC.Stan.Async,
  FireDAC.Phys, FireDAC.Phys.SQLite, FireDAC.Phys.SQLiteDef,
  FireDAC.Stan.ExprFuncs, FireDAC.Phys.SQLiteWrapper.Stat, FireDAC.FMXUI.Wait,
  FireDAC.Stan.Param, FireDAC.DatS, FireDAC.DApt.Intf, FireDAC.DApt, Data.DB,
  FireDAC.Comp.DataSet, FireDAC.Comp.Client, FMX.StdCtrls, FMX.Layouts,
  FMX.Controls.Presentation, FMX.Edit, FMX.ListBox, FMX.Objects, System.IOUtils,
  FMX.DialogService, FMX.DialogService.Async;

type
  TForm1 = class(TForm)
    ListBoxsiniflar: TListBox;
    ListBoxogrenciler: TListBox;
    Rectangle1: TRectangle;
    Rectangle2: TRectangle;
    Rectangle3: TRectangle;
    btsnfkaydet: TButton;
    btogrkaydet: TButton;
    FDPhysSQLiteDriverLink1: TFDPhysSQLiteDriverLink;
    FDConnection1: TFDConnection;
    FDQuery1: TFDQuery;
    Timer1: TTimer;
    Editsinifadi: TEdit;
    Editogrno: TEdit;
    Editogradi: TEdit;
    Button1: TButton;
    BtnShowDetailsClick: TButton;
    btsnfSil: TButton;
    procedure Timer1Timer(Sender: TObject);
    procedure FormCreate(Sender: TObject);
    procedure btsnfkaydetClick(Sender: TObject);
    procedure btogrkaydetClick(Sender: TObject);
    procedure ListBoxsiniflarChange(Sender: TObject);
    procedure ListBoxogrencilerClick(Sender: TObject);
    procedure BtnShowDetailsClickClick(Sender: TObject);
    procedure btsnfSilClick(Sender: TObject);
    procedure Button1Click(Sender: TObject);
  private
    procedure InitializeDatabase;
    procedure LoadClasses;
    procedure LoadStudents(sinifID: Integer);

  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.fmx}

uses Unit2;

procedure TForm1.LoadStudents(sinifID: Integer);
var
  Query: TFDQuery;
begin
  Query := TFDQuery.Create(nil);
  try
    Query.Connection := Form1.FDConnection1;
    Query.SQL.Text := 'SELECT * FROM ogrenciler WHERE sinif_id = :sinif_id';
    Query.Params[0].Value := sinifID;
    Query.Open;

    ListBoxogrenciler.Clear;
    while not Query.Eof do
    begin
      ListBoxogrenciler.Items.Add(Query.FieldByName('ogrenci_adi').AsString);
      Query.Next;
    end;
  finally
    Query.Free;
  end;
end;

procedure TForm1.BtnShowDetailsClickClick(Sender: TObject);
var
  Query: TFDQuery;
  ogrenciNo: Integer;
  ogrenciAdi: string;
begin
  if ListBoxogrenciler.ItemIndex <> -1 then
  begin
    ogrenciAdi := ListBoxogrenciler.Items[ListBoxogrenciler.ItemIndex];

    Query := TFDQuery.Create(nil);
    try
      Query.Connection := FDConnection1;
      Query.SQL.Text := 'SELECT ogrenci_no FROM ogrenciler WHERE ogrenci_adi = :ogrenci_adi';
      Query.Params[0].AsString := ogrenciAdi;
      Query.Open;

      if not Query.Eof then
      begin
        ogrenciNo := Query.FieldByName('ogrenci_no').AsInteger;

        if not Assigned(Form2) then
          Application.CreateForm(TForm2, Form2);

        Form2.ogrenciNo := ogrenciNo; // ogrenciNo'yu Form2'ye aktar
        Form2. ogrenciAdi := ogrenciAdi; // ogrenciAdi'yi Form2'ye aktar
        Form2.LoadStudentDetails; // Form2'deki bilgileri doldur

        Form2.Show;
      end;
    finally
      Query.Free;
    end;
  end
  else
    ShowMessage('Lütfen bir öğrenci seçin.');
end;
procedure TForm1.btogrkaydetClick(Sender: TObject);
var
  ogrenciNo: Integer;
  ogrenciAdi: string;
  sinifID: Integer;
begin
  ogrenciNo := StrToInt(Editogrno.Text); // Öğrenci numarasını Editogrno'dan al
  ogrenciAdi := Editogradi.Text; // Öğrenci adını Editogradi'den al

  if ogrenciNo = 0 then
  begin
    ShowMessage('Öğrenci numarası boş olamaz.');
    Exit;
  end;

  if ogrenciAdi = '' then
  begin
    ShowMessage('Öğrenci adı boş olamaz.');
    Exit;
  end;

  if ListBoxsiniflar.ItemIndex = -1 then
  begin
    ShowMessage('Lütfen bir sınıf seçin.');
    Exit;
  end;

  // Seçilen sınıfın ID'sini al
  sinifID := Integer(ListBoxsiniflar.Items.Objects[ListBoxsiniflar.ItemIndex]);

  // Öğrenci ekleme işlemi için SQL sorgusu
  Form1.FDConnection1.ExecSQL(
    'INSERT INTO ogrenciler (ogrenci_no, ogrenci_adi, sinif_id) VALUES (:ogrenci_no, :ogrenci_adi, :sinif_id);',
    [ogrenciNo, ogrenciAdi, sinifID] // ListBoxsiniflar'dan seçilen sınıfın ID'si
  );

  ShowMessage('Öğrenci kaydedildi: ' + ogrenciAdi);

  // Öğrenci eklendikten sonra listeyi güncelle
  LoadStudents(sinifID); // Bu fonksiyonu sınıf içerisinde implemente edeceğiz
end;

procedure TForm1.btsnfkaydetClick(Sender: TObject);
begin
  if Form1.Editsinifadi.Text <> '' then
  begin
    Form1.FDConnection1.ExecSQL('INSERT INTO siniflar (sinif_adi) VALUES (:sinif_adi);', [Form1.Editsinifadi.Text]);
    ShowMessage('Sınıf eklendi: ' + Form1.Editsinifadi.Text);

    Form1.LoadClasses; // Yeni sınıfı da içerecek şekilde sınıfları yeniden yükle
  end
  else
    ShowMessage('Sınıf adı boş olamaz');
end;
 procedure TForm1.btsnfSilClick(Sender: TObject);
var
  classID: Integer;
  Query: TFDQuery;
begin
  if Assigned(ListBoxsiniflar) and (ListBoxsiniflar.ItemIndex <> -1) then
  begin
    // Seçilen sınıfın ID'sini al
    classID := Integer(ListBoxsiniflar.Items.Objects[ListBoxsiniflar.ItemIndex]);
    // Kullanıcıya onay mesajı göster (asenkron olarak)
    TDialogServiceAsync.MessageDialog(
      'Sınıfı ve bu sınıfa ait öğrencileri silmek istediğinize emin misiniz?',
      TMsgDlgType.mtConfirmation,
      [TMsgDlgBtn.mbYes, TMsgDlgBtn.mbNo],
      TMsgDlgBtn.mbNo, // Default button
      0, // Help context
      procedure(const AResult: TModalResult)
      begin
        if AResult = mrYes then
        begin
          try
            // Öğrencileri silme işlemi
            Query := TFDQuery.Create(nil);
            try
              Query.Connection := FDConnection1;
              Query.SQL.Text := 'DELETE FROM ogrenciler WHERE sinif_id = :sinif_id';
              Query.Params[0].AsInteger := classID;
              Query.ExecSQL;
            finally
              Query.Free;
            end;
            // Sınıfı silme işlemi
            Query := TFDQuery.Create(nil);
            try
              Query.Connection := FDConnection1;
              Query.SQL.Text := 'DELETE FROM siniflar WHERE id = :id';
              Query.Params[0].AsInteger := classID;
              Query.ExecSQL;
            finally
              Query.Free;
            end;
            ShowMessage('Sınıf ve bu sınıfa ait öğrenciler başarıyla silindi.');
            // Sınıfları yeniden yükle
            LoadClasses;
            ListBoxogrenciler.Clear;
          except
            on E: Exception do
              ShowMessage('Hata: ' + E.Message);
          end;
        end
        else
          ShowMessage('İşlem iptal edildi.');
      end
    );
  end
  else
    ShowMessage('Lütfen silinecek bir sınıf seçin.');
end;

procedure TForm1.Button1Click(Sender: TObject);
begin
Halt;
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
  Timer1.Enabled := True;
end;

procedure TForm1.InitializeDatabase;
begin
  FDConnection1.ExecSQL('CREATE TABLE IF NOT EXISTS siniflar (' +
    'id INTEGER PRIMARY KEY AUTOINCREMENT,' +
    'sinif_adi TEXT NOT NULL);');

  FDConnection1.ExecSQL(
    'CREATE TABLE IF NOT EXISTS ogrenciler (' +
    'ogrenci_no INTEGER PRIMARY KEY,' +
    'ogrenci_adi TEXT NOT NULL,' +
    'sinif_id INTEGER,' +
    'FOREIGN KEY(sinif_id) REFERENCES siniflar(id)' +
    ');'
  );

  // 'bilgiler' tablosunu sil ve yeniden oluştur
  FDConnection1.ExecSQL('DROP TABLE IF EXISTS bilgiler');

FDConnection1.ExecSQL(
    'CREATE TABLE IF NOT EXISTS bilgiler (' +
    'id INTEGER PRIMARY KEY AUTOINCREMENT,' +
    'ogrenci_no INTEGER,' +
    'ogrenci_adi TEXT NOT NULL,' +
    'odevyok INTEGER NOT NULL,' +
    'odeveksik INTEGER NOT NULL,' +
    'odevalmis INTEGER NOT NULL,' + // Yeni sütun
    'worksheetundone INTEGER NOT NULL,' + // Yeni sütun
    'noworksheet INTEGER NOT NULL,' + // Yeni sütun
    'araceksik INTEGER NOT NULL,' + // Yeni sütun
    'FOREIGN KEY(ogrenci_no) REFERENCES ogrenciler(ogrenci_no)' +
    ');'
  );
end;

procedure TForm1.ListBoxogrencilerClick(Sender: TObject);
var
  Query: TFDQuery;
begin
  if ListBoxogrenciler.ItemIndex = -1 then
    Exit;
  Query := TFDQuery.Create(nil);
  try
    Query.Connection := FDConnection1;
    Query.SQL.Text := 'SELECT * FROM ogrenciler WHERE ogrenci_adi = :ogrenci_adi';
    Query.Params[0].AsString := ListBoxogrenciler.Items[ListBoxogrenciler.ItemIndex];
    Query.Open;
    if not Query.IsEmpty then
    begin
      Editogrno.Text := Query.FieldByName('ogrenci_no').AsString;
      Editogradi.Text := Query.FieldByName('ogrenci_adi').AsString;
    end;
  finally
    Query.Free;
  end;
end;

procedure TForm1.ListBoxsiniflarChange(Sender: TObject);
var
  sinifID: Integer;
begin
  // ListBoxsiniflar'dan seçilen sınıfın ID'sini al
  if ListBoxsiniflar.ItemIndex <> -1 then
  begin
    sinifID := Integer(ListBoxsiniflar.Items.Objects[ListBoxsiniflar.ItemIndex]);
    // Öğrencileri bu sınıfa göre yükle
    LoadStudents(sinifID);
  end
  else
  begin
    ListBoxogrenciler.Clear;
    ShowMessage('Lütfen bir sınıf seçin.');
  end;
end;

procedure TForm1.LoadClasses;
var
  Query: TFDQuery;
begin
  Query := TFDQuery.Create(nil);
  try
    Query.Connection := FDConnection1;
    Query.SQL.Text := 'SELECT * FROM siniflar';
    Query.Open;
    Form1.ListBoxsiniflar.Clear;
    while not Query.Eof do
    begin

      ListBoxsiniflar.Items.AddObject(Query.FieldByName('sinif_adi').AsString, TObject(Query.FieldByName('id').AsInteger));
      Query.Next;
    end;
  finally
    Query.Free;
  end;
end;



procedure TForm1.Timer1Timer(Sender: TObject);
var
  DatabasePath: string;
  FileStream: TFileStream;
begin
  DatabasePath := TPath.Combine(TPath.GetDocumentsPath, 'takip.db');

  if not TFile.Exists(DatabasePath) then
  begin
    FileStream := TFileStream.Create(DatabasePath, fmCreate);
    FileStream.Free;
  end;

  Form1.FDConnection1.Params.Database := DatabasePath;
  Form1.FDConnection1.Params.DriverID := 'SQLite';
  Form1.FDConnection1.Connected := True;

  InitializeDatabase;

  Form1.LoadClasses;
  Timer1.Enabled := False;
end;

end.
procedure TForm1.InitializeDatabase ile database oluştuyor sanırım, çünkü verileri(siniflar ve ogrenciler) kaydediyor. fdconnection ım var, driver sqlite e baplı. query, physqlitedriver.... var. form de sıkıntı yaşamadım. problemi form2 de yaşıyorum. form1 de seçilen öğrenciye ait detay bilgileri form2 de veritabanına yazıp görüntülenmesini istiyorum. çalışma anında kayıt etti görünüyor, ama programı açıp kapatınca sadece bilgiler tablosundaki veriler siliniyor. siniflar ve ogrenciler ise kayıt edildiği gibi duruyor. aslında telefonda veritabanını bulmak isteme amacım acaba bilgiler tablosunu create ediyor mu görmek. yazma izni olmasa sınıflara ve ogrencileri de kaydetmemesi lazım.
hazır tabloyu göndereyim dedim, deployment kısmından paketle kurulsun onu da beceremedim.
aşağıda 2. form kodlarım var.

Kod: Tümünü seç

unit Unit2;

interface

uses
  System.SysUtils, System.Types, System.UITypes, System.Classes, System.Variants,
  FMX.Types, FMX.Controls, FMX.Forms, FMX.Graphics, FMX.Dialogs,
  FMX.Controls.Presentation, FMX.Edit, FMX.Objects, FMX.StdCtrls,
  FireDAC.Stan.Intf, FireDAC.Stan.Option, FireDAC.Stan.Param,
  FireDAC.Stan.Error, FireDAC.DatS, FireDAC.Phys.Intf, FireDAC.DApt.Intf,
  FireDAC.Stan.Async, FireDAC.DApt, Data.DB, FireDAC.Comp.DataSet,
  FireDAC.Comp.Client, FireDAC.Stan.ExprFuncs, FireDAC.Phys.SQLiteWrapper.Stat,
  FireDAC.Phys.SQLiteDef, FireDAC.Phys, FireDAC.Phys.SQLite, FMX.Colors;

type
  TForm2 = class(TForm)
    Rectangle1: TRectangle;
    Rectangle2: TRectangle;
    Rectangle3: TRectangle;
    Rectangle4: TRectangle;
    Editno: TEdit;
    Editad: TEdit;
    Editodevyok: TEdit;
    Editodeveksik: TEdit;
    Editodevalmis: TEdit;
    Editworksheetundone: TEdit;
    Editnoworksheet: TEdit;
    Editaraceksik: TEdit;
    Button1: TButton;
    Buttonkaydet: TButton;
    FDQuery1: TFDQuery;
    Label1: TLabel;
    Label2: TLabel;
    Label3: TLabel;
    Label4: TLabel;
    Label5: TLabel;
    Label6: TLabel;
    Label7: TLabel;
    Label8: TLabel;
    FDPhysSQLiteDriverLink1: TFDPhysSQLiteDriverLink;
    ColorButton1: TColorButton;

    procedure ButtonkaydetClick(Sender: TObject);
    procedure Button1Click(Sender: TObject);
    procedure LoadStudentDetails;

  private
    procedure ClearEdits;
  public
    ogrenciNo: Integer;
    ogrenciAdi: string;
  end;

var
  Form2: TForm2;

implementation

{$R *.fmx}

uses Unit1;

procedure TForm2.Button1Click(Sender: TObject);
begin
  Close;
end;

procedure TForm2.ButtonkaydetClick(Sender: TObject);
var
  Query: TFDQuery;
begin
  Query := TFDQuery.Create(nil);
  try
    Query.Connection := Form1.FDConnection1;
    Query.SQL.Text :=
      'INSERT INTO bilgiler (ogrenci_no, ogrenci_adi, odevyok, odeveksik, odevalmis, worksheetundone, noworksheet, araceksik) ' +
      'VALUES (:ogrenci_no, :ogrenci_adi, COALESCE(:odevyok, 0), COALESCE(:odeveksik, 0), COALESCE(:odevalmis, 0), ' +
      'COALESCE(:worksheetundone, 0), COALESCE(:noworksheet, 0), COALESCE(:araceksik, 0))';

    // Parametrelerin atanması
    Query.Params[0].AsInteger := StrToInt(Editno.Text);
    Query.Params[1].AsString := Editad.Text;
    Query.Params[2].AsString := Editodevyok.Text; // Eğer Editodevyok.Text boş ise nil atayacak.
    Query.Params[3].AsString := Editodeveksik.Text; // Eğer Editodeveksik.Text boş ise nil atayacak.
    Query.Params[4].AsString := Editodevalmis.Text; // Eğer Editodevalmis.Text boş ise nil atayacak.
    Query.Params[5].AsString := Editworksheetundone.Text; // Eğer Editworksheetundone.Text boş ise nil atayacak.
    Query.Params[6].AsString := Editnoworksheet.Text; // Eğer Editnoworksheet.Text boş ise nil atayacak.
    Query.Params[7].AsString := Editnoworksheet.Text; // Eğer Editnoworksheet.Text boş ise nil atayacak.

    Query.ExecSQL;
    ShowMessage('Bilgiler kaydedildi.');
  except
    on E: Exception do
      ShowMessage('Hata: ' + E.Message);
  end;
  Query.Free;
end;


procedure TForm2.ClearEdits;
begin
  Editno.Text := '';
  Editad.Text := '';
  Editodevyok.Text := '';
  Editodeveksik.Text := '';
  Editodevalmis.Text := '';
  Editworksheetundone.Text := '';
  Editnoworksheet.Text := '';
  Editaraceksik.Text := '';
end;

procedure TForm2.LoadStudentDetails;
var
  Query: TFDQuery;
begin
  ClearEdits; // Editleri temizle

  // Editno ve Editad alanlarını ogrenciNo ve ogrenciAdi değişkenlerinden doldurun
  Editno.Text := IntToStr(ogrenciNo);
  Editad.Text := ogrenciAdi;

  Query := TFDQuery.Create(nil);
  try
    Query.Connection := Form1.FDConnection1;
    Query.SQL.Text := 'SELECT odevyok, odeveksik, odevalmis, worksheetundone, noworksheet, araceksik FROM bilgiler WHERE ogrenci_no = :ogrenci_no';
    Query.Params[0].AsInteger := ogrenciNo;
    Query.Open;

    if not Query.Eof then
    begin
      Editodevyok.Text := Query.FieldByName('odevyok').AsString;
      Editodeveksik.Text := Query.FieldByName('odeveksik').AsString;
      Editodevalmis.Text := Query.FieldByName('odevalmis').AsString;
      Editworksheetundone.Text := Query.FieldByName('worksheetundone').AsString;
      Editnoworksheet.Text := Query.FieldByName('noworksheet').AsString;
      Editaraceksik.Text := Query.FieldByName('araceksik').AsString;
    end
    else
    begin
      ShowMessage('Veritabanında bu öğrenci için bilgi bulunamadı.');
    end;
  finally
    Query.Free;
  end;
end;

end.
Dosya ekleri
001828.jpg
001828.jpg (867 Byte) 5586 kere görüntülendi
ertank
Kıdemli Üye
Mesajlar: 1716
Kayıt: 12 Eyl 2015 12:45

Re: Android cep telefonunda veritabanını bulamıyorum

Mesaj gönderen ertank »

Özetle;
- Manuel transaction başatıp commit edebilirsiniz.
- FDConnection transaction ayarlarınızı kontrol edebilirsiniz.
SQLite davranışı FDConnection ile nasıl bilmiyorum. Kendisi otomatik bir transaction başlatıyor ise commit edilmediği için kayıt etmiyor olması ihtimal.
Cevapla