Chuyển đến nội dung chính

Open-Interpreter: Hướng Dẫn Tác Nhân AI Mã Nguồn Mở cho Lập Trình

Tìm hiểu Open Interpreter là gì, tác nhân lập trình mã nguồn mở của nó hoạt động ra sao, cách cài đặt và sử dụng, và so sánh hỗ trợ mô hình cùng harness tác nhân với các công cụ lập trình AI khác.
Đã cập nhật 5 thg 10, 2026  · 15 phút đọc

Khám phá cùng AI

ChatGPTClaudePerplexity

Nếu bạn từng chạy một mô hình open-weight bên trong một tác nhân lập trình được xây cho mô hình khác, bạn sẽ biết đó không phải ý hay.

Mô hình thường đọc sai lược đồ công cụ và lặp đi lặp lại cùng một lệnh thất bại cho đến khi bạn dừng nó. Khi bạn quay về đúng mô hình mà tác nhân được xây dựng cho nó, cùng tác vụ sẽ chạy trơn tru. Vấn đề thường không nằm ở mô hình, mà ở bộ harness của tác nhân bao quanh, vì prompt và định dạng công cụ đã được tinh chỉnh cho đối tượng khác.

Open Interpreter giải quyết điều này bằng cách mô phỏng đúng harness mà mỗi mô hình đã được tinh chỉnh, như Claude Code hoặc Kimi Code. Đây là một tác nhân AI lập trình mã nguồn mở chạy từ terminal của bạn, và phiên bản hiện tại là dự án Rust xây trên Codex của OpenAI, không phải trợ lý máy tính viết bằng Python mà bạn có thể nhớ trước đây.

Trong bài viết này, tôi sẽ hướng dẫn bạn cài đặt, thiết lập mô hình và harness, quy trình lập trình thực hành, và so sánh Open Interpreter với Claude Code, OpenCode, và Codex.

Bạn mới làm quen với tác nhân AI? Hãy đăng ký khóa Introduction to AI Agents và nắm vững nền tảng chỉ trong một buổi chiều.

Open Interpreter là gì?

Open Interpreter cho một mô hình AI quyền truy cập vào dự án của bạn và các công cụ mà một lập trình viên sẽ dùng trên đó.

Bạn chỉ cần mô tả tác vụ bằng tiếng Anh đơn giản, và tác nhân sẽ làm việc trên mã của bạn. Nó có thể làm việc với:

  • Tệp: Đọc và chỉnh sửa mã của bạn
  • Lệnh: Chạy lệnh shell, script, và các bước build
  • Kho mã: Hoạt động với Git, nên có thể kiểm tra lịch sử dự án và hiển thị diff các thay đổi
  • Công cụ phát triển: Dùng test runner và linter để tự kiểm tra kết quả
  • Tác vụ nhiều bước: Xâu chuỗi các hành động này, từ điều tra ban đầu đến bản sửa lỗi đã kiểm thử

Dự án là mã nguồn mở theo giấy phép Apache 2.0. Nó cũng không bị giới hạn ở một nhà cung cấp mô hình. Bạn có thể kết nối với mô hình được lưu trữ, mô hình open-weight, hoặc mô hình chạy cục bộ trên máy của bạn.

Kho chính có hơn 68.000 sao trên GitHub tính đến tháng 9 năm 2026.

Cách Open Interpreter hoạt động

Open Interpreter vận hành theo một vòng lặp:

  1. Tác vụ: Bạn mô tả điều bạn muốn, ví dụ "sửa bài kiểm thử đang hỏng"
  2. Khảo sát: Mô hình đọc cấu trúc dự án và các tệp liên quan
  3. Lập kế hoạch: Quyết định công cụ hoặc hành động cần cho tác vụ
  4. Chỉnh sửa: Đọc hoặc thay đổi tệp
  5. Lệnh: Chạy lệnh shell, chẳng hạn như bộ bài kiểm thử
  6. Đánh giá: Kiểm tra đầu ra để xem thay đổi đã hiệu quả chưa
  7. Lặp lại: Lặp các bước 2-6 cho đến khi xong tác vụ hoặc cần bạn nhập liệu

Một số bước cần bạn phê duyệt trước, tùy cài đặt quyền. Tôi sẽ đề cập ở phần bảo mật.

Đây là cái nhìn trực quan hơn:

Cách Open Interpreter hoạt động

Cách Open Interpreter hoạt động

Điều cần nhớ là bạn không nói chuyện trực tiếp với mô hình. Open Interpreter gửi tác vụ của bạn tới mô hình, được định dạng bằng prompt và định nghĩa công cụ của harness đang hoạt động. Mô hình yêu cầu gọi công cụ, và Open Interpreter chạy chúng trên codebase của bạn. Sau đó kết quả được gửi lại cho mô hình cho bước kế tiếp.

Vì mô hình và harness là các lớp tách rời, bạn có thể thay đổi một trong hai mà không phải đụng tới phần còn lại của thiết lập.

Cách cài đặt Open Interpreter

Open Interpreter được cài như một binary độc lập, nên bạn không cần Python hay pip.

Nếu một bài blog cũ bảo bạn chạy pip install open-interpreter, đó là phiên bản Python kế thừa. Lệnh đó sẽ không mang lại tác nhân lập trình dựa trên Rust mà tôi đề cập trong bài này.

Bạn cũng nên cài Git trên máy. Open Interpreter chạy được không cần Git, nhưng Git giúp phiên làm việc nhận biết kho và xem diff.

macOS và Linux

Chạy script cài đặt từ terminal:

curl -fsSL https://www.openinterpreter.com/install | sh

Script tải bản phát hành phù hợp nền tảng của bạn và đặt lệnh interpreter vào ~/.local/bin.

Windows

Mở PowerShell và chạy:

irm https://www.openinterpreter.com/install.ps1 | iex

WSL cũng được hỗ trợ nếu bạn thích thiết lập kiểu Linux. Khi đó, chạy lệnh của macOS và Linux trong terminal WSL của bạn.

Xác minh cài đặt

Khởi động lại terminal để nạp PATH mới, sau đó kiểm tra phiên bản:

interpreter --version

Nếu bạn thấy số phiên bản, việc cài đặt đã thành công.

Kiểm tra phiên bản Open Interpreter

Kiểm tra phiên bản Open Interpreter

Khởi chạy phiên tương tác

Bắt đầu một phiên từ bất kỳ thư mục nào:

