Skip to content

Commit

Permalink
wip refactor document_test.exs
Browse files Browse the repository at this point in the history
  • Loading branch information
jaeyson committed Jan 13, 2025
1 parent 887ebd3 commit 389bed7
Show file tree
Hide file tree
Showing 22 changed files with 3,124 additions and 2,656 deletions.
5 changes: 5 additions & 0 deletions .gitattributes
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
* text=auto

*.ex diff=elixir
*.exs diff=elixir

22 changes: 19 additions & 3 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,7 @@ jobs:

- name: Start Typesense
run: |
docker run -d \
docker run -id \
-p 8108:8108 \
--name typesense \
-v /tmp/typesense-data:/data \
Expand All @@ -81,8 +81,24 @@ jobs:
--analytics-minute-rate-limit=100 \
--enable-cors
- name: Curl Typesense
run: sleep 1 && curl http://localhost:8108/health
- name: Wait for Typesense to be healthy
shell: bash
run: |
start_time=$(date +%s)
timeout=30
counter=0
until curl -s http://localhost:8108/health | grep -q '"ok":true'; do
if [ $counter -eq $timeout ]; then
echo "Timed out waiting for Typesense to be healthy"
exit 1
fi
echo "Waiting for Typesense to be healthy..."
sleep 1
counter=$((counter + 1))
done
end_time=$(date +%s)
elapsed=$((end_time - start_time))
echo "Typesense healthcheck elapsed: ${elapsed}s"
- name: Setup Elixir/OTP
uses: erlef/setup-beam@v1
Expand Down
24 changes: 5 additions & 19 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,31 +7,17 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0

## major.minor.patch (yyyy.mm.dd)

## 0.8.0 (2024.12.xx)
## 1.0.0 (2025.01.xx)

### Added

