การทดสอบแรงกดดัน
ปัจจัยที่มีผลต่อผลการทดสอบแรงกดดัน
- ความหน่วงของเครือข่ายระหว่างเครื่องทดสอบกับเซิร์ฟเวอร์ (แนะนำให้ทดสอบภายในเครือข่ายภายในหรือเครื่องของตัวเอง)
- แบนด์วิธระหว่างเครื่องทดสอบกับเซิร์ฟเวอร์ (แนะนำให้ทดสอบภายในเครือข่ายภายในหรือเครื่องของตัวเอง)
- การเปิดใช้งาน HTTP keep-alive หรือไม่ (แนะนำให้เปิด)
- จำนวนการเชื่อมต่อพร้อมกันเพียงพอหรือไม่ (ควรเปิดเชื่อมต่อพร้อมกันสูงขึ้นเมื่อต้องทำการทดสอบจากเครือข่ายภายนอก)
- จำนวนกระบวนการของเซิร์ฟเวอร์มีความเหมาะสมหรือไม่ (จำนวนกระบวนการสำหรับธุรกิจ helloworld แนะนำให้เท่ากับจำนวน CPU, และจำนวนกระบวนการสำหรับฐานข้อมูลแนะนำให้เป็นสี่เท่าของ CPU หรือมากกว่า)
- ประสิทธิภาพของธุรกิจอย่างแท้จริง (เช่น การใช้ฐานข้อมูลจากเครือข่ายภายนอกหรือไม่)
HTTP keep-alive คืออะไร?
กลไก HTTP Keep-Alive เป็นเทคนิคที่ใช้สำหรับการส่ง HTTP requests และ responses หลายๆ รายการผ่านการเชื่อมต่อ TCP เดียว ซึ่งมีผลกระทบต่อผลการทดสอบประสิทธิภาพเป็นอย่างมาก โดยปิดการใช้งาน keep-alive อาจทำให้ QPS ลดลงอย่างมาก
ปัจจุบันเบราว์เซอร์ส่วนใหญ่มีการเปิดใช้งาน keep-alive โดยค่าเริ่มต้น ซึ่งหมายความว่าเมื่อเบราว์เซอร์เข้าถึง URL HTTP หนึ่งจะเก็บการเชื่อมต่อไว้ชั่วคราวและไม่ปิด โดยเมื่อมีการร้องขอครั้งถัดไปจะใช้การเชื่อมต่อนี้ซ้ำ เพื่อเพิ่มประสิทธิภาพ
แนะนำให้เปิดใช้งาน keep-alive เมื่อทำการทดสอบแรงกดดัน
นอกจากนี้ ถ้าไม่ได้เปิดใช้งาน keep-alive การทดสอบแรงกดดันจะทำให้พอร์ตท้องถิ่นของไคลเอนต์หมดไปใกล้เคียงกับสถานะ timewait ส่งผลให้จำนวนคำขอทั้งหมดเกินกว่าจำนวนที่กำหนด (โดยปกติประมาณ 28,000) จะมีการร้องขอล้มเหลว
จะเปิดใช้งาน HTTP keep-alive ในระหว่างการทดสอบแรงกดดันได้อย่างไร?
หากใช้โปรแกรม ab สำหรับการทดสอบจำเป็นต้องเพิ่มตัวเลือก -k,例如 ab -n100000 -c200 -k http://127.0.0.1:8787/
apipost ต้องให้หัวกลับคืนมาพร้อม gzip header เพื่อนำไปเปิดใช้งาน keep-alive (ข้อบกพร่องของ apipost ให้ดูที่ด้านล่าง)
โปรแกรมทดสอบแรงกดดันอื่นๆ มักจะเปิดใช้งานโดยค่าเริ่มต้น
ทำไม QPS ถึงต่ำเมื่อทดสอบจากเครือข่ายภายนอก?
ความหน่วงของเครือข่ายภายนอกสูงทำให้ QPS ต่ำถือเป็นเรื่องปกติ เช่น การทดสอบหน้า baidu อาจจะมี QPS แค่ไม่กี่สิบ
แนะนำให้ทำการทดสอบในเครือข่ายภายในหรือเครื่องของตัวเอง เพื่อขจัดผลกระทบจากความหน่วงของเครือข่าย
หากจำเป็นต้องทำการทดสอบจากเครือข่ายภายนอกสามารถเพิ่มจำนวนเชื่อมต่อพร้อมกันเพื่อเพิ่มการส่งข้อมูล (ต้องมั่นใจว่าแบนด์วิธเพียงพอ)
ทำไมประสิทธิภาพลดลงเมื่อผ่าน nginx proxy?
การทำงานของ nginx จะใช้ทรัพยากรของระบบ นอกจากนี้ การสื่อสารระหว่าง nginx และ webman ก็ต้องใช้ทรัพยากรด้วย
อย่างไรก็ตาม ทรัพยากรของระบบมีอยู่อย่างจำกัด webman ไม่สามารถเข้าถึงทรัพยากรทั้งหมดของระบบ จึงเป็นที่ปกติที่ประสิทธิภาพของระบบโดยรวมอาจลดลง
เพื่อพยายามลดผลกระทบต่อประสิทธิภาพที่เกิดจาก nginx proxy ให้พิจารณาปิดบันทึก nginx (access_log off;
),
เปิดใช้งาน keep-alive ระหว่าง nginx ถึง webman โดยอ้างอิงจากnginx proxy
นอกจากนี้ HTTPS จะใช้ทรัพยากรมากกว่าการใช้งาน HTTP เนื่องจาก HTTPS ต้องมีการจัดการ SSL/TLS handshake, การเข้ารหัสและถอดรหัสข้อมูล, ขนาดของแพ็คเกจที่ใหญ่ขึ้นใช้แบนด์วิธมากขึ้นสิ่งเหล่านี้ทำให้ประสิทธิภาพลดลง
หากการทดสอบใช้การเชื่อมต่อแบบสั้น (ไม่มีการเปิด HTTP keep-alive) การร้องขอแต่ละครั้งจะต้องทำการเป็นส่วนหนึ่งของการสื่อสาร SSL/TLS handshake เพิ่มเติม ซึ่งจะส่งผลให้ประสิทธิภาพลดลงอย่างมาก แนะนำให้การทดสอบ HTTPS เปิดใช้งาน HTTP keep-alive
จะรู้ได้อย่างไรว่าเมื่อไหร่ระบบได้ถึงขีดจำกัดด้านประสิทธิภาพแล้ว?
โดยทั่วไป เมื่อ CPU ถึง 100% จะถือว่าประสิทธิภาพของระบบได้ถึงขีดจำกัดแล้ว หาก CPU ยังมีพื้นที่ว่างอยู่แสดงว่ายังไม่ได้ถึงขีดจำกัด ในขณะนั้นสามารถเพิ่มจำนวนการเชื่อมต่อพร้อมกันเพื่อเพิ่ม QPS
หากการเพิ่มจำนวนการเชื่อมต่อพร้อมกันไม่สามารถเพิ่ม QPS ได้ อาจเป็นเพราะจำนวนกระบวนการของ webman ไม่เพียงพอ กรุณาเพิ่มจำนวนกระบวนการของ webman หากยังไม่สามารถเพิ่มได้ให้พิจารณาแบนด์วิธเพียงพอหรือไม่
ทำไมผลการทดสอบของฉันแสดงให้เห็นว่า ประสิทธิภาพของ webman ต่ำกว่าเฟรมเวิร์ก gin ของ go?
การทดสอบจากtechempower แสดงให้เห็นว่าไม่ว่าในกรณีใดเว็บแมนจะมีค่าตัวชี้วัดสูงกว่า gin ประมาณหนึ่งเท่าตัว
หากผลของคุณไม่เช่นนั้นอาจเป็นเพราะคุณใช้ ORM ใน webman ซึ่งอาจส่งผลกระทบต่อประสิทธิภาพ พยายามเปรียบเทียบ webman+PDO ดั้งเดิม กับ gin+SQL ดั้งเดิม
การใช้ ORM ใน webman จะลดประสิทธิภาพไปเท่าไหร่?
ด้านล่างนี้เป็นชุดข้อมูลการทดสอบ
สภาพแวดล้อม
เซิร์ฟเวอร์ Aliyun 4 คอร์ 4G ฐานข้อมูล MySQL ภายในเครื่อง ทำการสุ่มค้นหาข้อมูลหนึ่งรายการจาก 100,000 รายการ แล้วส่งกลับในรูปแบบ json โดยกำลังทดสอบในเครื่อง
หากใช้ PDO ดั้งเดิม
webman QPS คือ 17,800
หากใช้ laravel ของ Db::table()
webman QPS ลดลงเหลือ 9,400 QPS
หากใช้ laravel ของ Model
webman QPS ลดลงเหลือ 7,200 QPS
ผลลัพธ์จาก thinkORM จะคล้ายกันไม่แตกต่างมาก
คำเตือน
แม้ว่าการใช้ ORM จะทำให้ประสิทธิภาพลดลง แต่สำหรับธุรกิจ 99% แล้วประสิทธิภาพยังถือว่ามีการขยายเกินไป หากคุณคือ 1% นั้นก็สามารถเพียงแค่เพิ่ม CPU หรือเซิร์ฟเวอร์ก็สามารถแก้ปัญหาได้อย่างง่ายดาย
เราควรหาจุดสมดุลในหลากหลายตัวชี้วัดเช่น ประสิทธิภาพในการพัฒนา, ความสามารถในการบำรุงรักษา, และประสิทธิภาพ แทนที่จะมุ่งเน้นไปที่ประสิทธิภาพเพียงอย่างเดียว
ทำไมใช้ apipost ทดสอบ QPS ถึงต่ำ?
โมดูลทดสอบแรงกดดันของ apipost มีข้อบกพร่อง หากเซิร์ฟเวอร์ไม่ส่งกลับ gzip header จะไม่สามารถรักษาการเชื่อมต่อ keep-alive ไว้ได้ ทำให้ประสิทธิภาพลดลงมาก
วิธีแก้ปัญหาคือส่งกลับข้อมูลที่ถูกบีบอัดในขณะที่เพิ่ม gzip header เช่น
<?php
namespace app\controller;
class IndexController
{
public function index()
{
return response(gzencode('hello webman'))->withHeader('Content-Encoding', 'gzip');
}
}
นอกจากนี้ apipost บางครั้งไม่สามารถให้แรงกดดันที่พอใจได้ซึ่งสะท้อนให้เห็นว่าจำนวนการเชื่อมต่อเดียวกันการใช้ apipost จะต่ำกว่า ab ประมาณ 50%
แนะนำให้ใช้ ab, wrk หรือซอฟต์แวร์ทดสอบแรงกดดันอื่น ๆ แทนที่จะใช้ apipost
ตั้งค่าจำนวนกระบวนการให้เหมาะสม
webman เปิดใช้งานจำนวนกระบวนการ cpu*4 โดยค่าเริ่มต้น ในความเป็นจริงการทดสอบแรงกดดันของธุรกิจ helloworld ที่ไม่มี IO ในเครือข่าย ควรตั้งจำนวนกระบวนการให้ตรงกับจำนวนคอร์ CPU เพื่อให้ประสิทธิภาพดีที่สุด เพราะจะช่วยลดต้นทุนการสลับกระบวนการ
หากเป็นธุรกิจที่มีฐานข้อมูล, Redis เป็นต้นที่เป็นการรองรับ I/O ที่เป็นบล็อก ควรตั้งค่าจำนวนกระบวนการเป็น 3-8 เท่าของ CPU เพราะในช่วงเวลานั้นต้องการจำนวนกระบวนการมากขึ้นเพื่อเพิ่มการเชื่อมต่อพร้อมกัน แต่ต้นทุนการสลับกระบวนการจะน้อยมากเมื่อเทียบกับ I/O ที่เป็นบล็อก
ขอบเขตอ้างอิงสำหรับการทดสอบแรงกดดัน
เซิร์ฟเวอร์คลาวด์ 4 คอร์ 4G 16 กระบวนการ ทดสอบในเครื่อง/เครือข่ายภายใน
- | เปิดใช้งาน keep-alive | ไม่เปิดใช้งาน keep-alive |
---|---|---|
hello world | 80,000-160,000 QPS | 10,000-30,000 QPS |
การค้นหารายการเดี่ยวในฐานข้อมูล | 10,000-20,000 QPS | 10,000 QPS |
ข้อมูลการทดสอบจากบุคคลที่สาม techempower
ตัวอย่างคำสั่งทดสอบแรงกดดัน
ab
# 100000 คำขอ 200 การเชื่อมต่อพร้อมกัน เปิดใช้งาน keep-alive
ab -n100000 -c200 -k http://127.0.0.1:8787/
# 100000 คำขอ 200 การเชื่อมต่อพร้อมกัน ไม่เปิดใช้งาน keep-alive
ab -n100000 -c200 http://127.0.0.1:8787/
wrk
# 200 การเชื่อมต่อพร้อมกัน ทดสอบเป็นเวลา 10 วินาที เปิดใช้งาน keep-alive (ตามค่าเริ่มต้น)
wrk -c 200 -d 10s http://example.com