interpreter

Bạn cũng có thể gõ i, là bí danh ngắn cho cùng lệnh.

Open Interpreter mở một giao diện terminal nơi bạn mô tả tác vụ bằng tiếng Anh đơn giản. Lần đầu khởi động, nó sẽ yêu cầu bạn kết nối nhà cung cấp mô hình. Tôi sẽ dùng một mô hình cục bộ qua Ollama ở phần tiếp theo, nên bạn có thể bỏ qua bước này lúc này.

Phiên tương tác Open Interpreter

Phiên tương tác Open Interpreter

Để thoát phiên, gõ /exit.

Cách sử dụng Open Interpreter

Cách nhanh nhất để hiểu một tác nhân lập trình là giao cho nó một tác vụ và xem nó xử lý thế nào.

Tôi sẽ dùng một dự án theo dõi thói quen nhỏ cho toàn bộ phần này. Nó có một hàm, một tệp kiểm thử, và một lỗi.

Tạo dự án demo

Dự án tính chuỗi dài nhất của các ngày liên tiếp cho một thói quen. Ví dụ, đếm bạn đã tập thể dục liên tục bao nhiêu ngày.

Bắt đầu với một thư mục dự án và môi trường ảo:

mkdir habit-tracker && cd habit-tracker
python3 -m venv .venv
source .venv/bin/activate
pip install pytest

Tạo habits.py với đoạn mã sau:

def longest_streak(dates):
    """Return the longest run of consecutive days.

    Each date is a 'YYYY-MM-DD' string, for example "2026-03-14".
    Duplicate dates count once.
    """
    days = sorted(set(dates))
    if not days:
        return 0

    longest = current = 1
    for previous, today in zip(days, days[1:]):
        if int(today[8:10]) - int(previous[8:10]) == 1:
            current += 1
            longest = max(longest, current)
        else:
            current = 1
    return longest

Sau đó tạo test_habits.py:

from habits import longest_streak


def test_streak_within_one_month():
    dates = ["2026-03-01", "2026-03-02", "2026-03-03", "2026-03-10"]
    assert longest_streak(dates) == 3


def test_duplicate_dates_count_once():
    dates = ["2026-03-01", "2026-03-01", "2026-03-02"]
    assert longest_streak(dates) == 2


def test_streak_across_month_boundary():
    dates = ["2026-01-30", "2026-01-31", "2026-02-01"]
    assert longest_streak(dates) == 3

Hàm có một lỗi. Tôi sẽ không chỉ ra, vì tìm lỗi là việc của tác nhân.

Thêm tệp .gitignore để môi trường ảo và các tệp cache không vào kho:

.venv/
__pycache__/
.pytest_cache/

Giờ hãy commit dự án:

git init
git add .
git commit -m "Initial commit"

Commit này cho bạn một điểm khởi đầu sạch. Lát nữa, bạn sẽ dùng nó để xem chính xác tác nhân đã thay đổi gì.

Chạy kiểm thử để xác nhận lỗi:

python -m pytest

Kết quả kiểm thử trình theo dõi thói quen

Kết quả kiểm thử trình theo dõi thói quen

Hai bài kiểm thử qua, và một bài hỏng. Đó là vấn đề Open Interpreter cần giải quyết.

Khởi động Open Interpreter với mô hình cục bộ

Bạn sẽ cần Ollama đã cài và chạy. Bạn cũng cần một mô hình hỗ trợ gọi công cụ, nên hãy pull nó:

ollama pull qwen3-coder:30b

Sau đó khởi chạy Open Interpreter từ thư mục dự án. Dùng cùng terminal, để tác nhân có thể sử dụng bản cài pytest trong môi trường ảo của bạn:

interpreter --oss --local-provider ollama -m qwen3-coder:30b

Ý nghĩa của từng cờ:

  • --oss: Dùng nhà cung cấp mã nguồn mở cục bộ

  • --local-provider ollama: Chọn Ollama thay vì LM Studio

  • -m qwen3-coder:30b: Đặt mô hình cho lần chạy này

Chạy /status để xác nhận nhà cung cấp đang hoạt động, mô hình, chế độ sandbox, và chính sách phê duyệt.

Phiên Open Interpreter với mô hình Ollama cục bộ

Phiên Open Interpreter với mô hình Ollama cục bộ

Yêu cầu điều tra lỗi

Bạn chưa muốn tác nhân chỉnh sửa gì cả. Hãy yêu cầu chẩn đoán trước:

The tests in this project are failing. Find the cause and explain how you'd fix it. Don't edit any files yet.

Tác nhân thường sẽ đọc tệp và chạy kiểm thử trước khi trả lời. Lệnh chạy trong sandbox, và nếu tác nhân cần quyền vượt mức sandbox cho phép, nó sẽ hỏi bạn trước.

Đầu ra Open Interpreter

Đầu ra Open Interpreter

Xem xét bản sửa đề xuất

Đọc kỹ phần giải thích trước khi bạn phê duyệt bất kỳ thay đổi nào.

Một chẩn đoán đúng sẽ nói rằng hàm chỉ so sánh ngày trong tháng, nên chuỗi sẽ đứt khi bước sang tháng mới. Một bản sửa tốt là so sánh ngày đầy đủ, ví dụ dùng date.fromisoformat() từ mô-đun datetime của Python.

Nếu chẩn đoán sai, hãy sửa ngay trong cùng phiên trước khi tác nhân chỉnh sửa bất kỳ mã nào.

Đề xuất sửa lỗi của Open Interpreter

Cho phép chỉnh sửa tệp và chạy kiểm thử

Khi bạn hài lòng với kế hoạch, hãy triển khai bản sửa:

Apply the fix to habits.py, then run the tests.

Tác nhân sẽ chỉnh sửa tệp và chạy lại pytest. Bạn muốn thấy cả ba bài kiểm thử đều pass.

Tất cả kiểm thử pass sau bản sửa

Tất cả kiểm thử pass sau bản sửa

Kiểm tra diff

Kiểm thử pass không nhất thiết nghĩa là lỗi trong mã của bạn đã được xử lý. Có thể bài kiểm thử đã được cập nhật để lách lỗi. Bạn vẫn cần rà soát mã.

Chạy /diff trong phiên để xem các thay đổi ở working-tree. Bạn cũng có thể chạy git diff sau khi thoát.

Diff các thay đổi do Open Interpreter thực hiện

Diff các thay đổi do Open Interpreter thực hiện

