#11 Update script jmeter spiderum – Cách mà tôi tổ chức cấu trúc kịch bản kiểm thử

Ở bài viết trước mình có nói về cách mình record script cho ra kịch bản kiểm thử hiệu năng spiderum, tuy nhiên với script thô sau khi record đó thì không thể bắt đầu kiểm thử được. Bên dưới là hình ảnh script thô.

Đối với script thô này thì mình không thể chạy được với số lượng CCUs giả lập lớn được mà chỉ có thể định hình được các bước và các request trong kịch bản kiểm thử mà thôi.

CCUs là gì thì bạn có thể đọc lại bài viết dưới nhé!

Sau khi có được script thô, mình sẽ phải phân loại và gom nhóm những kịch bản có thể dùng chung các thành phần nào, những kịch bản có giống nhau dữ liệu đầu vào hay không? Hay những kịch bản nào có thể tái sử dụng được thì sẽ gom thành một nhóm dùng chung theo hình thức tái sử dụng.Cũng không đơn giản theo kiểu mấy bạn cưỡi ngựa xem hoa với performance testing nói chỉ cần record là có thể kiểm thử hiệu năng được rồi, có gì khó đâu :))

Đầu tiên thì bạn phải hiểu một số định nghĩa cơ bản để có thể chia nhóm và phân loại được.

Test plan chứa các test case. Nó định nghĩa các test case và làm thế nào để đi đến test case đó.Một testplan hoàn chỉnh bao gồm một hoặc nhiều yếu tố như thread groups, logic controllers, sample-generating controllers, listeners, timers, assertions, và configuration elements.Một testplan phải bao gồm ít nhất 1 thread group.

Trong testplan thì có 2 thông số quan trọng mà bạn cần quan tâm đến đó là:

– Run Thread Groups consecutively (i.e. one at a time): Chạy liên tiếp (Chạy tuần tự từ trên xuống).
– Run teardown Thread Groups after shutdown of main threads: Chạy tearDown Thread Group sau khi Thread Group shutdown.

Thread Group là thành phần bắt buộc phải có trong 1 Test Plan. Các thành phần trong Thread group sẽ kiểm soát số lượng Threads mà Jmeter sử dụng trong suốt quá trình test như Number of thread (users), Ramp-up Period (in secords), Loop count.

Các thông số khác có lẽ các bạn cũng dễ hiểu, mình chỉ lưu ý một thông số đó là ramp-up.

0 < Ramp-up Period <= Duration

Bài trước mình có đề cập tới vấn đề tranh cãi của CCUs, tuy là đồng thời nhưng nó lại có một độ trễ phù hợp với thực tế. Ở đây Ramp-up time cũng vậy, nó là thời gian để cái máy tạo load tạo được đủ lượng users cần thiết. Nên nếu bạn nghĩ test 1000 users cùng lúc, thì ramp-up mình nghĩ là bằng 0 là sai nhé. Trong vòng 0 giây không thể load hết từng đó users cùng một lúc. Nếu bạn đặt ramp-up = 0 thì có nghĩa là máy tính của bạn có 0s để tạo đủ 1000 Threads. Bạn nghĩ máy bạn có chịu nổi không?

Nếu ramp-up = 0 chỉ có thực hiện cho spike test thôi chứ không phải load test

Spike testing được định nghĩa là một loại kiểm tra hiệu suất, trong đó ứng dụng sẽ được kiểm tra khi thực hiện tăng và giảm đột ngột số lượng lớn người dùng. Việc làm này giúp đánh giá hành vi của phần mềm và tìm ra điểm yếu của ứng dụng.

Load testing là một quá trình thêm nhu cầu vào một hệ thống hoặc thiết bị và đo lường phản ứng của nó. Load testing được thực hiện để xác định ứng xử của hệ thống trong các điều kiện tải bình thường và cao hơn điều kiện tải dự kiến.

Vậy con số nào Ramp-up là đủ
Nhìn vào 2 biểu đồ dưới nhé!

Ramp-up = Duration

2/3 duration <= Ramp-up <= Duration

Đối với mỗi dự án và số lượng CCUs yêu cầu đặt ra mà mình set ramp-up để đồ thị được đi lên từ từ đến điểm cực đại với độ dốc mà hệ thống chịu tại được trong thời gian đầu tránh thắt cổ chai ở luồng đăng nhập như ví dụ ở bài trước. Nên mình nghĩ đồ thị 2/3 bên trên sẽ hợp lý hơn.

