iT邦幫忙

2022 iThome 鐵人賽

DAY 26
0
Software Development

QA 三十天養成日記系列 第 26

[Day26][負載測試] K6 使用上常見的套件(module)有哪些?

  • 分享至 

  • xImage
  •  

K6 套件(module) 基本上我覺得很萬用,是足夠支撐所有測試情境的。
也主要介紹幾個較常用的 K6 本身支援的 module (JavaScript API)

http

主要是能發送 API,常使用為 get/post/put/del

GET code sample

import http from 'k6/http';
export const options = {
  vus: 1,
  duration: '1s',
};

export default function () {
  http.get('https://test.k6.io');
}

POST code sample

import http from 'k6/http';

const url = 'https://httpbin.test.k6.io/post';
const logoBin = open('./logo.png', 'b');
export default function () {
  let data = { name: 'Bert' };

  // Using a JSON string as body
  let res = http.post(url, JSON.stringify(data), {
    headers: { 'Content-Type': 'application/json' },
  });
  console.log(res.json().json.name); // Bert

  // Using an object as body, the headers will automatically include
  // 'Content-Type: application/x-www-form-urlencoded'.
  res = http.post(url, data);
  console.log(res.json().form.name); // Bert

  // Using a binary array as body. Make sure to open() the file as binary
  // (with the 'b' argument).
  http.post(url, logoBin, { headers: { 'Content-Type': 'image/png' } });

  // Using an ArrayBuffer as body. Make sure to pass the underlying ArrayBuffer
  // instance to http.post(), and not the TypedArray view.
  data = new Uint8Array([104, 101, 108, 108, 111]);
  http.post(url, data.buffer, { headers: { 'Content-Type': 'image/png' } });
}

html

解析 HTML 各元素,可能會需要取得 HTML 上的一些元素值做一些處理或換算。

code sample

import http from 'k6/http';

export default function () {
  const res = http.get('https://k6.io');
  const doc = parseHTML(res.body); // equivalent to res.html()
  const pageTitle = doc.find('head title').text();
  const langAttr = doc.find('html').attr('lang');
}

sleep

主要就是等待時間,有些時候使用 sleep 是為了更好模擬使用者情境
因為使用者真實操作 web 可能都會遇到有 loading 渲染的時間,所以我們將 sleep 算進來的話就當作是再重現這部分。

import http from 'k6/http';
import { sleep } from 'k6';
export const options = {
  vus: 1,
  duration: '1s',
};

export default function () {
  http.get('https://test.k6.io');
  sleep(1);
}

crypto

這一定也不陌生,非常強大的加密 module ,支援多種不同的加密方式如下:

  • hmac
  • md4
  • md5
  • sha256
  • sha384
  • sha512

通常是為了確保用戶資料安全而特別處理的。e.g. 密碼、API header 等

import crypto from 'k6/crypto';

export default function () {
  console.log(crypto.sha256('hello world!', 'hex'));
  const hasher = crypto.createHash('sha256');
  hasher.update('hello ');
  hasher.update('world!');
  console.log(hasher.digest('hex'));
}

Respone

INFO[0000] 7509e5bda0c762d2bac7f90d758b5b2263fa01ccbc542ab5e3df163be08e6ca9

encoding

import { check } from 'k6';
import encoding from 'k6/encoding';

export default function () {
  const str = 'hello world';
  const enc = 'aGVsbG8gd29ybGQ=';
  const buf = new Uint8Array([104, 101, 108, 108, 111, 32, 119, 111, 114, 108, 100]).buffer;
  check(null, {
    'is encoding string correct': () => encoding.b64encode(str) === enc,
    'is encoding ArrayBuffer correct': () => encoding.b64encode(buf) === enc,
  });
}

JSlib

k6本身支援蠻多受用的套件,但除此之外,他們還有支援一個是 JSlib 顧名思義就是 JS 庫
我覺得可以把它當作是外掛包因為其中還支援的很多額外的 module 可用。

但我不確定為什麼 k6 不把它納入官方的套件,卻須要用一個外掛包就是了XDD

  • httpx: 是將 k6/http 原本套件加以簡化處理,可以當成是優化版的 http

  • k6chaijs: 適用於 BDD 和 TDD 斷言風格

    import { describe, expect } from 'https://jslib.k6.io/k6chaijs/4.3.4.1/index.js';
    import http from 'k6/http';
    
    export const options = {
      thresholds: {
        checks: [{ threshold: 'rate == 1.00' }], // fail test on any expect() failure
      },
    };
    
    export default function testSuite() {
      describe('Basic API test', () => {
        const response = http.get('https://test-api.k6.io/public/crocodiles');
        expect(response.status, 'API status code').to.equal(200);
      });
    }
    
  • utils: k6 的小工具包

    import { sleep } from 'k6';
    import http from 'k6/http';
    
    import {
      randomIntBetween,
      randomString,
      randomItem,
      uuidv4,
      findBetween,
    } from 'https://jslib.k6.io/k6-utils/1.2.0/index.js';
    
    export default function () {
      const res = http.post(`https://test-api.k6.io/user/register/`, {
        first_name: randomItem(['Joe', 'Jane']), // random name
        last_name: `Jon${randomString(1, 'aeiou')}s`, //random character from given list
        username: `user_${randomString(10)}@example.com`, // random email address,
        password: uuidv4(), // random password in form of uuid
      });
    
      // find a string between two strings to grab the username:
      const username = findBetween(res.body, '"username":"', '"');
      console.log('username from response: ' + username);
    
      sleep(randomIntBetween(1, 5)); // sleep between 1 and 5 seconds.
    }
    
  • aws 主要是可以直接串接 AWS 上的 API 服務。


Q&A

Q: 那我可以用 npm install 方式安裝其他 JS 套件嗎?

答案是 可以

實作教學可以參考: https://blog.errorbaker.tw/posts/ruofan/k6-load-testing/

其實個人實作完後,覺得使用 webpack 打包再進行測試的對我們意義不大主要原因:

  1. 以我們團隊撰寫自動化來說,測試框架引入套件不多
  2. 評估我們的框架撰寫的方式,直接使用 k6 原本支援的模組就很足夠了
  3. 每次更改完腳本,都要在 rebuild 一次,才會吃到最新版
  4. 不能完全保證套件的相依性是正常的

上一篇
[Day25][負載測試] K6 常看的指標(Metrics)有哪些?
下一篇
[Day27][負載測試] K6 Cloud + Slack 擁有漂亮的測試報表還有訊息推播!
系列文
QA 三十天養成日記30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言