Phát triển Java 2.0: Theo dõi ứng dụng Java với Health Center API, Phần 1

Làm quen với Health Center API

Bản phát hành 2.1 của Health Center chứa các tính năng mạnh mẽ cho lập trình giao diện ứng dụng. Thư viện API cho phép những nhà lập trình Java™ nhúng Health Center trong các ứng dụng của họ và khai thác sức mạnh giám sát theo dõi của nó để khắc phục các vấn đề. Trong phần 1 này của bài báo bạn sẽ học về cách sử dụng Health Center API và làm sao để theo dõi tắc nghẽn (deadlock) trong khi chạy ứng dụng Java. Phần 2 sử dụng ứng dụng phát hiện tắc nghẽn được phát triển trong bài báo này và thêm một phương pháp để hiển thị lúc nào ứng dụng chiếm dụng nhiều CPU nhất trong chu kì hoạt động của nó.

Toby Corbin, Kỹ sư phần mềm, IBM Japan

Ảnh của Toby CorbinToby Corbin là trưởng nhóm phát triển cho công cụ theo dõi Health Center; ông cũng phát triển các công cụ khác bên trong Trung tâm công nghệ Java của IBM. Ông bắt đầu làm việc ở IBM từ năm 2001, trong vòng bốn năm, ông đã phát triển môi trường runtime Java hỗ trợ ngôn ngữ và toàn cầu hóa. Toby đã phát triển các thư viện Swing và AWT trong hai năm.



30 07 2013

Đã bao giờ bạn có một ứng dụng máy chủ bị treo mà không biết lý do, hoặc là một ứng dụng Java không phản hồi ứng dụng của bạn chạy thiếu bộ nhớ hay hiệu quả kém? Với Health Center thì bạn có thể khắc phục nhiều vấn đề một cách dễ dàng.

Giám sát và chuẩn đoán các vấn đề với Health Center

Công cụ Giám sát và Chẩn đoán cho Java của IBM® - Health Center (Health Center) là miễn phí, với chi phí thấp và API để giám sát một ứng dụng chạy trên Java virtual machine (JVM) của IBM. Với Health Center bạn có thể đánh giá các trạng thái của ứng dụng Java đang chạy một cách nhanh chóng bởi các thông tin cung cấp để xác định và giải quyết các vấn đề mắc phải. Bạn có thể:

  • Xác đinh được việc thiếu bộ nhớ heap
  • Phát hiện các phương thức nào là đang chiếm nhiều thời gian chạy nhất
  • Tắc nghẽn trong quá trình I/O
  • Quá trình thu dọn rác (garbage collection): quá trình giải phóng bộ nhớ trong heap
  • Có thể xem các nội dung đang chứa
  • Phân tích các sự kiện thời gian thực bất thường của WebSphere®
  • Theo dõi các thread trong ứng dụng
  • Phát hiện các bế tắc
  • Thu thập được dữ liệu dưới dạng biểu đồ

Bản phát hành mới nhất của Health Center là rất đầy đủ tiện ích và bạn có thể sử dụng để viết các ứng dụng theo dõi của bạn. Những vấn đề khó phát hiện nay đã có giải pháp.

Trong bài báo này, bạn sẽ được học cách viết một công cụ giám sát, và được dùng để kiểm tra các điều kiện gây tắc nghẽn của các ứng dụng. sau đó, sử dụng các nguyên lý để viết nhiều công cụ chuyên sâu, truy vấn từ quá trình giải phóng bộ nhớ. Xây dựng, tìm được nơi nào là ứng dụng chiếm dụng CPU nhiều nhất trong vòng đời của nó.

Yêu cầu hệ thống

Gói Health Center API yêu cầu phiên bản nhỏ nhất là eclipse 3.4 hoặc các bản từ 4.x trở lên.

Cài đặt gói API vào Eclipse

