TopDev

Shell Scripting Tự Động Hóa Mọi Việc Với Vài Dòng Code

minhdev 📖 12 phút đọc ✎ đã sửa

Shell Scripting Cơ Bản: Tự Động Hóa Mọi Việc Với Vài Dòng Code – Bí Kíp Của DevOps Và SysAdmin!

Bạn có cảm thấy mệt mỏi khi phải lặp đi lặp lại một chuỗi lệnh nhàm chán mỗi ngày? Hay bạn muốn tạo ra những công cụ nhỏ gọn của riêng mình để giải quyết các vấn đề thường gặp? Chào mừng bạn đến với thế giới của Shell Scripting – nơi những dòng lệnh biến thành các chương trình tự động hóa mạnh mẽ!

Shell Scripting là kỹ năng cốt lõi cho bất kỳ ai làm việc với Linux/Unix, từ lập trình viên, kỹ sư DevOps cho đến quản trị hệ thống. Bài viết này sẽ giúp bạn hiểu rõ Shell Script là gì, cách tạo và chạy chúng, cùng với các khái niệm cơ bản về biến, điều kiện, vòng lặp và hàm. Hãy cùng nhau khám phá!



I. Shell Script là gì? Tại Sao Nó Lại Hữu Ích Đến Vậy?#

Hãy tưởng tượng bạn có một danh sách các công việc cần làm: kiểm tra dung lượng ổ đĩa, xóa các tệp tạm thời, sao lưu dữ liệu, và gửi báo cáo qua email. Bạn có thể gõ từng lệnh một, nhưng sẽ mất thời gian và dễ gây lỗi.

Đây chính là lúc Shell Script phát huy tác dụng!

  • Shell Script là gì? Đơn giản là một tập tin văn bản chứa một chuỗi các lệnh Shell (mà bạn vẫn gõ trên Terminal). Khi bạn chạy script, Shell sẽ đọc và thực thi từng lệnh một theo thứ tự.

  • Tại sao chúng lại hữu ích? Tự động hóa: Thực hiện các tác vụ lặp đi lặp lại một cách tự động, không cần can thiệp thủ công.

    • Tiết kiệm thời gian: Thay vì gõ nhiều lệnh, chỉ cần chạy một script.

    • Giảm lỗi: Các lệnh được viết sẵn, giảm thiểu sai sót do gõ nhầm.

    • Tái sử dụng: Dễ dàng sử dụng lại script cho nhiều mục đích hoặc trên nhiều hệ thống khác nhau.

    • Công cụ tùy chỉnh: Xây dựng các công cụ riêng phù hợp với nhu cầu của bạn.

II. Tạo và Chạy Shell Script: Bước Khởi Đầu Của Mọi Kịch Bản!#

1. Tạo một Shell Script và làm cho nó có thể thực thi được#

Để tạo một Shell Script:

  • Viết các lệnh vào một tệp văn bản: Sử dụng bất kỳ trình soạn thảo văn bản nào (nano, vim, VS Code, Sublime Text,...). Lưu tệp với phần mở rộng .sh (ví dụ: my_script.sh), mặc dù không bắt buộc nhưng là một quy ước tốt.

  • Đặt quyền thực thi: Mặc định, các tệp mới không có quyền chạy. Bạn cần cấp quyền thực thi cho script: chmod +x my_script.sh chmod: lệnh thay đổi quyền truy cập.

    • +x: thêm quyền thực thi.

