Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side....

70
Mixing in Elixir to Build Search Friday, 16 March Code BEAM SF

Transcript of Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side....

Page 1: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Mixing in Elixir to Build SearchFriday, 16 March

Code BEAM SF

Page 2: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

AdrianSoftware EngineerSearch & Personalization

Building all things search at Teachers Pay Teacherswww.teacherspayteachers.com

● github/twitter: @drincruz● drincruz.com

Page 3: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

We're the World's Most Popular Online Marketplace for Original Educational Resources

Page 4: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql
Page 5: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Mixing in Elixir

What does that mean?

Page 6: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Mixing in Elixir

What does that mean?Breaking the monolith...

Page 7: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Mixing in Elixir

What does that mean?Breaking the monolith...by porting pages piecemeal

Page 8: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Let’s talk about search

Page 9: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Let’s talk about search

Page 10: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Let’s start searching...

Page 11: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql
Page 12: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql
Page 13: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Search suggestions

Page 14: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Seller suggestions

Page 15: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Resource suggestions

Page 16: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

JSON returned from autosuggest

Page 17: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Process to power autosuggest

Page 18: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Process to power autosuggest

Built on Phoenix

Page 19: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

autosuggest

A standalone service built as a proof-of-concept for Elixir adoption at TPT

Page 20: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

autosuggest

A standalone service built as a proof-of-concept for Elixir adoption at TPT

Thanks to Samira for owning this project

Page 21: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Now the information retrieval

The search part

Page 22: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

previous way to serve search (simplified)

Page 23: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

previous way to serve search (simplified)

search

Page 24: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

previous way to serve search (simplified)

search

product

Page 25: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

previous way to serve search (simplified)

search

product

home

Page 26: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

previous way to serve search (simplified)

search

product

home

Et cetera. ...everything else :)

Page 27: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Implementing more elixir

A GraphQL API

Page 28: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Mixing in GraphQL

Page 29: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Mixing in GraphQL And then this gave us more tools to debug and analyze search

Page 30: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Mixing in GraphQL And then this gave us more tools to debug and analyze search

graphiql

Page 31: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Mixing in GraphQL And then this gave us more tools to debug and analyze search

graphiql

Search replayerBuilt with Elixir running Cowboy

Page 32: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Mixing in GraphQL And then this gave us more tools to debug and analyze search

graphiql

Search replayerBuilt with Elixir running Cowboy

Recommendations Side-by-side

Page 33: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Mixing in GraphQL And then this gave us more tools to debug and analyze search

graphiql

Search replayerBuilt with Elixir running Cowboy

Recommendations Side-by-side

And lots of personalization tooling

Page 34: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

graphiql

Page 35: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

graphiql

graphql query

Page 36: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

graphiql

results

Page 37: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

graphiql

Just with graphiql, search became easier to debug

Page 38: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

graphiql

Just with graphiql, search became easier to debug

And also easier to test

Page 39: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

test "facet on grade group should return grades in the resultFacets" do

query = """

query {

searchProducts(query: "", limit: 5, facets: ["Grade-Level/1-2"]) {

resultFacets {

grades {

id

}

}

}

}

"""

Page 40: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

assert {:ok, result} = Poison.Parser.parse(response.body)

assert Map.has_key?(result, "data")

assert not Map.has_key?(result, "errors")

search_results = result["data"]["searchProducts"]

obs_grades = search_results["resultFacets"]["grades"]

assert length(obs_grades) == 2

assert Enum.member?(obs_grades, %{"id" => "Grades_First"})

assert Enum.member?(obs_grades, %{"id" => "Grades_Second"})

end

Page 41: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Testing our Search terms also became easier!

Page 42: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Testing our Search terms also became easier!

We convert our search string into an AST (abstract syntax tree)

Page 43: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

TptApi.SearchText.from_string("this and that")

{:ok, {:ast_and, [ast_word: 'this', ast_word: 'and', ast_word: 'that']}}

Typical unquoted text string

Page 44: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