Công cụ giám sát và chuẩn đoán IBM rất đơn giản được cài trong IBM Support Assistant (ISA). Để tích hợp Health Center trong ứng dụng của bạn và lập trình chống lại nó bằng việc sử dụng API, bước đầu bạn cài đặt nó vào môi trường công cụ Eclipse. Theo các bước sau:

  1. Khởi động môi trường phát triển Eclipse.
  2. Vào Help -> Install New Software.
  3. Nhập đường link cập nhật ISA.
    1. Chọn Add.
    2. Nhập ISA site vào ô name box.
    3. Nhập đường link URL vào ô location : http://public.dhe.ibm.com/software/isa/isa410/production/. Sau đó nhấn Enter để tiến hành tìm kiếm, có thể sẽ mất vài phút.
  4. Nhập Health Center vào ô tìm kiếm
  5. Chọn gói Health Center Core Feature và nhấn Next (xem Hình 1):
    Hình 1. Danh sách các phần mềm có thể cài đặt
    Hình ảnh các phần mềm có thể cài đặt
  6. Xác nhận lại chi tiết cài đặt và nhấn Next.
  7. Đọc và chấp nhận yêu cầu bản quyền sau đó nhấn Finish. Các bước cài đặt tính năng Health Center Core vào Eclipse IDE của bạn giờ đã thành công và có thể bắt đầu lập trình.
  8. Xác nhận lại chi tiết việc cài đặt và nhấn Next.

Sử dụng API, viết một ví dụ RCP đơn giản để phát hiện deadlock (tắc nghẽn). Đầu tiên, tạo một dự án mới kiểu Plug-in Project và thêm vào API Health Center. Làm theo các bước sau:

  1. Vào File -> New -> Project -> Plug-in Project.
  2. Đặt tên cho dự án, ví dụ HC_Deadlock. Nhấn Next.
  3. Xóa check box Generate an activator. Ở dòng "Would you like to create a rich client application", chọn Yes. Nhấn Next (xem Hình 2):
    Hình 2. Lựa chọn Plug-in project
    Hình ảnh các tùy chọn dự án plug-in
  4. Nhấn Next. Ở màn hình template, chọn Headless Hello RCP. Nhấn Finish.

Tiếp đó thêm package Health Center API vào project mới theo các bước sau:

  1. Để thêm API vào tệp manifest, hãy mở tệp MANIFEST.MF trong thư mục META-INF trong project mới của bạn (xem Hình 3):
    Hình 3. Plug-in Package Explorer
    Hình ảnh các plug-in Package Explorer
  2. Chọn tab Dependencies và nhấn Add. Trong trường Select a Plug-in, nhập healthcenter.api vào ô tìm kiếm. Chọn plug-in com.ibm.java.diagnostics.healthcenter.api—chú ý rằng phiên bản có thể sẽ khác (xem Hình 4):
    Hình 4. Lựa chọn plug-in Health Center API
    Hình ảnh lựa chọn plug-in Health Center API
  3. Nhấn OK. Lập lại bước lựa chọn tab Dependencies. Lần này, thêm org.eclipse.ui—một lần nữa tôi nhắc lại, có thể số phiên bản sẽ khác (xem Hình 5):
    Hình 5. Lựa chọn Plug-in của org.eclipse.ui
    Hình ảnh lựa chọn plug-in của org.eclipse.ui
  4. Nhấn OK, và sau đó lưu tệp lại.

API plug-in bây giờ đã được thêm vào trong ứng dụng của bạn và có thể bắt đầu lập trình.


Thử nghiệm với ứng dụng sinh tắc nghẽn (deadlock)

Trước khi bắt tay vào xây dựng ứng dụng giám sát tắc nghẽn (deadlock monitoring tool), hãy học cách để tạo ra tắc nghẽn. Đoạn mã sau đây trong danh sách 1 mô tả một chương trình đơn giản sinh tắc nghẽn:

Liệt kê 1. Một ứng dụng bị lỗi tắc nghẽn
public class GenerateDeadlock {
   AThread t1 = null;
   AThread t2 = null;
   AThread t3 = null;

   static class AThread extends Thread {
      Object hold;
      Object grab;

      AThread(String name, Object hold, Object grab) {
         super(name);
         this.hold = hold;
         this.grab = grab;
      }

      private void delay(long time) {
         try {
            Thread.sleep(time);
         } catch (InterruptedException e) {
         }
      }

      private void grabLocks() {
         System.out.println("Thread " + this + " about to hold " + hold);
         synchronized (hold) {
            System.out.println("  Thread " + this + " about to grab "
                  + grab);
            delay(5000);
            synchronized (grab) {
               System.out.println("    Thread " + this
                     + " got both monitors");
               delay(1000000);
            }
         }
      }

      public void run() {
         System.out.println("Thread " + this + " starting");
         for (int i = 0; i < 200000; i++) {
            grabLocks();
         }
         System.out.println("Thread " + this + " completed");
      }
   }