Ngoài ra trong thread group còn có một thông số ít ai để ý khi mà request bị lỗi, đó là Action to be takens after a Sample error:

Continue: nghĩa là tiếp tục chạy các sample khác bỏ qua sample bị lỗi (mặc định)
Start Next Thread Loop: là chuyển sang vòng lặp tiếp theo
Stop Thread: Dừng Thread hiện tại
Stop test: Dừng hoàn toàn để kiểm tra lỗi trước khi chạy tiếp
Stop test Now: Dừng hoàn toàn việc test một cách đột ngột

Ví dụ request socket lỗi ở record lần trước khi mình chạy, nó sẽ bỏ qua lỗi đó và tiếp tục chạy những request tiếp theo. Điều này bạn phải hiểu vì một khi request tiền điều kiện kiên quyết để chạy request dưới phải được đảm bảo thành công nếu không thì phần trăm error lỗi sẽ bị kéo theo một loạt khiến báo cáo report của bạn rất xấu.

Trong phần thread group này mình muốn đề cập tới 2 thành phần mà mình hay sử dụng trong dự án đó là SetUp Thread Group và TearDown Thread Group. 

Đây là combo thread group chạy trước và sau thread group chính trong kịch bản của bạn.

Mình có 2 ví dụ:

Test Plan
=> setUp Thread Group
=> => setUp Sampler
--
=> Main Thread Group
=> => Sampler
--
=> tearDown Thread Group
=> => tearDown Sampler
--
View Result Tree

Khi này bạn sẽ chạy các request trong sample của SetUp Thread Group trước sau đó chạy Main Thread Group và cuối cùng chạy TearDown Thread Group. Tuy nhiên khi bạn đảo thử tự lại

Test Plan
=> tearDown Thread Group
=> => tearDown Sampler
--
=> Main Thread Group
=> => Sampler
--
=> setUp Thread Group
=> => setUp Sampler
--
View Result Tree

Thật vi diệu nó vẫn chạy theo thứ tự trên SetUp Thread Group => Main Thread Group => TearDown Thread Group.

Và khi đó setting “Run teardown Thread Groups after shutdown of main threads” trong testplan bên trên sẽ phát huy tác dụng của nó.

Vậy bạn hỏi tôi chia việc chạy trước chạy sau như vậy để làm gì?

Là như vậy, bạn có 3 kịch bản: Đăng bài, bình luận và upvote. Vậy điểm chung giữa 3 kịch bản này là bạn phải đăng nhập và đăng xuất sau khi thực hiện từng kịch bản để có thể đăng nhập một người dùng khác với chu kỳ vòng lặp kế tiếp.

Như vậy khi bắt đầu 3 kịch bản thay vì bạn phải copy 3 lần kịch bản đăng nhập, đăng xuất thành 3 thread groups khác nhau thì bạn bỏ đăng nhập vào SetUp Thread Group và bỏ đăng xuất vào TearDown Thread Group, sau đó để 3 kịch bản của bạn muốn thực hiện ở giữa Main Thread Group. Vậy là có thể giải quyết vấn đề không bị lặp lại kịch bản mà vẫn đảm bảo được tổng thể kịch bản chung.

Ngoài ra, SetUp Thread Group mình thường để những script tạo prepare data (dữ liệu đầu vào khi chạy) và TearDown Thread Group mình thường để script dọn dẹp data sau khi chạy (data rác đối với lần chạy tiếp theo hoặc với môi trường kiểm thử nhằm mục đích không bị ảnh hưởng tới các phần kiểm thử khác)

Controllers trong Jmeter có 2 loại Samplers và Logical Controller. Cả 2 loại này đều có tác dụng điều khiển thực hiện quá trình test.

Samplers controller: Jmeter samplers cho phép định nghĩa các request có thể được gửi tới một server. Sampler có thể giả lập các request của người dùng tới target server. Mỗi Sampler sinh ra các mẫu kết quả (sample result), với rất nhiều các thuộc tính như hiệu năng, elapsed time, throughput…Mặc định, Jmeter gửi các request theo thứ tự mà các Samplers xuất hiện trên cây. Tuy nhiên, trật tự xử lý các Sampler có thể được cấu hình mở rộng thêm với các Logic Controller.

