day8 / re-frame-test

Cross platform (cljs and clj) utilities for testing re-frame applications
MIT License
109 stars 12 forks source link

How to avoid `re-frame: Subscribe was called outside of a reactive context` warnings in tests? #24

Closed ertugrulcetin closed 1 year ago

ertugrulcetin commented 1 year ago

After updating re-frame to the latest version ("1.3.0"), we started to get this error messages in tests: re-frame: Subscribe was called outside of a reactive context

Here is the test code sample:

(deftest when-rendering-as-text
  (run-test-sync
    (let [global-message (subscribe [:global-message])]
      (is (nil? @global-message)))))
mrrodriguez commented 1 year ago

In order to prevent this the "correct way", you'd need to ensure any subscription deref you make is in a "reactive context". I think this probably is more work than is useful in tests. I believe subscriptions are implemented as reagent.ratom/Reaction types. It isn't clear to me how a memory leak may work for this in the current version impl of IDeref/-deref for Reaction type.

If you aren't too concerned for a memory leak potential here do it being in a temporary testing context, I'd say eliminate the spam with:

(defn- disable-warn-when-not-reactive!
  "When running tests there may be reagent reactions deref'ed. This will generate a warning in
  `rs/warn-when-not-reactive` due to the possibility of a memory leak in an app that uses reactions
  in this way. To ensure all tests run in a reactive context is non-trivial and would require
  wrapping all eg. re-frame subscription deref's. We should not generally need to be too concerned
  with a memory leak like this in tests since this is a temporary process and we don't expect a
  large spam of subscription (or other reaction) deref's during testing."
  []
  (set! rs/warn-when-not-reactive (constantly nil)))

Where [re-frame.subs :as rs].

Call this somewhere before you run your tests.

Obviously this is a bit of a hack & subject to any changes to re-frame.subs/warn-when-not-reactive

ertugrulcetin commented 1 year ago

@mrrodriguez thanks!