2013-05-24 29 views
11

Có vẻ như ZeroMQ không hoạt động với ổ cắm theo các ổ cắm UNIX truyền thống. Tôi đã thiết kế kiến ​​trúc cho thuật toán tìm kiếm phân tán dựa trên nhận thức sai về ZeroMQ. Trong chương trình của tôi, có một đại lý chịu trách nhiệm giám sát các đại lý khác và thu thập dữ liệu của họ. Dữ liệu thực sẽ được chuyển giữa các tác nhân theo mẫu PULL-PUSH hoặc PUB-SUB. Mỗi tác nhân có một ổ cắm PULL lắng nghe cho các tin nhắn gửi đến. Mỗi thư bao gồm số ID chỉ định nhận dạng người gửi.Cách nhận IP công khai của người yêu cầu trong mẫu REQ-REP của ZeroMQ?

Ở giai đoạn khởi tạo, màn hình được cho là lắng nghe trên ổ cắm REP của nó. Mỗi tác nhân sẽ kết nối với ổ cắm REP nổi tiếng của màn hình và tự giới thiệu (gửi số ID của mình và số cổng mà tác nhân đang nghe). Màn hình lưu trữ tất cả dữ liệu về các tác nhân trong hồ sơ của ba trường: <ID, IP, port>. (Đây là nơi tôi có vấn đề với ZMQ.) Khi số lượng đại lý nhất định sẵn sàng, màn hình sẽ gửi tất cả dữ liệu (mỗi đại lý <IP,ID,port>) cho tất cả các đại lý. Bước cuối cùng được thực hiện bởi một mẫu PUB-SUB giữa các tác nhân và màn hình.

hình ảnh này có thể giúp để có được một ý tưởng những gì tôi có nghĩa là để thực hiện: De-centralized Search

Trong hình trên, màn hình nên gửi nó bảng để tất cả mọi người. Câu hỏi quan trọng là làm thế nào để có được địa chỉ IP công cộng của một người yêu cầu (bất kỳ đại lý nào) trong một mô hình REQ-REP? Tất cả các tác nhân liên kết với máy chủ cục bộ của họ (127.0.0.1). Chúng được cho là phân phối trên số lượng máy chủ tùy ý. Vì vậy, AFAIK họ cần phải biết IP công cộng của nhau.

Trong trường hợp không có giải pháp nào tồn tại, bất kỳ trợ giúp nào về thiết kế lại kiến ​​trúc đều phù hợp.

giải pháp Cập nhật

Một ứng cử viên tôi có thể nghĩ ra, là để sửa đổi từng đại lý để ràng buộc vào/IP công cộng của mình thay vì localhost. Nếu có một cách kỳ diệu để nhận địa chỉ IP công khai, bất kỳ nhân viên nào cũng có thể gửi địa chỉ của anh ấy đến màn hình.

Second Cập nhật

Hiện nay các đại lý có được địa chỉ IP công cộng của nó và gửi nó qua tin nhắn đến máy chủ:

std::string AIT::ABT_Socket::getIP() { 
    std::string address = ""; 
    FILE * fp = popen("ifconfig", "r"); 
    if (fp) { 
     char *p = NULL, *e; 
     size_t n; 
     while ((getline(&p, &n, fp) > 0) && p) { 
      if (p = strstr(p, "inet addr:")) { 
       p += 10; 
       if (e = strchr(p, ' ')) { 
        *e = '\0'; 
        return std::string(p); 
        address = std::string(p); 

       } 
      } 
     } 
    } 
    pclose(fp); 
    return address; 
} 
+0

Chỉ cần làm rõ, bạn đang nói màn hình cần biết địa chỉ IP của các đại lý để nó có thể gửi cho họ bảng của nó? – raffian

+0

Không. Màn hình cần biết địa chỉ IP của các đại lý, để gửi các địa chỉ IP đó tới tất cả các địa chỉ đó. Nói cách khác, để xây dựng bảng. Nó có thể gửi tin nhắn, nhưng nó không biết địa chỉ IP sử dụng ZeroMQ: D –

+0

Bạn có thể lưu địa chỉ IP trên mỗi tác nhân trong tập tin cấu hình hay chỉ sử dụng 'ifconfig' và phân tích 'địa chỉ inet' để nhận IP? Sau đó, mỗi tác nhân có thể gửi IP trong một tin nhắn đến màn hình – raffian

Trả lời

2

tăng có thể xác định địa chỉ IP của bạn một cách cầm tay như sau:

tcp::resolver resolver(io_service); 
tcp::resolver::query query(boost::asio::ip::host_name(), ""); 
tcp::resolver::iterator iter = resolver.resolve(query); 
tcp::resolver::iterator end; // End marker. 
while (iter != end) 
{ 
    tcp::endpoint ep = *iter++; 
    std::cout << ep << std::endl; 
} 

Nhưng điều đó không có nghĩa là sửa chữa dễ dàng - điều gì sẽ xảy ra nếu hộp có nhiều IP/NIC/WAN/LAN vv .... Khi nào Gần đây tôi có tình huống tương tự, tôi buộc người gọi phải cung cấp rõ ràng IP và cổng mong muốn trên dòng lệnh, sau đó chia sẻ nó khi kết nối với các quá trình khác trên máy chủ khác (trong trường hợp của tôi, qua HTTP).

0

Tại sao bạn không gửi thông qua một phần tải trọng?

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