Diff cụ thể phụ thuộc vào mô hình, nên của bạn có thể không khớp từng dòng như trên. Nếu bạn thích thay đổi đó, hãy commit, còn nếu không, hãy khôi phục tệp gốc:

git restore habits.py

Và đó là ý tưởng. Bạn mô tả vấn đề, tác nhân điều tra và sửa, và bạn rà soát mọi thay đổi trước khi nó trở thành một phần của mã nguồn.

Các mô hình trong Open Interpreter

Open Interpreter yêu cầu bạn tự mang mô hình đến.

Mọi yêu cầu đi qua ba lớp sau:

Lớp Ví dụ Quy định điều gì
Nhà cung cấp ollama Nơi yêu cầu được gửi tới và cách bạn xác thực
Mô hình devstral-small-2 Mô hình thực hiện công việc
Harness native Prompt, công cụ, và định dạng thông điệp bao quanh mô hình

Các lớp của yêu cầu

Bạn có thể kết nối những thứ sau:

  • Mô hình được lưu trữ: Mô hình thương mại từ các nhà cung cấp như OpenAI và Anthropic, với đăng nhập hoặc API key
  • Mô hình open-weight qua API: Các mô hình như Kimi K3 và DeepSeek, từ chính nhà cung cấp của chúng hoặc qua các gateway như OpenRouter
  • Mô hình cục bộ: Mô hình chạy trên phần cứng của bạn qua Ollama hoặc LM Studio, là các nhà cung cấp tích hợp sẵn không cần API key

Danh sách nhà cung cấp được tạo từ một danh mục mô hình công khai, và chỉ giữ lại các mô hình hỗ trợ gọi công cụ. Nếu một mô hình bạn mong đợi bị thiếu, đó thường là lý do.

Hãy chú ý ollama-cloud. Đây là một nhà cung cấp lưu trữ riêng, nên yêu cầu của bạn sẽ rời khỏi máy. Chỉ nhà cung cấp tích hợp sẵn ollama mới chạy mô hình cục bộ.

Chuyển đổi mô hình

Bạn có thể đổi mô hình ở ba cấp độ:

  • Bên trong một phiên: Chạy /model để chọn nhà cung cấp, mô hình, và mức độ reasoning

  • Cho một lần chạy: Truyền cờ -m, như ở phần trước

  • Mặc định: Đặt trong tệp cấu hình

Bạn có thể chạy /status bất kỳ lúc nào để xem nhà cung cấp và mô hình đang hoạt động.

Cấu hình nhà cung cấp

Open Interpreter đọc cài đặt từ ~/.openinterpreter/config.toml. Để đặt mặc định cấu hình Ollama ở phần trước, thêm hai dòng này:

model_provider = "ollama"
model = "qwen3-coder:30b"

Sau đó, interpreter sẽ khởi động với mô hình này, và bạn không cần cờ nào nữa.

Các nhà cung cấp lưu trữ đọc API key từ biến môi trường. Ví dụ, DeepSeek cần DEEPSEEK_API_KEY:

export DEEPSEEK_API_KEY="your-api-key"

Bạn cũng có thể thêm bất kỳ endpoint tương thích OpenAI nào làm nhà cung cấp tùy chỉnh:

model_provider = "my-provider"
model = "my-model"

[model_providers.my-provider]
name = "My Provider"
base_url = "https://api.example.com/v1"
env_key = "MY_PROVIDER_API_KEY"
wire_api = "chat"

Thiết lập wire_api cho Open Interpreter biết endpoint mong đợi định dạng yêu cầu nào. Dùng chat cho Chat Completions tương thích OpenAI, responses cho OpenAI Responses API, và messages cho endpoint kiểu Anthropic.

Một dự án đáng tin cậy cũng có thể có .openinterpreter/config.toml riêng, ghi đè cấu hình người dùng của bạn. Cờ dòng lệnh ghi đè cả hai. Nếu bạn không chắc giá trị nào thắng, chạy /debug-config để xem cài đặt hiệu lực và nguồn của chúng.

Vì sao cả mô hình và harness đều quan trọng

Mô hình quyết định tác nhân hiểu mã của bạn tốt đến đâu. Harness quyết định mô hình nhìn nhận tác vụ và công cụ như thế nào.

Bạn cần cả hai. Một mô hình tốt trong một harness lệch sẽ gửi lời gọi công cụ sai định dạng và đọc sai kết quả. Và một harness tốt không thể bù cho một mô hình không hiểu mã.

Đó là lý do Open Interpreter chọn một harness khi bạn chọn mô hình. Ví dụ:

  • Các mô hình Claude nhận harness claude-code

  • Kimi nhận kimi-code

  • Qwen nhận qwen-code

  • DeepSeek nhận claude-code-bare

Với các dòng mô hình khác, bạn có thể tự chọn harness bằng /harness.

Cần nhớ rằng kết quả yếu không phải lúc nào cũng do mô hình yếu. Trước khi đổi mô hình, hãy thử cùng mô hình đó với một harness khác, điều tôi sẽ trình bày chi tiết ở phần tiếp theo.

Các harness tác nhân của Open Interpreter

Mô phỏng harness là lý do chính tồn tại của phiên bản hiện tại Open Interpreter.

Một harness tác nhân là mọi thứ bao quanh mô hình để biến nó thành tác nhân. Nó bao gồm:

  • Hướng dẫn: System prompt nói cho mô hình cách hành xử và khi nào dùng công cụ, cùng nhiều thứ khác
  • Công cụ: Những hành động mô hình có thể thực hiện, như đọc tệp hoặc chạy lệnh, và lược đồ chính xác mỗi lần gọi phải tuân theo
  • Mẫu tương tác: Cách lời gọi công cụ và kết quả được đưa vào hội thoại, và khi nào vòng lặp dừng để hỏi ý kiến bạn
  • Môi trường thực thi: Nơi lệnh chạy, chúng có thể truy cập gì, và điều gì cần bạn phê duyệt

Nói đơn giản, harness quyết định mô hình nhìn tác vụ thế nào và các quyết định của nó biến thành hành động ra sao.