   private void createDeadlock() {
      System.out.println("Force 3 thread deadlock");
      String s1 = "obj 1";
      String s2 = "obj 2";
      String s3 = "obj 3";
      t1 = new AThread("Thread 1", s1, s2);
      t2 = new AThread("Thread 2", s2, s3);
      t3 = new AThread("Thread 3", s3, s1);
      t1.start();
      t2.start();
      t3.start();
   }

   public static void main(String[] args) {
      GenerateDeadlock d = new GenerateDeadlock();
      d.createDeadlock();
      try {
         Thread.sleep(1000);
      } catch (InterruptedException e) {
         e.printStackTrace();
      }
      System.out.println("Press a key to exit");
      try {
         System.in.read();
         System.exit(0);
      } catch (java.io.IOException e) {
      }
   }
}

Health Center gồm hai phần. Phần đầu là trình đại diện (agent) Health Center, sẽ tải ứng dụng muốn giám sát. Phần thứ hai của Health Center —trình khách (client)— sử dụng phương thức mà trình đại diện của hệ thống cung cấp, truy xuất vào cơ sở dữ liệu trong JVM. API này cho phép bạn truy nhập vào trình khách được khởi động từ ISA. Nhúng trình khách này vào ứng dụng của bạn để tiến hành kết nối với một ứng dụng đã được khởi động trước đó bởi trình Health Center và truy cập vào cơ sở dữ liệu mà Health Center giám sát. Tuy không được trang bị giao diện đồ họa (GUI) nhưng API cho bạn quyền truy xuất mọi dữ liệu trên thiết bị của mình. Hình 6 mô tả tổng quát mô hình trình đại diện – trình khách khi được cài đặt trong ISA và JVM:

Hình 6. Vị trí trình đại diện – trình khách của Health Center khi được cài đặt trong ISA và JVM
Sơ đồ vị trí của các khách hàng và đại lý Health Center trong ISA và JVM

Chạy chương trình trong Liệt kê 1 cùng với trình đại diện của Health Center. Yêu cầu tối thiểu cài đặt IBM Java của phiên bản Java 5 SR8, Java 6 SR1, hoặc Java 7. Có thể tải tại IBM developer kits.

Để chạy ứng dụng với trình đại diện sử dụng phiên bản Java SR10 (hoặc mới hơn), Java 6 SR5 (hoặc mới hơn), và Java 7, sử dụng lệnh sau (xem Hình 7):

java - Xhealthcenter GenerateDeadlock

Với phiên bản Java 5 SR9 (hoặc cũ hơn), phiên bản Java 6 SR4 (hoặc cũ hơn) sử dụng lệnh sau:

java - agentlib:healthcenter - Xtrace:output=healthcenter.out GenerateDeadlock
Hình 7. Tiến hành chạy chương trình GenerateDeadlock
Ảnh chụp cửa sổ dòng lệnh hiển thị chương trình GenerateDeadlock

Trình đại diện đã có sẵn từ phiên bản Java 5 SR9 và Java 6 SR3. Để tải về hoặc cập nhật được phiên bản mới nhất của trình đại diện, truy cập Health Center - Cài đặt trình đại diện Health Center.


Lập trình ứng dụng giám sát tắc nghẽn (deadlock)

Bạn sẵn sàng chỉnh sửa ứng dụng cơ bản Hello RCP World và biến nó trở thành công cụ phát hiện tắc nghẽn (deadlock) sử dụng Heath Center API. Mở tệp Applicaton.java (xem Hình 8):

Hình 8. Vị trí của tệp Applicaton.java
Ảnh chụp vị trí của mã Application.java

Cài đặt kết nối chi tiết

Bước đầu tiên, lấy một đối tượng ConnectionProperties, đối tượng này chứa thông tin chi tiết về ứng dụng bạn muốn kết nối tới. Đối tượng mặc định được để làm localhost với cổng 1972, nhưng bạn có thể thay đổi giá trị này (và thêm bảo mật) trong khai báo và ở các phương thức của lớp:

ConnectionProperties hcConn = new ConnectionProperties();

