Pomoc - Szukaj - Użytkownicy - Kalendarz
Pełna wersja: [PHP][MySQL]wybór kilku baz danych
Forum PHP.pl > Forum > Przedszkole
ZuyPan
Witam.
Piszę z kolejnym, tym razem pewnie banalnym problemem.
Jak połączyć się do kilku baz danych naraz?
Prosty przykład:

  1. <?php
  2. $host = 'localhost';
  3. $login = 'root';
  4. $haslo = '';
  5. $baza = 'bla bla bla';
  6. if (!mysql_connect($host, $login, $haslo) || !mysql_select_db($baza)){
  7. $wiadomosc .= '<font color="red">Błąd podczas łączenia z bazą mysql! Proszę spróbować ponownie za chwilę!<br>';
  8. }else{
  9.  
  10. $zapytanie = 'SELECT * FROM ustawienia';
  11. $query = mysql_query($zapytanie);
  12. $rekord = mysql_fetch_array($query);
  13.  
  14. }
  15. ?>


Tu łączymy się do jednej bazy - "bla bla bla". A ja bym chciał połączyć się jeszcze do "ble bla ble" za jednym zamachem. Jak to zrobić?
phpion
mysql_connect i zasada działania jak w pierwszym komentarzu (od "tpl99 at yandex dot ru").
ZuyPan
Cytat
Whenever you open two connections to a single database,
you are likely not to get any error when selecting not existing db.

<?php
$db1 = mysql_connect( ... );
mysql_select_db('existing_db',$db1);

$db2 = mysql_connect( ... );
mysql_select_db('not_existing_db', $db2);

mysql_query(... , $db2);
//will return no errors and the query wouldn't be executed.
?>

Pay attention and you may save few hours of debugging.


Dzięki smile.gif. Teraz tylko czy ja to dobrze zrozumiałem:

dla każdej innej bazy robi się osobne połączenie (w tym przypadku $db1 i $db2) a potem jeśli chce się zrobić zapytanie do pierwszej to w postaci mysql_query(... , $db1); a jeśli do drugiej to w postaci mysql_query(... , $db2);
phpion
Dobrze zrozumiałeś smile.gif
thek
Uwaga! Informacja powyżej jest niepełna. wywołanie connecta dla tych samych danych host, user pass zwróci ten sam identyfikator! To pułapka na jaką się nadziejesz niestety jeśli wywołasz kilkukrotnie connecta w obrębie jednego skryptu. Jeśli baza jest na tym samym hoście, to przed użyciem innej bazy musisz zmienić ją funkcją zmiany bazy. To co postulujecie, czyli inne $db1 i $db2 dla mysql_query można użyć tylko gdy funkcja connect dla obu połączeń zwraca inne identyfikatory. Da się to obejść na 2 sposoby:
1) jeśli znasz nazwę kanoniczną i IP serwera.
mysql_connect( 'host_jako_adres', 'user', 'pass')
mysql_connect( 'host_jako_IP', 'user', 'pass')
zwracają różne (!) identyfikatory połączenia, co można wykorzystać do łączenia się z 2 różnymi bazami na tym samym hoście, a to jest nieraz bardzo przydatne, jeśli user ma prawa do kilku baz. Kto nie wierzy niech sprawdzi:
  1. $db1 = mysql_connect( 'localhost', 'user', 'pass');
  2. mysql_select_db('existing_db',$db1);
  3. $db2 = mysql_connect( 'localhost', 'user', 'pass');
  4. mysql_select_db('existing_db',$db2);
  5. var_dump($db1);
  6. var_dump($db2);
a potem
  1. $db1 = mysql_connect( 'localhost', 'user', 'pass');
  2. mysql_select_db('existing_db',$db1);
  3. $db2 = mysql_connect( '127.0.0.1', 'user', 'pass');
  4. mysql_select_db('existing_db',$db2);
  5. var_dump($db1);
  6. var_dump($db2);
Sam się kiedyś zdziwiłem, że pierwszy przykład wskazuje mi w obu przypadkach ten sam id połączenia. Wywołanie drugie mysql_connect dla tych samych danych host-user-pass po prostu zwraca nam ten te same identyfikatory i nie tworzy nowego, przez co wywołanie zmiany bazy potrafi być nie do końca przewidywalne.
2) Użycie 4 parametru funkcji wymuszającego nowe połączenie zadziała. Ale 4 parametr jest ignorowany w "safe mode", więc jest kupa i trzeba używać mojego obejścia.
Wniosek? Znajomość nazwy hosta w formie IP i kanonicznej może być nieraz jedynym bezpiecznym rozwiązaniem jeśli nie znamy konfiguracji serwera a musimy nawiązywać połączenia do 2 baz na te same dane.
ZuyPan
ech... no to kiszka :/ Dedyk - bo na takim stronka będzie "siedzieć" stoi u kumpla z neta i puki co i tak nie sprawdzę czy działa - nie dostałem jeszcze danych dostępowych jedynie znam ip maszynki i adres: perfectmt2.pl (nie do końca wiem czy to miałeś na myśli mówiąc postać "kanoniczna") bo innym znanym mi "czymś" co mogło by być postacią kanoniczą jest "localhost".
W moim sposobie widziałem to tak (dopóki nie wyjawiłeś mi "strasznej" prawdy tongue.gif)