2. Shebang (#!/bin/bash) là gì và ý nghĩa của nó?#

  • Shebang là dòng đầu tiên trong mọi Shell Script, có dạng #! theo sau là đường dẫn đến trình thông dịch Shell mà bạn muốn sử dụng để chạy script.

  • Ví dụ: #!/bin/bash

  • Ý nghĩa: Nó cho hệ điều hành biết nên dùng Shell nào (Bash, Zsh, Python, Perl,...) để thực thi các lệnh trong tệp. Nếu không có shebang, hệ thống sẽ sử dụng Shell mặc định của người dùng để chạy script.

  • Ví dụ về tệp script hello.sh: ` #!/bin/bash

    Dòng này là shebang, chỉ định sử dụng bash để chạy script.

    Dòng bắt đầu bằng # là comment (chú thích), không được thực thi.

    echo "Hello, TopDev World!" Để chạy: ./hello.sh

    Output: Hello, TopDev World!

    `

III. Biến, Tham Số và Input: Dữ Liệu Trong Script!#

3. Khai báo và truy cập giá trị của biến#

  • Khai báo biến: Không có từ khóa đặc biệt, chỉ cần gán giá trị trực tiếp. name="Alice" age=30 Lưu ý: Không có khoảng trắng xung quanh dấu =.

  • Truy cập giá trị: Sử dụng dấu $ trước tên biến. ` echo "My name is $name and I am $age years old."

    Output: My name is Alice and I am 30 years old.

    Sử dụng dấu ngoặc nhọn{}để phân tách biến với các ký tự khác nếu cần: file_prefix="log" echo "Processing ${file_prefix}_data.txt" # Output: Processing log_data.txt

`

4. Tham số dòng lệnh ($1, $2, $@, $#)#

Khi chạy script, bạn có thể truyền thêm các giá trị (tham số) vào.

  • $1, $2, $3, ...: Tham số thứ nhất, thứ hai, thứ ba, v.v.

  • $0: Tên của script đang chạy.

  • $#: Tổng số tham số được truyền vào.

  • $@: Tất cả các tham số, được coi là các chuỗi riêng biệt (rất hữu ích khi truyền cho các lệnh khác).

  • $*: Tất cả các tham số, được coi là một chuỗi duy nhất.

  • Ví dụ về script process_args.sh: #!/bin/bash echo "Script name: $0" echo "First argument: $1" echo "Second argument: $2" echo "Total arguments: $#" echo "All arguments as separate strings: $@" echo "All arguments as a single string: $*" Chạy: ` ./process_args.sh apple banana orange

    Output:

    Script name: ./process_args.sh

    First argument: apple

    Second argument: banana

    Total arguments: 3

    All arguments as separate strings: apple banana orange

    All arguments as a single string: apple banana orange

    `

5. Biến môi trường và lệnh export#

  • Biến môi trường: Là các biến được thiết lập bởi hệ điều hành hoặc Shell, và chúng có sẵn cho mọi chương trình con (bao gồm cả các Shell Script) được khởi chạy từ Shell đó.

  • Ví dụ phổ biến: PATH: Chứa danh sách các thư mục mà Shell tìm kiếm các lệnh thực thi.

    • HOME: Đường dẫn đến thư mục người dùng.

    • USER: Tên người dùng hiện tại.

    • PWD: Thư mục làm việc hiện tại (giống pwd).

  • Lệnh export: Dùng để "xuất" một biến cục bộ trở thành biến môi trường, có thể truy cập được bởi các chương trình con. my_variable="Hello" export my_variable # Giờ đây my_variable là biến môi trường

6. Lệnh read - Nhận input từ người dùng#

  • Công dụng: Đọc một dòng từ stdin (thường là từ bàn phím) và lưu vào một biến.

  • Ví dụ: #!/bin/bash echo "Please enter your name:" read user_name echo "Hello, $user_name! Welcome to Shell Scripting." Chạy: ` ./script.sh

    Output:

    Please enter your name:

    (Bạn gõ tên và nhấn Enter)

    Hello, [Tên bạn]! Welcome to Shell Scripting.

    `

IV. Cấu Trúc Điều Khiển: Logic Của Shell Script!#

7. Cấu trúc điều khiển if-else#

Cho phép script đưa ra quyết định dựa trên điều kiện.

  • Cú pháp cơ bản: if [ condition ]; then # Lệnh nếu điều kiện đúng elif [ another_condition ]; then # Lệnh nếu điều kiện thứ hai đúng else # Lệnh nếu không có điều kiện nào đúng fi Lưu ý: Khoảng trắng xung quanh [] là bắt buộc. then phải nằm trên dòng mới hoặc sau ;. fi để kết thúc khối if.

8. Các toán tử so sánh số (-eq, -ne, -gt, -lt, -ge, -le)#

Sử dụng trong các điều kiện if để so sánh các giá trị số.

  • -eq: bằng (equal to)

  • -ne: không bằng (not equal to)

  • -gt: lớn hơn (greater than)

  • -lt: nhỏ hơn (less than)

  • -ge: lớn hơn hoặc bằng (greater than or equal to)

  • -le: nhỏ hơn hoặc bằng (less than or equal to)

  • Ví dụ: #!/bin/bash num1=10 num2=20 if [ "$num1" -lt "$num2" ]; then echo "$num1 is less than $num2." else echo "$num1 is not less than $num2." fi

9. Các toán tử so sánh chuỗi (=, !=, -z, -n)#

Sử dụng để so sánh các giá trị chuỗi.

  • = hoặc ==: bằng (equal to)

  • !=: không bằng (not equal to)

  • -z string: True nếu chuỗi rỗng (zero length).

  • -n string: True nếu chuỗi không rỗng (non-zero length).

  • Ví dụ: #!/bin/bash name="Alice" if [ "$name" = "Alice" ]; then echo "Hello Alice!" elif [ -z "$name" ]; then echo "Name is empty." else echo "You are not Alice." fi

10. Lệnh test hoặc [ dùng để làm gì trong điều kiện?#

[ thực chất là một lệnh alias (bí danh) cho lệnh test. Chúng dùng để đánh giá một biểu thức điều kiện và trả về trạng thái thoát (exit status) 0 (true) hoặc 1 (false). Lệnh if sẽ kiểm tra trạng thái thoát này.

  • Cú pháp: ` test -f "myfile.txt" && echo "File exists."

    Tương đương với:

    [ -f "myfile.txt" ] && echo "File exists." **man test** để xem tất cả các tùy chọn kiểm tra (-fcho tệp tin thường,-d` cho thư mục, v.v.).

11. &&|| trong Shell Script (logic AND/OR)#

  • && (AND): Thực thi lệnh thứ hai CHỈ KHI lệnh thứ nhất thành công (trả về exit status 0). Ví dụ: mkdir my_folder && cd my_folder (Tạo thư mục, sau đó di chuyển vào nếu tạo thành công).

  • || (OR): Thực thi lệnh thứ hai CHỈ KHI lệnh thứ nhất THẤT BẠI (trả về exit status khác 0). Ví dụ: command_that_might_fail || echo "Command failed!" (Nếu lệnh thất bại, in ra thông báo).

V. Cấu Trúc Lặp: Lặp Đi Lặp Lại Công Việc!#

12. Cấu trúc lặp for#

Lặp qua một danh sách các mục.

  • Cú pháp: for item in list_of_items; do # Lệnh thực thi với mỗi item done

  • Ví dụ: ` #!/bin/bash for fruit in apple banana orange; do echo "I like $fruit." done

    Lặp qua các tệp trong thư mục hiện tại

    for file in *.txt; do echo "Processing $file" done `

13. Cấu trúc lặp while#

Lặp lại một khối lệnh chừng nào một điều kiện vẫn còn đúng.

  • Cú pháp: while [ condition ]; do # Lệnh thực thi chừng nào điều kiện đúng done

  • Ví dụ: #!/bin/bash count=1 while [ $count -le 5 ]; do echo "Count: $count" count=$((count + 1)) # Tăng biến count done

VI. Hàm (Functions): Tái Sử Dụng Code!#

14. Hàm trong Shell Script: Định nghĩa và gọi hàm#

Hàm cho phép bạn nhóm một khối lệnh lại thành một đơn vị có thể gọi lại nhiều lần.

  • Định nghĩa hàm: ` function my_function { # Các lệnh trong hàm }

    Hoặc cú pháp ngắn gọn hơn:

    my_function() { # Các lệnh trong hàm } `

  • Gọi hàm: my_function

  • Ví dụ: ` #!/bin/bash

    greet_user() { echo "Hello, $1!" # $1 là tham số đầu tiên khi gọi hàm echo "Today is $(date)." }

    greet_user "Alice" greet_user "Bob" `

VII. Xử Lý Lỗi & Nâng Cao: Giúp Script Vững Chắc!#

15. Xử lý lỗi trong Shell Script (set -e, exit)#

  • set -e: Khi đặt ở đầu script, nó sẽ khiến script thoát ngay lập tức nếu có bất kỳ lệnh nào thất bại (trả về exit status khác 0). Cực kỳ hữu ích để tránh các lỗi không lường trước. #!/bin/bash set -e # Script sẽ dừng ngay nếu có lỗi echo "Starting process..." cp non_existent_file.txt /tmp/ # Lệnh này sẽ lỗi echo "This line will not be executed if previous command fails."

  • exit [status_code]: Dừng script và trả về một mã trạng thái thoát. exit 0: thành công.

    • exit 1 (hoặc bất kỳ số khác 0): thất bại. `

    #!/bin/bash if [ ! -f "config.txt" ]; then echo "Error: config.txt not found!" >&2 exit 1 # Thoát với mã lỗi 1 fi echo "Config file found. Continuing..." `

16. Lệnh trap dùng để làm gì?#

  • trap: Dùng để "bẫy" các tín hiệu hệ thống (như Ctrl+C, lỗi chương trình, thoát script) và thực thi một lệnh hoặc hàm khi tín hiệu đó xảy ra. Rất hữu ích cho việc "dọn dẹp" (cleanup) tài nguyên.

  • Ví dụ: ` #!/bin/bash cleanup() { echo "Caught Ctrl+C. Cleaning up temporary files..." rm -f /tmp/my_temp_file.txt exit 1 # Thoát script sau khi dọn dẹp }

    trap cleanup INT TERM EXIT # Khi nhận tín hiệu INT (Ctrl+C), TERM (terminate), EXIT (thoát script), gọi hàm cleanup

    echo "Creating a temporary file..." touch /tmp/my_temp_file.txt echo "Script running. Press Ctrl+C to trigger cleanup." sleep 60 # Giả lập công việc lâu dài echo "Script finished normally." `

VIII. Ví Dụ Thực Tế: Viết Shell Script Đầu Tiên!#

17. Shell Script kiểm tra tệp tồn tại#

Đây là một Shell Script đơn giản nhận một tên tệp làm tham số và kiểm tra xem tệp đó có tồn tại hay không.

` #!/bin/bash

Kiểm tra xem có đủ tham số đầu vào không

if [ "$#" -ne 1 ]; then echo "Usage: $0 " echo "Example: $0 my_document.txt" exit 1 # Thoát với mã lỗi 1 nếu không đủ tham số fi

filename="$1" # Gán tham số đầu tiên vào biến filename

Kiểm tra xem tệp có tồn tại và là một tệp thông thường không

if [ -f "$filename" ]; then echo "File '$filename' exists and is a regular file." else echo "File '$filename' does not exist or is not a regular file." exit 1 # Thoát với mã lỗi 1 nếu tệp không tồn tại fi

echo "Script finished successfully." exit 0 # Thoát với mã 0 nếu thành công `

Cách chạy script trên:

  • Lưu đoạn code trên vào tệp check_file.sh.

  • Cấp quyền thực thi: chmod +x check_file.sh

  • Chạy thử: ./check_file.sh non_existent_file.txt ./check_file.sh existing_file.txt # Thay bằng tên tệp có sẵn trên máy bạn ./check_file.sh # Chạy mà không có tham số



Lời Kết#

Bạn đã đi một chặng đường dài! Từ việc hiểu Shell Script là gì, cách tạo và chạy chúng, cho đến việc sử dụng biến, tham số, điều kiện, vòng lặp và thậm chí cả hàm và xử lý lỗi. Đây là những kiến thức nền tảng vững chắc để bạn bắt đầu tự động hóa các tác vụ hàng ngày và xây dựng các công cụ riêng của mình.

Shell Scripting là một kỹ năng vô giá trong bất kỳ môi trường Linux/Unix nào. Hãy tiếp tục thực hành, thử nghiệm và đừng ngại mắc lỗi. Đó là cách tốt nhất để học và trở nên thành thạo!

Bài liên quan trong #Shell

✓ Đã sao chép link