2012-02-27 50 views
6

Próbuję napisać spory fragment danych do pliku, który jest otwierany za pomocą fopen() w php. Opakowanie protokołu, którego używam, to ftp, więc plik jest zdalny na serwerze z uruchomionym kodem php. Plik, do którego piszę, znajduje się na serwerze Windows.php fwrite() nie kończy zapisywania danych ciągów do pliku, dlaczego?

Sprawdziłem, czy plik rzeczywiście został utworzony przez mój kod php, ale problem polega na tym, że dane w pliku są albo nieistniejące (0 KB), albo zapis do pliku zatrzymuje się przedwcześnie. Nie wiem, dlaczego tak się dzieje.

Oto kod używam do obsługi operacji:

$file_handle = fopen($node['ftp'].$path_to_lut, "wb", 0, $node['ftp_context']); 
include_once($file); 

if ($file_handle) 
{ 
    fwrite($file_handle, $string); //$string is inside included $file 
    fclose($file_handle); 
} else { 
    die('There was a problem opening the file.'); 
} 

Ten kod działa poprawnie, gdy gospodarzem go na moim komputerze lokalnym, ale kiedy przesłać go do mojego witryną (Rackspace cloud), to zawiedzie. To prowadzi mnie do przekonania, że ​​jest to problem związany z konfiguracją mojego serwera w Rackspace, ale chcę wiedzieć, czy jest coś, co mogę zrobić, aby mój kod php uczynił go bardziej niezawodnym.

Jakieś pomysły, aby zapewnić, że fwrite zakończy pisanie ciągu na zdalnym komputerze?

Dzięki!

Ok, zmieniłem kod, który zapisuje do pliku tak:

if ($file_handle) 
{ 
    if ($bytesWritten = fwrite($file_handle, $string)) { 
     echo "There were " . $bytesWritten . " bytes written to the text file."; 
    } 

    if (!fflush($file_handle)) { 
     die("There was a problem outputting all the data to the text file."); 
    } 

    if (!fclose($file_handle)) { 
     die("There was a problem closing the text file."); 
    } 

} else { 

    die("No file to write data to. Sorry."); 

} 

Co jest dziwne jest to, że echo sprawozdanie zawiera następujące informacje:

Były 10330 bajtów zapisanych do plik tekstowy.

A jednak, gdy sprawdzam rozmiar pliku tekstowego za pomocą protokołu FTP, pokazuje on wartość 0K, a dane w pliku są w rzeczywistości obcięte. Nie mogę sobie wyobrazić, że ma to związek z samym serwerem FTP, ponieważ działa on, jeśli PHP jest hostowane na komputerze innym niż na Rackspace Cloud.

** AKTUALIZACJA ** Rozmawiałem z przedstawicielem Rackspace Cloud, który wspomniał, że wymaga pasywnego ftp, jeśli zamierzasz korzystać z ftp ze swoich serwerów. Ustawiłem serwer zdalny do obsługi pasywnych połączeń FTP i sprawdziłem, czy pasywny ftp działa teraz na serwerze zdalnym za pośrednictwem klienta FTP ftp OSX. I dodaje:

ftp_pasv($file_handle, true); 

Zaraz po fopen() oświadczenie, ale pojawia się błąd z PHP mówiąc, że nie zapewniają ważny zasób do ftp_pasv(). Jak mogę się upewnić, że połączenie ze stroną ftp, którą tworzy PHP, to PASV, a nie ACTIVE i nadal używać fwrite()? Nawiasem mówiąc, zauważyłem, że komputer z systemem Windows zgłasza, że ​​plik zapisany przez mój kod PHP ma 4096 bajtów na dysku. Nigdy nie przekracza tej kwoty. Doprowadziło mnie to do zmiany wartości php output_buffering na 65536 tylko po to, aby rozwiązać problem, ale to też nie rozwiązało problemu. . .

** UPDATE CZĘŚĆ Duex **