Open Interpreter có một tập các chế độ harness tích hợp. Đây là những cái bạn sẽ dùng nhiều nhất:

  • native: Harness riêng của Open Interpreter, kế thừa từ Codex

  • claude-code: Mô phỏng prompt và bề mặt công cụ của Claude Code từ Anthropic

  • kimi-code: Bản viết lại bằng Rust của harness Kimi Code mà Moonshot khuyến nghị cho các mô hình Kimi

  • qwen-code: Mô phỏng Qwen Code CLI của Alibaba cho các mô hình Qwen

  • swe-agent: Mô phỏng SWE-agent, một tác nhân nghiên cứu được xây để xử lý các issue trên GitHub

Danh sách đầy đủ còn có các biến thể như claude-code-bare, kimi-cli, deepseek-tui, zcode, và minimal. Chạy /harness trong một phiên để xem phiên bản của bạn hỗ trợ gì.

Bạn có thể chuyển harness giữa phiên bằng /harness, hoặc đặt mặc định trong ~/.openinterpreter/config.toml:

harness = "kimi-code"
harness_guidance = true

Thiết lập harness_guidance thêm hướng dẫn độ tin cậy ở nơi harness cho phép. Đặt false nếu bạn muốn mô phỏng chặt chẽ hơn. Nếu để trống harness, Open Interpreter sẽ chọn dựa trên dòng mô hình, như bạn đã thấy ở phần trước.

Vì sao harness quan trọng

Hầu hết nhà cung cấp mô hình tinh chỉnh mô hình lập trình của họ bên trong một thiết lập tác nhân cụ thể, và họ phát hành một harness khuyến nghị kèm theo.

Mô hình quen với harness đó. Nó học phong cách prompt, tên công cụ, định dạng chỉnh sửa tệp, và cách kết quả công cụ được trả về.

Giả sử bạn chạy một mô hình được tinh chỉnh cho chỉnh sửa search-and-replace bên trong một harness kỳ vọng các tệp patch đầy đủ. Mô hình biết thay đổi nào cần làm, nhưng cứ mô tả thay đổi sai định dạng. Vòng lặp tác nhân tiêu tốn token mà không tiến triển.

Kết quả công cụ cũng tương tự. Nếu harness trả về kết quả ở định dạng mô hình chưa thấy, mô hình sẽ đọc sai. Nếu harness xóa reasoning của mô hình giữa các lượt, một mô hình có tư duy sẽ mất dấu kế hoạch của chính nó.

Điều này có nghĩa cùng một mô hình có thể trông tốt trong một tác nhân và tệ trong tác nhân khác, mà không thay đổi trọng số. Đây cũng là lý do kết quả benchmark lập trình thường nêu rõ harness dùng cho mỗi lần chạy.

Các mô hình đầu bảng thường có thể hồi phục khi gặp harness lạ, nhưng mô hình nhỏ và rẻ thường không. Open Interpreter không ép mọi mô hình vào một định dạng, mà thay đổi định dạng để phù hợp mô hình.

Bạn có thể tự thử với dự án demo. Khôi phục tệp gốc bằng git restore habits.py, chuyển harness bằng /harness, và đưa cho tác nhân cùng prompt như trước. Rồi so sánh số bước và cách nó định dạng chỉnh sửa.

Tính năng chính của Open Interpreter

Bạn đã thấy phần lớn các tính năng này trong bài. Dưới đây là ý nghĩa của từng tính năng trong phát triển hằng ngày.

Lập trình nhận biết kho mã

Open Interpreter hoạt động bên trong kho Git của bạn. Nó đọc cấu trúc dự án và theo dõi những gì nó đã thay đổi.

Hai lệnh gạch chéo hữu ích ở đây. /diff hiển thị các thay đổi ở working-tree, và /review yêu cầu tác nhân kiểm tra các thay đổi hiện tại để tìm bug và hồi quy trước khi bạn commit. Bạn có thể chạy cùng bài review mà không mở phiên:

interpreter exec review --uncommitted

Các phiên cũng được lưu. Nếu bạn dừng giữa chừng một tác vụ, interpreter resume --last sẽ tiếp tục từ nơi bạn bỏ dở.

Terminal và thực thi lệnh

Tác nhân chạy các lệnh giống như bạn, ví dụ bộ kiểm thử, linter, script build, và trình quản lý gói. Tất cả chạy trong sandbox gốc trên macOS, Linux, và Windows.

Các lệnh chạy lâu có thể chạy nền. Dùng /ps để liệt kê và /stop để dừng.

Cho script và pipeline CI, interpreter exec chạy một tác vụ không cần giao diện tương tác:

interpreter exec "fix the failing test"

Linh hoạt về mô hình

Bạn có thể đổi nhà cung cấp và mô hình bất kỳ lúc nào với /model. Cấu hình, AGENTS.md, và kỹ năng vẫn áp dụng sau khi đổi.

Hồ sơ (profile) rất hữu ích. Giả sử bạn muốn mô hình rẻ cho công việc thường nhật và mô hình mạnh hơn cho review mã. Bạn có thể định nghĩa cả hai trong cấu hình:

[profiles.review]
model_provider = "deepseek"
model = "deepseek-v4-pro"
sandbox_mode = "read-only"

Sau đó khởi chạy với interpreter --profile review khi bạn cần.

Chuyển đổi harness

/harness thay đổi cách mô hình nhìn tác vụ mà không đổi mô hình. Đây là điều đầu tiên nên thử khi một mô hình gặp khó với lời gọi công cụ, trước khi bạn chuyển sang mô hình lớn hơn.

MCP và công cụ

Model Context Protocol (MCP) kết nối tác nhân với các công cụ mà nó không được thiết kế sẵn để làm việc, như máy chủ tài liệu hoặc cơ sở dữ liệu. Bạn thêm máy chủ trong cấu hình:

[mcp_servers.docs]
command = "npx"
args = ["-y", "your-docs-mcp-server"]
default_tools_approval_mode = "prompt"

Chạy /mcp để xem các máy chủ đã cấu hình và công cụ của chúng. Thiết lập default_tools_approval_mode khiến tác nhân hỏi trước khi dùng công cụ từ máy chủ đó.

Chiều ngược lại cũng hoạt động. interpreter mcp-server phơi bày Open Interpreter như một máy chủ MCP, và interpreter acp chạy nó bên trong các trình soạn thảo hỗ trợ Agent Client Protocol, một tiêu chuẩn mở để kết nối trình soạn thảo với tác nhân lập trình.

Kỹ năng và AGENTS.md

AGENTS.md là tệp Markdown trong kho của bạn với các quy tắc dự án mà tác nhân đọc ở mọi tác vụ. Với trình theo dõi thói quen, nó có thể như sau:

