In software development and computer systems there has always been a conflict between the little “humanity” of the engines and the interactions with it.

Social analysis brings us an undeniable statement: we are all different.

Spice Girls

Although fashion displays a cyclic model in which seasons and styles are standardized for most people, we must always consider that the user has his/her personal tastes and that this should be reflected in their interaction with computer systems. The same should happen with search engines and their results, no search is the same as any person is, so we must try to make people feel unique and special when performing their searches so they have a feeling that the search engine “understands” them.

To achieve this, at Empathy.co we have developed Context! It ’s a customisation system that will allow us to generate an user profile, so that the searches fit the client’s tastes and preferences. You can find more about Context functionalities here.

How to apply contextualisation to your searches

The first step is to _activate the contextualisation for your searches. O_ur integrations experts will cset up the most interesting fields for each use case and, from that moment, interactions and searches of each user will generate a totally anonymous preference profile that will allow personalising the results.

So … tell me what you want, what you really, really want.

In the following visual example we can see how Mel C and Vicky achieve different results in the search for jeans thanks to that customisation.

All credits to Paula Natal

So … how do I access contextualisation data?

These data, also called affinity model, can be obtained thanks to the anonymous user identifier that is generated when entering e-commerce and is divided into two parts; user preferences, related to the features of the products seen and purchased during each search, and a list of the products visited by the user. In the following script we can access this data with a small and simple script made in GO:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
package main

import (
    "fmt"
    "net/http"
    "net/url"
    "encoding/json"
    )

const (
    //Header
    contentType        = "Content-Type"
    applicationJson    = "application/json"

    //URLs
    userContextUrl     = "https://api.empathybroker.com/contextsearch/v2/usercontext/all/{your_site}"
    userAffModelUrl    = "https://api.empathybroker.com/contextsearch/v2/usercontext/preferences/{your_site}"
    userLastProdUrl    = "https://api.empathybroker.com/contextsearch/v2/usercontext/products/{your_site}"

    //Request constants
    userParam          = "user"
    queryParam         = "query"
    rowsParam          = "rows"
)

var httpClient = &http.Client{}

//Handle errors in http request and print status and headers
func handleHttpResponse(resp *http.Response, err error) {
    //Handle error
    if err != nil {
        panic(err)
    }

    //Print details
    fmt.Println("Http Response Status: ", resp.Status)
    fmt.Println("Http Response Headers: ", resp.Header)

    //Print response
    var result map[string]interface{}
    json.NewDecoder(resp.Body).Decode(&result)
    fmt.Println("Response: ", result)
}

//Method to get all the user affinity model preferences
func getUserAffinityModel(user string, rows string) {

    baseUrl, err := url.Parse(userAffModelUrl)
    if err != nil {
        fmt.Println("Malformed URL: ", err.Error())
        return
    }

    //Complete query params
    params := url.Values{}
    params.Add(userParam, user)
    params.Add(rowsParam, rows)

    // Add query params to the URL
    baseUrl.RawQuery = params.Encode()

     //Do http request
    req, _ := http.NewRequest(http.MethodGet, baseUrl.String(), nil)
    req.Header.Set(contentType, applicationJson)
     
    resp, err := httpClient.Do(req)
    handleHttpResponse(resp, err)
}

//Method to get the user last products viewed
func getUserLastProductsViewed(user string, query string, rows string) {

    baseUrl, err := url.Parse(userAffModelUrl)
    if err != nil {
        fmt.Println("Malformed URL: ", err.Error())
        return
    }

    //Complete query params
    params := url.Values{}
    params.Add(userParam, user)
    params.Add(queryParam, query)
    params.Add(rowsParam, rows)

    // Add query params to the URL
    baseUrl.RawQuery = params.Encode()

     //Do http request
    req, _ := http.NewRequest(http.MethodGet, baseUrl.String(), nil)
    req.Header.Set(contentType, applicationJson)
     
    resp, err := httpClient.Do(req)
    handleHttpResponse(resp, err)
}


//Method to get all the user personalisation model
func getUserContext(user string, query string, rows string) {

    baseUrl, err := url.Parse(userContextUrl)
    if err != nil {
        fmt.Println("Malformed URL: ", err.Error())
        return
    }

    //Complete query params
    params := url.Values{}
    params.Add(userParam, user)
    params.Add(queryParam, query)
    params.Add(rowsParam, rows)

    // Add query params to the URL
    baseUrl.RawQuery = params.Encode()

     //Do http request
    req, _ := http.NewRequest(http.MethodGet, baseUrl.String(), nil)
    req.Header.Set(contentType, applicationJson)
     
    resp, err := httpClient.Do(req)
    handleHttpResponse(resp, err)
}