* Use [`open_api_typesense` library](https://github.com/jaeyson/open_api_typesense)
* Moar teztsss for coverage.
* External docs link for example of using another HTTP client.
* Test coverage

### Changed

* Internal implementation and used `OpenApiTypesense`

### Removed

* This version has lots of backwards-incompatible
changes that the following Modules are removed,
in favor of using [`OpenApiTypesense`](https://github.com/jaeyson/open_api_typesense):
- `Cluster`
- `Collection`
- `Document`
- `HttpClient`
- `Search`

### Added

* `{:error, String.t()}` type for `Search.search/3`
* Backwards-incompatible changes, in favor of using [`OpenApiTypesense`](https://github.com/jaeyson/open_api_typesense).
* Bump dependencies

## 0.7.3 (2024.11.11)

Expand Down
167 changes: 138 additions & 29 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,52 +1,84 @@
<p align="center">
<img alt="Typesense logo" src="https://github.com/typesense/typesense/raw/main/assets/typesense_logo.svg" width="298">
<img alt="lightning-bolt.svg" src="https://github.com/jaeyson/ex_typesense/raw/main/assets/lightning-bolt.svg" width="200">
<source media="(prefers-color-scheme: dark)" srcset="https://github.com/elixir-lang/elixir-lang.github.com/raw/main/images/logo/logo-dark.png">
<img alt="Elixir logo" src="https://github.com/elixir-lang/elixir-lang.github.com/raw/main/images/logo/logo.png" width="200">
<img
alt="Typesense logo"
src="https://github.com/typesense/typesense/raw/main/assets/typesense_logo.svg"
width="298">
<img
alt="lightning bolt svg"
src="https://github.com/jaeyson/ex_typesense/raw/main/assets/lightning-bolt.svg"
width="200">
<source
media="(prefers-color-scheme: dark)"
srcset="https://github.com/elixir-lang/elixir-lang.github.com/raw/main/images/logo/logo-dark.png">
<img
alt="Elixir logo"
src="https://github.com/elixir-lang/elixir-lang.github.com/raw/main/images/logo/logo.png"
width="200">
</p>

<h1 align="center">ExTypesense</h1>

<p align="center">
<a href="https://hex.pm/packages/ex_typesense">
<img src="https://img.shields.io/hexpm/v/ex_typesense">
<img
alt="ex_typesense latest version badge"
src="https://img.shields.io/hexpm/v/ex_typesense"
>
</a>
<a href="https://hexdocs.pm/ex_typesense">
<img src="https://img.shields.io/badge/hex-docs-lightgreen.svg">
<img
alt="ex_typesense hexdocs badge"
src="https://img.shields.io/badge/hex-docs-lightgreen.svg"
>
</a>
<a href="https://github.com/jaeyson/ex_typesense/actions/workflows/ci.yml">
<img src="https://github.com/jaeyson/ex_typesense/actions/workflows/ci.yml/badge.svg">
<img
alt="Github actions workflow badge"
src="https://github.com/jaeyson/ex_typesense/actions/workflows/ci.yml/badge.svg"
>
</a>
<a href="https://hexdocs.pm/ex_typesense/license.html">
<img src="https://img.shields.io/hexpm/l/ex_typesense">
<img
alt="ex_typesense license badge"
src="https://img.shields.io/hexpm/l/ex_typesense"
>
</a>
<a href="https://typesense.org/docs/27.1/api">
<img src="https://img.shields.io/badge/Typesense-v27.1-darkblue">
<img
alt="Latest Typesense version compatible badge"
src="https://img.shields.io/badge/Typesense-v27.1-darkblue"
>
</a>
<a href="https://coveralls.io/github/jaeyson/ex_typesense?branch=main">
<img src="https://coveralls.io/repos/github/jaeyson/ex_typesense/badge.svg?branch=main">
<img
alt="Test coverage badge"
src="https://coveralls.io/repos/github/jaeyson/ex_typesense/badge.svg?branch=main"
>
</a>
</p>

[Typesense](https://typesense.org) client for [Elixir](https://elixir-lang.org) with support for your Ecto schemas.

> Under the hood, this library utilizes [open_api_typesense](https://github.com/jaeyson/open_api_typesense) to make sure it adheres to [Typesense's OpenAPI spec](https://github.com/typesense/typesense-api-spec).
> Under the hood, this library utilizes [open_api_typesense](https://github.com/jaeyson/open_api_typesense)
> to make sure it adheres to [Typesense's OpenAPI spec](https://github.com/typesense/typesense-api-spec).
> **Note**: `0.8.0` contains **LOTS** of breaking changes.
> **Note**: `1.0.0` contains **LOTS** of breaking changes.
> **Note**: Breaking changes if you're upgrading from `0.3.x` to `0.5.x` versions and above.
## Installation

ExTypesense requires Elixir `~> 1.14.x`. Read the [Changelog](CHANGELOG.md) for all available releases and requirements. This library is published to both [Hex.pm](https://hex.pm/ex_typesense) and [GitHub ](https://github.com/jaeyson/ex_typesense.git) repository.
ExTypesense requires Elixir `~> 1.14.x`. Read the [Changelog](CHANGELOG.md) for all available
releases and requirements. This library is published to both [Hex.pm](https://hex.pm/ex_typesense)
and [GitHub ](https://github.com/jaeyson/ex_typesense.git) repository.

Add `:ex_typesense` to your list of dependencies in the Elixir project config file, `mix.exs`:

```elixir
def deps do
[
# From default Hex package manager
{:ex_typesense, "~> 0.8"}
{:ex_typesense, "~> 1.0"}

# Or from GitHub repository, if you want the latest greatest from main branch
{:ex_typesense, git: "https://github.com/jaeyson/ex_typesense.git"}
Expand All @@ -70,7 +102,8 @@ Otherwise, go to step #1 if you're using [Cloud hosted](https://cloud.typesense.

### 1. Add credential to config

After you have setup a [local](./guides/running_local_typesense.md) Typesense or [Cloud hosted](https://cloud.typesense.org) instance, there are 2 ways to set the credentials:
After you have setup a [local](./guides/running_local_typesense.md) Typesense or
[Cloud hosted](https://cloud.typesense.org) instance, there are 2 ways to set the credentials:

#### Option 1: Set credentials via config (e.g. `config/runtime.exs`)

Expand All @@ -79,28 +112,28 @@ You can set the following config details to the config file:
```elixir
# e.g. config/runtime.exs
if config_env() == :prod do # if you'll use this in prod environment
config :ex_typesense,
config :open_api_typesense,
api_key: "xyz",
host: "localhost",
port: 8108,
scheme: "http",
options: %{}
scheme: "http"
...
```

> **Note**: The `options` key can be used to pass additional configuration options such as custom Finch instance or receive timeout settings. You can add any options supported by Req here. For more details check [Req documentation](https://hexdocs.pm/req/Req.Steps.html#run_finch/1-request-options).
> **Note**: The `options` key can be used to pass additional configuration options such as custom
Finch instance or receive timeout settings. You can add any options supported by Req here. For
more details check [Req documentation](https://hexdocs.pm/req/Req.Steps.html#run_finch/1-request-options).

> **Note**: If you use this for adding tests in your app, you might want to add this in `config/test.exs`:
For Cloud hosted, you can generate and obtain the credentials from cluster instance admin interface:

```elixir
config :ex_typesense,
config :open_api_typesense,
api_key: "credential", # Admin API key
host: "111222333aaabbbcc-9.x9.typesense.net", # Nodes
port: 443,
scheme: "https",
options: %{}
scheme: "https"
```

#### Option 2: Set credentials from a map
Expand Down Expand Up @@ -169,9 +202,24 @@ conn =
ExTypesense.search(conn, collection_name, query)
```

Or just plain map

```elixir
conn = %{
host: "127.0.0.1",
api_key: "xyz",
port: 8108,
scheme: "http"
}

ExTypesense.health(conn)
```

### 2. Create a collection

There are 2 ways to create a collection, either via [Ecto schema](https://hexdocs.pm/ecto/Ecto.Schema.html) or using map ([an Elixir data type](https://hexdocs.pm/elixir/keywords-and-maps.html#maps-as-key-value-pairs)):
There are 2 ways to create a collection, either via
[Ecto schema](https://hexdocs.pm/ecto/Ecto.Schema.html) or using map
([an Elixir data type](https://hexdocs.pm/elixir/keywords-and-maps.html#maps-as-key-value-pairs)):

#### Option 1: using Ecto

Expand Down Expand Up @@ -209,10 +257,11 @@ defmodule Person do

@impl ExTypesense
def get_field_types do
primary_field = __MODULE__.__schema__(:source) <> "_id"
name = __MODULE__.__schema__(:source)
primary_field = name <> "_id"

%{
# Or might as well just write persons_id instead. Up to you.
name: name,
default_sorting_field: primary_field,
fields: [
%{name: primary_field, type: "int32"},
Expand Down Expand Up @@ -281,16 +330,76 @@ mix api.gen default priv/open_api.yml

### Use non-default Finch adapter

For instance, in a scenario where an application has multiple Finch pools configured for different services, a developer might want to specify a particular Finch pool for the `HttpClient` to use. This can be achieved by configuring the options as follows:
For instance, in a scenario where an application has multiple Finch pools configured for
different services, a developer might want to specify a particular Finch pool for the
`HttpClient` to use. This can be achieved by configuring the options as follows:

```elixir
config :ex_typesense,
config :open_api_typesense,
api_key: "XXXXXX",
#...
options: [finch: MyApp.CustomFinch]
options: [finch: MyApp.CustomFinch] # <- add options
```

In this example, `MyApp.CustomFinch` is a custom Finch pool that the developer has
configured with specific connection options or other settings that differ from the
default Finch pool.

## Using another client

By default this library is using [Req](https://hexdocs.pm/req/readme.html). In order to use another HTTP client,
OpenApiTypesense has a callback function ([Behaviours](https://hexdocs.pm/elixir/typespecs.html#behaviours))
called `request` that contains 2 args:

1. `conn`: your connection map
2. `params`: payload, header, and client-related stuffs.

> #### `conn` and `params` {: .info}
>
> you can change the name `conn` and/or `params` however you want,
> since it's just a variable.
Here's a custom client example (`:httpc`) in order to match the usage:

```elixir
defmodule MyApp.CustomClient do
def request(conn, params) do
uri = %URI{
scheme: conn.scheme,
host: conn.host,
port: conn.port,
path: params.url,
query: URI.encode_query(params[:query] || %{})
}

[{content_type, _schema}] = params.request

request = {
URI.to_string(uri),
[{~c"x-typesense-api-key", String.to_charlist(conn.api_key)}],
String.to_charlist(content_type),
Jason.encode!(params.body)
}

{:ok, {_status, _header, body}} = :httpc.request(params.method, request, [], [])

Jason.decode!(body)
end
end
```

Then add your client in your config file:

```elixir
config :open_api_typesense,
api_key: "credential", # Admin API key
host: "111222333aaabbbcc-9.x9.typesense.net", # Nodes
port: 443,
scheme: "https",
client: MyApp.CustomClient # <- add this
```

In this example, `MyApp.CustomFinch` is a custom Finch pool that the developer has configured with specific connection options or other settings that differ from the default Finch pool.
Visit this docs for further [examples]()

## License

Expand Down
5 changes: 2 additions & 3 deletions config/config.exs
Original file line number Diff line number Diff line change
@@ -1,10 +1,9 @@
import Config

if config_env() in [:dev, :test] do
config :ex_typesense,
config :open_api_typesense,
api_key: "xyz",
host: "localhost",
port: 8108,
scheme: "http",
options: %{}
scheme: "http"
end
Loading

0 comments on commit 389bed7

Please sign in to comment.