2012-05-04 36 views
7

Đây là mã mà tôi đang sử dụng:dữ liệu đọc từ fsockopen sử dụng fgets/fread treo

if (!($fp = fsockopen('ssl://imap.gmail.com', '993', $errno, $errstr, 15))) 
    echo "Could not connect to host"; 
$server_response = fread($fp, 256); 
echo $server_response; 

fwrite($fp, "C01 CAPABILITY"."\r\n"); 
while (!feof($fp)) { 
    echo fgets($fp, 256); 
} 

tôi nhận được câu trả lời đầu tiên:

OK Gimap ready for requests from xx.xx.xx.xx v3if9968808ibd.15 

nhưng sau đó lần trang ra. Tôi đã tìm kiếm thông qua stream_set_blocking, stream_set_timeout, stream_select, fread, vv nhưng không thể làm cho nó hoạt động. Tôi cần phải đọc tất cả dữ liệu mà máy chủ gửi và sau đó tiếp tục với các lệnh khác (tôi sẽ truy xuất email bằng imap).

Cảm ơn

+0

Bạn có chắc chắn câu trả lời duy nhất là 256 ký tự dài? Và bạn có chắc rằng ổ cắm có thể ghi được không? Có thể tập lệnh của bạn bị treo trên 'fwrite()' vì ổ cắm không thể ghi được ... – shadyyx

+0

Có. Tôi đã thử nghiệm rằng bằng cách thay thế vòng lặp while bằng cách viết fgets đơn giản ($ fp, 256) hai lần. Và đây là phản hồi mà tôi nhận được: * CAPABILITY IMAP4rev1 UNSELECT IDLE NAMESPACE QUOTA ID XLIST TRẺ EM X-GM-EXT-1 XYZZY SASL-IR AUTH = XOAUTH C01 OK –

Trả lời

8

Tập lệnh của bạn bị treo trong vòng lặp while ở cuối. Điều này là do bạn đã sử dụng !feof() làm điều kiện cho vòng lặp và máy chủ không đóng kết nối. Điều này có nghĩa là feof() sẽ luôn trả lại false và vòng lặp sẽ tiếp tục mãi mãi.

này sẽ không vấn đề khi bạn viết một thực hiện đầy đủ, như bạn sẽ tìm kiếm mã phản ứng và có thể phá vỡ ra khỏi vòng lặp cho phù hợp, ví dụ:

<?php 

    // Open a socket 
    if (!($fp = fsockopen('ssl://imap.gmail.com', 993, $errno, $errstr, 15))) { 
     die("Could not connect to host"); 
    } 

    // Set timout to 1 second 
    if (!stream_set_timeout($fp, 1)) die("Could not set timeout"); 

    // Fetch first line of response and echo it 
    echo fgets($fp); 

    // Send data to server 
    echo "Writing data..."; 
    fwrite($fp, "C01 CAPABILITY\r\n"); 
    echo " Done\r\n"; 

    // Keep fetching lines until response code is correct 
    while ($line = fgets($fp)) { 
    echo $line; 
    $line = preg_split('/\s+/', $line, 0, PREG_SPLIT_NO_EMPTY); 
    $code = $line[0]; 
    if (strtoupper($code) == 'C01') { 
     break; 
    } 
    } 

    echo "I've finished!"; 
+0

Cảm ơn. Bây giờ tôi chỉ cần tìm ra mã phản hồi cho các lệnh khác ... –

+1

[RFC là bạn của bạn] (http://tools.ietf.org/html/rfc3501) ;-) (Đừng quên xử lý các phản hồi lỗi cũng như, hoặc kịch bản của bạn sẽ treo mãi mãi chờ đợi phản ứng 'C01' nó sẽ không bao giờ nhận được) – DaveRandom

+0

Có. Tôi đã đi qua các lệnh đó một thời gian rồi. Cảm ơn một lần nữa. –

1

Tập lệnh của bạn sẽ hoạt động. Trong thực tế, nó đang làm việc.

Xem kết quả dưới đây trên máy tính của tôi khi tôi chạy mã của bạn:

* OK Gimap ready for requests from xx.xx.xx.xx l5if4585958ebb.20 
* CAPABILITY IMAP4rev1 UNSELECT IDLE NAMESPACE QUOTA ID XLIST CHILDREN X-GM-EXT-1 XYZZY SASL-IR AUTH=XOAUTH 
C01 OK Thats all she wrote! l5if4585958ebb.20 

Kể từ gmail không ngắt kết nối bạn. Không có kết thúc của tập tin xảy ra. Và tải trang chỉ đơn giản là hết thời gian.

Nói cách khác: Tập lệnh của bạn sẽ tiếp tục chờ và đợi cho đến khi gmail ngắt kết nối, điều này thật không may xảy ra sau khi tải trang của bạn đã hết thời gian chờ.

+0

Bạn có nhận được kết quả ngay lập tức hay không. 1-2 phút) để hết thời gian chờ ?? –

+0

Vấn đề có thể là bạn đang cố gắng chạy nó từ một trang web tôi có đúng không? Trang hết thời gian trước khi gmail ngắt kết nối (vì vậy feof() không bao giờ trả về đúng). Nó có thể mất một phần của bộ đệm trong quá trình định thời gian. – Woutifier

+0

Có. Tôi có một trang .php có mã này. Có chuyện gì vậy? –

Các vấn đề liên quan