Bài 15: Xử lý thư mục và tệp tin

Bài viết này tập trung vào việc điều khiển hệ thống tệp tin và thư mục trên máy chủ (không phải máy khách). Bài này được chia làm các phần sau:
Phần 1: Các hàm căn bản xử lý tệp và thư mục
Phần 2: Cách thức truy xuất dữ liệu từ tệp tin.
Phần 3: Tải file lên máy chủ.

Phần I. Các hàm cơ bản để xử lý tệp và thư mục

I. Một số hàm xử lý thư mục
1. Thay đổi thư mục gốc
Để thay đổi thư mục gốc, ta dùng hàm chroot
Cú pháp:
PHP Code:
bool chroot ( string directory)
Hàm này trả về true nếu như thư mục gốc được chuyển đổi thành thư mục có đường dẫn là directory.

2. Thay đổi thư mục hiện hành
Cú pháp:
PHP Code:
bool chdir ( string directory)
Thay đổi thư mục hiện hành sang thư mục có đường dẫn là directory. Hàm trả về TRUE nếu thành công, ngược lại là FALSE.

3. Trả về thư mục hiện hành
Để lấy đường dẫn của thư mục hiện hành, ta dùng hàm getcwd:
PHP Code:
string getcwd ()
4. Hiển thị danh sách các tệp và thư mục con của một thư mục nào đó:
Để làm điều này, ta dùng hàm scandir
VD:
PHP Code:
<?php
$dir    = '/source';
$files1 = scandir($dir);
print_r($files1);
?>
hơ hơ, đây chính là cách mà mấy con remview hoặc backdoor của mấy chú hacker hay sử dụng để duyệt qua các tệp và thư mục trên máy chủ đây mà

5. Tạo một thư mục mới
Để tạo một thư mục mới trên máy chủ, ta dùng hàm mkdir():
bool mkdir ( string pathname [, int mode [, bool recursive [, resource context]]])
VD:
PHP Code:
<?php
mkdir("/uploads/images"); // tạo một thư mục images trong thư mục uploads tại thư mục gốc của website.
?>
6. Xoá một thư mục
Để xoá một thư mục mới trên máy chủ, ta dùng hàm rmdir():
bool rmdir (string pathname)

VD:
PHP Code:
<?php
rmdir("/uploads/images"); // Xoá thư mục images trong thư mục uploads tại thư mục gốc của website.
?>
II. Một số hàm xử lý tệp tin

1. Đổi tên tệp tin:
Để đổi tên tệp tin, ta dùng hàm rename:
PHP Code:
bool rename ( string oldname, string newname)
Hàm này sẽ cố gắng đổi tên từ oldname sang tên mới (newname). Hàm sẽ trả về TRUE nếu thành công, ngược lại là FALSE

2. Xóa tệp tin
Để xóa tên tệp tin, ta dùng hàm unlink() hoặc delete():
PHP Code:
int unlink ( string filename)
Hàm này sẽ xóa file có đường dẫn (tên) là filename. Trả về TRUE nếu thành công, ngược lại là FALSE

3. Copy file
Để copy file, ta dùng hàm copy có cấu trúc như sau:
PHP Code:
int copy ( string source, string dest)
Hàm này sẽ tạo ra một bản copy file nguồn (sourse) sang file đích (dest). Hàm trả về TRUE nếu thành công, ngược lại là FALSE

Ví dụ:
PHP Code:
<?
// Tạo ra một file backup của file có tên là $file. File backup sẽ được bổ sung phần đuôi mới là .bak:
if (!copy($file, $file.'.bak')) {
    print ("Lỗi copy $file...<br>\n");
}
?>
Hàm kiểm tra sự tồn tại của một file:
Khi xử lý các file, ta thường kiểm tra look file có tồn tại hay không trước khi tiến hành các thao tác đọc, ghi dữ liệu:
Cú pháp:
PHP Code:
bool file_exists ( string filename)
Hàm này sẽ trả về TRUE nếu thành công, ngược lại là FALSE.

