Exclude client code from the native build

browser_only is the ppx to exclude client code from the server build, making sure a library can run on both build targets.

For example, if you're using Webapi to query the DOM or using LocalStorage. This code should only run on the client, and there's no equivalent or fallback on the server, in order to compile and run successfully on the server, you can use browser_only or switch%platform.

Usage

The ppx expose a browser_only attribute that can be used to discard a function or a value, and switch%platform to conditionally execute code based on the platform.

Add server-reason-react.browser_ppx into to your pps field under a dune stanzas (melange.emit, libraries or executable) in your dune files.

You would need to add it on both "server" and "client" dune files. Adding the -js flag server-reason-react.browser_ppx -js for the client and without for the server:

; server exectuable
(executable
 (name server)
 (preprocess
  (pps server-reason-react.browser_ppx)))

; melange emitting JavaScript
(melange.emit
 (target app)
 (preprocess
  (pps server-reason-react.browser_ppx -js)))

browser_only

let%browser_only countDomNodes = (id) => {
  let elements = Webapi.Element.querySelector("#" ++ id);
  let arr_elements = Webapi.Element.toArray(elements);
  Array.length(arr_elements);
};

The method tagged by browser_only will keep the function untouched for the client build, but for the server build, will be transformed to a function that raises the exception Runtime.Impossible_in_ssr.

If this function runs on the server, it will raise an exception, and the server will crash. In order to prevent this, you can use try to catch the exception and provide a default behaviour/value.

Following with the example from above:

let%browser_only countDomNodes = (id) => {
  let elements = Webapi.Element.querySelector("#" ++ id);
  let arr_elements = Webapi.Element.toArray(elements);
  Array.length(arr_elements);
}

let main = id =>
  try(countDomNodes(id)) {
  | _ => 0
  };

switch%platform

switch%platform allows to conditionally execute code based on the platform. There are some cases where you need to run a specific code only on the server or only on the client.

switch%platform (Runtime.platform) {
| Server => print_endline("This prints to the terminal")
| Client => Js.log("This prints to the console")
};

Next

Externals and melange attributes