2011-10-07 14 views
6

Mam bazę danych sqlite3 na niektórych systemach, które muszę pobrać podczas bieżącej operacji. Zatrzymanie lub wstrzymanie dostępu do procesów nie jest możliwe. W zakresie, w jakim to rozumiem, muszę posiadać blokadę SHARED (jak opisano w http://www.sqlite.org/lockingv3.html) do bazy danych podczas pobierania, aby uniknąć zmian w bazie danych i uszkodzenia podczas pobierania. W jaki sposób mogę uzyskać taki zamek? Pobieranie jest kontrolowane z poziomu programu C++, więc potrzebowałbym uzyskać blokadę.Blokowanie sqlite3 db do pobrania pliku

EDYCJA: thkala zasugerował zrobić zrzut db. Ale wolałbym znaleźć rozwiązanie z blokowaniem, ponieważ nie jestem pewien, czy będzie dostępna wystarczająca ilość pamięci dla pełnej kopii bazy danych.

Odpowiedz

8

Nie, nie. nie i nie!

Przesyłanie wiadomości za pomocą zamków i ręczne kopiowanie plików to stary sposób na robienie rzeczy. SQLite ma teraz poprawną nazwę, którą możesz użyć. Jest to zalecany sposób wykonywania kopii SQLite w trybie on-line - można go użyć do utworzenia kopii bazy danych, którą można następnie pobrać w dogodnym dla siebie momencie.

EDIT:

Jeśli koniecznie mieć użyć blokady, można użyć metody opisane here - ewentualnie po przetłumaczeniu na język C:

  • otworzyć bazę danych

  • użytku instrukcja BEGIN IMMEDIATE, aby uzyskać dostęp do udostępnionej blokady.

  • Kopiuj/pobierz pliki ręcznie - upewnij się, że nie ominie Cię żadna. Istnieje co najmniej plik DB, plik kroniki i ewentualnie plik WAL. Możesz umieścić DB w oddzielnym katalogu, aby wszystko było prostsze.

  • ROLLBACK Transakcja, którą właśnie rozpocząłeś.

rozumiem, jak ta metoda może być przydatna w niektórych przypadkach, ale muszę powtórzyć, że to nie jestzalecana metoda dłużej.

+0

Nie wiedziałem o kopii zapasowej interfejsu API, bardzo ładne! – RushPL

+0

Używanie kopii zapasowej interfejsu API jest problemem, ponieważ nie jestem pewien, czy mam wystarczającą ilość wolnego miejsca na wykonanie pełnej kopii bazy danych. –

-3

Rozwiązanie tutaj jest złe, pozostawiając je potomności, a dla ludzi, aby dowiedzieć się, dlaczego to zły pomysł.

Myślę, że można również uciec z kopiowaniem bazy danych wraz z dziennikiem. (Skopiuj oba pliki db i journal do plików tmp, a następnie pobierz je) Następnie na zdalnym końcu spróbuj otworzyć ten databse i naprawi się sam . Jest to przewidziane, że aplikacja używa właściwych transakcji.

Proszę przeczytać poniższe uwagi, które wyjaśniają, dlaczego tak się dzieje:

Istotą tego jest, można skopiować dziennik db &, ale tylko jeśli można dostać zarówno z dokładnie tym samym momencie, w czasie .

Co jest mniej więcej niemożliwe.

+3

NIE! NIE! NIE! To * przepis * na uszkodzenie danych! Dzienniki DB wymagają odpowiedniej semantyki systemu plików - czego NIE MASZ podczas kopiowania plików przez sieć. -1 – thkala

+0

Problem 1: Przez Internet plik DB można pobrać sekundami lub nawet * minutami * po/przed dziennikiem. – thkala

+0

Nie sądzę, że to zadziała, jeśli podczas kopiowania będzie dostęp do zapisu. –

2

I niby pomijane rozwiązanie: Zacznij transakcję z

BEGIN IMMEDIATE TRANSCTION 

i zakończyć go z

END TRANSACTION 

aby nabyć blokadę. Słowa kluczowe IMMEDIATE nie są domyślne, a db jest już zablokowany (RESERVED lock aquired), gdy połączenie zostanie zwrócone.

Powiązane problemy