func main() { 
    //Get user affinity model
    getUserAffinityModel("userId", "2")

    //Get user last products viewed
    getUserLastProductsViewed("userId", "query", "2")

    //Get complete user context
    getUserContext("userId", "query", "2")
}

Our customisation system also includes a system that allows you to customise without the user personal information, since we will analyze the general data of the searches and their interactions for ALL users. In this way we will generate a general affinity model as well as a list of the most viewed products for each search, so that we can obtain these preferences for each search and offer the user much more adjusted results to the trends. In the following script we can access this data with a small and simple script made in GO:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
package main

import (
    "fmt"
    "net/http"
    "net/url"
    "encoding/json"
    )

const (
    //Header
    contentType        = "Content-Type"
    applicationJson    = "application/json"

    //URLs
    queryContextUrl     = "https://api.empathybroker.com/contextsearch/v2/querycontext/all/{your_site}"
    queryAffModelUrl    = "https://api.empathybroker.com/contextsearch/v2/querycontext/attributes/{your_site}"
    queryLastProdUrl    = "https://api.empathybroker.com/contextsearch/v2/querycontext/products/{your_site}"

    //Request constants
    queryParam         = "query"
    rowsParam          = "rows"
)

var httpClient = &http.Client{}

//Handle errors in http request and print status and headers
func handleHttpResponse(resp *http.Response, err error) {
    //Handle error
    if err != nil {
        panic(err)
    }

    //Print details
    fmt.Println("Http Response Status: ", resp.Status)
    fmt.Println("Http Response Headers: ", resp.Header)

    //Print response
    var result map[string]interface{}
    json.NewDecoder(resp.Body).Decode(&result)
    fmt.Println("Response: ", result)
}

//Method to get all the query affinity model preferences
func getQueryAffinityModel(query string, rows string) {

    baseUrl, err := url.Parse(queryAffModelUrl)
    if err != nil {
        fmt.Println("Malformed URL: ", err.Error())
        return
    }

    //Complete query params
    params := url.Values{}
    params.Add(queryParam, query)
    params.Add(rowsParam, rows)

    // Add query params to the URL
    baseUrl.RawQuery = params.Encode()

     //Do http request
    req, _ := http.NewRequest(http.MethodGet, baseUrl.String(), nil)
    req.Header.Set(contentType, applicationJson)
     
    resp, err := httpClient.Do(req)
    handleHttpResponse(resp, err)
}

//Method to get the query top products viewed
func getQueryLastProductsViewed(query string, rows string) {

    baseUrl, err := url.Parse(queryLastProdUrl)
    if err != nil {
        fmt.Println("Malformed URL: ", err.Error())
        return
    }

    //Complete query params
    params := url.Values{}
    params.Add(queryParam, query)
    params.Add(rowsParam, rows)

    // Add query params to the URL
    baseUrl.RawQuery = params.Encode()

     //Do http request
    req, _ := http.NewRequest(http.MethodGet, baseUrl.String(), nil)
    req.Header.Set(contentType, applicationJson)
     
    resp, err := httpClient.Do(req)
    handleHttpResponse(resp, err)
}


//Method to get all the query personalisation model
func getQueryContext(query string, rows string) {

    baseUrl, err := url.Parse(queryContextUrl)
    if err != nil {
        fmt.Println("Malformed URL: ", err.Error())
        return
    }

    //Complete query params
    params := url.Values{}
    params.Add(queryParam, query)
    params.Add(rowsParam, rows)

    // Add query params to the URL
    baseUrl.RawQuery = params.Encode()

     //Do http request
    req, _ := http.NewRequest(http.MethodGet, baseUrl.String(), nil)
    req.Header.Set(contentType, applicationJson)
     
    resp, err := httpClient.Do(req)
    handleHttpResponse(resp, err)
}

func main() { 
    //Get query affinity model
    getQueryAffinityModel("query", "2")

    //Get query last products viewed
    getQueryLastProductsViewed("query", "2")

    //Get complete query context
    getQueryContext("query", "2")
}

Sounds good right? This service can be consumed and integrated into your own search system, but it is also fully integrated into ours, so you can start using contextualisation now!

Of course, listening to a great hit like this this will help you find better results for sure!

Spice girls clapping