]> git.kaiwu.me - njs.git/commitdiff
Modules: limit shared dict state save frequency
authorDmitry Volyntsev <xeioex@nginx.com>
Sat, 10 Oct 2026 01:16:25 +0000 (18:16 -0700)
committerDmitry Volyntsev <xeioexception@gmail.com>
Thu, 15 Oct 2026 01:49:05 +0000 (18:49 -0700)
Saving shared dict zone content to file is scheduled with a maximum
rate of one write per second in each worker.  The total rate can be
larger by a factor of the number of running workers.

Postpone a zone save if the previous save was less than one second
ago, using a shared timestamp to limit the rate across all workers.

nginx/ngx_js_shared_dict.c

index f324fd0cb730f82b217f9c59c2d67e1505c78929..9515f8ea97006142773414a4caf2dfcebbb0f9f5 100644 (file)
@@ -19,6 +19,7 @@ typedef struct {
     ngx_rbtree_t           rbtree_expire;
     ngx_rbtree_node_t      sentinel_expire;
 
+    ngx_msec_t             last_write;
     ngx_uint_t             dirty;
     ngx_uint_t             writing;
 } ngx_js_dict_sh_t;
@@ -2562,6 +2563,7 @@ ngx_js_dict_save(ngx_js_dict_t *dict)
     u_char                 *name;
     ngx_int_t               rc;
     ngx_log_t              *log;
+    ngx_msec_t              now;
     njs_chb_t               chain;
     ngx_file_t              file;
     ngx_pool_t             *pool;
@@ -2569,6 +2571,8 @@ ngx_js_dict_save(ngx_js_dict_t *dict)
     njs_chb_node_t         *node;
     ngx_ext_rename_file_t   ext;
 
+    now = ngx_current_msec;
+
     log = dict->shm_zone->shm.log;
 
     pool = ngx_create_pool(NGX_DEFAULT_POOL_SIZE, log);
@@ -2590,6 +2594,12 @@ ngx_js_dict_save(ngx_js_dict_t *dict)
         return NGX_AGAIN;
     }
 
+    if ((ngx_msec_int_t) (now - dict->sh->last_write) < 1000) {
+        ngx_rwlock_unlock(&dict->sh->rwlock);
+        ngx_destroy_pool(pool);
+        return NGX_AGAIN;
+    }
+
     ngx_rwlock_downgrade(&dict->sh->rwlock);
 
     NGX_CHB_CTX_INIT(&chain, pool);
@@ -2604,6 +2614,7 @@ ngx_js_dict_save(ngx_js_dict_t *dict)
 
     dict->sh->writing = 1;
     dict->sh->dirty = 0;
+    dict->sh->last_write = now;
 
     ngx_rwlock_unlock(&dict->sh->rwlock);
 
@@ -2972,6 +2983,8 @@ ngx_js_dict_init_zone(ngx_shm_zone_t *shm_zone, void *data)
 
     dict->shpool->data = dict->sh;
 
+    dict->sh->last_write = ngx_current_msec;
+
     ngx_rbtree_init(&dict->sh->rbtree, &dict->sh->sentinel,
                     ngx_str_rbtree_insert_value);