Phần III. Tải file từ máy khách lên máy chủ.

Trong quá trình trao đổi dữ liệu giữa máy khách và máy chủ, tải file là một công việc rất thường gặp. Đó  không phải là không là việc tải một file hình ảnh lên máy chủ, 1 file zip hay 1 file tài liệu bất kỳ nào đó. Sau khi đưa lên máy chủ, các file này sẽ được cung cấp liên kết để người dùng không phải là không tải file về sử dụng.

Cách tải file thông dụng nhất hiện nay là sử dụng giao thức FTP. Tuy nhiên, tài khoản ftp thường ít được chia sẻ vì nó liên quan rất nhiều đến hệ thống, và thường chỉ có các admin mới có được tài khoản này. Vì vậy, các trang web động thường sử dụng một cách khác để truyền tải file lên dựa vào chuần giao thức HTTP (sử dụng HTML Form).

I. tạo lên form HTML để cho phép người dùng lựa chọn file cần tải
Quay tr tại lại một form trong HTML, chúng ta đã biết các thành phần căn bản của form như: tên form, các phần tử nhập dữ liệu như textarea, thẻ input, thẻ lựa chọn select - option...
Để  không phải là không cho phép người dùng lựa chọn một file nào đó trên máy tính và tải lên, form HTML này sẽ có một cấu trúc hơi đặc biệt một chút, và có một thành phần là thẻ input với type="file".

Trước tiên, chúng ta quay tr tại lại với thẻ <form>

Như  ở trên, chúng ta đã biết thẻ form có một số thuộc tính:
- method: Xác định kiểu truyền dữ liệu là GET hay POST. Để tải file, method bắt buộc phải có kiểu POST (vì dữ liệu trong file thường là lớn hơn những gì mà GET không phải là không truyền tải).
- name: Xác định tên của form (tên này có thể được dùng để truyền dữ liệu qua javascript)
- action: Xác định địa chỉ URL mà dữ liêu cần gửi tới
Để tải file, ta phải biết thêm một thuộc tính nữa, đó là thuộc tính enctype với giá trị là multipart/form-data.

Như vậy, để tải file, ta phải làm một form như sau:
HTML Code:
<form enctype="multipart/form-data" action="địa_chỉ_web" method="post">
Các thành phần trong form như văn bản, hình ảnh, ô nhập liệu...
</form>
Tiếp đó, chúng ta sẽ trang bị một ô để cho phép người dùng lựa chọn file cần tải lên. Thành phần này cũng vẫn là thẻ input Nhưng với type="file":
<input name="ten_phan_tu" type="file">
Khi đưa thẻ này vào, nó sẽ hiển thị một ô và nút Browse bên cạnh. người sử dung sẽ kích chuột vào nút Browse để lựa chọn file như chúng ta thường thấy.

Dưới đây là một form đơn giản chỉ chứa một ô để tải file và nút submit:

HTML Code:
<form enctype="multipart/form-data" method="post">
 Lựa chọn file cần tải: <input name="UserFileName" type="file">
 <input type="submit" value="Submit">
</form>
II. Xử lý file trên máy chủ
Như vậy ta đã xây dựng được một form để cho phép các thánh chọn file. Sau khi mọi người bấm nút Submit, file sẽ được tải lên máy chủ, và được máy chủ lưu vào một thư mục tạm, đồng thời sinh ra một mảng có tên là $_FILES["tên_phần_tử_trên_form"] hoặc có một tên khác là $HTTP_POST_FILES["tên_phần_tử_trên_form"]. Việc tiếp theo là ta phải xử lý cái file đó như thế nào?

Trước tiên, chúng ta thử tìm hiểu look cái mảng kia chứa những thông tin gì:

