From 139cfe1426652204f4d940e4e96f4f8ac541eed4 Mon Sep 17 00:00:00 2001 From: Garry Hill Date: Tue, 5 Nov 2024 12:01:09 +0000 Subject: [PATCH] Use new header and param names --- packages/elixir-client/lib/electric/client.ex | 2 +- .../lib/electric/client/fetch/request.ex | 18 ++-- .../lib/electric/client/fetch/response.ex | 16 ++-- .../lib/electric/client/message.ex | 6 +- .../elixir-client/lib/electric/client/mock.ex | 12 +-- .../lib/electric/client/shape_definition.ex | 13 ++- .../lib/electric/client/stream.ex | 37 ++++---- .../{request_test.ex => request_test.exs} | 37 +++++++- .../electric/client/fetch/response_test.exs | 16 ++-- .../test/electric/client/mock_test.exs | 4 +- .../electric/client/shape_definition_test.exs | 8 +- .../test/electric/client_test.exs | 94 ++++++++++--------- 12 files changed, 148 insertions(+), 115 deletions(-) rename packages/elixir-client/test/electric/client/fetch/{request_test.ex => request_test.exs} (68%) diff --git a/packages/elixir-client/lib/electric/client.ex b/packages/elixir-client/lib/electric/client.ex index a893b5a3c3..41dee35d0c 100644 --- a/packages/elixir-client/lib/electric/client.ex +++ b/packages/elixir-client/lib/electric/client.ex @@ -154,7 +154,7 @@ defmodule Electric.Client do ] ) - @type shape_id :: String.t() + @type shape_handle :: String.t() @type cursor :: integer() @type update_mode :: :modified | :full @type column :: %{ diff --git a/packages/elixir-client/lib/electric/client/fetch/request.ex b/packages/elixir-client/lib/electric/client/fetch/request.ex index 961b0545a7..fd35b269b7 100644 --- a/packages/elixir-client/lib/electric/client/fetch/request.ex +++ b/packages/elixir-client/lib/electric/client/fetch/request.ex @@ -11,7 +11,7 @@ defmodule Electric.Client.Fetch.Request do defstruct [ :base_url, - :shape_id, + :shape_handle, :live, :shape, :next_cursor, @@ -30,7 +30,7 @@ defmodule Electric.Client.Fetch.Request do method: quote(do: :get | :head | :delete), base_url: quote(do: URI.t()), offset: quote(do: Electric.Client.Offset.t()), - shape_id: quote(do: Electric.Client.shape_id() | nil), + shape_handle: quote(do: Electric.Client.shape_handle() | nil), update_mode: quote(do: Electric.Client.update_mode()), live: quote(do: boolean()), next_cursor: quote(do: Electric.Client.cursor()), @@ -61,14 +61,14 @@ defmodule Electric.Client.Fetch.Request do {:via, Registry, {Electric.Client.Registry, {__MODULE__, request_id}}} end - defp request_id(%Client{fetch: {fetch_impl, _}}, %__MODULE__{shape_id: nil} = request) do + defp request_id(%Client{fetch: {fetch_impl, _}}, %__MODULE__{shape_handle: nil} = request) do %{base_url: base_url, shape: shape_definition} = request {fetch_impl, base_url, shape_definition} end defp request_id(%Client{fetch: {fetch_impl, _}}, %__MODULE__{} = request) do - %{base_url: base_url, offset: offset, live: live, shape_id: shape_id} = request - {fetch_impl, base_url, shape_id, Offset.to_tuple(offset), live} + %{base_url: base_url, offset: offset, live: live, shape_handle: shape_handle} = request + {fetch_impl, base_url, shape_handle, Offset.to_tuple(offset), live} end @doc """ @@ -76,8 +76,8 @@ defmodule Electric.Client.Fetch.Request do """ @spec url(t()) :: binary() def url(%__MODULE__{} = request, opts \\ []) do - %{base_url: base_url, shape: shape} = request - path = "/v1/shape/#{ShapeDefinition.url_table_name(shape)}" + %{base_url: base_url} = request + path = "/v1/shape" uri = URI.append_path(base_url, path) if Keyword.get(opts, :query, true) do @@ -96,7 +96,7 @@ defmodule Electric.Client.Fetch.Request do shape: shape, update_mode: update_mode, live: live?, - shape_id: shape_id, + shape_handle: shape_handle, offset: %Offset{} = offset, next_cursor: cursor, params: params @@ -106,7 +106,7 @@ defmodule Electric.Client.Fetch.Request do |> Map.merge(ShapeDefinition.params(shape)) |> Map.merge(%{"offset" => Offset.to_string(offset)}) |> Util.map_put_if("update_mode", to_string(update_mode), update_mode != :modified) - |> Util.map_put_if("shape_id", shape_id, is_binary(shape_id)) + |> Util.map_put_if("handle", shape_handle, is_binary(shape_handle)) |> Util.map_put_if("live", "true", live?) |> Util.map_put_if("cursor", cursor, !is_nil(cursor)) end diff --git a/packages/elixir-client/lib/electric/client/fetch/response.ex b/packages/elixir-client/lib/electric/client/fetch/response.ex index 07158f197b..c36710164a 100644 --- a/packages/elixir-client/lib/electric/client/fetch/response.ex +++ b/packages/elixir-client/lib/electric/client/fetch/response.ex @@ -4,7 +4,7 @@ defmodule Electric.Client.Fetch.Response do defstruct [ :status, :last_offset, - :shape_id, + :shape_handle, :schema, :next_cursor, body: [], @@ -16,7 +16,7 @@ defmodule Electric.Client.Fetch.Response do body: [map()], headers: %{String.t() => [String.t()]}, last_offset: nil | Client.Offset.t(), - shape_id: nil | Client.shape_id(), + shape_handle: nil | Client.shape_handle(), schema: nil | Client.schema(), next_cursor: nil | Client.cursor() } @@ -27,7 +27,7 @@ defmodule Electric.Client.Fetch.Response do status: status, headers: decode_headers(headers), body: body, - shape_id: decode_shape_id(headers), + shape_handle: decode_shape_handle(headers), last_offset: decode_offset(headers), schema: decode_schema(headers), next_cursor: decode_next_cursor(headers) @@ -38,13 +38,13 @@ defmodule Electric.Client.Fetch.Response do Map.new(headers, fn {k, v} -> {k, List.wrap(v)} end) end - defp decode_shape_id(%{"electric-shape-id" => shape_id}) do - unlist(shape_id) + defp decode_shape_handle(%{"electric-handle" => shape_handle}) do + unlist(shape_handle) end - defp decode_shape_id(_headers), do: nil + defp decode_shape_handle(_headers), do: nil - defp decode_offset(%{"electric-chunk-last-offset" => offset}) do + defp decode_offset(%{"electric-offset" => offset}) do offset |> unlist() |> Client.Offset.from_string!() end @@ -60,7 +60,7 @@ defmodule Electric.Client.Fetch.Response do defp unlist([]), do: nil defp unlist(value), do: value - defp decode_next_cursor(%{"electric-next-cursor" => cursor}) do + defp decode_next_cursor(%{"electric-cursor" => cursor}) do cursor |> unlist() |> String.to_integer() end diff --git a/packages/elixir-client/lib/electric/client/message.ex b/packages/elixir-client/lib/electric/client/message.ex index 8d323f959a..5e5d14b337 100644 --- a/packages/elixir-client/lib/electric/client/message.ex +++ b/packages/elixir-client/lib/electric/client/message.ex @@ -104,12 +104,12 @@ defmodule Electric.Client.Message do ``` """ - @enforce_keys [:shape_id, :offset, :schema] + @enforce_keys [:shape_handle, :offset, :schema] - defstruct [:shape_id, :offset, :schema] + defstruct [:shape_handle, :offset, :schema] @type t :: %__MODULE__{ - shape_id: Client.shape_id(), + shape_handle: Client.shape_handle(), offset: Offset.t(), schema: Client.schema() } diff --git a/packages/elixir-client/lib/electric/client/mock.ex b/packages/elixir-client/lib/electric/client/mock.ex index 8a8629baf1..d0ff235ad0 100644 --- a/packages/elixir-client/lib/electric/client/mock.ex +++ b/packages/elixir-client/lib/electric/client/mock.ex @@ -17,7 +17,7 @@ defmodule Electric.Client.Mock do status: 200, schema: %{id: %{type: "int8"}, name: %{type: "text"}}, last_offset: Client.Offset.first(), - shape_id: "users-1", + shape_handle: "users-1", body: Electric.Client.Mock.transaction(users, operation: :insert) ) @@ -82,7 +82,7 @@ defmodule Electric.Client.Mock do | {:headers, %{String.t() => String.t() | [String.t(), ...]}} | {:body, [map()]} | {:schema, Client.schema()} - | {:shape_id, Client.shape_id()} + | {:shape_handle, Client.shape_handle()} | {:last_offset, Client.Offset.t()} @type response_opts :: [response_opt()] @@ -197,21 +197,21 @@ defmodule Electric.Client.Mock do headers: headers(opts[:headers] || []), body: jsonify(opts[:body] || []), schema: Keyword.get(opts, :schema, nil), - shape_id: Keyword.get(opts, :shape_id, nil), + shape_handle: Keyword.get(opts, :shape_handle, nil), last_offset: Keyword.get(opts, :last_offset, nil) } end @spec headers([ - {:shape_id, Client.shape_id()} + {:shape_handle, Client.shape_handle()} | {:last_offset, Client.Offset.t()} | {:schema, Client.schema()} ]) :: %{String.t() => [String.t()]} def headers(args) do %{} - |> put_optional_header("electric-shape-id", args[:shape_id]) + |> put_optional_header("electric-handle", args[:shape_handle]) |> put_optional_header( - "electric-chunk-last-offset", + "electric-offset", args[:last_offset], &Client.Offset.to_string/1 ) diff --git a/packages/elixir-client/lib/electric/client/shape_definition.ex b/packages/elixir-client/lib/electric/client/shape_definition.ex index d3ebb1424a..9b6d4e564c 100644 --- a/packages/elixir-client/lib/electric/client/shape_definition.ex +++ b/packages/elixir-client/lib/electric/client/shape_definition.ex @@ -53,8 +53,6 @@ defmodule Electric.Client.ShapeDefinition do @type option :: unquote(NimbleOptions.option_typespec(@schema)) @type options :: [option()] - @quot "%22" - @spec new(String.t(), options()) :: {:ok, t()} | {:error, term()} @doc """ Create a `ShapeDefinition` for the given `table_name`. @@ -94,7 +92,7 @@ defmodule Electric.Client.ShapeDefinition do "my_app.my_table" iex> ShapeDefinition.url_table_name(ShapeDefinition.new!("my table", namespace: "my app")) - "%22my app%22.%22my table%22" + ~s["my app"."my table"] """ @spec url_table_name(t()) :: String.t() @@ -116,9 +114,9 @@ defmodule Electric.Client.ShapeDefinition do defp quote_table_name(name) do IO.iodata_to_binary([ - @quot, - :binary.replace(name, ~s["], ~s[#{@quot}#{@quot}], [:global]), - @quot + ?", + :binary.replace(name, ~s["], ~s[""], [:global]), + ?" ]) end @@ -126,8 +124,9 @@ defmodule Electric.Client.ShapeDefinition do @spec params(t()) :: Electric.Client.Fetch.Request.params() def params(%__MODULE__{} = shape) do %{where: where, columns: columns} = shape + table_name = url_table_name(shape) - %{} + %{table: table_name} |> Util.map_put_if("where", where, is_binary(where)) |> Util.map_put_if("columns", fn -> Enum.join(columns, ",") end, is_list(columns)) end diff --git a/packages/elixir-client/lib/electric/client/stream.ex b/packages/elixir-client/lib/electric/client/stream.ex index 3089993fa7..e9206a6da0 100644 --- a/packages/elixir-client/lib/electric/client/stream.ex +++ b/packages/elixir-client/lib/electric/client/stream.ex @@ -18,7 +18,7 @@ defmodule Electric.Client.Stream do up_to_date?: false, update_mode: :modified, offset: Offset.before_all(), - shape_id: nil, + shape_handle: nil, next_cursor: nil, state: :init, opts: %{} @@ -92,7 +92,7 @@ defmodule Electric.Client.Stream do up_to_date?: boolean(), offset: Offset.t(), update_mode: Client.update_mode(), - shape_id: nil | Client.shape_id(), + shape_handle: nil | Client.shape_handle(), state: :init | :stream | :done, opts: opts() } @@ -150,12 +150,13 @@ defmodule Electric.Client.Stream do defp handle_response(%Fetch.Response{status: status} = resp, stream) when status in 200..299 do start_offset = stream.offset - shape_id = shape_id!(resp) + shape_handle = shape_handle!(resp) final_offset = last_offset(resp, stream.offset) next_cursor = resp.next_cursor %{value_mapper_fun: value_mapper_fun} = - stream = handle_schema(resp, %{stream | shape_id: shape_id, next_cursor: next_cursor}) + stream = + handle_schema(resp, %{stream | shape_handle: shape_handle, next_cursor: next_cursor}) resp.body |> List.wrap() @@ -178,7 +179,7 @@ defmodule Electric.Client.Stream do offset = last_offset(resp, stream.offset) stream - |> reset(shape_id(resp)) + |> reset(shape_handle(resp)) |> buffer(Enum.flat_map(resp.body, &Message.parse(&1, offset, value_mapper_fun))) |> dispatch() end @@ -208,7 +209,7 @@ defmodule Electric.Client.Stream do resume_message = %Message.ResumeMessage{ schema: stream.schema, offset: offset, - shape_id: stream.shape_id + shape_handle: stream.shape_handle } {:halt, {offset, %{stream | buffer: :queue.in(resume_message, stream.buffer), state: :done}}} @@ -218,7 +219,7 @@ defmodule Electric.Client.Stream do resume_message = %Message.ResumeMessage{ schema: stream.schema, offset: stream.offset, - shape_id: stream.shape_id + shape_handle: stream.shape_handle } {msgs, %{stream | buffer: :queue.in(resume_message, stream.buffer), state: :done}} @@ -241,14 +242,14 @@ defmodule Electric.Client.Stream do shape: shape, up_to_date?: up_to_date?, update_mode: update_mode, - shape_id: shape_id, + shape_handle: shape_handle, offset: offset, next_cursor: cursor } = stream Client.request(client, offset: offset, - shape_id: shape_id, + shape_handle: shape_handle, update_mode: update_mode, live: up_to_date?, next_cursor: cursor, @@ -266,11 +267,11 @@ defmodule Electric.Client.Stream do Fetch.Request.request(stream.client, request) end - defp reset(stream, shape_id) do + defp reset(stream, shape_handle) do %{ stream | offset: Offset.before_all(), - shape_id: shape_id, + shape_handle: shape_handle, up_to_date?: false, buffer: :queue.new(), schema: nil, @@ -282,13 +283,13 @@ defmodule Electric.Client.Stream do %{stream | buffer: Enum.reduce(msgs, stream.buffer, &:queue.in/2)} end - defp shape_id!(resp) do - shape_id(resp) || - raise Client.Error, message: "Missing electric-shape-id header", resp: resp + defp shape_handle!(resp) do + shape_handle(resp) || + raise Client.Error, message: "Missing electric-handle header", resp: resp end - defp shape_id(%Fetch.Response{shape_id: shape_id}) do - shape_id + defp shape_handle(%Fetch.Response{shape_handle: shape_handle}) do + shape_handle end defp last_offset(%Fetch.Response{last_offset: %Offset{} = offset}, _offset) do @@ -323,9 +324,9 @@ defmodule Electric.Client.Stream do end defp resume(%{opts: %{resume: %Message.ResumeMessage{} = resume}} = stream) do - %{shape_id: shape_id, offset: offset, schema: schema} = resume + %{shape_handle: shape_handle, offset: offset, schema: schema} = resume - generate_value_mapper(schema, %{stream | shape_id: shape_id, offset: offset}) + generate_value_mapper(schema, %{stream | shape_handle: shape_handle, offset: offset}) end defp resume(stream) do diff --git a/packages/elixir-client/test/electric/client/fetch/request_test.ex b/packages/elixir-client/test/electric/client/fetch/request_test.exs similarity index 68% rename from packages/elixir-client/test/electric/client/fetch/request_test.ex rename to packages/elixir-client/test/electric/client/fetch/request_test.exs index 53b8503ab0..7cc193a7c6 100644 --- a/packages/elixir-client/test/electric/client/fetch/request_test.ex +++ b/packages/elixir-client/test/electric/client/fetch/request_test.exs @@ -13,7 +13,7 @@ defmodule Electric.Client.Fetch.RequestTest do request = Client.request(client!(), offset: Client.Offset.new(1234, 1), - shape_id: "my-shape", + shape_handle: "my-shape", live: true, next_cursor: 123_948, shape: Client.shape!("my_table") @@ -23,7 +23,7 @@ defmodule Electric.Client.Fetch.RequestTest do {:ok, uri} = URI.new(url) assert %{ - path: "/v1/shape/my_table", + path: "/v1/shape", scheme: "https", host: "cloud.electric.com", query: query @@ -32,10 +32,37 @@ defmodule Electric.Client.Fetch.RequestTest do params = URI.decode_query(query) assert %{ + "table" => "my_table", "cursor" => "123948", "live" => "true", "offset" => "1234_1", - "shape_id" => "my-shape" + "handle" => "my-shape" + } = params + end + + test "wraps table names in quotes" do + request = + Client.request(client!(), + offset: Client.Offset.new(1234, 1), + shape_handle: "my-shape", + live: true, + next_cursor: 123_948, + shape: Client.shape!("my table", namespace: "Wobbly") + ) + + url = Request.url(request) + {:ok, uri} = URI.new(url) + + assert %{query: query} = uri + + params = URI.decode_query(query) + + assert %{ + "table" => ~s["Wobbly"."my table"], + "cursor" => "123948", + "live" => "true", + "offset" => "1234_1", + "handle" => "my-shape" } = params end @@ -43,7 +70,7 @@ defmodule Electric.Client.Fetch.RequestTest do request = Client.request(client!(), offset: Client.Offset.new(1234, 1), - shape_id: "my-shape", + shape_handle: "my-shape", live: true, next_cursor: 123_948, shape: Client.shape!("my_table"), @@ -65,7 +92,7 @@ defmodule Electric.Client.Fetch.RequestTest do request = Client.request(client!(), offset: Client.Offset.new(1234, 1), - shape_id: "my-shape", + shape_handle: "my-shape", live: true, next_cursor: 123_948, shape: Client.shape!("my_table", columns: columns) diff --git a/packages/elixir-client/test/electric/client/fetch/response_test.exs b/packages/elixir-client/test/electric/client/fetch/response_test.exs index 01e8b1a6bd..a64675e0c6 100644 --- a/packages/elixir-client/test/electric/client/fetch/response_test.exs +++ b/packages/elixir-client/test/electric/client/fetch/response_test.exs @@ -7,10 +7,10 @@ defmodule Electric.Client.Fetch.ResponseTest do schema = %{id: %{type: "int8"}} headers = %{ - "electric-shape-id" => "1234987-2349827349", - "electric-chunk-last-offset" => "29827_3", + "electric-handle" => "1234987-2349827349", + "electric-offset" => "29827_3", "electric-schema" => Jason.encode!(schema), - "electric-next-cursor" => "2394829387" + "electric-cursor" => "2394829387" } # headers are normalised lists of values @@ -19,7 +19,7 @@ defmodule Electric.Client.Fetch.ResponseTest do assert %{ status: 200, headers: ^expected_headers, - shape_id: "1234987-2349827349", + shape_handle: "1234987-2349827349", last_offset: %Electric.Client.Offset{tx: 29827, op: 3}, schema: ^schema, next_cursor: 2_394_829_387 @@ -30,16 +30,16 @@ defmodule Electric.Client.Fetch.ResponseTest do schema = %{id: %{type: "int8"}} headers = %{ - "electric-shape-id" => ["1234987-2349827349"], - "electric-chunk-last-offset" => ["29827_3"], + "electric-handle" => ["1234987-2349827349"], + "electric-offset" => ["29827_3"], "electric-schema" => [Jason.encode!(schema)], - "electric-next-cursor" => ["2394829387"] + "electric-cursor" => ["2394829387"] } assert %{ status: 200, headers: ^headers, - shape_id: "1234987-2349827349", + shape_handle: "1234987-2349827349", last_offset: %Electric.Client.Offset{tx: 29827, op: 3}, schema: ^schema, next_cursor: 2_394_829_387 diff --git a/packages/elixir-client/test/electric/client/mock_test.exs b/packages/elixir-client/test/electric/client/mock_test.exs index 37a191f56a..8d213b803e 100644 --- a/packages/elixir-client/test/electric/client/mock_test.exs +++ b/packages/elixir-client/test/electric/client/mock_test.exs @@ -30,7 +30,7 @@ defmodule Electric.Client.MockTest do status: 200, schema: %{id: %{type: "int8"}}, last_offset: Offset.new(0, 0), - shape_id: "my-shape", + shape_handle: "my-shape", body: [ Client.Mock.change(value: %{id: "1111"}), Client.Mock.change(value: %{id: "2222"}), @@ -43,7 +43,7 @@ defmodule Electric.Client.MockTest do status: 200, schema: %{id: %{type: "int8"}}, last_offset: Offset.new(0, 0), - shape_id: "my-shape", + shape_handle: "my-shape", body: [ Client.Mock.change(value: %{id: "4444"}), Client.Mock.up_to_date() diff --git a/packages/elixir-client/test/electric/client/shape_definition_test.exs b/packages/elixir-client/test/electric/client/shape_definition_test.exs index 1aedaa5ada..22287262ac 100644 --- a/packages/elixir-client/test/electric/client/shape_definition_test.exs +++ b/packages/elixir-client/test/electric/client/shape_definition_test.exs @@ -19,10 +19,10 @@ defmodule Electric.Client.ShapeDefinitionTest do describe "table_name/1" do test "quotes the name if it contains characters other than [0-9a-z_-]" do assert ~s|my_table29| = ShapeDefinition.url_table_name(ShapeDefinition.new!("my_table29")) - assert ~s|%22my table%22| = ShapeDefinition.url_table_name(ShapeDefinition.new!("my table")) - assert ~s|%22MyTable%22| = ShapeDefinition.url_table_name(ShapeDefinition.new!("MyTable")) + assert ~s|"my table"| = ShapeDefinition.url_table_name(ShapeDefinition.new!("my table")) + assert ~s|"MyTable"| = ShapeDefinition.url_table_name(ShapeDefinition.new!("MyTable")) - assert ~s|%22My%22%22Table%22%22%22| = + assert ~s|"My""Table"""| = ShapeDefinition.url_table_name(ShapeDefinition.new!(~s|My"Table"|)) end @@ -32,7 +32,7 @@ defmodule Electric.Client.ShapeDefinitionTest do ShapeDefinition.new!("my_table", namespace: "my_schema") ) - assert ~s|%22my schema%22.%22my table%22| = + assert ~s|"my schema"."my table"| = ShapeDefinition.url_table_name( ShapeDefinition.new!("my table", namespace: "my schema") ) diff --git a/packages/elixir-client/test/electric/client_test.exs b/packages/elixir-client/test/electric/client_test.exs index 3b3a2c2f5c..6f81c4ec29 100644 --- a/packages/elixir-client/test/electric/client_test.exs +++ b/packages/elixir-client/test/electric/client_test.exs @@ -250,10 +250,10 @@ defmodule Electric.ClientTest do conn |> Plug.Conn.put_resp_content_type("application/json") - |> put_optional_header("electric-shape-id", opts[:shape_id]) - |> put_optional_header("electric-chunk-last-offset", opts[:last_offset]) + |> put_optional_header("electric-handle", opts[:shape_handle]) + |> put_optional_header("electric-offset", opts[:last_offset]) |> put_optional_header("electric-schema", opts[:schema]) - |> put_optional_header("electric-next-cursor", opts[:cursor]) + |> put_optional_header("electric-cursor", opts[:cursor]) |> Plug.Conn.resp(status, body) end @@ -294,18 +294,18 @@ defmodule Electric.ClientTest do %{ "-1" => [ &bypass_resp(&1, body1, - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "1_0", schema: schema ) ], "1_0" => [ &bypass_resp(&1, "", - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "1_0" ), &bypass_resp(&1, body2, - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "2_0" ) ] @@ -316,7 +316,8 @@ defmodule Electric.ClientTest do parent = self() Bypass.expect(ctx.bypass, fn - %{request_path: "/v1/shape/my_table", query_params: %{"offset" => offset}} = conn -> + %{request_path: "/v1/shape", query_params: %{"table" => "my_table", "offset" => offset}} = + conn -> fun = Agent.get_and_update(responses, fn resps -> Map.get_and_update(resps, offset, fn [fun | rest] -> {fun, rest} end) @@ -376,7 +377,7 @@ defmodule Electric.ClientTest do %{ "-1" => [ &bypass_resp(&1, body1, - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "1_0", cursor: "299292", schema: schema @@ -385,7 +386,7 @@ defmodule Electric.ClientTest do "1_0" => [ fn %{query_params: %{"cursor" => "299292"}} = conn -> bypass_resp(conn, body2, - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "2_0" ) end @@ -397,7 +398,8 @@ defmodule Electric.ClientTest do parent = self() Bypass.expect(ctx.bypass, fn - %{request_path: "/v1/shape/my_table", query_params: %{"offset" => offset}} = conn -> + %{request_path: "/v1/shape", query_params: %{"table" => "my_table", "offset" => offset}} = + conn -> fun = Agent.get_and_update(responses, fn resps -> Map.get_and_update(resps, offset, fn [fun | rest] -> {fun, rest} end) @@ -452,12 +454,12 @@ defmodule Electric.ClientTest do %{ {"-1", nil, false} => [ &bypass_resp(&1, Jason.encode!(body1), - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "1_0", schema: Jason.encode!(%{"id" => %{type: "text"}}) ), &bypass_resp(&1, Jason.encode!(body1), - shape_id: "my-shape-2", + shape_handle: "my-shape-2", last_offset: "1_0", schema: Jason.encode!(%{"id" => %{type: "text"}}) ) @@ -481,7 +483,7 @@ defmodule Electric.ClientTest do end) ++ [ &bypass_resp(&1, Jason.encode!(body2), - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "2_0" ) ] @@ -492,15 +494,15 @@ defmodule Electric.ClientTest do Bypass.expect(ctx.bypass, fn %{ - request_path: "/v1/shape/my_table", - query_params: %{"offset" => offset} = query_params + request_path: "/v1/shape", + query_params: %{"table" => "my_table", "offset" => offset} = query_params } = conn -> - shape_id = Map.get(query_params, "shape_id", nil) + shape_handle = Map.get(query_params, "handle", nil) live = Map.get(query_params, "live", "false") == "true" fun = Agent.get_and_update(responses, fn resps -> - Map.get_and_update(resps, {offset, shape_id, live}, fn [fun | rest] -> + Map.get_and_update(resps, {offset, shape_handle, live}, fn [fun | rest] -> {fun, rest} end) end) @@ -542,12 +544,12 @@ defmodule Electric.ClientTest do %{ {"-1", nil} => [ &bypass_resp(&1, Jason.encode!(body1), - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "1_0", schema: Jason.encode!(%{"id" => %{type: "text"}}) ), &bypass_resp(&1, Jason.encode!(body1), - shape_id: "my-shape-2", + shape_handle: "my-shape-2", last_offset: "1_0", schema: Jason.encode!(%{"id" => %{type: "text"}}) ) @@ -557,7 +559,7 @@ defmodule Electric.ClientTest do status: 400 ), &bypass_resp(&1, Jason.encode!(body1), - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "2_0" ) ] @@ -569,14 +571,14 @@ defmodule Electric.ClientTest do Bypass.expect(ctx.bypass, fn %{ - request_path: "/v1/shape/my_table", - query_params: %{"offset" => offset} = query_params + request_path: "/v1/shape", + query_params: %{"table" => "my_table", "offset" => offset} = query_params } = conn -> - shape_id = Map.get(query_params, "shape_id", nil) + shape_handle = Map.get(query_params, "handle", nil) fun = Agent.get_and_update(responses, fn resps -> - Map.get_and_update(resps, {offset, shape_id}, fn [fun | rest] -> {fun, rest} end) + Map.get_and_update(resps, {offset, shape_handle}, fn [fun | rest] -> {fun, rest} end) end) send(parent, {:offset, offset}) @@ -617,14 +619,14 @@ defmodule Electric.ClientTest do %{ {"-1", nil} => [ &bypass_resp(&1, Jason.encode!(body1), - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "1_0", schema: Jason.encode!(%{"id" => %{type: "text"}}) ) ], {"-1", "my-shape-2"} => [ &bypass_resp(&1, Jason.encode!(body1), - shape_id: "my-shape-2", + shape_handle: "my-shape-2", last_offset: "1_0", schema: Jason.encode!(%{"id" => %{type: "text"}}) ) @@ -632,7 +634,7 @@ defmodule Electric.ClientTest do {"1_0", "my-shape"} => [ &bypass_resp(&1, Jason.encode!([%{"headers" => %{"control" => "must-refetch"}}]), status: 409, - shape_id: "my-shape-2" + shape_handle: "my-shape-2" ) ] } @@ -643,14 +645,14 @@ defmodule Electric.ClientTest do Bypass.expect(ctx.bypass, fn %{ - request_path: "/v1/shape/my_table", - query_params: %{"offset" => offset} = query_params + request_path: "/v1/shape", + query_params: %{"table" => "my_table", "offset" => offset} = query_params } = conn -> - shape_id = Map.get(query_params, "shape_id", nil) + shape_handle = Map.get(query_params, "handle", nil) fun = Agent.get_and_update(responses, fn resps -> - Map.get_and_update(resps, {offset, shape_id}, fn [fun | rest] -> {fun, rest} end) + Map.get_and_update(resps, {offset, shape_handle}, fn [fun | rest] -> {fun, rest} end) end) send(parent, {:offset, offset}) @@ -702,17 +704,21 @@ defmodule Electric.ClientTest do end defp bypass_response(ctx, responses) do - path = "/v1/shape/#{ctx.table_name}" + %{table_name: table_name} = ctx + path = "/v1/shape" parent = self() Bypass.expect( ctx.bypass, - fn %{request_path: ^path, query_params: %{"offset" => offset} = query_params} = conn -> - shape_id = Map.get(query_params, "shape_id", nil) + fn %{ + request_path: ^path, + query_params: %{"table" => ^table_name, "offset" => offset} = query_params + } = conn -> + shape_handle = Map.get(query_params, "handle", nil) fun = Agent.get_and_update(responses, fn resps -> - Map.get_and_update(resps, {offset, shape_id}, fn [fun | rest] -> {fun, rest} end) + Map.get_and_update(resps, {offset, shape_handle}, fn [fun | rest] -> {fun, rest} end) end) send(parent, {:offset, offset}) @@ -759,20 +765,20 @@ defmodule Electric.ClientTest do %{ {"-1", nil} => [ &bypass_resp(&1, Jason.encode!(body1), - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "1_0", schema: Jason.encode!(%{"id" => %{type: "text"}}) ) ], {"1_0", "my-shape"} => [ &bypass_resp(&1, Jason.encode!(body2), - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "2_0" ) ], {"2_0", "my-shape"} => [ &bypass_resp(&1, Jason.encode!(body3), - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "3_0" ) ] @@ -797,7 +803,7 @@ defmodule Electric.ClientTest do }, up_to_date(2, 0), %ResumeMessage{ - shape_id: "my-shape", + shape_handle: "my-shape", offset: offset(2, 0), schema: %{id: %{type: "text"}} } @@ -829,13 +835,13 @@ defmodule Electric.ClientTest do %{ {"2_0", "my-shape"} => [ &bypass_resp(&1, Jason.encode!(body3), - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "3_0" ) ], {"3_0", "my-shape"} => [ &bypass_resp(&1, Jason.encode!(body4), - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "4_0" ) ] @@ -846,7 +852,7 @@ defmodule Electric.ClientTest do bypass_response(ctx, responses) resume = %ResumeMessage{ - shape_id: "my-shape", + shape_handle: "my-shape", offset: offset(2, 0), schema: %{id: %{type: "text"}} } @@ -899,7 +905,7 @@ defmodule Electric.ClientTest do %{ {"-1", nil} => [ &bypass_resp(&1, Jason.encode!(body1), - shape_id: "my-shape", + shape_handle: "my-shape", last_offset: "1234_0", schema: Jason.encode!(%{"id" => %{type: "text"}, "value" => %{type: "text"}}) ) @@ -939,7 +945,7 @@ defmodule Electric.ClientTest do offset: %Electric.Client.Offset{tx: 1234, op: 0} }, %ResumeMessage{ - shape_id: "my-shape", + shape_handle: "my-shape", offset: offset(1234, 0), schema: %{id: %{type: "text"}} }