Tải bản đầy đủ (.pdf) (44 trang)

Bài giảng lập trình ứng dụng mạng bài 3 GV võ tấn dũng

Bạn đang xem bản rút gọn của tài liệu. Xem và tải ngay bản đầy đủ của tài liệu tại đây (390.37 KB, 44 trang )

TRƯỜNG CAO ĐẲNG CÔNG NGHỆ THÔNG TIN TP.HCM

LẬP TRÌNH ỨNG DỤNG MẠNG

BÀI 3

RMI

(Remote Method Invoke)

GIẢNG VIÊN:

VÕ TẤN DŨNG


PHẦN 1

GV: Võ Tấn Dũng

GIỚI THIỆU
TỔNG QUAN VỀ RMI


TỔNG QUAN VỀ RMI
• Thông thường các chương trình của chúng ta được viết
dưới dạng thủ tục hay hàm. Mã lệnh của hàm (hay thủ
tục) được nạp thẳng vào bộ nhớ và thực thi ngay trên
máy cục bộ. Vậy thì có cách nào nạp nội dung của hàm
hay đối tượng ở một máy nào đó và gọi chúng từ một
máy khác hay không?


3

GV: Võ Tấn Dũng

• RMI (Remote Method Invoke – có nghĩa là gọi phương
thức từ xa) là cách thức giao tiếp giữa các đối tượng
Java có mã lệnh cài đặt nằm trên máy khác nhau có thể
gọi lẫn nhau.


Local Machine (Client)
Remote Machine (Server)

SampleServer
remoteObject;
int s;

s=remoteObject.sum(1,2);

1,2
public int sum(int a,int b)
{
return a + b;
}

3

4

GV: Võ Tấn Dũng


System.out.println(s);


STUB và SKELETON

5

GV: Võ Tấn Dũng

• Các tham số truyền cho các phương thức của đối tượng
ở xa phải được đóng gói và chuyển qua mạng để đến
được với phương thức thực sự (việc truyền kết quả trở về
cũng vậy).
• Để giải quyết các vấn đề trên, đối tượng Java trên hai
máy khác nhau không gọi nhau trực tiếp mà thông qua
các lớp trung gian nằm trên cả máy khách và máy chủ.
• Phía máy khách, lớp trung gian này được gọi là Stub.
Phía máy chủ, lớp trung gian này được gọi là Skeleton.


Computer A

A1
A2

C1_skel

C1_stub


Computer C

C1

B1_stub

B1_skel

Computer B
6

GV: Võ Tấn Dũng

B1


CƠ CHẾ HOẠT ĐỘNG CỦA RMI
Remote Machine

• Đầu tiên RMI-server đăng
ký tên của nó với bộ
Registry.

bind
RMI Server
Registry
skeleton

• RMI-client tìm tên của
RMI-server trong bộ

Registry để thiết lập truy
cập từ xa với RMI-server.

return

call

lookup

stub

RMI Client

Local Machine

7

GV: Võ Tấn Dũng

• Stub đóng gói tham số rồi
gửi đến Skeleton.
Skeleton gọi phương thức
từ xa rồi đóng gói kết quả
gửi về Stub.


GIAO TIẾP STUB-SKELETON
return

RMI Server


• Client gọi một phương thức từ xa, lời gọi này đầu
tiên được chuyển tiếp đến Stub.
• Stub có nhiệm vụ gửi tiếp lời yêu cầu này đến
Skeleton phía server bằng cách Stub mở một
socket đến server, đóng gói các tham số rồi truyền
luồng dữ liệu này đến Skeleton.
• Skeleton chứa đựng một phương thức nhận các
lời yêu cầu từ xa, mở gói tham số, gọi hàm thực
sự trên server để tính toán rồi trả kết quả về Stub
phía client.
8

GV: Võ Tấn Dũng

Stub

RMI Client

skeleton

call


PHẦN 2

GV: Võ Tấn Dũng

THIẾT KẾ
ỨNG DỤNG PHÂN TÁN RMI



CÁC BƯỚC XÂY DỰNG MỘT RMI

10

GV: Võ Tấn Dũng

1. Định nghĩa một giao tiếp từ xa (remote interface) trên
server.
2. Xây dựng một đối tượng từ xa (remote object) bằng cách
hiện thực giao tiếp từ xa (remote interface).
3. Xây dựng chương trình phía client.
4. Biên dịch các file Java nguồn (phía client và server).
5. Sinh ra các Stub phía client và Skeleton phía server.
6. Khởi động bộ đăng ký RMI (RMI registry)
7. Khởi động các đối tượng từ xa phía server
8. Chạy chương trình phía client.


Step 1: ĐỊNH NGHĨA MỘT REMOTE INTERFACE
Để tạo một ứng dụng RMI, bước đầu tiên là định nghĩa một Remote
Interface giữa các đối tượng Client và Sever.
Các phương thức trong Remote Inteface muốn được gọi từ xa đều
phải có khả năng ném ra ngoại lệ RemoteException.

/* Calculator.java */
package calculator;
import java.rmi.*;


11

GV: Võ Tấn Dũng

