defmodule BerrypodWeb.ErrorHTML do @moduledoc """ This module is invoked by your endpoint in case of errors on HTML requests. See config/config.exs. """ use BerrypodWeb, :html alias Berrypod.Pages alias Berrypod.Pages.Defaults alias Berrypod.Settings alias Berrypod.Settings.ThemeSettings alias Berrypod.Media alias Berrypod.Products alias Berrypod.Theme.{CSSCache, CSSGenerator} def render("404.html", assigns) do render_error_page( assigns, "404", "Page not found", "Sorry, we couldn't find the page you're looking for." ) end def render("500.html", assigns) do render_error_page( assigns, "500", "Server error", "Something went wrong on our end. Please try again later." ) end def render(template, _assigns) do Phoenix.Controller.status_message_from_template(template) end defp render_error_page(assigns, error_code, error_title, error_description) do site_live = safe_load(&Settings.site_live?/0) || false assigns = assigns |> Map.put(:error_code, error_code) |> Map.put(:error_title, error_title) |> Map.put(:error_description, error_description) |> Map.put(:site_live, site_live) if site_live do render_themed_error(assigns) else render_minimal_error(assigns) end end defp render_minimal_error(assigns) do ~H""" {@error_code} - {@error_title}

{@error_code}

{@error_title}

{@error_description}

""" end defp render_themed_error(assigns) do {theme_settings, generated_css} = load_theme_data() logo_image = safe_load(&Media.get_logo/0) header_image = safe_load(&Media.get_header/0) categories = safe_load(fn -> Products.list_categories() end) || [] page = safe_load(fn -> Pages.get_page("error") end) || Defaults.for_slug("error") assigns = assigns |> Map.put(:theme_settings, theme_settings) |> Map.put(:site_name, safe_load(&Settings.site_name/0) || "Store Name") |> Map.put(:site_description, safe_load(&Settings.site_description/0) || "") |> Map.put(:generated_css, generated_css) |> Map.put(:logo_image, logo_image) |> Map.put(:header_image, header_image) |> Map.put(:categories, categories) |> Map.put(:mode, :shop) |> Map.put(:cart_items, []) |> Map.put(:cart_count, 0) |> Map.put(:cart_subtotal, "£0.00") |> Map.put(:page, page) |> Map.put( :header_nav_items, load_nav("header_nav", &BerrypodWeb.ThemeHook.default_header_nav/0) ) |> Map.put( :footer_nav_items, load_nav("footer_nav", &BerrypodWeb.ThemeHook.default_footer_nav/0) ) # Load block data (e.g. products for featured_products block) extra = safe_load(fn -> Pages.load_block_data(page.blocks, assigns) end) || %{} assigns = Map.merge(assigns, extra) ~H""" {@error_code} - {@error_title}
""" end defp load_theme_data do try do theme_settings = Settings.get_theme_settings() generated_css = case CSSCache.get() do {:ok, css} -> css :miss -> css = CSSGenerator.generate(theme_settings, &BerrypodWeb.Endpoint.static_path/1) CSSCache.put(css) css end {theme_settings, generated_css} rescue _ -> {%ThemeSettings{}, ""} end end defp safe_load(fun) do try do fun.() rescue _ -> nil end end defp load_nav(key, default_fn) do case safe_load(fn -> Settings.get_setting(key) end) do items when is_list(items) -> items _ -> default_fn.() end end end