2012-05-15 15 views
6

Przechowuję hierarchie plików katalogów i plików.Kaskadowe usuwanie tabeli danych i tabeli wyszukiwania w tym samym czasie

W tabeli innodb przechowuję szczegóły każdego katalogu/pliku i zachowuję macierzystą relację podrzędną z ograniczeniem klucza obcego, które będzie kaskadowane przy usuwaniu.

Tabela myisam służy do wyszukiwania tych katalogów/plików za pomocą wyszukiwania pełnotekstowego. Zawiera nazwy i identyfikatory każdego rzędu.

Wszystkie wiersze w tabeli danych (tabela innodb) będą miały odpowiedni wiersz w tabeli wyszukiwania (tabela myisam), a dodawanie lub usuwanie wierszy z tabeli danych musi być odzwierciedlone w tabeli wyszukiwania.

Próbuję znaleźć najlepsze rozwiązanie, aby zachować spójność danych między dwiema tabelami podczas usuwania katalogu nadrzędnego. Tabela innodb jest w porządku. Usuwam rodzica, kasowanie kasuje przez dzieci, dopóki wszystkie nie zostaną usunięte. Usunięcie odpowiednich wierszy z tabeli myisam jest trudniejsze.

Moja pierwsza myśl polegała na użyciu wyzwalacza do usunięcia na stole innodb. Po usunięciu wiersza usuwa on odpowiedni wiersz z tabeli myisam. Jednak ponieważ MySQL nie aktywuje wyzwalaczy podczas kasowania kasowania (znany błąd od 7 lat, który został naprawiony przez wspomnienie braku wsparcia w instrukcji), nie jest to możliwe.

Moja druga myśl została umieszczona relacja nadrzędna podrzędność w tabela wyszukiwania, ale jest to tabela myisam do obsługi funkcji wyszukiwania pełnego tekstu, a więc nie obsługuje ograniczeń klucza obcego.

Słyszałem, że innodb obsługuje teraz wyszukiwanie pełnotekstowe, więc pomyślałem, że mógłbym zmienić silnik tabeli wyszukiwania, ale jest on dostępny tylko w wersji laboratoryjnej.

Moja ostatnia myśl polegała na tym, aby porzucić ograniczenia związane z kluczem obcym i używać tylko wyzwalaczy, aby zachować spójność danych. Po usunięciu usuń z tabeli innodb i myisam, gdzie parent = OLD.id. Jednakże, aby zapobiec nieskończonym pętlom, które mogą uszkodzić wszystkie dane w tabeli, MySQL nie obsługuje manipulowania danymi w tej samej tabeli, która aktywowała wyzwalacz.

Uciekłem programowo, pobierając wszystkie dzieci w katalogu nadrzędnym poprzez pętlę żądań, jednak uważam, że musi być lepsza opcja. Czy jest jakaś inna praca, która byłaby bardziej wydajna? W tym momencie jedynymi dwiema opcjami, jakie mogę wymyślić, są oczekiwanie, aż jedno z powyższych podejść zostanie naprawione lub zmienione na inny RDBMS, taki jak PostgreSQL, który obsługuje wypalanie wyzwalaczy z kaskowego usunięcia.

Wszelkie inne pomysły będą mile widziane.

+0

Nie jestem pewien, czy to rozumiem, jestem raczej zdezorientowany twoim związkiem między dwiema tabelami. Otrzymuję to, że definiujesz relację między 2 tabelami, które różnią się od siebie nawzajem. Próbowałem już tego wcześniej i napotkałem problemy przy zachowaniu spójności danych, jeśli chcesz zachować spójność danych poprzez relację tabelową z użytkownikiem kluczy zagranicznych i podstawowych, użyj innodb na wszystkich tabelach, w których będziesz definiował swój związek. –

+0

Tabela wyszukiwania (myisam) jest używana jako moja wyszukiwarka dla tabeli danych (innodb). Ponieważ jednak katalogi z podkatalogami i plikami są usuwane, zmiany muszą uwzględniać zarówno tabelę danych, jak i tabelę wyszukiwania. Nie mogę użyć innodb dla wyszukiwarki ze względu na brak pełnej obsługi wyszukiwania tekstowego (przynajmniej w tym czasie). Relacja jest dobrze zdefiniowana w tabeli danych, ale usunięcia nie są odzwierciedlane w tabeli wyszukiwania. – JayceTDE

+0

+1 za dobrze napisane pytanie; niestety nie widzę żadnych alternatyw dla obecnego podejścia, ale może ktoś inny coś wymyśli – Daan

Odpowiedz

1

Tego rodzaju bóle głowy są właśnie tym, co sprawiło, że odsuwając się od mysql, gdzie to możliwe.

... Czuję, że ma być lepszym rozwiązaniem ...

Niestety nie ma. Prostym problemem jest to, że nie można usunąć kaskady i mysql wie, co właśnie usunięto. Dlatego twoja jedyna opcja to dowiedzieć się, co ma zamiar usunąć, zanim to zrobi (jest to algorytm, który zasugerowałeś na końcu).

Ponieważ kaskadowanie spowoduje uszkodzenie danych, nie należy używać klucza on update cascade, aby próba usunięcia katalogu nadrzędnego bez usunięcia dziecka zakończyła się niepowodzeniem.

Zalecam, aby utworzyć procedurę podnoszenia ciężkiego (usuwania) dla ciebie. Zapobiegnie to dużemu IO pomiędzy aplikacją a bazą danych, ponieważ jest ona ponownie wykorzystywana we wszystkich katalogach. Zapewni to również wspólny kod, jeśli kiedykolwiek uzyskasz dostęp do tej samej bazy danych za pośrednictwem innej aplikacji (lub po prostu chcesz coś zrobić ręcznie).

Jak stwierdziłem najpierw, używam PostgreSQL w większości tych dni. To jest jeden z przykładów tego.

Powiązane problemy