001package arez; 002 003import javax.annotation.Nonnull; 004import javax.annotation.Nullable; 005import static org.realityforge.braincheck.Guards.*; 006 007/** 008 * Interface that allows caller to release any resources associated with element. 009 * It is safe to invoke {@link #dispose()} multiple times on a element. Once an 010 * element is disposed, no methods should be invoked on element. 011 */ 012public interface Disposable 013{ 014 /** 015 * Dispose the element. See {@link Disposable} for a description of the implications. 016 */ 017 void dispose(); 018 019 /** 020 * Return true if dispose() has been called on object. 021 * 022 * @return true if dispose has been called. 023 */ 024 boolean isDisposed(); 025 026 /** 027 * Return true if {@link #isDisposed()} returns false. 028 * 029 * @return true if {@link #isDisposed()} returns false. 030 */ 031 default boolean isNotDisposed() 032 { 033 return !isDisposed(); 034 } 035 036 /** 037 * Dispose the supplied object if it is Disposable, else do nothing. 038 * 039 * @param object the object to dispose. 040 */ 041 static void dispose( @Nullable final Object object ) 042 { 043 if ( object instanceof Disposable ) 044 { 045 ( (Disposable) object ).dispose(); 046 } 047 } 048 049 /** 050 * Return true if the parameter is Disposable and has been disposed, else return false. 051 * 052 * @param object the object to check disposed state. 053 * @return true if the parameter is Disposable and has been disposed, else return false. 054 */ 055 static boolean isDisposed( @Nullable final Object object ) 056 { 057 return object instanceof Disposable && ( (Disposable) object ).isDisposed(); 058 } 059 060 /** 061 * Return true if {@link #isDisposed(Object)} returns false for the same parameter. 062 * 063 * @param object the object to check state. 064 * @return true if the parameter is not Disposable or has not been disposed, else return false. 065 */ 066 static boolean isNotDisposed( @Nullable final Object object ) 067 { 068 return !isDisposed( object ); 069 } 070 071 /** 072 * Cast specified object to instance of Disposable. 073 * Invariant checks will verify that the cast is valid before proceeding. 074 * 075 * @param object the object to cast to Disposable. 076 * @return the object cast to Disposable. 077 */ 078 @Nonnull 079 static Disposable asDisposable( @Nonnull final Object object ) 080 { 081 if ( Arez.shouldCheckApiInvariants() ) 082 { 083 apiInvariant( () -> object instanceof Disposable, 084 () -> "Object passed to asDisposable does not implement Disposable. Object: " + object ); 085 } 086 return (Disposable) object; 087 } 088}