Logic Controllers: Logic Controller cho phép bạn xử lý trật tự xử lý Samplers hay Request trong một Thread. Logic Controllers sẽ quyết định “When & How” gửi yêu cầu đến một máy chủ web.

Logic Controller mà Jmeter cung cấp:

– Simple Controller là một container lưu trữ user request, nó không giống các controller khác, controller này không cung cấp chức năng ngoài của thiết bị lưu trữ.

– Loop Controller làm cho các user request chạy trong số lần được xác định hoặc lặp vô hạn

– Once Only Controller được sử dụng khi bạn muốn chạy một số yêu cầu đặc biệt chỉ sử dụng một lần thậm chí nếu bạn có nhiều thread trong một Thread Group

– Interleave Controller giúp thực hiện lặp lại các thành phần con tuy nhiên mỗi l lần lặp lại sẽ thực hiện một thành phần con khác không trùng với thành phần con cũ cho đến khi hết tất cả các thành phần bên trong nó.

– Random Controller tương tự như Interleave controller, điểm khác biệt nằm ở chỗ nó không thực hiện theo thứ tự tuần tự mà thực hiện 1 element con bất kỳ của nó

– Random Order Controller tương tự như Simpler Controller, điểm khác biệt nằm ở chỗ nó sẽ thực hiện mỗi phần tử con 1 lần, nhưng thứ tự thực hiện các phần tử con là random

– Throughput Controller được sử dụng để điều khiển dòng thực hiện

– Runtime Controller giúp kiểm soát thời gian được phép chạy

– If Controller làm việc theo cách đơn giản một biểu thức If được xử lý trong bất kỳ ngôn ngữ lập trình nào

– While Controller thực thi thành phần dưới nó tới tận khi điều kiện trở thành sai

– Switch Controller tương tự như Interleave Controller, nhưng thay vì lần lượt thực hiện các phần tử con của nó, nó thực hiện 1 phần tử theo giá trị switch

– ForEach Controller tương tự như Loop Controller nhưng số lần lặp lại không được xác định trước, nó chỉ thực thi hết tất cả các thành phần con bên trong

– Module Controller giúp chia các controller thành nhiều thành phần có thể tái sử dụng

– Include Controller được thiết kế để sử dụng gói kiểm thử mở rộng. Bộ điều khiển này cho phép bạn sử dụng nhiều test plans trong JMeter

– Transaction Controller để đo tổng thời gian thực hiện để hoàn thành việc thực hiện kiểm thử. Transaction Controller cho phép tạo ra các sampler bổ sung, các sampler này sẽ đo thời gian tổng thực hiện để test lồng các yếu tố với nhau

– Recording Controller là một nơi để lưu trữ lại các bước thực hiện khi thực hiện record các bước kiểm thử

Timer để đảm bảo chạy performance test có thể giống thực tế nhất thì Jmeter có hỗ trợ timer giúp bạn có thể set các giá trị thời gian giữa các samples hay request. Mặc định, một thread JMeter gửi các yêu cầu mà không cần tạm dừng giữa các sample.

Jmeter cung cấp các loại Timer sau:
– Constant Timer
– Gaussian Random Timer
– Uniform Random Timer
– Constant Throughput Timer
– Synchronizing Timer
– BeanShell Time

Assertions giúp bạn kiểm tra tính đúng đắn của bước trước đó rồi mới thực hiện bước tiếp theo. Nó cho phép thêm một số kiểm tra để xác nhận phản hồi từ server. Sử dụng assertion bạn có thể chứng minh rằng ứng dụng của bạn đang trả lại dữ liệu chính xác.

Jmeter cung cấp các loại Assertion sau:
– Beanshell Assertion
– BSF Assertion
– Compare Assertion
– JSR223 Assertion
– Response Assertion
– Duration Assertion
– Size Assertion
– XML Assertion
– BeanShell Assertion
– MD5Hex Assertion
– HTML Assertion
– XPath Assertion
– XML Schema Assertion