# AGENTS.md
- Run the tests with python -m pytest before you finish a task.
- Use the Python standard library only. Don't add new dependencies.

Bạn cũng có thể chạy /init, và tác nhân sẽ viết phiên bản đầu tiên cho bạn.

Kỹ năng (skills) là các quy trình làm việc tái sử dụng, đóng gói thành thư mục trong .agents/skills trong dự án của bạn hoặc ~/.agents/skills cho người dùng. Tác nhân tự động phát hiện kỹ năng khi một tác vụ khớp. Chạy /skills để xem những gì có sẵn.

Cả hai đều là định dạng chia sẻ, nên cùng tệp hoạt động với các tác nhân lập trình khác hỗ trợ chúng. Open Interpreter cũng hỗ trợ hook, chạy lệnh của bạn tại các điểm cố định trong phiên. Bạn rà soát và tin cậy chúng bằng /hooks.

Sandbox và phê duyệt

Hai cài đặt kiểm soát tác nhân có thể làm gì:

  • Chế độ sandbox: read-only, workspace-write, hoặc danger-full-access

  • Chính sách phê duyệt: untrusted, on-request, hoặc never

Sandbox quyết định điều gì là có thể, và chính sách phê duyệt quyết định khi nào tác nhân hỏi trước. Với workspace-write và on-request, tác nhân có thể chỉnh sửa dự án của bạn và chạy kiểm thử, nhưng sẽ hỏi trước khi cần quyền vượt quá.

Bạn có thể thay đổi cả hai bằng /permissions hoặc bằng cờ -s và -a. Cũng có cờ --yolo bỏ qua cả hai, và tài liệu gắn nhãn là nguy hiểm. Tôi sẽ trình bày chi tiết hơn ở phần bảo mật.

Open Interpreter cho mô hình cục bộ và open

Open Interpreter tự mô tả là tác nhân lập trình xây cho các mô hình giá rẻ.

Các tác nhân lập trình độc quyền lớn nhất được xây quanh mô hình của chính nhà cung cấp. Open Interpreter cho bạn một tác nhân làm việc với mô hình độc quyền, mô hình open-weight lưu trữ, và mô hình cục bộ.

Mô hình open-weight

Các mô hình open-weight như Kimi, DeepSeek, GLM, và Qwen có trọng số công khai. Bạn có thể dùng chúng qua nhà cung cấp bên thứ ba hoặc trên phần cứng của chính bạn.

Điều đó mang lại hai lợi ích. Mô hình open-weight lưu trữ thường có chi phí mỗi token thấp hơn mô hình độc quyền hàng đầu. Và bạn không bị giới hạn ở một máy chủ, vì cùng mô hình chạy ở bất kỳ nơi nào có trọng số của nó.

Open Interpreter có hướng dẫn nhà cung cấp riêng cho Kimi K3, DeepSeek, và GLM. Nó cũng chọn harness phù hợp cho các dòng mô hình này.

Suy luận cục bộ

Ollama và LM Studio là nhà cung cấp tích hợp sẵn, nên bạn có thể chạy mô hình trên máy của mình mà không cần API key hay chi phí theo token.

Cái giá là phần cứng. Khi tôi thử devstral-small-2 trên MacBook Pro M1 Max với 64GB bộ nhớ hợp nhất, riêng mô hình đã chiếm 26 GB. Cửa sổ ngữ cảnh mặc định của Ollama quá nhỏ cho vòng lặp tác nhân, và ở 128k token, mức dùng bộ nhớ cứ tăng giảm cho đến khi phiên bị treo.

Các tác nhân lập trình cần cửa sổ ngữ cảnh lớn, vì system prompt, định nghĩa công cụ, nội dung tệp, và đầu ra lệnh đều phải vừa. Ollama khuyến nghị ít nhất 64k token cho các tác nhân kiểu Codex. Và cửa sổ ngữ cảnh lớn hơn dùng nhiều bộ nhớ hơn ngoài phần mô hình.

Chi phí và quyền riêng tư

Open Interpreter chạy trên máy của bạn, nhưng mô hình thì không bắt buộc.

Mã của bạn đi đâu tùy thuộc vào nhà cung cấp:

  • Nhà cung cấp cục bộ: Prompt, nội dung tệp, và đầu ra lệnh ở lại trên máy của bạn
  • Nhà cung cấp lưu trữ: Tất cả những thứ đó sẽ đến máy chủ của nhà cung cấp, kể cả khi mô hình là open-weight

Cấu hình, phiên, và log của bạn luôn được lưu cục bộ tại ~/.openinterpreter bất kể thế nào.

Nếu bạn cần kiểm soát nhiều hơn, bạn có thể thêm nhà cung cấp tùy chỉnh trỏ tới máy chủ suy luận của riêng bạn. Bất kỳ máy chủ nào có API tương thích OpenAI đều hoạt động, ví dụ triển khai vLLM trên GPU của công ty bạn. Như vậy, bạn có thiết lập lưu trữ nhưng hạ tầng là của bạn.

Hiệu năng sử dụng công cụ

Các mô hình open không giỏi gọi công cụ như nhau. Bạn sẽ thấy việc dùng công cụ kém thể hiện qua lời gọi sai định dạng, vòng lặp, dừng sớm, hoặc bỏ qua đầu ra lệnh.

Harness phù hợp sẽ giúp, nhưng không thể sửa một mô hình không thể lập kế hoạch tác vụ nhiều bước. Các mô hình cục bộ nhỏ gặp vấn đề nhiều nhất ở đây.

Trước khi trỏ một mô hình mới vào dự án thực, hãy thử nó trên một kho nhỏ như trình theo dõi thói quen tôi đã trình bày. Nếu thấy điểm yếu, hãy thử một harness khác trước khi chuyển sang mô hình lớn hơn.

Dưới đây là tóm tắt nhanh các lựa chọn của bạn:

  Nơi chạy suy luận Chi phí Mã rời khỏi máy bạn?
Mô hình lưu trữ độc quyền Máy chủ của nhà cung cấp Theo token hoặc thuê bao Có
Mô hình open-weight lưu trữ Máy chủ của nhà cung cấp Theo token, thường thấp hơn Có
Mô hình open-weight cục bộ Phần cứng của bạn Phần cứng và điện năng Không

Các lựa chọn của Open Interpreter cho mô hình cục bộ và open

Open Interpreter so với các tác nhân lập trình AI khác

