code: def granger_causality_tests(
      ts_cause: TimeSeries,
      ts_effect: TimeSeries,
      maxlag: int,
      addconst: bool = True,
  ) -> None:
      """
      Provides four tests for granger non causality of 2 time series using
      :func:`statsmodels.tsa.stattools.grangercausalitytests`.
      See [1]_.
  
  
      Parameters
      ----------
      ts_cause
          A univariate deterministic time series. The statistical test determines if this time series
          'Granger causes' the time series ts_effect (second parameter). Missing values are not supported.
          if H_0 (non causality) is rejected (p near 0), then there is a 'granger causality'.
      ts_effect
          Univariate time series 'Granger caused' by ts_cause.
      maxlag
          If an integer, computes the test for all lags up to maxlag.
          If an iterable, computes the tests only for the lags in maxlag.
      addconst
          Include a constant in the model.
  
      Returns
      -------
      Dict
          All test results, dictionary keys are the number of lags. For each lag the values are a tuple,
          with the first element a dictionary with test statistic, pvalues, degrees of freedom, the second element are
          the OLS estimation results for the restricted model, the unrestricted model and the restriction (contrast)
          matrix for the parameter f_test.
  
      References
      ----------
      .. [1] https://www.statsmodels.org/dev/generated/statsmodels.tsa.stattools.grangercausalitytests.html
      """
  
      ts_cause._assert_univariate()
      ts_effect._assert_univariate()
  
      ts_cause._assert_deterministic()
      ts_effect._assert_deterministic()
  
      raise_if_not(
          ts_cause.freq == ts_effect.freq,
          "ts_cause and ts_effect must have the same frequency.",
      )
  
      if not ts_cause.has_same_time_as(ts_effect):
          logger.warning(
              "ts_cause and ts_effect time series have different time index. "
              "We will slice-intersect ts_cause with ts_effect."
          )
  
      ts_cause = ts_cause.slice_intersect(ts_effect)
      ts_effect = ts_effect.slice_intersect(ts_cause)
  
      if not stationarity_tests(ts_cause):
          logger.warning(
              "ts_cause doesn't seem to be stationary. Please review granger causality validity in your problem context."
          )
      if not stationarity_tests(ts_effect):
          logger.warning(
              "ts_effect doesn't seem to be stationary. Please review granger causality validity in your problem context."
          )
  
      return grangercausalitytests(
          np.concatenate(
              (
                  ts_effect.values(copy=False),
                  ts_cause.values(copy=False),
              ),
              axis=1,
          ),
          maxlag,
          addconst,
      )
  
imports: import math
  from typing import List, Optional, Sequence, Tuple, Union
  import matplotlib.pyplot
  import numpy
  from scipy.signal import argrelmax
  from scipy.stats import norm
  from statsmodels.tsa.seasonal import MSTL, STL, seasonal_decompose
  from statsmodels.tsa.stattools import acf, adfuller, grangercausalitytests, kpss, pacf
  from darts import TimeSeries
  from darts.logging import get_logger, raise_if, raise_if_not, raise_log
  from .missing_values import fill_missing_values
  from .utils import ModelMode, SeasonalityMode
label_desc: Use image node_id 10 for calling a global function with example usage: granger_causality_tests(ts_cause, ts_effect, maxlag, addconst) and returns: grangercausalitytests