How to Set JVM Parameters for a Platform Handling 1 Million Daily Logins on an 8 GB Server
This article explains how to estimate capacity, choose appropriate garbage collectors, and configure JVM memory settings—including heap size, young generation, thread stack, and GC options—for a service that processes one million login requests per day on a node with 8 GB of RAM, providing step‑by‑step guidance and example command lines.
The author revisits a technical interview question about configuring JVM parameters for a platform that receives 1 M login requests daily on a service node with 8 GB memory, offering both practical tuning steps and interview preparation insights.
Step 1: Capacity Planning for a New System
Estimate object creation rate per second, calculate required young generation size, and determine the number of machines needed to keep Minor GC frequency low. Example: with three 4C8G servers, allocating a 4 GB heap (2 GB young generation) can handle the load.
Step 2: Choosing a Garbage Collector
Throughput vs. Latency
Throughput‑oriented configurations favor larger heaps (fewer GC pauses but longer pause times), while latency‑oriented setups use smaller heaps to reduce pause duration. The trade‑off must be evaluated based on service requirements.
GC Design Considerations
GC must not allocate new objects while collecting.
Stop‑The‑World (STW) pauses halt request processing.
Young generation uses copying algorithms; old generation prefers non‑copying to save space.
The goal of any collector is to reduce GC frequency and pause time.
CMS vs. G1
ParNew+CMS is common for low‑latency services, while G1 is the recommended default for newer JVMs and larger heaps.
Step 3: Partition Size Planning
Set -Xms and -Xmx to about half of physical memory (e.g., 4 GB for an 8 GB node). Choose -Xmn (young generation) based on workload: stateless web services may use up to 75 % of the heap, while stateful services often keep it around 33 %.
Configure thread stack size with -Xss (typically 512 KB–1 MB).
JVM Parameter
Description
Default
Recommended
-Xms
Initial heap size
OS memory /64
~50 % of RAM
-Xmx
Maximum heap size
OS memory /4
~50 % of RAM
-Xmn
Young generation size
~1/3 of heap
3/8 of heap (Sun default) or adjust per workload
-Xss
Thread stack size
Depends on JDK/OS
512 KB–1 MB
Step 4: Tuning Survivor and Tenuring
Use -XX:SurvivorRatio=8 to set Eden:Survivor = 8:1:1 (e.g., 1.6 GB Eden, 0.2 GB each Survivor). Adjust -XX:MaxTenuringThreshold (e.g., 5) so objects survive only a few Minor GCs before promotion.
Step 5: Direct Allocation of Large Objects
Set -XX:PretenureSizeThreshold=1M to allocate objects larger than 1 MB directly in the old generation.
Step 6: CMS Old‑Generation Optimisation
For JDK 8, the default collector is Parallel GC; for heaps larger than 4 GB, G1 is preferred. For low‑latency services, use ParNew+CMS with options such as -XX:CMSInitiatingOccupancyFraction=70 and -XX:+UseCMSInitiatingOccupancyOnly .
Step 7: OOM and GC Logging
Enable heap dumps on OOM with -XX:+HeapDumpOnOutOfMemoryError and specify a path. Add GC logging flags like -Xloggc:/path/gc.log , -XX:+PrintGCDetails , and -XX:+PrintGCDateStamps for troubleshooting.
Step 8: General JVM Parameter Templates
Example template for a 4C8G machine (response‑oriented):
-Xms4g
-Xmx4g
-Xmn2g
-Xss1m
-XX:SurvivorRatio=8
-XX:MaxTenuringThreshold=10
-XX:+UseConcMarkSweepGC
-XX:CMSInitiatingOccupancyFraction=70
-XX:+UseCMSInitiatingOccupancyOnly
-XX:+AlwaysPreTouch
-XX:+HeapDumpOnOutOfMemoryError
-verbose:gc
-XX:+PrintGCDetails
-XX:+PrintGCDateStamps
-Xloggc:gc.logFor throughput‑oriented workloads, a G1 template (8C16G) is recommended:
-Xms8g
-Xmx8g
-Xss1m
-XX:+UseG1GC
-XX:MaxGCPauseMillis=150
-XX:InitiatingHeapOccupancyPercent=40
-XX:+HeapDumpOnOutOfMemoryError
-verbose:gc
-XX:+PrintGCDetails
-XX:+PrintGCDateStamps
-Xloggc:gc.logAdditional Topics
What is ZGC?
ZGC is a low‑latency collector introduced in JDK 11, targeting pause times under 10 ms for heaps up to several terabytes.
How to Choose a Collector
Small heap or single‑core: -XX:+UseSerialGC
Throughput‑oriented: -XX:+UseParallelGC
Low‑latency: -XX:+UseConcMarkSweepGC , -XX:+UseG1GC , or -XX:+UseZGC
Metaspace vs. Permanent Generation
Java 8 replaced the fixed‑size PermGen with native‑memory‑backed Metaspace, eliminating the OutOfMemoryError: PermGen space issue and allowing the size to grow with available system memory.
Stop‑The‑World, OopMap, and Safepoints
GC pauses require all Java threads to stop at safepoints, where the JVM knows the locations of object references via OopMaps.
Overall, the article provides a comprehensive step‑by‑step guide to capacity estimation, GC selection, memory partitioning, and JVM flag tuning for high‑traffic login services.
Code Ape Tech Column
Former Ant Group P8 engineer, pure technologist, sharing full‑stack Java, job interview and career advice through a column. Site: java-family.cn
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.