Open Interpreter có nhiều điểm chung với các tác nhân lập trình chạy trong terminal khác. Khác biệt nằm ở quyền sở hữu công cụ và mô hình mà nó được xây cho.

Open Interpreter so với Claude Code

Claude Code là tác nhân lập trình trong terminal của Anthropic. Khác biệt đầu tiên là quyền sở hữu - Claude Code là độc quyền, trong khi Open Interpreter mã nguồn mở theo Apache 2.0. Bạn có thể đọc và thay đổi mọi phần của Open Interpreter.

Khác biệt thứ hai là lựa chọn mô hình. Claude Code được xây cho các mô hình Claude. Bạn có thể trỏ nó tới các endpoint tương thích Anthropic từ nhà cung cấp khác, nhưng harness của nó vẫn tinh chỉnh cho Claude. Open Interpreter coi lựa chọn mô hình là tính năng cốt lõi.

So sánh harness mới thú vị. Bản thân Claude Code là một trong các harness mà Open Interpreter mô phỏng. Với chế độ claude-code, bất kỳ mô hình nào cũng nhận được prompt và công cụ kiểu Claude Code bên trong runtime của Open Interpreter. Giao diện và lệnh gạch chéo vẫn là của Open Interpreter, nên đây không phải cùng sản phẩm với mô hình khác.

Cả hai công cụ đều ưu tiên terminal. Mỗi bên đều có phiên tương tác và chế độ không tương tác cho script và CI. Về hướng dẫn dự án, Claude Code đọc CLAUDE.md, còn Open Interpreter dùng định dạng chia sẻ AGENTS.md.

Claude Code có hệ sinh thái lớn hơn. Nó đi kèm extension IDE, ứng dụng desktop và web, chợ plugin, subagent, và SDK. Open Interpreter trẻ hơn, và dựa vào các tiêu chuẩn chia sẻ như MCP, kỹ năng, AGENTS.md, và Agent Client Protocol thay vì hệ sinh thái riêng.

Nếu bạn làm việc với mô hình Claude và muốn trải nghiệm mượt mà nhất, Claude Code là lựa chọn an toàn hơn. Nếu bạn muốn chạy mô hình khác hoặc tránh công cụ độc quyền, hãy chọn Open Interpreter.

Open Interpreter so với OpenCode

OpenCode là đối sánh gần nhất. Cả hai đều mã nguồn mở, ưu tiên terminal, và được xây để làm việc với danh sách dài nhà cung cấp mô hình.

Hỗ trợ mô hình trên giấy tờ thì tương tự. OpenCode hỗ trợ hơn 75 nhà cung cấp, và Open Interpreter tạo danh sách nhà cung cấp từ danh mục mô hình công khai. Cả hai chạy mô hình cục bộ qua Ollama.

Trải nghiệm terminal khác biệt nhiều hơn. OpenCode có TUI riêng với tích hợp Language Server Protocol (LSP), đưa các chẩn đoán mã như lỗi kiểu trả về cho mô hình. TUI của Open Interpreter đến từ Codex.

Về cấu hình, OpenCode dùng tệp opencode.json, còn Open Interpreter dùng config.toml với profile.

Kiến trúc tác nhân là khác biệt chính. OpenCode chạy dạng client và server, nơi TUI là một client của server cục bộ mà các client khác cũng có thể kết nối. Nó có sẵn tác nhân build và plan, và hỗ trợ tác nhân tùy chỉnh và subagent. Nó điều chỉnh system prompt theo từng dòng mô hình, nhưng công cụ và vòng lặp vẫn là của OpenCode. Open Interpreter đi xa hơn và thay cả harness, gồm lược đồ công cụ và định dạng thông điệp. Các bản build mới còn có cả chế độ harness opencode.

Về phía phát triển, OpenCode là codebase riêng, do đội ngũ và cộng đồng của họ xây dựng. Open Interpreter xây trên một nhánh (fork) của Codex, nên phần lớn runtime đến từ upstream. Đó là sự đánh đổi. Open Interpreter nhận được sandbox và runtime của Codex sẵn, trong khi OpenCode kiểm soát toàn bộ stack.

Open Interpreter so với Codex

Hai công cụ này không phải đối thủ theo nghĩa thông thường. Open Interpreter là một nhánh của Codex.

Chúng chia sẻ runtime Rust, TUI, sandbox, phê duyệt, AGENTS.md, kỹ năng, MCP, chế độ exec, và phần lớn lệnh gạch chéo. Khi tôi chạy Open Interpreter, gợi ý tiếp tục phiên vẫn ghi codex resume.

Codex là tác nhân của OpenAI, xây quanh các mô hình OpenAI. Nó hỗ trợ mô hình cục bộ với --oss và nhà cung cấp tùy chỉnh, nhưng trải nghiệm mặc định hướng tới OpenAI.

Open Interpreter mở rộng Codex theo vài hướng:

  • Mô phỏng harness: Thay prompt, lược đồ công cụ, và định dạng thông điệp để phù hợp từng dòng mô hình

  • Hỗ trợ nhà cung cấp: Có danh mục nhà cung cấp được tạo và hướng dẫn riêng cho Kimi K3, DeepSeek, và GLM

  • Chat Completions: Cờ --chat-completions chạy bất kỳ nhà cung cấp tương thích OpenAI

  • Ghi đè Codex SDK: Ứng dụng xây trên Codex SDK có thể chạy qua Open Interpreter

Open Interpreter cũng lưu cấu hình và phiên dưới ~/.openinterpreter, nên không xung đột với cài đặt Codex.

Nếu bạn chủ yếu dùng mô hình OpenAI, Codex là lựa chọn tốt hơn. Nếu bạn dùng mô hình khác, Open Interpreter cho bạn cùng quy trình làm việc với hỗ trợ tốt hơn cho chúng.

Dưới đây là tóm tắt nhanh:

  Giấy phép Mô hình Cách tiếp cận harness Cấu hình
Open Interpreter Mã nguồn mở (Apache 2.0) Bất kỳ nhà cung cấp nào, lưu trữ hoặc cục bộ Mô phỏng harness theo mô hình config.toml
Claude Code Độc quyền Xây cho mô hình Claude Harness riêng của Claude Code settings.json và CLAUDE.md
OpenCode Mã nguồn mở (MIT) 75+ nhà cung cấp, lưu trữ hoặc cục bộ Một harness với prompt theo từng mô hình opencode.json
Codex Mã nguồn mở (Apache 2.0) Xây cho mô hình OpenAI với --oss Harness riêng của Codex config.toml