Khi bạn có đối tượng ConnectionProperties, kết nối tới ứng dụng mà bạn muốn giám sát, cái mà đã được sẵn sàng bắt đầu với trình đại diện Health Center. Tạo một kết nối gọi tới phương thức tĩnh HealthCenterFactory.connect(hcConn, true). Nó sẽ trả về một đối tượng HealthCenter, đối tượng này sẽ là kết nối trực tiếp vào Health Center và cho phép truy cập vào tất cả dữ liệu mà Health Center đang giám sát. Cuộc gọi kết nối bắt đầu có hiệu quả bởi một đối tượng của Health Center trong ứng dụng của bạn và bắt đầu thu thập dữ liệu:

HealthCenter hcMon = HealthCenterFactory.connect(hcConn,true);

Lấy dữ liệu

Bây giờ bạn đã có đối tượng HealthCenter, bạn có thể truy vấn dữ liệu. API được trình bày giống với GUI: bước đầu tiên sau khi nó yêu cầu một đối tượng HealthCenter là gọi tới kiểu dữ liệu mà bạn quan tâm. Ví dụ, bạn muốn kiểm tra những tắc nghẽn, là những phần của lớp ThreadsData. Bạn có thể truy cập với hàm getThreadsData() của đối tượng HealthCenter như sau:

ThreadsData hcThreadsData = HealthCenter.getThreadsData();

Lớp ThreadsData có một phương thức deadlockDetected() có chức năng trả về true nếu một tắc nghẽn (deadlock) bị phát hiện. Nhờ sự thăm dò của phương thức trên bạn có thể được thông báo nếu một tắc nghẽn (deadlock) xảy ra:

if(hcThreadsData.deadlockDetected()) {
      do something
}

Truy cập công cụ khuyến cáo và phân tích

Health Center có xây dựng công cụ khuyến cáo sẽ cũng cấp tất cả sự phân tích và trả về những kết quả tìm được. Bạn dễ dàng nhìn thấy những kết quả ở tab "Analysis and Recommendations" khi bạn chạy phiên bản đầy đủ của Health Center (xem Hình 9):

Hình 9. Tab "Analysis and recommendations" của Health Center
Ảnh chụp bảng phân tích và khuyến nghị của trung tâm y tế Health Center

Để truy vấn một vài khuyến cáo ta có thể sử dụng một vài phương thức. getAllRecommendations() trả về một mảng của tất cả các khuyến cáo, nhưng bạn có thể chỉ truy vấn khuyến cáo đặc biệt bằng thương thức getCriticalRecommendations(), là phương thức được gọi bởi đối tượng ThreadsData:

String[] hcThreadsRec = hcThreadsData.getCriticalRecommendations()

Xem toàn bộ mã nguồn

Năm hàm gọi trước là cần thiết để được nhúng vào Health Center trong ứng dụng của bạn và kiểm tra những tắc nghẽn trong ứng dụng mà bạn muốn giám sát. Liệt kê 2 dưới đây sẽ cho bạn thấy toàn bộ mã nguồn với những hàm sử dụng ở trên:

Liệt kê 2. Toàn bộ mã nguồn được thể hiện trong 5 hàm gọi khi sử dụng
package deadlockdemo;

import org.eclipse.equinox.app.IApplication;
import org.eclipse.equinox.app.IApplicationContext;
import org.eclipse.swt.widgets.Display;
import org.eclipse.swt.widgets.MessageBox;
import org.eclipse.swt.widgets.Shell;

import com.ibm.java.diagnostics.healthcenter.api.ConnectionProperties;
import com.ibm.java.diagnostics.healthcenter.api.HealthCenter;
import com.ibm.java.diagnostics.healthcenter.api.factory.HealthCenterFactory;
import com.ibm.java.diagnostics.healthcenter.api.threads.ThreadsData;

/**
 * This class controls all aspects of the application's execution
 */
public class Application implements IApplication {
   HealthCenter hcMon;