Listener giúp bạn có thể thu thập lắng nghe các kết quả của mỗi request, đây chính là đầu vào cho các báo cáo report của bạn. Các listener được hiển thị một cách real time ngay khi đang thực thi request hay sample dưới các dạng khác nhau như graph, tree, table Mặt khác nó còn có thể tổng hợp lại tất cả các sample dưới dạng csv, xml, txt. Nó được thêm vào bất cứ nơi nào trong test plan và chỉ thu thập dữ liệu từ thành phần cùng cấp hoặc cấp dưới nó.

Jmeter cung cấp các loại Listener sau:
– Sample Result Save
– Configuration
– Graph Full Results
– Graph Results
– Spline Visualizer
– Assertion Results
– View Results Tree
– Aggregate Report
– View Results in Table
– Simple Data Writer
– Monitor Results
– Distribution Graph (alpha)
– Aggregate Graph- Mailer Visualizer
– BeanShell Listener- Summary Report

Configuration Element cho phép người dùng tạo các giá trị mặc định và các biến được sử dụng trong các samples. Khi bạn muốn cấu hình, thêm hoặc chỉnh sửa lại những thông số hay những loại test tương ứng. Jmeter không phải chỉ kiểm thử hiệu suất của hệ thống server mà nó còn kiểm thử được những loại khác như database, băng thông, giao thức nên config này sẽ đáp ứng được từng loại kiểm thử khác nhau. Trong scope của nó, một Configuration Element được thực hiện đầu tiên, trước tất các sampler trong cùng scope đó. Vì vậy, một Configuration Element chỉ được access trong nội bộ nhánh mà nó được đặt.

Jmeter cung cấp các loại Configuration Elements JMeter sau:
– CSV Data Set Config
– FTP Request Defaults
– HTTP Authorization Manager
– HTTP Cookie Manager
– HTTP Proxy Server
– HTTP Request Defaults
– HTTP Header Manager
– Java Request Defaults
– JDBC Connection Configuration
– Login Config Element
– LDAP Request Defaults
– LDAP Extended Request Defaults
– TCP Sampler Config
– User Defned Variables
– Simple Config Element

Tương tự như setup và teardown chạy trước và sau thread group chính thì đối với element (phần tử, thành phần) của một request hay sampler thì sẽ có 2 phần chạy trước và sau mỗi request giúp bạn có thể cập nhật các bước trong kịch bản có thể phù hợp nhất. Mình thường dùng phần này để lấy dữ liệu từ bước trước làm đầu vào cho bước sau của một kịch bản

Pre-processors cho phép chỉnh sửa các Samplers trong scope của nó. PreProcessor thường được sử dụng để chỉnh sửa thiết lập của một Sample Request trước khi nó được chạy, hoặc update các variables không được extract từ các response text.

Danh sách các Pre-Processor Elements JMeter cung cấp:
– HTML Link Parser
– HTTP URL Re-writing Modifer
– HTML Parameter Mask
– HTTP User Parameter Modifer
– User Parameters
– Counter
– BeanShell PreProcessor

Post-processors được thực hiện sau khi một request vừa được tạo ra từ 1 Sampler. Thông thường, Post processor được đặt làm con của một Sampler, để đảm bảo nó được chạy chỉ sau Sampler đó, không liên quan tới các Sampler sau đó. Post Processor Element là đặc biệt hữu dụng để xử lý các response data, ví dụ như để thu được các giá trị cụ thể cho các sử dụng về sau.

Danh sách các Post-Processor Elements JMeter cung cấp:
– Regular Expression Extractor
– XPath Extractor
– Result Status Action Handler
– Save Responses to a file
– Generate Summary Results
– BeanShell PostProcessor

Ngoài ra mình còn có CSV Data Set Config cái này dùng để đọc nhiều data đầu vào cùng vào các biến để sử dụng trong toàn bộ kịch bản.

Hiện tại mình chỉ update script để chạy một CCUs sau đó kiểm duyệt lại tính đúng đắn của script trước. Sau khi mọi thứ được hoàn tất mình sẽ gắn CSV Data Set Config để có thể có được bộ dữ liệu lớn để thực thi kiểm thử. Vấn đề đọc và sử dụng CSV Data Set Config trong chiến dịch lần này thì mình sẽ đề cập đến trong bài viết sau nhé!

Trước tiên phải chạy đúng và chất lượng đã trước khi chạy với số lượng nhiều.

Leave a Reply