TptApi.SearchText.from_string(~s("this and that"))

{:ok, {:ast_quoted, 'this and that'}}

Quoted string

Page 45: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

TptApi.SearchText.from_string("this -that")

{:ok, {:ast_and, [ast_word: 'this', ast_not: {:ast_word, 'that'}]}}

Advanced negative searching

Page 46: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

test "successfully parse nice inputs", %{nice_inputs: inputs} do

for {input, expected} <- inputs do

assert {:ok, expected} == TptApi.SearchText.from_string(input)

end

end

We test a list of different search terms we support

Page 47: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

[...

{"fractions \"cheese bananas\"", {:ast_and,

[ast_word: 'fractions', ast_quoted: 'cheese bananas']}},

{"fractions -\"cheese bananas\"", {:ast_and,

[ast_word: 'fractions', ast_not: {:ast_quoted, 'cheese bananas'}]}},

{"fractions \"cheese or bananas\"", {:ast_and,

[{:ast_word, 'fractions'}, {:ast_quoted, 'cheese or bananas'}]}},

...]

That list looks similar to the following

Page 48: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Search analytics

Search is not easy

Page 49: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Search analytics

Search is not easyBut that’s why we A/B test and look at a lot of data

Page 50: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Internal eval is important

Page 51: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Internal eval is important

replays Search or Browse graphql queries and gets aggregate data

Page 52: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Internal eval is important

Side by Side search comparisons for A/B tests

Page 53: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

facets

|> Enum.map(&(Task.async(Replayer.Browse, :do_browse, [&1, cfg.a_url_params])))

|> Enum.map(&Task.await/1)

|> update_with_rank()

Example on Replayer of Top 100 Browses

Page 54: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

# Snippet of GraphQL query in Replayer.Browse.do_browse/2 totalCount,

results{

type,

url,

name,

description(maxLength: 300),

images{large},

downloads,

views,

votes,

abbreviatedGrades,

ratings{scoreAverage, count},

sold,

price,

isFree,

author{id, name, icon{location}}

# … more code

Page 55: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

*WAD: weighted average discountFull disclosure: the data here does not represent what is in production :)

Page 56: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Mixing Elixir for tooling

Replaced PHP tooling

Page 57: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Mixing Elixir for tooling

Replaced PHP toolingAlso a great learning project for onboarding

Page 58: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Mixing Elixir for tooling

Replaced PHP toolingAlso a great learning project for onboarding

Thanks to Louis for bootstrapping this project

Page 59: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Related searches

An SEO initiative

Page 60: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Related searches

An SEO initiativeBuilt easily in the new elixir platform

Page 61: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

(refresher)

Autosuggest endpoint

Page 62: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

(refresher)

Autosuggest endpoint GraphQL API

Page 63: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

defp run_query(path) do

uri =

Application.get_env(:tpt_api, :autosuggest_api_root)

<> "/#{path}"

|> URI.parse()

HTTPUtil.get_json!(uri, [], [timeout: @timeout, recv_timeout:

@timeout])

end

Page 64: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Now on our Search pages in React

Page 65: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Elixir Mixed In

Page 66: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Elixir Mixed In

● Autosuggest helped push adoption forward

Page 67: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Elixir Mixed In

● Autosuggest helped push adoption forward● GraphQL API provided great decoupling benefits

Page 68: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Elixir Mixed In

● Autosuggest helped push adoption forward● GraphQL API provided great decoupling benefits● Having engineers bootstrap Elixir projects provide good learning

Page 69: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Elixir Mixed In

● Autosuggest helped push adoption forward● GraphQL API provided great decoupling benefits● Having engineers bootstrap Elixir projects provide good learning● engineering.teacherspayteachers.com

Page 70: Mixing in Elixir to Build Search...Built with Elixir running Cowboy Recommendations Side-by-side. Mixing in GraphQL And then this gave us more tools to debug and analyze search graphiql

Thank You Code BEAM SF!

@drincruzhttps://www.teacherspayteachers.com/Careers