public interface Calculator extends Remote
{
public int sum(int x,int y) throws RemoteException;
}


Step 2: HIỆN THỰC REMOTE INTERFACE
Lớp Calculator ở Step 1 chỉ là một Remote Interface, nó chỉ đặc tả các phương thức
của đối tượng. Từ giao tiếp đó, đối tượng thực sự phải được cài đặt như sau:

/* CalculatorImpl.java*/
import java.rmi.*;

C:\RMI>javac CalculatorImpl.java

12

GV: Võ Tấn Dũng

public class CalculatorImpl implements Calculator
{
public int addNum(int x,int y) throws RemoteException
{
System.out.println(“Client request to calculate”);
return (x+y);
}

}


Step 2: HIỆN THỰC REMOTE INTERFACE

(tt)

Bây giờ ta viết một chương trình để cài đặt đối tượng Calculator trên
máy server. Ta đặt tên chương trình này là CalculatorServer:
/* CalculatorServer.java*/
C:\RMI>javac CalculatorServer.java
import java.rmi.server.*;
Import java.rmi.*;
public class CalculatorServer {
public static void main(String args[]) {
try{
//tạo đối tượng Calculator thực sự

CalculatorImpl c=new CalculatorImpl();
System.out.println(“Exporting Calculator…”);
//thông báo sự hiện diện của đối tượng cho máy ảo Java

UnicastRemoteObject.exportObject(c);
Naming.bind(“rmi://localhost/Mycalculator”,c);
System.out.println(“Register Calculator!”);
} catch(Exception e) { System.out.println(e); }
}
}

13


GV: Võ Tấn Dũng

//đăng ký đối tượng với bộ quản lý rmi


Step 3: XÂY DỰNG CHƯƠNG TRÌNH PHÍA CLIENT
Ở bước này ta thiết kế chương trình phía bên máy khách (client) có khả
năng gọi và sử dụng đối tượng Calculator trên máy chủ (server), như sau:
/* CalculatorClient.java*/
Import java.rmi.*;
public class CalculatorClient {
public static void main(String args[]) {
try{
//tìm đối tượng cần truy xuất theo tên

System.out.println(“Finding object…”);
Calculator c=(Calculator)Naming.lookup
(“rmi://localhost/MyCalculator”);
//gọi phương thức của đối tượng

System.out.println(c.addNum(12,1));
} catch(Exception e) { System.out.println(e); }
}
Chú ý: ở đây c thuộc lớp Calculator nhưng thực tế khi chạy thì chương trình sẽ gọi CalculatorImpl.class
14

GV: Võ Tấn Dũng

}



Step 4: BIÊN DỊCH CÁC FILE JAVA NGUỒN
Phía server ta đã có các fie nguồn là Calculator.java,
CalculatorImpl.java, CalculatorServer.java. Tiến hành
biên dịch chúng như sau:
C:\RMI>javac Calculator.java
C:\RMI>javac CalculatorImpl.java
C:\RMI>javac CalculatorServer.java
Phía bên Client ta đã có file nguồn là
CalculatorClient.java. Tiến hành biên dịch như sau:

15

GV: Võ Tấn Dũng

C:\RMI>javac CalculatorClient.java


Step 5: SINH LỚP TRUNG GIAN STUB & SKETLETON

Dựa vào lớp cài đặt CalculatorImpl.class, trình biên dịch
rmic.exe của Java của Java sẽ cung cấp cho ta hai lớp
trung gian Stub và Skeleton. Mở của sổ DOS-promp (cmd)
rồi đánh lệnh biên dịch sau:
C:\RMI>rmic CalculatorImpl

16

GV: Võ Tấn Dũng


Kết quả ta sẽ thu được hai tập tin CalculatorImpl_Stub.class
và CalculatorImpl_Skel.class


Step 6: CHẠY CHƯƠNG TRÌNH rmiregistry.exe

17

GV: Võ Tấn Dũng

Mở cửa sổ DOS-prompt (cmd) chạy chương trình rmiregistry
từ dòng lệnh như sau:
C:\RMI>rmiregistry.exe
Chương trình này có thể không phản hồi cho ta thông tin gì cả
bởi vì đây là chương trình chạy ở dạng service. Nó có nhiệm vụ
đón nhận các kết nối chứa thông tin về đối tượng do phương
thức Naming.bind() gửi đến. Tốt nhất là sau khi khởi động
rmiregistry.exe trong cửa sổ DOS-prompt ta hãy thu nhỏ cửa sổ
này trên thanh Taskbar của Windows. Khi đã được khởi động thì
bộ quản lý rmiregistry này luôn trong trạng thái sẵn sàng phục vụ.
Mặc định rmiregistry.exe lắng nghe các kết nối gửi đến cổng
1099. Ta có thể chỉ định số hiệu cổng khác cho rmiregistry. Ví dụ
lệnh sau sẽ chạy rmiregistry.exe trên cổng 2003
C:\RMI>rmiregistry.exe 2003
Tùy theo phiên bản Java mà ta cài đặt, ta có thể tìm thấy
rmiregistry.exe trong thư mục như C:\Java\jdk1.6.0_11\bin


Step 7: KHỞI ĐỘNG CÁC ĐỐI TƯỢNG PHÍA SERVER

Ta đã mở một cửa sổ DOS-prompt chạy rmiregistry.exe.
Bây giờ ta mở một cửa sổ DOS-prompt khác chạy chương
trình CalculatorServer như sau:

C:\RMI>java CalculatorServer
Exporting Calculator…
Register Calculator!

18

GV: Võ Tấn Dũng

Cũng như rmiregistry.exe, sau khi CalculatorServer được
gọi, hàm Naming.bind() sẽ đi vào vòng lặp vô tận để chờ
nhận yêu cầu từ client đến. Đến lúc này ta đã có 2 chương
trình chạy ở chế độ hậu trường là rmiregistry.exe và
CalculatorServer. Mỗi chương trình chạy trên một cửa sổ
độc lập.


Step 8: CHẠY CHƯƠNG TRÌNH PHÍA CLIENT
Bây giờ ta mở thêm một cửa sổ DOS-prompt thứ
ba để chạy chương trình CalculatorClient như sau:
C:\RMI>java CalculatorClient
Finding Object…
13

19

GV: Võ Tấn Dũng


(kết quả trả về tổng của 12+1 chính là lời gọi đến
phương thức addNum() của đối tượng
CalculatorImpl. Theo dõi cửa sổ DOS-prompt nơi
chương trình CalculatorServer đang chạy ta sẽ
thấy kết xuất sau: “Client request to calculate”.)


PHẦN 3

GV: Võ Tấn Dũng

VẤN ĐỀ CHUYỂN THAM SỐ TRONG
LỜI GỌI PHƯƠNG THỨC TỪ XA


• Trong Java, đối tượng được truyền theo tham chiếu còn các
kiểu dữ liệu đơn giản như int, char,… được truyền theo tham
trị.
• Đối với việc truyền tham số qua mạng theo cơ chế RMI thì có
hai nguyên tắc sau:
- Tất cả các kiểu dữ liệu đơn giản như int, char,… đều được
truyền theo tham trị.
- Tất cả các dữ liệu kiểu đối tượng muốn truyền qua mạng đều
buộc phải cài đặt một trong hai tiếp là Remote hoặc
Serializable. Các đối tượng cài giao tiếp Remote sẽ được
truyền theo tham chiếu còn các đối tượng cài đặt giao tiếp
Serializable sẽ được truyền theo tham trị.
• Hầu như các kiểu dữ liệu đối tượng cơ bản như String, Date,
Time,… trong Java đều cài đặt giao tiếp Serializable cho nên

chúng được chuyển cho các lời gọi hàm hay phương thức từ
21
xa theo tham trị.

GV: Võ Tấn Dũng

CHUYỂN THAM SỐ TRONG RMI


GV: Võ Tấn Dũng

CHUYỂN ĐỐI TƯỢNG ĐẾN
TRÌNH CHỦ THEO THAM TRỊ


CHUYỂN ĐỐI TƯỢNG THEO THAM TRỊ

23

GV: Võ Tấn Dũng

• Tất cả các lớp đối tượng cài đặt giao tiếp Serializable đều
được Java xem như là có khả năng tuần tự hóa. Nghĩa là
ta có thể yêu cầu Java lưu toàn bộ đối tượng lên đĩa cứng
thành một tập tin nào đó, sau đó đem tập tin này đền máy
khác ta có thể khôi phục đối tượng về trạng thái ban đầu
mà không cần phải khởi tạo đối tượng mới bằng lệnh new.
• Trong thuật ngữ lập trình phân tán, quy trình chuyển tham
số và dữ liệu qua lại giữa hai lớp trung gian Stub và
Skeleton được gọi là mashaling và un-mashaling.

• Trong các lời gọi phương thức RMI, kiểu dữ liệu đối tượng
nếu không cài đặt một trong hai giao tiếp Serializable hoặc
Remote thì sẽ không thể dùng làm tham số truyền qua
mạng được.


VÍ DỤ CHUYỂN ĐỐI TƯỢNG THEO THAM TRỊ

24

GV: Võ Tấn Dũng

• Sau đây chúng ta xây dựng một chương trình chuyển tham
số đối tượng theo tham trị qua mạng từ máy khách đến
máy chủ trong RMI.
• Chương trình này tựa trò chơi ném bóng, trình khách sẽ
ném một một quả banh (đối tượng Ball) lên máy chủ, trình
chủ sẽ tiếp nhận quả banh và trả về cho trình khách.


VÍ DỤ CHUYỂN ĐỐI TƯỢNG THEO THAM TRỊ
(step 1)

• Bước 1: Thiết kế lớp Ball.class được dùng làm tham số
chuyền qua mạng giữa trình khách và trình chủ.

25

GV: Võ Tấn Dũng


/* Ball.java*/
Import java.io.*;
public class Ball implements Serializable {
int weight=0;
public Ball(int w){
weight=w;
}
public int getWeight(){
return weight;
}
public void setWeight(int w){
weight=w;
}
}


×