plik config.php (includuje się go w każdym pliku gdzie korzysta się z bazy)
  1. $host = 'localhost';
  2. $login = 'root';
  3. $haslo = 'bla bla';
  4.  
  5. $polaczenie1 = mysql_connect($host, $login, $haslo);
  6. if ($baza1){
  7. mysql_select_db($baza, $polaczenie1);
  8. }else{
  9. $wiadomosc .= '<font color="red">Błąd podczas łączenia z bazą mysql! Proszę spróbować ponownie za chwilę!<br>';
  10. }
  11. if ($baza2){ //zmienna $baza i $baza2 będą ustalane w każdym pliku przed wywołaniem include ('config.php');
  12. $polaczenie2 = mysql_connect($host, $login, $haslo);
  13. if ($polaczenie2){
  14. mysql_select_db($baza2, $polaczenie2);
  15. }else{
  16. $wiadomosc .= '<font color="red">Błąd podczas łączenia z bazą mysql! Proszę spróbować ponownie za chwilę!<br>';
  17. }
  18.  
  19. }
  20.  
  21. if ($polaczenie1){
  22.  
  23.  
  24. $zapytanie = 'SELECT * FROM ustawienia';
  25. $query = mysql_query($zapytanie, $polaczenie1);
  26. $rekord = mysql_fetch_array($query);
  27.  
  28. }
  29. ?>

W takim wypadku powyższy skrypt chyba nie zadziała. Chyba, że jednak tongue.gif Korzystając z okazji czy przy "$rekord = mysql_fetch_array($query);" (w 3 linijka z kodem od końca) też trzeba dodawać 2 parametr w postaci $polaczenie1 ?
thek
Identyfikator połaczenia wykorzystują tylko określone funkcje: mysql_query, mysql_error, mysql_insert_id i parę jeszcze innych. Funkcje korzystające już z wyniku tej, która go używa, zazwyczaj nie smile.gif A że mysql_fetch_* używają wyniku z mysql_query, to nie posiadają go jako parametru opcjonalnego. Twoim rozwiązaniem jest użycie wspomnianego 4 parametru funkcji mysql_connect, która wymusza utworzenie nowego połączenia. Innymi słowy zrób tak:
$polaczenie2 = mysql_connect($host, $login, $haslo, true);
i powiedz czy to jest to co chciałeś winksmiley.jpg Przy czym dla pewności na końcu skryptu używałbym mysql_close, by zamykać otwarte połączenia.
ZuyPan
Działa! smile.gif z dodaniem parametru "true" do 2 połączenia z bazą wszystko działa tak jak chciałem smile.gif Ładnie pobiera wyniki z 2 różnych baz na jednym hoście i użytkowniku smile.gif
Ech... Co ja bym dał żeby wiedzieć tyle co Ty biggrin.gif
wookieb
A nie prościej użyć PDO?
ZuyPan
PDO? oświeć mnie winksmiley.jpg
ZuyPan
Z tego co widzę to to jest jakoś obiektowo zrobione, a ja się nie mam zamiaru "babrać" w tym czymś
wookieb
Bardziej babrasz właśnie z mysql_connect.
Poza tym co to za argument "nie mam zamiaru 'babrać' się"...
ZuyPan
Z tym, że babrając się w ten sposób coś rozumiem, i jestem w stanie sam sobie to stworzyć natomiast przy zabawie z obiektówką gubię się w pierwszej linijce kodu i najzwyczajniej w świecie jej nie rozumiem. Wydaje mi się zabawą w kotka i myszkę po całym skrypcie. Każdy robi tak jak lubi smile.gif Temat raczej już wyczerpany.
wookieb
Bo wydaje mi się, ze nie chcesz zrozumieć. Dla mnie o wiele bardziej zrozumiałe jest to
  1. $user = 'user';
  2. $password = 'haslo';
  3.  
  4. $db1 = new PDO('mysql:dbname=test2;host=127.0.0.1', $user, $password);
  5. $db2 = new PDO('mysql:dbname=test;host=127.0.0.1', $user, $password);

niż zabawa z mysql. Zresztą co tutaj wielkiego rozumieć?

Zalety: o wiele wygodniejsze zadawania zapytań, porządek i wiele innych.
No ale cóż twój wybór. Po prostu mówię jakie podejście jest prawidłowe i jakich powinno się unikać.
To jest wersja lo-fi głównej zawartości. Aby zobaczyć pełną wersję z większą zawartością, obrazkami i formatowaniem proszę kliknij tutaj.
Invision Power Board © 2001-2025 Invision Power Services, Inc.