FinalizablePyObject (Jython API documentation)
Date: 2022-09-10

org.python.core.finalization

## Interface FinalizablePyObject

- All Known Implementing Classes:
    PyBZ2File, PyBZ2FileDerived, PyInstance

      public interface FinalizablePyObject

  This interface allows `PyObject`s to have finalizers. Alternatively one can use `FinalizableBuiltin`.

  The difference is that `__del__()` can be overridden by a new-style subclass's `__del__`-method on Python-side, while `FinalizableBuiltin.__del_builtin__()` is always called. If a Python-side finalizer exists, `FinalizableBuiltin.__del_builtin__()` will be called after the Python-side finalizer has been processed.

  One can even implement both interfaces. If both interfaces are implemented, the `FinalizeTrigger` will call `__del__()` first and then `FinalizableBuiltin.__del_builtin__()`. If a new-style subclass has an own, Python-side `__del__`-method, this overrides the Java-implemented `__del__()`, but not `FinalizableBuiltin.__del_builtin__()`, which will be called after the Python-side finalizer.

  If you are writing a custom built-in that shall directly extend `PyObject` or some other not-yet-finalizable builtin and have a finalizer, follow the instructions below.

  1. Let your subclass implement `FinalizablePyObject` (or `FinalizableBuiltin`).
  2. In every constructor call
     `FinalizeTrigger.ensureFinalizer(this);`
  3. Write your `__del__()`-method however you intend it. (or `FinalizableBuiltin.__del_builtin__()` if `FinalizableBuiltin` was used)
  4. (optional)
     If your finalizer resurrects the object (Python allows this) and you wish the finalizer to run again on next collection of the object:
     In the block where the resurrection occurs, let your `__del__()`- or `FinalizableBuiltin.__del_builtin__()`-method call
     `FinalizeTrigger.ensureFinalizer(this);`. If you implement `__del__` in Python and need this functionality, you can simply call `someObject.__ensure_finalizer__()`
     Note that this is Jython-specific and should be surrounded by a `try/except`-block to ensure compatibility with other Python implementations.

  Note: Regarding to object resurrection, Jython currently behaves like CPython ≥ 3.4. That means the finalizer `__del__()` or `FinalizableBuiltin.__del_builtin__()` is called only the first time an object gets gc'ed. If pre-3.4.-behavior is required for some reason (i.e. have the finalizer called repeatedly on every collection after a resurrection), one can achieve this manually via step 5).

  The built-in function `__ensure_finalizer__` is also useful if a class acquires a finalizer after instances have already been created. Usually only those instances that were created after their class acquired the finalizer will actually be finalized (in contrast to CPython). However, one can manually tell earlier created instances to become finalizable by calling `__ensure_finalizer__()` on them. As mentioned above, it is recommended to surround this with a `try/except`-block to ensure compatibility with other Python implementations.

  Note that it is not possible to override `__ensure_finalizer__` on Python side. If one overrides `__ensure_finalizer__` on Python side, Jython will ignore the override-implementation and still call the original one.

  It is possible to switch finalization on and off at any desired time for a certain object. This can be helpful if it is only necessary to have `__del__()` or `FinalizableBuiltin.__del_builtin__()` called for certain configurations of an object.

  To turn off the finalizer, call:

       ((FinalizeTrigger) JyAttribute.getAttr(this, JyAttribute.FINALIZE_TRIGGER_ATTR)).clear();

  To turn it on again, call

       ((FinalizeTrigger) JyAttribute.getAttr(this, JyAttribute.FINALIZE_TRIGGER_ATTR)).trigger(this);

  See Also:
    `JyAttribute.FINALIZE_TRIGGER_ATTR`, `FinalizableBuiltin.__del_builtin__()`

- - ### Method Summary

    All Methods Instance Methods Abstract Methods
    Modifier and Type | Method and Description
    --- | ---
    `void` | `__del__()`

- - ### Method Detail

    - #### __del__

          void __del__()

Jython homepage