Open Interpreter so sánh với các tác nhân lập trình AI khác

Bảo mật và quyền của Open Interpreter

Điều tệ nhất chatbot có thể làm là đưa câu trả lời tệ, và bạn có thể bỏ qua. Một tác nhân lập trình thì chạy lệnh trên máy của bạn, đọc và ghi tệp, và có thể truy cập mạng. Một quyết định tệ của mô hình, hoặc một cuộc tấn công prompt injection, có thể gây thiệt hại thực sự. Prompt injection là chỉ dẫn ẩn trong nội dung mà tác nhân đọc, như README hoặc trang web.

Open Interpreter thừa hưởng mô hình bảo mật từ runtime Codex. Nó có hai lớp - một sandbox giới hạn khả năng, và một chính sách phê duyệt quyết định khi nào tác nhân hỏi bạn trước.

Thực thi lệnh và truy cập hệ tệp

Mọi lệnh tác nhân chạy đều đi qua sandbox cấp hệ điều hành trên macOS, Linux, và Windows. Có ba chế độ sandbox:

  • read-only: Tác nhân có thể đọc tệp, nhưng không thể thay đổi gì

  • workspace-write: Tác nhân có thể chỉnh sửa tệp và chạy lệnh trong thư mục dự án của bạn

  • danger-full-access: Không có sandbox

Với workspace-write, việc ghi tệp bị giới hạn trong workspace đang hoạt động. Tác nhân có thể sửa mã của bạn, nhưng không thể chỉnh sửa tệp ở nơi khác trên máy.

Truy cập mạng

Ở chế độ workspace-write, các lệnh mặc định không có quyền mạng. Điều này chặn tải xuống và ngăn tác nhân gửi mã của bạn đi đâu đó.

Một số tác vụ cần mạng, ví dụ cài gói. Bạn có thể bật truy cập mạng trong cấu hình:

sandbox_mode = "workspace-write"

[sandbox_workspace_write]
network_access = true

Chỉ bật cho các dự án thực sự cần.

Phê duyệt

Chính sách phê duyệt quyết định khi nào tác nhân dừng lại và hỏi:

  • untrusted: Hỏi trước khi chạy các lệnh không nằm trong danh sách tin cậy

  • on-request: Hỏi khi một tác vụ cần quyền vượt mức sandbox cho phép

  • never: Không bao giờ hỏi

Với dự án có kiểm soát phiên bản, workspace-write cùng on-request là mặc định tốt. Tác nhân làm việc trong dự án của bạn và hỏi trước khi đi xa hơn. Git cho bạn đường lui nếu có trục trặc.

Cờ --yolo tắt cả sandbox và phê duyệt. Chỉ dùng trong môi trường có thể bỏ đi, như container hoặc VM.

Thông tin xác thực và bí mật

Các lệnh tác nhân chạy sẽ kế thừa môi trường shell của bạn. Nếu API key của bạn ở biến môi trường, các lệnh đó có thể thấy chúng.

Bạn có thể giới hạn bằng shell_environment_policy:

[shell_environment_policy]
inherit = "core"
exclude = ["AWS_*", "*_TOKEN"]

Thiết lập core chỉ truyền các biến cơ bản như HOME và PATH, và exclude loại bỏ mọi thứ khớp mẫu.

Tệp cũng là một rủi ro. Tác nhân có thể đọc tệp .env trong dự án của bạn ngay cả ở chế độ read-only. Với nhà cung cấp lưu trữ, bất cứ thứ gì tác nhân đọc đều được gửi lên máy chủ của nhà cung cấp.

Điều cần nhớ là sandbox giới hạn thiệt hại, nhưng bạn vẫn nên coi nó là lưới an toàn, không phải đảm bảo tuyệt đối.

Trước khi để tác nhân tự chạy, hãy chạy /status và kiểm tra chế độ sandbox và chính sách phê duyệt.

Sự phát triển của Open Interpreter

Nếu bạn thấy một bài viết về Open Interpreter mở đầu bằng pip install, không phải sai. Nó mô tả một dự án khác.

Open Interpreter nguyên bản ra mắt năm 2023 dưới dạng dự án Python. Nó cho phép mô hình ngôn ngữ chạy mã Python, JavaScript, và shell trên máy của bạn, và được biết đến như một thay thế mã nguồn mở cho Code Interpreter của ChatGPT. Các phiên bản sau thêm điều khiển máy tính, để mô hình làm việc với desktop của bạn.

Dự án chính hiện tại là bản viết lại bằng Rust dựa trên Codex. Nó tập trung vào tác nhân lập trình và mô phỏng harness, không phải điều khiển máy tính tổng quát.

Phiên bản Python không biến mất. Nó tiếp tục dưới dạng nhánh cộng đồng tại endolith/open-interpreter.

Cả hai phiên bản dùng cùng tên, cùng lịch sử kho GitHub, và cùng lệnh interpreter, nên rất dễ nhầm lẫn.

Nhưng một dấu hiệu rất rõ là:

  • pip install open-interpreter: Phiên bản Python kế thừa

  • curl hoặc trình cài PowerShell: Phiên bản Rust hiện tại

Ưu điểm và hạn chế của Open Interpreter

Open Interpreter không phải công cụ phù hợp cho mọi thiết lập. Dưới đây là nơi nó hợp lý và nơi không.

Ưu điểm

  • Mã nguồn mở: Giấy phép Apache 2.0, bạn có thể đọc, kiểm toán, và fork toàn bộ codebase

  • Lựa chọn mô hình: Bạn có thể dùng mô hình lưu trữ, open-weight, và cục bộ từ một tác nhân, và chuyển đổi giữa chúng trong phiên

  • Nhiều harness tác nhân: Bạn tiến gần hơn tới hiệu năng mà mô hình đã được tinh chỉnh, điều mà ít tác nhân khác cung cấp

  • Phát triển gốc terminal: Phù hợp với workflow shell và Git hiện có, và chế độ exec hoạt động trong script và CI

  • Mô hình mở và giá thấp hơn: Dự án được xây xoay quanh chúng, với hướng dẫn nhà cung cấp riêng và harness phù hợp

  • Khả năng mở rộng: MCP, kỹ năng, hook, AGENTS.md, Agent Client Protocol, và ghi đè Codex SDK cho phép bạn kết nối với công cụ khác