Với mẫu trên, tên_phần_tử_trên_form là UserFileName (tương ứng với thẻ <input name="UserFileName" type="file">)
Như vậy khi mọi người chọn file rồi kích chọn Submit thì trình duyệt sẽ gửi file lên. Sau khi hoàn tất việc gửi file, máy chủ sẽ sinh ra một mảng có tên là $_FILES["UserFileName"].

Mảng này chứa các thông tin sau:

$_FILES['UserFileName']['name']: Tên gốc của file trên máy khách
$_FILES['UserFileName']['type']: Kiểu MIME của file (nếu trình duyệt cung cấp thông tin). Ví dụ: "image/gif".
$_FILES['UserFileName']['size']: Kích thước của file được tải tính theo byte
$_FILES['UserFileName']['tmp_name']: Tên tạm của file khi nó đã được tải và lưu trên thư mục tạm của máy chủ.

Như vậy chúng ta đã có được đầy đủ các thông tin để xử lý file. File này có thể được m ở ra để lấy dữ liệu, có thể được copy vào một thư mục nào đó, hoặc bị xoá bỏ, hay đổi tên... Xin thông qua thêm phần I và phần II tại trên để biết các thao tác điều khiển tệp và thư mục.

Dưới đây là một mẫu lấy từ PHP Manual:
PHP Code:
// Đoạn mã HTML để tạo form
<form enctype="multipart/form-data" action="_URL_" method="post">
 <input type="hidden" name="MAX_FILE_SIZE" value="30000" />
 Send this file: <input name="userfile" type="file" />
 <input type="submit" value="Send File" />
</form>

// Đoạn chương trình xử lý file đã upload:
$uploaddir = '/var/www/uploads/';
$uploadfile = $uploaddir . $_FILES['userfile']['name'];

print "<pre>";
if (move_uploaded_file($_FILES['userfile']['tmp_name'], $uploadfile)) {
    print "File is valid, and was successfully uploaded. ";
    print "Here's some more debugging info:\n";
    print_r($_FILES);
} else {
    print "Possible file upload attack!  Here's some debugging info:\n";
    print_r($_FILES);
}
print "</pre>";
Kỹ thuật tải các file có dung lượng lớn

Kỹ thuật tải file trình bày tại trên sẽ bị giới hạn trên đủ thứ phương diện: Khi tải file lớn,  công sức tải lâu sẽ gây hiện tượng script timeout, đường truyền không phải là không bị ngắt, nghẽn, bị giới hạn kích thước tải trong file php.ini (thường có kích thước tối đa khoảng 2 MB)...

Để tải các file có dung lượng cực lớn, chúng ta phải làm theo cách khác, thông thường, đó là sử dụng phối hợp với AJAX.

Nguyên lý của nó là: thay vì truyền cả file lớn, chúng ta sẽ chia ra thành từng phần nhỏ để gửi đi. Sau đó, trên máy chủ sẽ thực hiện việc ghép các phần nhỏ lại với nhau để cho ra một file hoàn chỉnh. Làm theo cách này sẽ cho phép tải các file dung lượng rất lớn, lại không phải là không theo dõi được tiến độ tải file.

Giải thuật mô phỏng đơn giản như sau:
Bước 1: M ở file trên máy khách, truy cập đến vị trí dữ liệu đã tải trước đó (nếu có)
Bước 2: Đọc một phần dữ liệu trên máy khách tính từ vị trí dữ liệu đã tải trước đó (nếu có). Đánh dấu vị trí dữ liệu đã tải
Bước 3: Chuyển phần dữ liêu đó vào một phần tử form, submit
Bước 4: Máy chủ nhận dữ liệu, m ở file và ghi phần dữ liệu vào đúng vị trí trên file
Bước 5: Máy chủ yêu cầu gửi tiếp, quay lại bước 1. Nếu đã hết thì kết thúc.
Share on Google Plus

About Unknown

This is a short description in the author block about the author. You edit it by entering text in the "Biographical Info" field in the user admin panel.
    Blogger Comment
    Facebook Comment

0 nhận xét:

Đăng nhận xét