Rozwiązywanie problemu na moim wirtualnym serwerem w chmurze Sites Rackspace produkt okazał się zbyt trudne, ponieważ nie oferują wystarczających uprawnień administratora. Stworzyłem bardzo mały serwer w chmurze na produkcie Cloud Server Rackspace i skonfigurowałem wszystko do punktu, w którym wciąż widzę ten sam błąd z fwrite(). Aby upewnić się, że mogę zapisać plik z tego serwera na zdalny serwer, użyłem podstawowych poleceń ftp w mojej powłoce bash na serwerze w chmurze. Wszystko działało dobrze. Zakładam więc, że w php implementacji fwrite() występuje błąd i prawdopodobnie wynika to z jakiegoś problemu z dławieniem danych.Kiedy piszę do zdalnego serwera z mojego lokalnego środowiska, które ma powolne upsteed w porównaniu do tego, co jest oferowane na serwerze Rackspace Cloud, działa dobrze. Czy istnieje sposób na skuteczne zmniejszenie szybkości zapisu? Po prostu pytając :)

** UPDATE CZĘŚĆ III *

Więc wziąłem sugestię od @a smutny facet i realizowane funkcje, które mogą pomóc ktoś próbuje pisać do nowego pliku i przesłanie go wyłączyć w całości przez ftp:

function writeFileAndFTP($filename=null, $data=null, $node=null, $local_path=null, $remote_path=null) 
{ 

    // !Determin the path and the file to upload from the webserver 
    $file = $local_path.'/'.$filename; 


    // !Open a new file to write to on the local machine 
    if (!($file_handle = fopen($file, "wb", 0))) { 
     die("There was a problem opening ".$file." for writing!"); 
    } 


    // !Write the file to local disk 
    if ($bytesWritten = fwrite($file_handle, $data)) { 
     //echo "There were " . $bytesWritten . " bytes written to " . $file; 
    } 

    // !Close the file from writing 
    if (!fclose($file_handle)) { 
     die("There was a problem closing " . $file); 
    } 

    // !Create connection to remote FTP server 
    $ftp_cxn = ftp_connect($node['addr'], $node['ftp_port']) or die("Couldn't connect to the ftp server."); 

    // !Login to the remote server 
    ftp_login($ftp_cxn, $node['user'], getPwd($node['ID'])) or die("Couldn't login to the ftp server."); 

    // !Set PASV or ACTIVE FTP 
    ftp_pasv($ftp_cxn, true); 


    // !Upload the file 
    if (!ftp_put($ftp_cxn, $remote_path.'/'.$filename, $file, FTP_ASCII)) { 
     die("There was an issue ftp'ing the file to ".$node['addr'].$remote_path); 
    } 

    // !Close the ftp connection 
    ftp_close($ftp_cxn); 

} 
+0

'include_once ($ plik);' - gdzie jest ten kod? – hakre

+0

Wygląda to następująco: '$ string =" ciąg o długości 20 linii ";' – ariestav

+0

Co to jest 'var_dump ($ node ['ftp_context']);' output? (usuń nazwę użytkownika/hasło). – hakre

Odpowiedz

4

długość łańcucha fwrite można napisać w jednym zamachem jest ograniczony na niektórych platformach (dlatego zwraca liczbę zapisanych bajtów). Możesz spróbować uruchomić go w pętli, ale lepszym pomysłem jest po prostu użyć file_put_contents, który gwarantuje, że cały ciąg zostanie zapisany.

http://www.php.net/manual/en/function.file-put-contents.php

+0

Interesujące, dzięki za wskaźnik. Czy z ciekawości istnieje dyrektywa apache, którą mogę ustawić w pliku .htaccess, aby zmienić limit danych dla fwrite()? – ariestav

+0

Wątpliwe) plus, jeśli używasz ftp, to raczej chodzi o sieć, tak myślę. Czy file_put_contents działa? –

+0

sprawdzanie teraz. . . – ariestav