setCache(key, cache, setAsMain = false, _safely = true) {
        const tiledImage = this.tiledImage;
        if (!tiledImage) {
            return null; //async can access outside its lifetime
        }

        const overwritesMainCache = key === this.cacheKey;
        if (_safely) {
            $.console.assert(cache instanceof $.CacheRecord, "[Tile.setCache] cache must be a CacheRecord object!");
            if (overwritesMainCache || setAsMain) {
                // Need to get the supported type for rendering out of the active drawer.
                const supportedTypes = tiledImage.viewer.drawer.getSupportedDataFormats();
                const conversion = $.converter.getConversionPath(cache.type, supportedTypes);
                $.console.assert(conversion, "[Tile.setCache] data was set for the default tile cache we are unable" +
                    `to render. Make sure OpenSeadragon.converter was taught to convert ${cache.type} to (one of): ${conversion.toString()}`);
            }
        }

        const havingRecord = this._caches[key];
        if (havingRecord !== cache) {
            this._caches[key] = cache;
            cache.addTile(this);  // keep reference bidirectional
            if (havingRecord) {
                havingRecord.removeTile(this);
                tiledImage._tileCache.safeUnloadCache(havingRecord);
            }
        }

        // Update cache key if differs and main requested
        if (!overwritesMainCache && setAsMain) {
            this._updateMainCacheKey(key);
        }
        return cache;
    }
Add cache object to the tile

@param {string} key cache key, if unique, new cache object is created, else existing cache attached
@param {OpenSeadragon.CacheRecord} cache the cache object to attach to this tile
@param {boolean} [setAsMain=false] if true, the key will be set as the tile.cacheKey,
  no effect if key === this.cacheKey
@param [_safely=true] private
@returns {OpenSeadragon.CacheRecord|null} - Returns cache parameter reference if attached.