   public Object start(IApplicationContext context) throws Exception {
      ConnectionProperties hcConn = new ConnectionProperties();
      hcMon = HealthCenterFactory.connect(hcConn, true);
      try {
         System.out
               .println("Waiting for 10 seconds to allow initial data to be
                        parsed from the connection");
         Thread.sleep(10000);
      } catch (InterruptedException e) {
         e.printStackTrace();
      }
      checkForDeadlock();
      return IApplication.EXIT_OK;
   }

   public void stop() {
      // nothing to do
   }

   public void checkForDeadlock() {
      while (!detectDeadlock()) {
         try {
            Thread.sleep(5000);
         } catch (InterruptedException e) {
            e.printStackTrace();
         }
      }
   }

   private boolean detectDeadlock() {
      ThreadsData hcthreadsData = hcMon.getThreadsData();
      if (hcthreadsData == null) {
         System.out.println("No threads yet");
      } else {
         if (hcthreadsData.deadlockDetected()) {
            Display display = new Display();
            Shell shell = new Shell(display);

            MessageBox mb = new MessageBox(shell);
            String deadlockMessage = new String();
            String[] hcThreadsRec = hcthreadsData
                  .getCriticalRecommendations();
            for (String rec : hcThreadsRec) {
               deadlockMessage = deadlockMessage + rec + "\n";
            }
            mb.setMessage(deadlockMessage);
            mb.setText("Deadlock detected");
            mb.open();
            display.dispose();
            return true;
         }
      }
      return false;
   }
}

Giám sát tắc nghẽn (deadlock)

Bây giờ bạn có một ứng dựng giám sát tắc nghẽn chạy ngầm bên dưới tất cả các ứng dụng khác của hệ điều hành. Và khi có tắc nghẽn sẽ có một hộp thoại như sau (xem Hình 10):

Hình 10. Hộp thoại phát hiện các kết quả tắc nghẽn
Ảnh chụp bảng kết quả nhận diện deadlock

Kết luận

Bài báo đã giới thiệu những khái niệm ban đầu của Health Center API và hướng dẫn cách viết một ứng dụng điều khiển để kiểm tra điều kiện tắc nghẽn . Bạn có thể áp dụng các kỹ thuật này để triết xuất cũng như sử dụng bất cứ đối tượng dữ liệu nào bên trong Health Center. Trong Phần 2, ban sẽ “mục sở thị” sâu hơn các khái niệm được đề cập ở phần 1. Ngoài ra bạn còn có thể học cách đưa thêm vào hệ thống của mình các phương thức tạm gọi là “khung nhìn trực quan” (profiling view) trong các xác định điểm chết hay tắc nghẽn (deadlock) của ứng dụng.

Tài nguyên

Học tập

Lấy sản phẩm và công nghệ

Thảo luận

Bình luận

developerWorks: Đăng nhập

Các trường được đánh dấu hoa thị là bắt buộc (*).


Bạn cần một ID của IBM?
Bạn quên định danh?


Bạn quên mật khẩu?
Đổi mật khẩu

Bằng việc nhấn Gửi, bạn đã đồng ý với các điều khoản sử dụng developerWorks Điều khoản sử dụng.

 


Ở lần bạn đăng nhập đầu tiên vào trang developerWorks, một hồ sơ cá nhân của bạn được tạo ra. Thông tin trong bản hồ sơ này (tên bạn, nước/vùng lãnh thổ, và tên cơ quan) sẽ được trưng ra cho mọi người và sẽ đi cùng các nội dung mà bạn đăng, trừ khi bạn chọn việc ẩn tên cơ quan của bạn. Bạn có thể cập nhật tài khoản trên trang IBM bất cứ khi nào.

Thông tin gửi đi được đảm bảo an toàn.

Chọn tên hiển thị của bạn



Lần đầu tiên bạn đăng nhập vào trang developerWorks, một bản trích ngang được tạo ra cho bạn, bạn cần phải chọn một tên để hiển thị. Tên hiển thị của bạn sẽ đi kèm theo các nội dung mà bạn đăng tải trên developerWorks.

Tên hiển thị cần có từ 3 đến 30 ký tự. Tên xuất hiện của bạn phải là duy nhất trên trang Cộng đồng developerWorks và vì lí do an ninh nó không phải là địa chỉ email của bạn.

Các trường được đánh dấu hoa thị là bắt buộc (*).

(Tên hiển thị cần có từ 3 đến 30 ký tự)

Bằng việc nhấn Gửi, bạn đã đồng ý với các điều khoản sử dụng developerWorks Điều khoản sử dụng.

 


Thông tin gửi đi được đảm bảo an toàn.


static.content.url=http://www.ibm.com/developerworks/js/artrating/
SITE_ID=70
Zone=Công nghệ Java
ArticleID=939429
ArticleTitle=Phát triển Java 2.0: Theo dõi ứng dụng Java với Health Center API, Phần 1
publish-date=07302013