On this page

    M

    process.finalization.register

    History
    process.finalization.register(ref, callback): void
    Stability: 1.1Active Development
    Attributes
    The reference to the resource that is being tracked.
    callback:Function
    The callback function to be called when the resource is finalized.
    The reference to the resource that is being tracked.
    event:string
    The event that triggered the finalization. Defaults to 'exit'.

    This function registers a callback to be called when the process emits the exit event if the ref object was not garbage collected. If the object ref was garbage collected before the exit event is emitted, the callback will be removed from the finalization registry, and it will not be called on process exit.

    Inside the callback you can release the resources allocated by the ref object. Be aware that all limitations applied to the beforeExit event are also applied to the callback function, this means that there is a possibility that the callback will not be called under special circumstances.

    The idea of ​​this function is to help you free up resources when the starts process exiting, but also let the object be garbage collected if it is no longer being used.

    Eg: you can register an object that contains a buffer, you want to make sure that buffer is released when the process exit, but if the object is garbage collected before the process exit, we no longer need to release the buffer, so in this case we just remove the callback from the finalization registry.

    const { finalization } = require('node:process');
    
    // Please make sure that the function passed to finalization.register()
    // does not create a closure around unnecessary objects.
    function onFinalize(obj, event) {
      // You can do whatever you want with the object
      obj.dispose();
    }
    
    function setup() {
      // This object can be safely garbage collected,
      // and the resulting shutdown function will not be called.
      // There are no leaks.
      const myDisposableObject = {
        dispose() {
          // Free your resources synchronously
        },
      };
    
      finalization.register(myDisposableObject, onFinalize);
    }
    
    setup();
    import { finalization } from 'node:process';
    
    // Please make sure that the function passed to finalization.register()
    // does not create a closure around unnecessary objects.
    function onFinalize(obj, event) {
      // You can do whatever you want with the object
      obj.dispose();
    }
    
    function setup() {
      // This object can be safely garbage collected,
      // and the resulting shutdown function will not be called.
      // There are no leaks.
      const myDisposableObject = {
        dispose() {
          // Free your resources synchronously
        },
      };
    
      finalization.register(myDisposableObject, onFinalize);
    }
    
    setup();

    The code above relies on the following assumptions:

    • arrow functions are avoided
    • regular functions are recommended to be within the global context (root)

    Regular functions could reference the context where the obj lives, making the obj not garbage collectible.

    Arrow functions will hold the previous context. Consider, for example:

    class Test {
      constructor() {
        finalization.register(this, (ref) => ref.dispose());
    
        // Even something like this is highly discouraged
        // finalization.register(this, () => this.dispose());
      }
      dispose() {}
    }

    It is very unlikely (not impossible) that this object will be garbage collected, but if it is not, dispose will be called when process.exit is called.

    Be careful and avoid relying on this feature for the disposal of critical resources, as it is not guaranteed that the callback will be called under all circumstances.