defmodule Dust.Testing do @moduledoc """ Test helpers for applications that use Dust. In :manual test mode, Dust uses a memory cache and no server connection. Use these functions to control Dust state in tests. """ @doc "Populate the cache with known state. get/enum will return this data." def seed(store, entries) when is_map(entries) do Enum.each(entries, fn {path, value} -> type = detect_type(value) Dust.SyncEngine.seed_entry(store, path, value, type) end) :ok end @doc "Fire an event through the subscriber pipeline as if the server sent it. Synchronous." def emit(store, path, opts \\ []) do op = Keyword.get(opts, :op, :set) value = Keyword.get(opts, :value) meta = Keyword.get(opts, :meta, %{}) event = %{ "store" => store, "path" => path, "op" => to_string(op), "value" => value, "store_seq" => System.unique_integer([:positive]), "device_id" => "test", "client_op_id" => "test_#{System.unique_integer([:positive])}" } |> Map.merge(if meta != %{}, do: %{"meta" => meta}, else: %{}) Dust.SyncEngine.handle_server_event(store, event) :ok end @doc "Control what Dust.status/1 returns." def set_status(store, connection_status, opts \\ []) do store_seq = Keyword.get(opts, :store_seq, 0) Dust.SyncEngine.set_status(store, connection_status) capabilities = opts |> Keyword.take([:permissions, :scopes, :store_access]) |> Map.new() if map_size(capabilities) > 0 do Dust.SyncEngine.set_capabilities(store, capabilities) end if store_seq > 0 do Dust.SyncEngine.set_store_seq(store, store_seq) end :ok end @doc "Build an event map for testing subscriber modules in isolation." def build_event(store, path, opts \\ []) do %{ store: store, path: path, op: Keyword.get(opts, :op, :set), value: Keyword.get(opts, :value), store_seq: Keyword.get(opts, :store_seq, 1), committed: true, source: :server, device_id: "test", client_op_id: "test" } end defp detect_type(v) when is_boolean(v), do: "boolean" defp detect_type(v) when is_map(v), do: "map" defp detect_type(v) when is_binary(v), do: "string" defp detect_type(v) when is_integer(v), do: "integer" defp detect_type(v) when is_float(v), do: "float" defp detect_type(nil), do: "null" defp detect_type(_), do: "string" end