code: def memoized_func(
      key: str, cache: Cache = cache_manager.cache
  ) -> Callable[..., Any]:
      """
      Decorator with configurable key and cache backend.
  
          @memoized_func(key="{a}+{b}", cache=cache_manager.data_cache)
          def sum(a: int, b: int) -> int:
              return a + b
  
      In the example above the result for `1+2` will be stored under the key of name "1+2",
      in the `cache_manager.data_cache` cache.
  
      Note: this decorator should be used only with functions that return primitives,
      otherwise the deserialization might not work correctly.
  
      enable_cache is treated as True by default,
      except enable_cache = False is passed to the decorated function.
  
      force means whether to force refresh the cache and is treated as False by default,
      except force = True is passed to the decorated function.
  
      timeout of cache is set to 600 seconds by default,
      except cache_timeout = {timeout in seconds} is passed to the decorated function.
  
      :param key: a callable function that takes function arguments and returns
                  the caching key.
      :param cache: a FlaskCache instance that will store the cache.
      """
  
      def wrap(f: Callable[..., Any]) -> Callable[..., Any]:
          def wrapped_f(*args: Any, **kwargs: Any) -> Any:
              if not kwargs.get("cache", True):
                  return f(*args, **kwargs)
  
              # format the key using args/kwargs passed to the decorated function
              signature = inspect.signature(f)
              bound_args = signature.bind(*args, **kwargs)
              bound_args.apply_defaults()
              cache_key = key.format(**bound_args.arguments)
  
              obj = cache.get(cache_key)
              if not kwargs.get("force") and obj is not None:
                  return obj
              obj = f(*args, **kwargs)
              cache.set(
                  cache_key, obj, timeout=kwargs.get("cache_timeout", 0)
              )
              return obj
  
          return wrapped_f
  
      return wrap
  
file_path: superset/superset/utils/cache.py
imports: from __future__ import annotations
  import inspect
  import logging
  from datetime import datetime, timedelta
  from functools import wraps
  from typing import Any, Callable, TYPE_CHECKING
  from flask import current_app, request
  from flask_caching import Cache
  from flask_caching.backends import NullCache
  from werkzeug.wrappers import Response
  from superset import db
  from superset.extensions import cache_manager
  from superset.models.cache import CacheKey
  from superset.utils.core import json_int_dttm_ser
  from superset.utils.hashing import md5_sha_from_dict
label_desc: Use image node_id 3 for calling a global function with example usage: memoized_func(key, cache) and returns: wrap, wrapped_f, obj, f, obj