Hạn chế

  • Chất lượng mô hình biến thiên: Tác nhân chỉ tốt bằng mô hình phía sau nó, và không harness nào sửa được một mô hình không thể lập kế hoạch đa bước

  • Mô hình cục bộ cần phần cứng mạnh: Trong thử nghiệm của tôi, riêng devstral-small-2 đã chiếm 26 GB bộ nhớ, trước cả cửa sổ ngữ cảnh lớn mà tác nhân lập trình cần

  • Thiết lập tốn công hơn: Bạn tự quản lý nhà cung cấp, cửa sổ ngữ cảnh, harness, và cài đặt sandbox. Cũng có vài góc cạnh thô, như thương hiệu Codex còn sót và cảnh báo metadata cho mô hình Ollama

  • Thực thi lệnh có rủi ro: Sandbox và phê duyệt làm giảm rủi ro, nhưng không loại bỏ nó

  • Mã vẫn cần review: Kiểm thử pass không đảm bảo bản sửa đúng, nên bạn phải đọc mọi diff

Kết luận

Open Interpreter là một tác nhân lập trình mã nguồn mở hoạt động với mô hình bạn chọn, dù mô hình đó được lưu trữ, open-weight, hay chạy trên máy của bạn.

Quy trình làm việc đơn giản. Bạn chọn mô hình và harness, trỏ tác nhân vào một dự án, và để nó khảo sát, chỉnh sửa, và chạy lệnh cho đến khi hoàn thành tác vụ. Sau đó bạn rà soát kết quả.

Mô phỏng harness khiến nó khác biệt so với đối thủ. Open Interpreter không ép mọi mô hình vào một thiết lập tác nhân. Nó thay đổi thiết lập để phù hợp mô hình, và điều đó có thể tạo nên khác biệt. Mô hình cũng quyết định chất lượng công việc, và quyền hạn quyết định tác nhân có thể sửa gì. Việc rà soát của bạn là bước kiểm tra cuối trước khi thay đổi chạm tới codebase.

Nếu bạn muốn lấy chứng chỉ kỹ sư AI, hãy đăng ký lộ trình Associate AI Engineer for Developers và chuyển mình vào thế giới AI theo nhịp độ của riêng bạn.


Dario Radečić's photo
Author
Dario Radečić
LinkedIn
Chuyên gia Khoa học Dữ liệu Cấp cao, làm việc tại Croatia. Tác giả Công nghệ Hàng đầu với hơn 700 bài viết đã xuất bản, đạt trên 10 triệu lượt xem. Tác giả cuốn sách Tự động hóa Machine Learning với TPOT.

FAQs

Open Interpreter dùng để làm gì?

Open Interpreter là một tác nhân lập trình mã nguồn mở làm việc trên các dự án của bạn từ terminal. Bạn mô tả tác vụ, và nó đọc mã, chỉnh sửa tệp, chạy lệnh, và kiểm tra kết quả cho đến khi hoàn tất. Lập trình viên dùng nó để sửa lỗi, tái cấu trúc, review mã, và tự động hóa trong script và pipeline CI.

Open Interpreter có miễn phí không?

Có, Open Interpreter là mã nguồn mở theo giấy phép Apache 2.0, nên bản thân công cụ không mất phí. Bạn vẫn trả cho mô hình bạn kết nối. Nhà cung cấp lưu trữ tính theo token hoặc thuê bao, trong khi mô hình cục bộ qua Ollama hoặc LM Studio không tốn theo token nhưng cần phần cứng tốt.

Open Interpreter có an toàn khi sử dụng không?

Open Interpreter chạy lệnh trong sandbox cấp hệ điều hành và hỏi phê duyệt trước khi vượt quá giới hạn sandbox. Mặc định, chế độ workspace-write giới hạn việc ghi tệp trong thư mục dự án của bạn và chặn truy cập mạng. Sandbox giảm rủi ro nhưng không loại bỏ, nên hãy kiểm tra cài đặt quyền bằng /status và rà soát mọi thay đổi trước khi commit.

Sự khác nhau giữa phiên bản Rust và Python của Open Interpreter là gì?

Phiên bản Python ban đầu cho phép mô hình ngôn ngữ chạy mã trên máy bạn và điều khiển máy tính, và bạn cài bằng pip install open-interpreter. Phiên bản hiện tại là bản viết lại bằng Rust dựa trên Codex của OpenAI, tập trung vào tác nhân lập trình và mô phỏng harness, và được cài qua script độc lập. Phiên bản Python tiếp tục dưới dạng nhánh cộng đồng, nên cả hai vẫn có ý nghĩa ngày nay.

Vì sao mô hình Ollama cục bộ của tôi bị lặp hoặc treo trong Open Interpreter?

Nguyên nhân phổ biến nhất là cửa sổ ngữ cảnh quá nhỏ. System prompt, định nghĩa công cụ, và nội dung tệp không vừa, khiến mô hình mất dấu tác vụ. Đặt OLLAMA_CONTEXT_LENGTH ít nhất 65536, và xác nhận giá trị bằng ollama ps. Nếu mức dùng bộ nhớ vẫn cứ tăng rồi giảm sau đó, mô hình quá lớn so với máy của bạn, hãy chuyển sang mô hình nhỏ hơn như qwen3-coder:30b hoặc gpt-oss:20b.

Chủ đề
Trí tuệ Nhân tạo

Học với DataCamp

Lộ trình

Kỹ sư Trợ lý Trí tuệ Nhân tạo (AI) cho Lập trình viên

26 giờ
Học cách tích hợp trí tuệ nhân tạo (AI) vào các ứng dụng phần mềm thông qua việc sử dụng các giao diện lập trình ứng dụng (API) và các thư viện mã nguồn mở. Hãy bắt đầu hành trình trở thành Kỹ sư Trí tuệ Nhân tạo ngay hôm nay!
Xem chi tiếtRight Arrow
Bắt Đầu Khóa Học
Xem thêmRight Arrow
Liên quan

blog

Claude Opus 4.6: Tính năng, Điểm chuẩn, Bài kiểm tra thực hành và hơn thế nữa

Mô hình mới nhất của Anthropic dẫn đầu ở mã hóa tác tử và lập luận phức tạp. Thêm vào đó, nó có cửa sổ ngữ cảnh 1M.
Matt Crabtree's photo

Matt Crabtree

10 phút

Xem ThêmXem Thêm