From c97726d8b854a8322f5b64885119f53f34600548 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Eray=20Ayd=C4=B1n?= Date: Tue, 3 Feb 2026 21:42:10 +0300 Subject: [PATCH 1/4] chore: improve sync.sh script Add strict error handling, retry logic, and reduce code duplication. Related-Task: INTER-1793 --- sync.sh | 30 +++++++++++++++++++++++------- 1 file changed, 23 insertions(+), 7 deletions(-) diff --git a/sync.sh b/sync.sh index 5125b396..f2ef8ba4 100755 --- a/sync.sh +++ b/sync.sh @@ -1,6 +1,13 @@ #!/bin/bash +set -euo pipefail -curl -o ./res/fingerprint-server-api.yaml https://fingerprintjs.github.io/fingerprint-pro-server-api-openapi/schemas/fingerprint-server-api-compact.yaml +defaultBaseUrl="https://fingerprintjs.github.io/fingerprint-pro-server-api-openapi" +schemaUrl="${1:-$defaultBaseUrl/schemas/fingerprint-server-api-compact.yaml}" +examplesBaseUrl="${2:-$defaultBaseUrl/examples}" + +mkdir -p ./res + +curl -fSL --retry 3 -o ./res/fingerprint-server-api.yaml "$schemaUrl" examplesList=( 'get_visits_200_limit_1.json' @@ -34,12 +41,21 @@ sharedExamplesList=( '429_error_too_many_requests.json' ) -for example in ${examplesList[*]}; do - curl -o ./test/mocks/"$example" https://fingerprintjs.github.io/fingerprint-pro-server-api-openapi/examples/"$example" -done +baseDestination="./test/mocks" +mkdir -p "$baseDestination" + +download_example() { + local subpath="$1" + shift + local examples=("$@") + + for example in "${examples[@]}"; do + echo "Downloading $example" + curl -fSL --retry 3 -o "$baseDestination/$example" "$examplesBaseUrl/$subpath$example" + done +} -for example in ${sharedExamplesList[*]}; do - curl -o ./test/mocks/"$example" https://fingerprintjs.github.io/fingerprint-pro-server-api-openapi/examples/shared/"$example" -done +download_example "" "${examplesList[@]}" +download_example "shared/" "${sharedExamplesList[@]}" ./generate.sh From c1d3781888f2bbb979abd8fbeba35739b921ed5c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Eray=20Ayd=C4=B1n?= Date: Tue, 3 Feb 2026 23:15:16 +0300 Subject: [PATCH 2/4] chore: update sync.sh to use Server API v4 Update sync script to fetch v4 schema and examples. Removes deprecated v3-only mocks. Related-Task: INTER-1795 --- res/fingerprint-server-api.yaml | 3789 +++++++---------- sync.sh | 66 +- test/mocks/errors/400_visitor_id_invalid.json | 2 +- .../mocks/errors/400_visitor_id_required.json | 2 +- .../mocks/errors/403_feature_not_enabled.json | 2 +- .../errors/403_secret_api_key_not_found.json | 6 + .../errors/403_secret_api_key_required.json | 6 + test/mocks/errors/403_token_not_found.json | 6 - test/mocks/errors/403_token_required.json | 6 - test/mocks/errors/403_wrong_region.json | 2 +- test/mocks/errors/404_visitor_not_found.json | 2 +- test/mocks/errors/429_too_many_requests.json | 2 +- test/mocks/events/get_event_200.json | 282 ++ .../events/search/get_event_search_200.json | 287 ++ .../update_event_multiple_fields_request.json | 7 + .../update_event_one_field_request.json | 3 + test/mocks/get_event_200.json | 354 -- test/mocks/get_event_200_all_errors.json | 164 - .../get_event_200_botd_failed_error.json | 69 - test/mocks/get_event_200_extra_fields.json | 91 - ...event_200_identification_failed_error.json | 23 - ...get_event_200_too_many_requests_error.json | 16 - .../get_event_200_with_broken_format.json | 301 -- .../get_event_200_with_unknown_field.json | 299 -- test/mocks/get_event_search_200.json | 354 -- test/mocks/get_visitors_200_limit_1.json | 61 - test/mocks/get_visitors_200_limit_500.json | 3030 ------------- test/mocks/get_visitors_400_bad_request.json | 3 - test/mocks/get_visitors_403_forbidden.json | 3 - .../get_visitors_429_too_many_requests.json | 3 - .../get_related_visitors_200.json | 10 - .../get_related_visitors_200_empty.json | 3 - .../update_event_multiple_fields_request.json | 7 - .../mocks/update_event_one_field_request.json | 3 - test/mocks/webhook.json | 293 -- test/mocks/webhook/webhook_event.json | 282 ++ 36 files changed, 2498 insertions(+), 7341 deletions(-) create mode 100644 test/mocks/errors/403_secret_api_key_not_found.json create mode 100644 test/mocks/errors/403_secret_api_key_required.json delete mode 100644 test/mocks/errors/403_token_not_found.json delete mode 100644 test/mocks/errors/403_token_required.json create mode 100644 test/mocks/events/get_event_200.json create mode 100644 test/mocks/events/search/get_event_search_200.json create mode 100644 test/mocks/events/update_event_multiple_fields_request.json create mode 100644 test/mocks/events/update_event_one_field_request.json delete mode 100644 test/mocks/get_event_200.json delete mode 100644 test/mocks/get_event_200_all_errors.json delete mode 100644 test/mocks/get_event_200_botd_failed_error.json delete mode 100644 test/mocks/get_event_200_extra_fields.json delete mode 100644 test/mocks/get_event_200_identification_failed_error.json delete mode 100644 test/mocks/get_event_200_too_many_requests_error.json delete mode 100644 test/mocks/get_event_200_with_broken_format.json delete mode 100644 test/mocks/get_event_200_with_unknown_field.json delete mode 100644 test/mocks/get_event_search_200.json delete mode 100644 test/mocks/get_visitors_200_limit_1.json delete mode 100644 test/mocks/get_visitors_200_limit_500.json delete mode 100644 test/mocks/get_visitors_400_bad_request.json delete mode 100644 test/mocks/get_visitors_403_forbidden.json delete mode 100644 test/mocks/get_visitors_429_too_many_requests.json delete mode 100644 test/mocks/related-visitors/get_related_visitors_200.json delete mode 100644 test/mocks/related-visitors/get_related_visitors_200_empty.json delete mode 100644 test/mocks/update_event_multiple_fields_request.json delete mode 100644 test/mocks/update_event_one_field_request.json delete mode 100644 test/mocks/webhook.json create mode 100644 test/mocks/webhook/webhook_event.json diff --git a/res/fingerprint-server-api.yaml b/res/fingerprint-server-api.yaml index 71a4fa75..8da52a0c 100644 --- a/res/fingerprint-server-api.yaml +++ b/res/fingerprint-server-api.yaml @@ -1,14 +1,14 @@ -openapi: 3.0.3 +openapi: 3.1.1 info: - title: Fingerprint Server API + title: Server API description: > - Fingerprint Server API allows you to search, update, and delete - identification events in a server environment. It can be used for data - exports, decision-making, and data analysis scenarios. + Fingerprint Server API allows you to get, search, and update Events in a + server environment. It can be used for data exports, decision-making, and + data analysis scenarios. Server API is intended for server-side usage, it's not intended to be used from the client side, whether it's a browser or a mobile device. - version: '3' + version: '4' contact: name: Fingerprint Support email: support@fingerprint.com @@ -25,37 +25,30 @@ tags: description: API documentation url: https://dev.fingerprint.com/reference/pro-server-api servers: - - url: https://api.fpjs.io + - url: https://api.fpjs.io/v4 description: Global - - url: https://eu.api.fpjs.io + - url: https://eu.api.fpjs.io/v4 description: EU - - url: https://ap.api.fpjs.io + - url: https://ap.api.fpjs.io/v4 description: Asia (Mumbai) security: - - ApiKeyHeader: [] - - ApiKeyQuery: [] + - bearerAuth: [] paths: - /events/{request_id}: + /events/{event_id}: get: tags: - Fingerprint operationId: getEvent - summary: Get event by request ID + summary: Get an event by event ID description: > Get a detailed analysis of an individual identification event, including - Smart Signals. + Smart Signals. - Please note that the response includes mobile signals (e.g. `rootApps`) - even if the request originated from a non-mobile platform. - It is highly recommended that you **ignore** the mobile signals for such - requests. - - - Use `requestId` as the URL path parameter. This API method is scoped to - a request, i.e. all returned information is by `requestId`. + Use `event_id` as the URL path parameter. This API method is scoped to a + request, i.e. all returned information is by `event_id`. parameters: - - name: request_id + - name: event_id in: path required: true schema: @@ -63,14 +56,32 @@ paths: description: >- The unique [identifier](https://dev.fingerprint.com/reference/get-function#requestid) - of each identification request. + of each identification request (`requestId` can be used in its + place). + - name: ruleset_id + in: query + required: false + schema: + type: string + description: > + The ID of the ruleset to evaluate against the event, producing the + action to take for this event. + + The resulting action is returned in the `rule_action` attribute of + the response. responses: '200': description: OK. content: application/json: schema: - $ref: '#/components/schemas/EventsGetResponse' + $ref: '#/components/schemas/Event' + '400': + description: Bad request. The event Id provided is not valid. + content: + application/json: + schema: + $ref: '#/components/schemas/ErrorResponse' '403': description: Forbidden. Access to this API is denied. content: @@ -78,45 +89,64 @@ paths: schema: $ref: '#/components/schemas/ErrorResponse' '404': - description: >- - Not found. The request ID cannot be found in this application's - data. + description: Not found. The event Id cannot be found in this workspace's data. + content: + application/json: + schema: + $ref: '#/components/schemas/ErrorResponse' + '429': + description: Too Many Requests. The request is throttled. + content: + application/json: + schema: + $ref: '#/components/schemas/ErrorResponse' + '500': + description: Workspace error. content: application/json: schema: $ref: '#/components/schemas/ErrorResponse' - put: + patch: tags: - Fingerprint operationId: updateEvent - summary: Update an event with a given request ID + summary: Update an event description: > - Change information in existing events specified by `requestId` or *flag + Change information in existing events specified by `event_id` or *flag suspicious events*. - When an event is created, it is assigned `linkedId` and `tag` submitted - through the JS agent parameters. This information might not be available - on the client so the Server API allows for updating the attributes after - the fact. + When an event is created, it can be assigned `linked_id` and `tags` + submitted through the JS agent parameters. + This information might not have been available on the client initially, + so the Server API permits updating these attributes after the fact. - **Warning** It's not possible to update events older than 10 days. + + **Warning** It's not possible to update events older than one month. + + + **Warning** Trying to update an event immediately after creation may + temporarily result in an + + error (HTTP 409 Conflict. The event is not mutable yet.) as the event is + fully propagated across our systems. In such a case, simply retry the + request. parameters: - - name: request_id + - name: event_id in: path required: true schema: type: string description: >- The unique event - [identifier](https://dev.fingerprint.com/reference/get-function#requestid). + [identifier](https://dev.fingerprint.com/reference/get-function#event_id). requestBody: required: true content: application/json: schema: - $ref: '#/components/schemas/EventsUpdateRequest' + $ref: '#/components/schemas/EventUpdate' responses: '200': description: OK. @@ -133,9 +163,7 @@ paths: schema: $ref: '#/components/schemas/ErrorResponse' '404': - description: >- - Not found. The request ID cannot be found in this application's - data. + description: Not found. The event Id cannot be found in this workspace's data. content: application/json: schema: @@ -146,29 +174,68 @@ paths: application/json: schema: $ref: '#/components/schemas/ErrorResponse' - /events/search: + /events: get: tags: - Fingerprint operationId: searchEvents - summary: Get events via search + summary: Search events description: > - Search for identification events, including Smart Signals, using - multiple filtering criteria. If you don't provide `start` or `end` - parameters, the default search range is the last 7 days. + ## Search + + + The `/v4/events` endpoint provides a convenient way to search for past + events based on specific parameters. Typical use cases and queries + include: - Please note that events include mobile signals (e.g. `rootApps`) even if - the request originated from a non-mobile platform. We recommend you - **ignore** mobile signals for such requests. + - Searching for events associated with a single `visitor_id` within a + time range to get historical behavior of a visitor. + + - Searching for events associated with a single `linked_id` within a + time range to get all events associated with your internal account + identifier. + + - Excluding all bot traffic from the query (`good` and `bad` bots) + + + If you don't provide `start` or `end` parameters, the default search + range is the **last 7 days**. + + + ### Filtering events with the `suspect` flag + + + The `/v4/events` endpoint unlocks a powerful method for fraud protection + analytics. The `suspect` flag is exposed in all events where it was + previously set by the update API. + + + You can also apply the `suspect` query parameter as a filter to find all + potentially fraudulent activity that you previously marked as `suspect`. + This helps identify patterns of fraudulent behavior. + + + ### Environment scoping + + + If you use a secret key that is scoped to an environment, you will only + get events associated with the same environment. With a workspace-scoped + environment, you will get events from all environments. + + + Smart Signals not activated for your workspace or are not included in + the response. parameters: - name: limit in: query - required: true + required: false schema: type: integer format: int32 minimum: 1 + maximum: 100 + default: 10 example: 10 description: | Limit the number of events returned. @@ -177,24 +244,22 @@ paths: schema: type: string description: > - Use `pagination_key` to get the next page of results. + Use `pagination_key` to get the next page of results. - When more results are available (e.g., you requested up to 200 - results for your search using `limit`, but there are more than 200 - events total matching your request), the `paginationKey` top-level - attribute is added to the response. The key corresponds to the - `timestamp` of the last returned event. In the following request, - use that value in the `pagination_key` parameter to get the next - page of results: + When more results are available (e.g., you requested up to 100 + results for your query using `limit`, but there are more than 100 + events total matching your request), the `pagination_key` field is + added to the response. The key corresponds to the `timestamp` of the + last returned event. In the following request, use that value in the + `pagination_key` parameter to get the next page of results: 1. First request, returning most recent 200 events: `GET - api-base-url/events/search?limit=200` + api-base-url/events?limit=100` - 2. Use `response.paginationKey` to get the next page of results: - `GET - api-base-url/events/search?limit=200&pagination_key=1740815825085` + 2. Use `response.pagination_key` to get the next page of results: + `GET api-base-url/events?limit=100&pagination_key=1740815825085` - name: visitor_id in: query schema: @@ -202,7 +267,7 @@ paths: description: > Unique [visitor identifier](https://dev.fingerprint.com/reference/get-function#visitorid) - issued by Fingerprint Pro. + issued by Fingerprint Identification and all active Smart Signals. Filter for events matching this `visitor_id`. - name: bot @@ -215,39 +280,73 @@ paths: - bad - none description: > - Filter events by the Bot Detection result, specifically: + Filter events by the Bot Detection result, specifically: `all` - events where any kind of bot was detected. `good` - events where a good bot was detected. `bad` - events where a bad bot was detected. `none` - events where no bot was detected. - > Note: When using this parameter, only events with the - `products.botd.data.bot.result` property set to a valid value are - returned. Events without a `products.botd` Smart Signal result are - left out of the response. + > Note: When using this parameter, only events with the `botd.bot` + property set to a valid value are returned. Events without a `botd` + Smart Signal result are left out of the response. - name: ip_address in: query schema: type: string description: > - Filter events by IP address range. The range can be as specific as a - single IP (/32 for IPv4 or /128 for IPv6) + Filter events by IP address or IP range (if CIDR notation is used). + If CIDR notation is not used, a /32 for IPv4 or /128 for IPv6 is + assumed. + + Examples of range based queries: 10.0.0.0/24, 192.168.0.1/32 + - name: asn + in: query + schema: + type: string + description: > + Filter events by the ASN associated with the event's IP address. - All ip_address filters must use CIDR notation, for example, - 10.0.0.0/24, 192.168.0.1/32 + This corresponds to the `ip_info.(v4|v6).asn` property in the + response. - name: linked_id in: query schema: type: string description: > - Filter events by your custom identifier. + Filter events by your custom identifier. You can use [linked - IDs](https://dev.fingerprint.com/reference/get-function#linkedid) to + Ids](https://dev.fingerprint.com/reference/get-function#linkedid) to associate identification requests with your own identifier, for - example, session ID, purchase ID, or transaction ID. You can then + example, session Id, purchase Id, or transaction Id. You can then use this `linked_id` parameter to retrieve all events associated with your custom identifier. + - name: url + in: query + schema: + type: string + description: | + Filter events by the URL (`url` property) associated with the event. + - name: bundle_id + in: query + schema: + type: string + description: | + Filter events by the Bundle ID (iOS) associated with the event. + - name: package_name + in: query + schema: + type: string + description: > + Filter events by the Package Name (Android) associated with the + event. + - name: origin + in: query + schema: + type: string + description: > + Filter events by the origin field of the event. This is applicable + to web events only (e.g., https://example.com) - name: start in: query schema: @@ -276,7 +375,7 @@ paths: type: boolean description: > Filter events previously tagged as suspicious via the [Update - API](https://dev.fingerprint.com/reference/updateevent). + API](https://dev.fingerprint.com/reference/updateevent). > Note: When using this parameter, only events with the `suspect` property explicitly set to `true` or `false` are returned. Events @@ -286,143 +385,135 @@ paths: schema: type: boolean description: > - Filter events by VPN Detection result. + Filter events by VPN Detection result. - > Note: When using this parameter, only events with the - `products.vpn.data.result` property set to `true` or `false` are - returned. Events without a `products.vpn` Smart Signal result are - left out of the response. + > Note: When using this parameter, only events with the `vpn` + property set to `true` or `false` are returned. Events without a + `vpn` Smart Signal result are left out of the response. - name: virtual_machine in: query schema: type: boolean description: > - Filter events by Virtual Machine Detection result. + Filter events by Virtual Machine Detection result. > Note: When using this parameter, only events with the - `products.virtualMachine.data.result` property set to `true` or - `false` are returned. Events without a `products.virtualMachine` - Smart Signal result are left out of the response. + `virtual_machine` property set to `true` or `false` are returned. + Events without a `virtual_machine` Smart Signal result are left out + of the response. - name: tampering in: query schema: type: boolean description: > - Filter events by Tampering Detection result. + Filter events by Browser Tampering Detection result. > Note: When using this parameter, only events with the - `products.tampering.data.result` property set to `true` or `false` - are returned. Events without a `products.tampering` Smart Signal - result are left out of the response. + `tampering.result` property set to `true` or `false` are returned. + Events without a `tampering` Smart Signal result are left out of the + response. - name: anti_detect_browser in: query schema: type: boolean description: > - Filter events by Anti-detect Browser Detection result. + Filter events by Anti-detect Browser Detection result. > Note: When using this parameter, only events with the - `products.tampering.data.antiDetectBrowser` property set to `true` - or `false` are returned. Events without a `products.tampering` Smart - Signal result are left out of the response. + `tampering.anti_detect_browser` property set to `true` or `false` + are returned. Events without a `tampering` Smart Signal result are + left out of the response. - name: incognito in: query schema: type: boolean description: > - Filter events by Browser Incognito Detection result. + Filter events by Browser Incognito Detection result. - > Note: When using this parameter, only events with the - `products.incognito.data.result` property set to `true` or `false` - are returned. Events without a `products.incognito` Smart Signal - result are left out of the response. + > Note: When using this parameter, only events with the `incognito` + property set to `true` or `false` are returned. Events without an + `incognito` Smart Signal result are left out of the response. - name: privacy_settings in: query schema: type: boolean description: > - Filter events by Privacy Settings Detection result. + Filter events by Privacy Settings Detection result. > Note: When using this parameter, only events with the - `products.privacySettings.data.result` property set to `true` or - `false` are returned. Events without a `products.privacySettings` - Smart Signal result are left out of the response. + `privacy_settings` property set to `true` or `false` are returned. + Events without a `privacy_settings` Smart Signal result are left out + of the response. - name: jailbroken in: query schema: type: boolean description: > - Filter events by Jailbroken Device Detection result. + Filter events by Jailbroken Device Detection result. - > Note: When using this parameter, only events with the - `products.jailbroken.data.result` property set to `true` or `false` - are returned. Events without a `products.jailbroken` Smart Signal - result are left out of the response. + > Note: When using this parameter, only events with the `jailbroken` + property set to `true` or `false` are returned. Events without a + `jailbroken` Smart Signal result are left out of the response. - name: frida in: query schema: type: boolean description: > - Filter events by Frida Detection result. + Filter events by Frida Detection result. - > Note: When using this parameter, only events with the - `products.frida.data.result` property set to `true` or `false` are - returned. Events without a `products.frida` Smart Signal result are - left out of the response. + > Note: When using this parameter, only events with the `frida` + property set to `true` or `false` are returned. Events without a + `frida` Smart Signal result are left out of the response. - name: factory_reset in: query schema: type: boolean description: > - Filter events by Factory Reset Detection result. + Filter events by Factory Reset Detection result. - > Note: When using this parameter, only events with the - `products.factoryReset.data.result` property set to `true` or - `false` are returned. Events without a `products.factoryReset` Smart - Signal result are left out of the response. + > Note: When using this parameter, only events with a + `factory_reset` time. Events without a `factory_reset` Smart Signal + result are left out of the response. - name: cloned_app in: query schema: type: boolean description: > - Filter events by Cloned App Detection result. + Filter events by Cloned App Detection result. - > Note: When using this parameter, only events with the - `products.clonedApp.data.result` property set to `true` or `false` - are returned. Events without a `products.clonedApp` Smart Signal - result are left out of the response. + > Note: When using this parameter, only events with the `cloned_app` + property set to `true` or `false` are returned. Events without a + `cloned_app` Smart Signal result are left out of the response. - name: emulator in: query schema: type: boolean description: > - Filter events by Android Emulator Detection result. + Filter events by Android Emulator Detection result. - > Note: When using this parameter, only events with the - `products.emulator.data.result` property set to `true` or `false` - are returned. Events without a `products.emulator` Smart Signal - result are left out of the response. + > Note: When using this parameter, only events with the `emulator` + property set to `true` or `false` are returned. Events without an + `emulator` Smart Signal result are left out of the response. - name: root_apps in: query schema: type: boolean description: > - Filter events by Rooted Device Detection result. + Filter events by Rooted Device Detection result. - > Note: When using this parameter, only events with the - `products.rootApps.data.result` property set to `true` or `false` - are returned. Events without a `products.rootApps` Smart Signal - result are left out of the response. + > Note: When using this parameter, only events with the `root_apps` + property set to `true` or `false` are returned. Events without a + `root_apps` Smart Signal result are left out of the response. - name: vpn_confidence in: query schema: type: string enum: - - high + - high, - medium - low description: > - Filter events by VPN Detection result confidence level. + Filter events by VPN Detection result confidence level. `high` - events with high VPN Detection confidence. @@ -431,9 +522,8 @@ paths: `low` - events with low VPN Detection confidence. > Note: When using this parameter, only events with the - `products.vpn.data.confidence` property set to a valid value are - returned. Events without a `products.vpn` Smart Signal result are - left out of the response. + `vpn.confidence` property set to a valid value are returned. Events + without a `vpn` Smart Signal result are left out of the response. - name: min_suspect_score in: query schema: @@ -444,33 +534,9 @@ paths: threshold. > Note: When using this parameter, only events where the - `products.suspectScore.data.result` property set to a value - exceeding your threshold are returned. Events without a - `products.suspectScore` Smart Signal result are left out of the - response. - - name: ip_blocklist - in: query - schema: - type: boolean - description: > - Filter events by IP Blocklist Detection result. - - > Note: When using this parameter, only events with the - `products.ipBlocklist.data.result` property set to `true` or `false` - are returned. Events without a `products.ipBlocklist` Smart Signal - result are left out of the response. - - name: datacenter - in: query - schema: - type: boolean - description: > - Filter events by Datacenter Detection result. - - > Note: When using this parameter, only events with the - `products.ipInfo.data.v4.datacenter.result` or - `products.ipInfo.data.v6.datacenter.result` property set to `true` - or `false` are returned. Events without a `products.ipInfo` Smart - Signal result are left out of the response. + `suspect_score` property set to a value exceeding your threshold are + returned. Events without a `suspect_score` Smart Signal result are + left out of the response. - name: developer_tools in: query schema: @@ -479,9 +545,9 @@ paths: Filter events by Developer Tools detection result. > Note: When using this parameter, only events with the - `products.developerTools.data.result` property set to `true` or - `false` are returned. Events without a `products.developerTools` - Smart Signal result are left out of the response. + `developer_tools` property set to `true` or `false` are returned. + Events without a `developer_tools` Smart Signal result are left out + of the response. - name: location_spoofing in: query schema: @@ -490,9 +556,9 @@ paths: Filter events by Location Spoofing detection result. > Note: When using this parameter, only events with the - `products.locationSpoofing.data.result` property set to `true` or - `false` are returned. Events without a `products.locationSpoofing` - Smart Signal result are left out of the response. + `location_spoofing` property set to `true` or `false` are returned. + Events without a `location_spoofing` Smart Signal result are left + out of the response. - name: mitm_attack in: query schema: @@ -501,9 +567,9 @@ paths: Filter events by MITM (Man-in-the-Middle) Attack detection result. > Note: When using this parameter, only events with the - `products.mitmAttack.data.result` property set to `true` or `false` - are returned. Events without a `products.mitmAttack` Smart Signal - result are left out of the response. + `mitm_attack` property set to `true` or `false` are returned. Events + without a `mitm_attack` Smart Signal result are left out of the + response. - name: proxy in: query schema: @@ -511,17 +577,16 @@ paths: description: > Filter events by Proxy detection result. - > Note: When using this parameter, only events with the - `products.proxy.data.result` property set to `true` or `false` are - returned. Events without a `products.proxy` Smart Signal result are - left out of the response. + > Note: When using this parameter, only events with the `proxy` + property set to `true` or `false` are returned. Events without a + `proxy` Smart Signal result are left out of the response. - name: sdk_version in: query schema: type: string description: > Filter events by a specific SDK version associated with the - identification event. Example: `3.11.14` + identification event (`sdk.version` property). Example: `3.11.14` - name: sdk_platform in: query schema: @@ -532,24 +597,24 @@ paths: - ios description: > Filter events by the SDK Platform associated with the identification - event. + event (`sdk.platform` property) . - `js` - JavaScript agent (Web). + `js` - Javascript agent (Web). `ios` - Apple iOS based devices. `android` - Android based devices. - name: environment in: query - description: | - Filter for events by providing one or more environment IDs. + description: > + Filter for events by providing one or more environment IDs + (`environment_id` property). required: false schema: type: array items: type: string style: form - explode: true - name: proximity_id in: query schema: @@ -558,38 +623,36 @@ paths: Filter events by the most precise Proximity ID provided by default. > Note: When using this parameter, only events with the - `products.proximity.id` property matching the provided ID are - returned. Events without a `products.proximity` result are left out - of the response. - - name: proximity_precision_radius + `proximity.id` property matching the provided ID are returned. + Events without a `proximity` result are left out of the response. + - name: total_hits in: query schema: type: integer - format: int32 - enum: - - 10 - - 25 - - 65 - - 175 - - 450 - - 1200 - - 3300 - - 8500 - - 22500 + format: int64 + minimum: 1 + maximum: 1000 + description: > + When set, the response will include a `total_hits` property with a + count of total query matches across all pages, up to the specified + limit. + - name: tor_node + in: query + schema: + type: boolean description: > - Filter events by Proximity Radius. + Filter events by Tor Node detection result. - > Note: When using this parameter, only events with the - `products.proximity.precisionRadius` property set to a valid value - are returned. Events without a `products.proximity` result are left - out of the response. + > Note: When using this parameter, only events with the `tor_node` + property set to `true` or `false` are returned. Events without a + `tor_node` detection result are left out of the response. responses: '200': description: Events matching the filter(s). content: application/json: schema: - $ref: '#/components/schemas/SearchEventsResponse' + $ref: '#/components/schemas/EventSearch' '400': description: >- Bad request. One or more supplied search parameters are invalid, or @@ -604,162 +667,13 @@ paths: application/json: schema: $ref: '#/components/schemas/ErrorResponse' - /visitors/{visitor_id}: - get: - tags: - - Fingerprint - operationId: getVisits - summary: Get visits by visitor ID - description: > - Get a history of visits (identification events) for a specific - `visitorId`. Use the `visitorId` as a URL path parameter. - - Only information from the _Identification_ product is returned. - - - #### Headers - - - * `Retry-After` — Present in case of `429 Too many requests`. Indicates - how long you should wait before making a follow-up request. The value is - non-negative decimal integer indicating the seconds to delay after the - response is received. - x-flatten-optional-params: true - parameters: - - name: visitor_id - in: path - required: true - schema: - type: string - description: >- - Unique [visitor - identifier](https://dev.fingerprint.com/reference/get-function#visitorid) - issued by Fingerprint Pro. - - name: request_id - in: query - schema: - type: string - description: > - Filter visits by `requestId`. - - - Every identification request has a unique identifier associated with - it called `requestId`. This identifier is returned to the client in - the identification - [result](https://dev.fingerprint.com/reference/get-function#requestid). - When you filter visits by `requestId`, only one visit will be - returned. - x-go-skip-pointer: true - - name: linked_id - in: query - schema: - type: string - description: > - Filter visits by your custom identifier. - - - You can use - [`linkedId`](https://dev.fingerprint.com/reference/get-function#linkedid) - to associate identification requests with your own identifier, for - example: session ID, purchase ID, or transaction ID. You can then - use this `linked_id` parameter to retrieve all events associated - with your custom identifier. - x-go-skip-pointer: true - - name: limit - in: query - schema: - type: integer - format: int32 - minimum: 0 - description: > - Limit scanned results. - - - For performance reasons, the API first scans some number of events - before filtering them. Use `limit` to specify how many events are - scanned before they are filtered by `requestId` or `linkedId`. - Results are always returned sorted by the timestamp (most recent - first). - - By default, the most recent 100 visits are scanned, the maximum is - 500. - x-go-skip-pointer: true - - name: paginationKey - in: query - schema: - type: string - description: > - Use `paginationKey` to get the next page of results. - - - When more results are available (e.g., you requested 200 results - using `limit` parameter, but a total of 600 results are available), - the `paginationKey` top-level attribute is added to the response. - The key corresponds to the `requestId` of the last returned event. - In the following request, use that value in the `paginationKey` - parameter to get the next page of results: - - - 1. First request, returning most recent 200 events: `GET - api-base-url/visitors/:visitorId?limit=200` - - 2. Use `response.paginationKey` to get the next page of results: - `GET - api-base-url/visitors/:visitorId?limit=200&paginationKey=1683900801733.Ogvu1j` - - - Pagination happens during scanning and before filtering, so you can - get less visits than the `limit` you specified with more available - on the next page. When there are no more results available for - scanning, the `paginationKey` attribute is not returned. - x-go-skip-pointer: true - - name: before - in: query - deprecated: true - schema: - type: integer - format: int64 - minimum: 0 - description: > - ⚠️ Deprecated pagination method, please use `paginationKey` instead. - Timestamp (in milliseconds since epoch) used to paginate results. - x-go-skip-pointer: true - responses: - '200': - description: OK. - content: - application/json: - schema: - $ref: '#/components/schemas/VisitorsGetResponse' - '400': - description: >- - Bad request. The visitor ID or query parameters are missing or in - the wrong format. - content: - application/json: - schema: - $ref: '#/components/schemas/ErrorPlainResponse' - '403': - description: Forbidden. Access to this API is denied. + '500': + description: Workspace error. content: application/json: schema: - $ref: '#/components/schemas/ErrorPlainResponse' - '429': - description: Too Many Requests. The request is throttled. - headers: - Retry-After: - description: >- - Indicates how many seconds you should wait before attempting the - next request. - schema: - type: integer - format: int32 - minimum: 0 - content: - application/json: - schema: - $ref: '#/components/schemas/ErrorPlainResponse' + $ref: '#/components/schemas/ErrorResponse' + /visitors/{visitor_id}: delete: tags: - Fingerprint @@ -769,6 +683,7 @@ paths: Request deleting all data associated with the specified visitor ID. This API is useful for compliance with privacy regulations. + ### Which data is deleted? - Browser (or device) properties @@ -806,16 +721,11 @@ paths: - If the same browser (or device) requests to identify, it will receive a different visitor ID. - - If you request [`/events` - API](https://dev.fingerprint.com/reference/getevent) with a `request_id` + - If you request [`/v4/events` + API](https://dev.fingerprint.com/reference/getevent) with an `event_id` that was made outside of the 10 days, you will still receive a valid response. - - If you request [`/visitors` - API](https://dev.fingerprint.com/reference/getvisits) for the deleted - visitor ID, the response will include identification requests that were - made outside of those 10 days. - ### Interested? @@ -849,9 +759,7 @@ paths: schema: $ref: '#/components/schemas/ErrorResponse' '404': - description: >- - Not found. The visitor ID cannot be found in this application's - data. + description: Not found. The visitor ID cannot be found in this workspace's data. content: application/json: schema: @@ -862,243 +770,106 @@ paths: application/json: schema: $ref: '#/components/schemas/ErrorResponse' - /related-visitors: - get: - tags: - - Fingerprint - operationId: getRelatedVisitors - summary: Get Related Visitors +components: + securitySchemes: + bearerAuth: + type: http + scheme: bearer + bearerFormat: string + description: >- + Add your Secret API Key to the Authorization header using the standard + Bearer format: `Authorization: Bearer ` + schemas: + EventId: + type: string description: > - Related visitors API lets you link web visits and in-app browser visits - that originated from the same mobile device. - - It searches the past 6 months of identification events to find the - visitor IDs that belong to the same mobile device as the given visitor - ID. - - - ⚠️ Please note that this API is not enabled by default and is billable - separately. ⚠️ - - - If you would like to use Related visitors API, please contact our - [support team](https://fingerprint.com/support). - - To learn more, see [Related visitors API - reference](https://dev.fingerprint.com/reference/related-visitors-api). - parameters: - - name: visitor_id - in: query - required: true - schema: - type: string - description: >- - The [visitor - ID](https://dev.fingerprint.com/reference/get-function#visitorid) - for which you want to find the other visitor IDs that originated - from the same mobile device. - responses: - '200': - description: OK. - content: - application/json: - schema: - $ref: '#/components/schemas/RelatedVisitorsResponse' - '400': - description: >- - Bad request. The visitor ID parameter is missing or in the wrong - format. - content: - application/json: - schema: - $ref: '#/components/schemas/ErrorResponse' - '403': - description: Forbidden. Access to this API is denied. - content: - application/json: - schema: - $ref: '#/components/schemas/ErrorResponse' - '404': - description: >- - Not found. The visitor ID cannot be found in this application's - data. - content: - application/json: - schema: - $ref: '#/components/schemas/ErrorResponse' - '429': - description: Too Many Requests. The request is throttled. - content: - application/json: - schema: - $ref: '#/components/schemas/ErrorResponse' - /webhook: - trace: - summary: Dummy path to describe webhook format. - tags: - - Fingerprint + Unique identifier of the user's request. The first portion of the + event_id is a unix epoch milliseconds timestamp For example: + `1758130560902.8tRtrH` + Timestamp: + description: Timestamp of the event with millisecond precision in Unix time. + type: integer + format: int64 + LinkedId: + type: string + description: A customer-provided id that was sent with the request. + EnvironmentId: + type: string + description: | + Environment Id of the event. For example: `ae_47abaca3db2c7c43` + Suspect: + type: boolean description: >- - Fake path to describe webhook format. More information about webhooks - can be found in the - [documentation](https://dev.fingerprint.com/docs/webhooks) - x-flatten-optional-params: true - requestBody: - content: - application/json: - schema: - $ref: '#/components/schemas/Webhook' - responses: - default: - description: Dummy for the schema - callbacks: - webhook: - webhook: - post: - summary: Webhook example - description: >- - You can use HTTP basic authentication and set up credentials in - your [Fingerprint - account](https://dashboard.fingerprint.com/login) - requestBody: - content: - application/json: - schema: - $ref: '#/components/schemas/Webhook' - responses: - default: - description: The server doesn't validate the answer. -components: - securitySchemes: - ApiKeyHeader: - type: apiKey - in: header - name: Auth-API-Key - ApiKeyQuery: - type: apiKey - in: query - name: api_key - schemas: - BrowserDetails: - type: object - additionalProperties: false - required: - - browserName - - browserFullVersion - - browserMajorVersion - - os - - osVersion - - device - - userAgent - properties: - browserName: - type: string - browserMajorVersion: - type: string - browserFullVersion: - type: string - os: - type: string - osVersion: - type: string - device: - type: string - userAgent: - type: string - GeolocationCity: + Field is `true` if you have previously set the `suspect` flag for this + event using the [Server API Update event + endpoint](https://dev.fingerprint.com/reference/updateevent). + Integration: type: object additionalProperties: false - required: - - name - properties: - name: - type: string - GeolocationCountry: - type: object - additionalProperties: false - required: - - code - - name properties: - code: - type: string - minLength: 2 - maxLength: 2 name: type: string - GeolocationContinent: - type: object - additionalProperties: false - required: - - code - - name - properties: - code: - type: string - minLength: 2 - maxLength: 2 - name: + description: The name of the specific integration, e.g. "fingerprint-pro-react". + version: type: string - GeolocationSubdivision: + description: The version of the specific integration, e.g. "3.11.10". + subintegration: + type: object + additionalProperties: false + properties: + name: + type: string + description: The name of the specific subintegration, e.g. "preact". + version: + type: string + description: The version of the specific subintegration, e.g. "10.21.0". + SDK: type: object + description: Contains information about the SDK used to perform the request. additionalProperties: false required: - - isoCode - - name + - platform + - version properties: - isoCode: + platform: type: string - name: + enum: + - js + - android + - ios + - unknown + description: Platform of the SDK used for the identification request. + version: type: string - GeolocationSubdivisions: + description: > + Version string of the SDK used for the identification request. For + example: `"3.12.1"` + integrations: + type: array + items: + $ref: '#/components/schemas/Integration' + Replayed: + type: boolean + description: > + `true` if we determined that this payload was replayed, `false` + otherwise. + TriggeredBy: type: array + description: The rule(s) associated with triggering the webhook via rule engine. items: - $ref: '#/components/schemas/GeolocationSubdivision' - DeprecatedGeolocation: - deprecated: true - type: object - description: >- - This field is **deprecated** and will not return a result for - **applications created after January 23rd, 2024**. Please use the [IP - Geolocation Smart - signal](https://dev.fingerprint.com/docs/smart-signals-overview#ip-geolocation) - for geolocation information. - additionalProperties: false - properties: - accuracyRadius: - type: integer - minimum: 0 - description: >- - The IP address is likely to be within this radius (in km) of the - specified location. - latitude: - type: number - format: double - minimum: -90 - maximum: 90 - longitude: - type: number - format: double - minimum: -180 - maximum: 180 - postalCode: - type: string - timezone: - type: string - format: timezone - city: - $ref: '#/components/schemas/GeolocationCity' - country: - $ref: '#/components/schemas/GeolocationCountry' - continent: - $ref: '#/components/schemas/GeolocationContinent' - subdivisions: - $ref: '#/components/schemas/GeolocationSubdivisions' - Tag: - type: object - description: >- - A customer-provided value or an object that was sent with identification - request. - additionalProperties: true + type: object + additionalProperties: false + required: + - id + - name + - description + properties: + id: + type: string + name: + type: string + description: + type: string IdentificationConfidence: type: object additionalProperties: false @@ -1113,328 +884,301 @@ components: description: >- The confidence score is a floating-point number between 0 and 1 that represents the probability of accurate identification. - revision: + version: type: string description: >- - The revision name of the method used to calculate the Confidence + The version name of the method used to calculate the Confidence score. This field is only present for customers who opted in to an alternative calculation method. comment: type: string - IdentificationSeenAt: - type: object - additionalProperties: false - required: - - global - - subscription - properties: - global: - type: string - nullable: true - format: date-time - x-ogen-time-format: 2006-01-02T15:04:05.999Z07:00 - subscription: - type: string - nullable: true - format: date-time - x-ogen-time-format: 2006-01-02T15:04:05.999Z07:00 - RawDeviceAttributeError: - type: object - additionalProperties: false - properties: - name: - type: string - message: - type: string - RawDeviceAttribute: - type: object - additionalProperties: false - properties: - value: - title: value - error: - $ref: '#/components/schemas/RawDeviceAttributeError' - RawDeviceAttributes: - type: object - description: > - It includes 35+ raw browser identification attributes to provide - Fingerprint users with even more information than our standard visitor - ID provides. This enables Fingerprint users to not have to run our - open-source product in conjunction with Fingerprint Pro Plus and - Enterprise to get those additional attributes. - - Warning: The raw signals data can change at any moment as we improve the - product. We cannot guarantee the internal shape of raw device attributes - to be stable, so typical semantic versioning rules do not apply here. - Use this data with caution without assuming a specific structure beyond - the generic type provided here. - additionalProperties: - $ref: '#/components/schemas/RawDeviceAttribute' - SDK: - type: object - description: Contains information about the SDK used to perform the request. - additionalProperties: false - required: - - platform - - version - properties: - platform: - type: string - description: Platform of the SDK. - version: - type: string - description: SDK version string. Identification: type: object additionalProperties: false required: - - visitorId - - requestId - - browserDetails - - incognito - - ip - - timestamp - - time - - url - - tag - - visitorFound - - firstSeenAt - - lastSeenAt - - replayed + - visitor_id + - visitor_found properties: - visitorId: + visitor_id: type: string description: >- String of 20 characters that uniquely identifies the visitor's browser or mobile device. - requestId: - type: string - description: Unique identifier of the user's request. - browserDetails: - $ref: '#/components/schemas/BrowserDetails' - incognito: - description: Flag if user used incognito session. - type: boolean - ip: - type: string - description: IP address of the requesting browser or bot. - ipLocation: - $ref: '#/components/schemas/DeprecatedGeolocation' - linkedId: - type: string - description: A customer-provided id that was sent with the request. - suspect: - description: >- - Field is `true` if you have previously set the `suspect` flag for - this event using the [Server API Update event - endpoint](https://dev.fingerprint.com/reference/updateevent). - type: boolean - timestamp: - description: Timestamp of the event with millisecond precision in Unix time. - type: integer - format: int64 - time: - type: string - format: date-time - x-ogen-time-format: 2006-01-02T15:04:05Z07:00 - description: >- - Time expressed according to ISO 8601 in UTC format, when the request - from the JS agent was made. We recommend to treat requests that are - older than 2 minutes as malicious. Otherwise, request replay attacks - are possible. - url: - type: string - description: Page URL from which the request was sent. - tag: - $ref: '#/components/schemas/Tag' confidence: $ref: '#/components/schemas/IdentificationConfidence' - visitorFound: + visitor_found: type: boolean description: Attribute represents if a visitor had been identified before. - firstSeenAt: - $ref: '#/components/schemas/IdentificationSeenAt' - lastSeenAt: - $ref: '#/components/schemas/IdentificationSeenAt' - components: - $ref: '#/components/schemas/RawDeviceAttributes' - replayed: - type: boolean + first_seen_at: + type: integer + format: int64 description: > - `true` if we determined that this payload was replayed, `false` - otherwise. - sdk: - $ref: '#/components/schemas/SDK' - environmentId: - type: string - description: Environment ID associated with the event - ErrorCode: - type: string - enum: - - RequestCannotBeParsed - - TokenRequired - - TokenNotFound - - SubscriptionNotActive - - WrongRegion - - FeatureNotEnabled - - RequestNotFound - - VisitorNotFound - - TooManyRequests - - 429 Too Many Requests - - StateNotReady - - Failed - description: | - Error code: - * `RequestCannotBeParsed` - the query parameters or JSON payload contains some errors - that prevented us from parsing it (wrong type/surpassed limits). - * `TokenRequired` - `Auth-API-Key` header is missing or empty. - * `TokenNotFound` - no Fingerprint application found for specified secret key. - * `SubscriptionNotActive` - Fingerprint application is not active. - * `WrongRegion` - server and application region differ. - * `FeatureNotEnabled` - this feature (for example, Delete API) is not enabled for your application. - * `RequestNotFound` - the specified request ID was not found. It never existed, expired, or it has been deleted. - * `VisitorNotFound` - The specified visitor ID was not found. It never existed or it may have already been deleted. - * `TooManyRequests` - the limit on secret API key requests per second has been exceeded. - * `429 Too Many Requests` - the limit on secret API key requests per second has been exceeded. - * `StateNotReady` - The event specified with request id is - not ready for updates yet. Try again. - This error happens in rare cases when update API is called immediately - after receiving the request id on the client. In case you need to send - information right away, we recommend using the JS agent API instead. - * `Failed` - internal server error. - Error: + Unix epoch time milliseconds timestamp indicating the time at which + this visitor ID was first seen. example: `1758069706642` - + Corresponding to Wed Sep 17 2025 00:41:46 GMT+0000 + last_seen_at: + type: integer + format: int64 + description: > + Unix epoch time milliseconds timestamp indicating the time at which + this visitor ID was last seen. example: `1758069706642` - + Corresponding to Wed Sep 17 2025 00:41:46 GMT+0000 + SupplementaryIDHighRecall: type: object additionalProperties: false + description: >- + A supplementary browser identifier that prioritizes coverage over + precision. The High Recall ID algorithm matches more generously, i.e., + this identifier will remain the same even when there are subtle + differences between two requests. This algorithm does not create as many + new visitor IDs as the standard algorithms do, but there could be an + increase in false-positive identification. required: - - code - - message + - visitor_id + - visitor_found properties: - code: - $ref: '#/components/schemas/ErrorCode' - message: + visitor_id: type: string - ProductIdentification: + description: >- + String of 20 characters that uniquely identifies the visitor's + browser or mobile device. + visitor_found: + type: boolean + description: Attribute represents if a visitor had been identified before. + confidence: + $ref: '#/components/schemas/IdentificationConfidence' + first_seen_at: + type: integer + format: int64 + description: > + Unix epoch time milliseconds timestamp indicating the time at which + this ID was first seen. example: `1758069706642` - Corresponding to + Wed Sep 17 2025 00:41:46 GMT+0000 + last_seen_at: + type: integer + format: int64 + description: > + Unix epoch time milliseconds timestamp indicating the time at which + this ID was last seen. example: `1758069706642` - Corresponding to + Wed Sep 17 2025 00:41:46 GMT+0000 + Tags: type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/Identification' - error: - $ref: '#/components/schemas/Error' - BotdBotResult: + description: >- + A customer-provided value or an object that was sent with the + identification request or updated later. + additionalProperties: true + Url: type: string - enum: - - notDetected - - good - - bad - description: | - Bot detection result: - * `notDetected` - the visitor is not a bot - * `good` - good bot detected, such as Google bot, Baidu Spider, AlexaBot and so on - * `bad` - bad bot detected, such as Selenium, Puppeteer, Playwright, headless browsers, and so on - BotdBot: - type: object - description: Stores bot detection result - additionalProperties: false - required: - - result - properties: - result: - $ref: '#/components/schemas/BotdBotResult' - type: - type: string - Botd: + description: > + Page URL from which the request was sent. For example + `https://example.com/` + BundleId: + type: string + description: > + Bundle Id of the iOS application integrated with the Fingerprint SDK for + the event. For example: `com.foo.app` + PackageName: + type: string + description: > + Package name of the Android application integrated with the Fingerprint + SDK for the event. For example: `com.foo.app` + IpAddress: + type: string + description: IP address of the requesting browser or bot. + UserAgent: + type: string + description: > + User Agent of the client, for example: `Mozilla/5.0 (Windows NT 6.1; + Win64; x64) ....` + ClientReferrer: + type: string + description: > + Client Referrer field corresponds to the `document.referrer` field + gathered during an identification request. The value is an empty string + if the user navigated to the page directly (not through a link, but, for + example, by using a bookmark) For example: + `https://example.com/blog/my-article` + BrowserDetails: type: object - description: Contains all the information from Bot Detection product additionalProperties: false required: - - bot - - url - - ip - - time - - userAgent - - requestId + - browser_name + - browser_full_version + - browser_major_version + - os + - os_version + - device properties: - bot: - $ref: '#/components/schemas/BotdBot' - meta: - $ref: '#/components/schemas/Tag' - linkedId: + browser_name: type: string - description: A customer-provided id that was sent with the request. - url: + browser_major_version: type: string - description: Page URL from which the request was sent. - ip: + browser_full_version: type: string - description: IP address of the requesting browser or bot. - time: + os: type: string - format: date-time - x-ogen-time-format: 2006-01-02T15:04:05.999Z07:00 - description: >- - Time in UTC when the request from the JS agent was made. We - recommend to treat requests that are older than 2 minutes as - malicious. Otherwise, request replay attacks are possible. - userAgent: + os_version: type: string - requestId: + device: type: string - description: Unique identifier of the user's request. - ProductBotd: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/Botd' - error: - $ref: '#/components/schemas/Error' - RootApps: + Proximity: type: object + description: > + Proximity ID represents a fixed geographical zone in a discrete global + grid within which the device is observed. additionalProperties: false required: - - result - properties: - result: - type: boolean - description: > - Android specific root management apps detection. There are 2 - values: - * `true` - Root Management Apps detected (e.g. Magisk). - * `false` - No Root Management Apps detected or the client isn't Android. - ProductRootApps: - type: object - additionalProperties: false + - id + - precision_radius + - confidence properties: - data: - $ref: '#/components/schemas/RootApps' - error: - $ref: '#/components/schemas/Error' - Emulator: + id: + type: string + description: | + A stable privacy-preserving identifier for a given proximity zone. + precision_radius: + type: integer + format: int32 + enum: + - 10 + - 25 + - 65 + - 175 + - 450 + - 1200 + - 3300 + - 8500 + - 22500 + description: | + The radius of the proximity zone’s precision level, in meters. + confidence: + type: number + format: float + minimum: 0 + maximum: 1 + description: > + A value between `0` and `1` representing the likelihood that the + true device location lies within the mapped proximity zone. + * Scores closer to `1` indicate high confidence that the location is inside the mapped proximity zone. + * Scores closer to `0` indicate lower confidence, suggesting the true location may fall in an adjacent zone. + BotResult: + type: string + enum: + - bad + - good + - not_detected + description: | + Bot detection result: + * `bad` - bad bot detected, such as Selenium, Puppeteer, Playwright, headless browsers, and so on + * `good` - good bot detected, such as Google bot, Baidu Spider, AlexaBot and so on + * `not_detected` - the visitor is not a bot + BotType: + type: string + description: | + Additional classification of the bot type if detected. + BotInfo: type: object + description: Extended bot information. additionalProperties: false required: - - result + - category + - provider + - name + - identity + - confidence properties: - result: - type: boolean + category: + type: string + description: The type and purpose of the bot. + provider: + type: string + description: The organization or company operating the bot. + provider_url: + type: string + description: The URL of the bot provider's website. + name: + type: string + description: The specific name or identifier of the bot. + identity: + type: string + enum: + - verified + - signed + - spoofed + - unknown description: | - Android specific emulator detection. There are 2 values: - * `true` - Emulated environment detected (e.g. launch inside of AVD). - * `false` - No signs of emulated environment detected or the client is not Android. - ProductEmulator: + The verification status of the bot's identity: + * `verified` - well-known bot with publicly verifiable identity, directed by the bot provider. + * `signed` - bot that signs its platform via Web Bot Auth, directed by the bot provider’s customers. + * `spoofed` - bot that claims a public identity but fails verification. + * `unknown` - bot that does not publish a verifiable identity. + confidence: + type: string + enum: + - low + - medium + - high + description: Confidence level of the bot identification. + ClonedApp: + type: boolean + description: > + Android specific cloned application detection. There are 2 values: * + `true` - Presence of app cloners work detected (e.g. fully cloned + application found or launch of it inside of a not main working profile + detected). * `false` - No signs of cloned application detected or the + client is not Android. + DeveloperTools: + type: boolean + description: > + `true` if the browser is Chrome with DevTools open or Firefox with + Developer Tools open, `false` otherwise. + Emulator: + type: boolean + description: > + Android specific emulator detection. There are 2 values: + + * `true` - Emulated environment detected (e.g. launch inside of AVD). + + * `false` - No signs of emulated environment detected or the client is + not Android. + FactoryReset: + type: integer + format: int64 + description: > + The time of the most recent factory reset that happened on the **mobile + device** is expressed as Unix epoch time. When a factory reset cannot be + detected on the mobile device or when the request is initiated from a + browser, this field will correspond to the *epoch* time (i.e 1 Jan 1970 + UTC) as a value of 0. See [Factory Reset + Detection](https://dev.fingerprint.com/docs/smart-signals-overview#factory-reset-detection) + to learn more about this Smart Signal. + Frida: + type: boolean + description: > + [Frida](https://frida.re/docs/) detection for Android and iOS devices. + There are 2 values: + + * `true` - Frida detected + + * `false` - No signs of Frida or the client is not a mobile device. + IPBlockList: type: object additionalProperties: false properties: - data: - $ref: '#/components/schemas/Emulator' - error: - $ref: '#/components/schemas/Error' + email_spam: + type: boolean + description: IP address was part of a known email spam attack (SMTP). + attack_source: + type: boolean + description: IP address was part of a known network attack (SSH/HTTPS). + tor_node: + type: boolean + description: IP address was part of known TOR network activity. Geolocation: type: object additionalProperties: false properties: - accuracyRadius: + accuracy_radius: type: integer minimum: 0 description: >- @@ -1450,50 +1194,43 @@ components: format: double minimum: -180 maximum: 180 - postalCode: + postal_code: type: string timezone: type: string format: timezone - city: - $ref: '#/components/schemas/GeolocationCity' - country: - $ref: '#/components/schemas/GeolocationCountry' - continent: - $ref: '#/components/schemas/GeolocationContinent' - subdivisions: - $ref: '#/components/schemas/GeolocationSubdivisions' - IPInfoASN: - type: object - additionalProperties: false - required: - - asn - - name - - network - properties: - asn: + city_name: type: string - name: + country_code: type: string - network: + minLength: 2 + maxLength: 2 + country_name: type: string - IPInfoDataCenter: - type: object - additionalProperties: false - required: - - result - - name - properties: - result: - type: boolean - name: + continent_code: type: string + minLength: 2 + maxLength: 2 + continent_name: + type: string + subdivisions: + type: array + items: + type: object + additionalProperties: false + required: + - iso_code + - name + properties: + iso_code: + type: string + name: + type: string IPInfoV4: type: object additionalProperties: false required: - address - - geolocation properties: address: type: string @@ -1501,15 +1238,22 @@ components: geolocation: $ref: '#/components/schemas/Geolocation' asn: - $ref: '#/components/schemas/IPInfoASN' - datacenter: - $ref: '#/components/schemas/IPInfoDataCenter' + type: string + asn_name: + type: string + asn_network: + type: string + asn_type: + type: string + datacenter_result: + type: boolean + datacenter_name: + type: string IPInfoV6: type: object additionalProperties: false required: - address - - geolocation properties: address: type: string @@ -1517,9 +1261,17 @@ components: geolocation: $ref: '#/components/schemas/Geolocation' asn: - $ref: '#/components/schemas/IPInfoASN' - datacenter: - $ref: '#/components/schemas/IPInfoDataCenter' + type: string + asn_name: + type: string + asn_network: + type: string + asn_type: + type: string + datacenter_result: + type: boolean + datacenter_name: + type: string IPInfo: type: object description: >- @@ -1531,1464 +1283,1115 @@ components: $ref: '#/components/schemas/IPInfoV4' v6: $ref: '#/components/schemas/IPInfoV6' - ProductIPInfo: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/IPInfo' - error: - $ref: '#/components/schemas/Error' - IPBlocklistDetails: - type: object - additionalProperties: false - required: - - emailSpam - - attackSource - properties: - emailSpam: - type: boolean - description: IP address was part of a known email spam attack (SMTP). - attackSource: - type: boolean - description: IP address was part of a known network attack (SSH/HTTPS). - IPBlocklist: - type: object - additionalProperties: false - required: - - result - - details - properties: - result: - type: boolean - description: > - `true` if request IP address is part of any database that we use to - search for known malicious actors, `false` otherwise. - details: - $ref: '#/components/schemas/IPBlocklistDetails' - ProductIPBlocklist: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/IPBlocklist' - error: - $ref: '#/components/schemas/Error' - Tor: - type: object - additionalProperties: false - required: - - result - properties: - result: - type: boolean - description: > - `true` if the request IP address is a known tor exit node, `false` - otherwise. - ProductTor: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/Tor' - error: - $ref: '#/components/schemas/Error' - VPNConfidence: + Proxy: + type: boolean + description: > + IP address was used by a public proxy provider or belonged to a known + recent residential proxy + ProxyConfidence: type: string enum: - low - medium - high - description: >- - A confidence rating for the VPN detection result — "low", "medium", or - "high". Depends on the combination of results returned from all VPN - detection methods. - VPNMethods: + description: > + Confidence level of the proxy detection. If a proxy is not detected, + confidence is "high". If it's detected, can be "low", "medium", or + "high". + ProxyDetails: type: object additionalProperties: false + description: Proxy detection details (present if `proxy` is `true`) required: - - timezoneMismatch - - publicVPN - - auxiliaryMobile - - osMismatch - - relay + - proxy_type properties: - timezoneMismatch: - type: boolean - description: >- - The browser timezone doesn't match the timezone inferred from the - request IP address. - publicVPN: - type: boolean - description: >- - Request IP address is owned and used by a public VPN service - provider. - auxiliaryMobile: - type: boolean - description: >- - This method applies to mobile devices only. Indicates the result of - additional methods used to detect a VPN in mobile devices. - osMismatch: - type: boolean - description: >- - The browser runs on a different operating system than the operating - system inferred from the request network signature. - relay: - type: boolean + proxy_type: + type: string + enum: + - residential + - data_center description: > - Request IP address belongs to a relay service provider, indicating - the use of relay services like [Apple Private - relay](https://support.apple.com/en-us/102602) or [Cloudflare - Warp](https://developers.cloudflare.com/warp-client/). + Residential proxies use real user IP addresses to appear as + legitimate traffic, + while data center proxies are public proxies hosted in data centers + last_seen_at: + type: integer + format: int64 + description: > + Unix millisecond timestamp with hourly resolution of when this IP + was last seen as a proxy + provider: + type: string + description: > + String representing the last proxy service provider detected when + this - * Like VPNs, relay services anonymize the visitor's true IP address. + IP was synced. An IP can be shared by multiple service providers. + Incognito: + type: boolean + description: > + `true` if we detected incognito mode used in the browser, `false` + otherwise. + Jailbroken: + type: boolean + description: | + iOS specific jailbreak detection. There are 2 values: + * `true` - Jailbreak detected. + * `false` - No signs of jailbreak or the client is not iOS. + LocationSpoofing: + type: boolean + description: >- + Flag indicating whether the request came from a mobile device with + location spoofing enabled. + MitMAttack: + type: boolean + description: > + * `true` - When requests made from your users' mobile devices to + Fingerprint servers have been intercepted and potentially modified. - * Unlike traditional VPNs, relay services don't let visitors spoof - their location by choosing an exit node in a different country. + * `false` - Otherwise or when the request originated from a browser. + See [MitM Attack + Detection](https://dev.fingerprint.com/docs/smart-signals-reference#mitm-attack-detection) + to learn more about this Smart Signal. + PrivacySettings: + type: boolean + description: > + `true` if the request is from a privacy aware browser (e.g. Tor) or from + a browser in which fingerprinting is blocked. Otherwise `false`. + RootApps: + type: boolean + description: > + Android specific root management apps detection. There are 2 values: - This field allows you to differentiate VPN users and relay service - users in your fraud prevention logic. - VPN: + * `true` - Root Management Apps detected (e.g. Magisk). + + * `false` - No Root Management Apps detected or the client isn't + Android. + RulesetId: + type: string + description: The ID of the evaluated ruleset. + RuleId: + type: string + description: The ID of the rule that matched the identification event. + RuleExpression: + type: string + description: The expression of the rule that matched the identification event. + RuleActionType: + type: string + description: Describes the action to take with the request. + enum: + - allow + - block + RuleActionHeaderField: type: object - additionalProperties: false required: - - result - - confidence - - originTimezone - - originCountry - - methods + - name + - value properties: - result: - type: boolean - description: >- - VPN or other anonymizing service has been used when sending the - request. - confidence: - $ref: '#/components/schemas/VPNConfidence' - originTimezone: + name: type: string - description: Local timezone which is used in timezoneMismatch method. - originCountry: + description: The header field name. + value: type: string + description: The value of the header field. + RequestHeaderModifications: + type: object + description: >- + The set of header modifications to apply, in the following order: + remove, set, append. + properties: + remove: + type: array + description: The list of headers to remove. + items: + type: string + set: + type: array description: >- - Country of the request (only for Android SDK version >= 2.4.0, ISO - 3166 format or unknown). - methods: - $ref: '#/components/schemas/VPNMethods' - ProductVPN: + The list of headers to set, overwriting any existing headers with + the same name. + items: + $ref: '#/components/schemas/RuleActionHeaderField' + append: + type: array + description: The list of headers to append. + items: + $ref: '#/components/schemas/RuleActionHeaderField' + EventRuleActionAllow: type: object - additionalProperties: false + description: >- + Informs the client that the request should be forwarded to the origin + with optional request header modifications. + required: + - type properties: - data: - $ref: '#/components/schemas/VPN' - error: - $ref: '#/components/schemas/Error' - ProxyConfidence: + type: + $ref: '#/components/schemas/RuleActionType' + const: allow + request_header_modifications: + $ref: '#/components/schemas/RequestHeaderModifications' + StatusCode: + type: integer + description: A valid HTTP status code. + RuleActionBody: type: string - enum: - - low - - medium - - high - description: | - Confidence level of the proxy detection. - If a proxy is not detected, confidence is "high". - If it's detected, can be "low", "medium", or "high". - ProxyDetails: + description: The response body to send to the client. + EventRuleActionBlock: type: object - nullable: true - additionalProperties: false - description: Proxy detection details (present if proxy is detected) + description: >- + Informs the client the request should be blocked using the response + described by this rule action. required: - - proxyType + - type properties: - proxyType: - type: string - enum: - - residential - - data_center - description: > - Residential proxies use real user IP addresses to appear as - legitimate traffic, - - while data center proxies are public proxies hosted in data centers - lastSeenAt: - type: string - format: date-time - x-ogen-time-format: 2006-01-02T15:00:00.000Z - description: | - ISO 8601 formatted timestamp in UTC with hourly resolution - of when this IP was last seen as a proxy when available. - Proxy: - type: object - additionalProperties: false - required: - - result - - confidence - properties: - result: - type: boolean - description: > - IP address was used by a public proxy provider or belonged to a - known recent residential proxy - confidence: - $ref: '#/components/schemas/ProxyConfidence' - details: - $ref: '#/components/schemas/ProxyDetails' - ProductProxy: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/Proxy' - error: - $ref: '#/components/schemas/Error' - Incognito: + type: + $ref: '#/components/schemas/RuleActionType' + const: block + status_code: + $ref: '#/components/schemas/StatusCode' + headers: + type: array + description: A list of headers to send. + items: + $ref: '#/components/schemas/RuleActionHeaderField' + body: + $ref: '#/components/schemas/RuleActionBody' + EventRuleAction: type: object - additionalProperties: false + description: >- + Describes the action the client should take, according to the rule in + the ruleset that matched the event. When getting an event by event ID, + the rule_action will only be included when the ruleset_id query + parameter is specified. required: - - result - properties: - result: - type: boolean - description: > - `true` if we detected incognito mode used in the browser, `false` - otherwise. - ProductIncognito: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/Incognito' - error: - $ref: '#/components/schemas/Error' + - ruleset_id + properties: + ruleset_id: + $ref: '#/components/schemas/RulesetId' + rule_id: + $ref: '#/components/schemas/RuleId' + rule_expression: + $ref: '#/components/schemas/RuleExpression' + oneOf: + - $ref: '#/components/schemas/EventRuleActionAllow' + - $ref: '#/components/schemas/EventRuleActionBlock' + discriminator: + propertyName: type + mapping: + allow: EventRuleActionAllow.yaml + block: EventRuleActionBlock.yaml + SuspectScore: + type: integer + description: > + Suspect Score is an easy way to integrate Smart Signals into your fraud + protection work flow. It is a weighted representation of all Smart + Signals present in the payload that helps identify suspicious activity. + The value range is [0; S] where S is sum of all Smart Signals weights. + See more details here: https://dev.fingerprint.com/docs/suspect-score Tampering: + type: boolean + description: > + Flag indicating browser tampering was detected. This happens when + either: + * There are inconsistencies in the browser configuration that cross internal tampering thresholds (see `tampering_details.anomaly_score`). + * The browser signature resembles an "anti-detect" browser specifically designed to evade fingerprinting (see `tampering_details.anti_detect_browser`). + TamperingDetails: type: object additionalProperties: false - required: - - result - - anomalyScore - - antiDetectBrowser properties: - result: - type: boolean - description: > - Indicates if an identification request from a browser or an Android - SDK has been tampered with. Not supported in the iOS SDK, is always - `false` for iOS requests. - * `true` - If the request meets either of the following conditions: - * Contains anomalous browser or device attributes that could not have been legitimately produced by the JavaScript agent or the Android SDK (see `anomalyScore`). - * Originated from an anti-detect browser like Incognition (see `antiDetectBrowser`). - * `false` - If the request is considered genuine or was generated by the iOS SDK. - anomalyScore: + anomaly_score: type: number format: double minimum: 0 maximum: 1 - description: > - A score that indicates the extent of anomalous data in the request. - This field applies to requests originating from **both** browsers - and Android SDKs. - * Values above `0.5` indicate that the request has been tampered with. - * Values below `0.5` indicate that the request is genuine. - antiDetectBrowser: - type: boolean - description: > - Anti-detect browsers try to evade identification by masking or - manipulating their fingerprint to imitate legitimate browser - configurations. This field does not apply to requests originating - from mobile SDKs. - * `true` - The browser resembles a known anti-detect browser, for example, Incognition. - * `false` - The browser does not resemble an anti-detect browser or the request originates from a mobile SDK. - ProductTampering: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/Tampering' - error: - $ref: '#/components/schemas/Error' - ClonedApp: - type: object - additionalProperties: false - required: - - result - properties: - result: - type: boolean - description: | - Android specific cloned application detection. There are 2 values: - * `true` - Presence of app cloners work detected (e.g. fully cloned application found or launch of it inside of a not main working profile detected). - * `false` - No signs of cloned application detected or the client is not Android. - ProductClonedApp: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/ClonedApp' - error: - $ref: '#/components/schemas/Error' - FactoryReset: - type: object - additionalProperties: false - required: - - time - - timestamp - properties: - time: - type: string - format: date-time - description: > - Indicates the time (in UTC) of the most recent factory reset that - happened on the **mobile device**. - - When a factory reset cannot be detected on the mobile device or when - the request is initiated from a browser, this field will correspond - to the *epoch* time (i.e 1 Jan 1970 UTC). - - See [Factory Reset - Detection](https://dev.fingerprint.com/docs/smart-signals-overview#factory-reset-detection) - to learn more about this Smart Signal. - timestamp: - type: integer - format: int64 - description: > - This field is just another representation of the value in the `time` - field. - - The time of the most recent factory reset that happened on the - **mobile device** is expressed as Unix epoch time. - ProductFactoryReset: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/FactoryReset' - error: - $ref: '#/components/schemas/Error' - Jailbroken: - type: object - additionalProperties: false - required: - - result - properties: - result: - type: boolean + x-platforms: + - android + - ios + - browser description: | - iOS specific jailbreak detection. There are 2 values: - * `true` - Jailbreak detected. - * `false` - No signs of jailbreak or the client is not iOS. - ProductJailbroken: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/Jailbroken' - error: - $ref: '#/components/schemas/Error' - Frida: - type: object - additionalProperties: false - required: - - result - properties: - result: - type: boolean - description: > - [Frida](https://frida.re/docs/) detection for Android and iOS - devices. There are 2 values: - * `true` - Frida detected - * `false` - No signs of Frida or the client is not a mobile device. - ProductFrida: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/Frida' - error: - $ref: '#/components/schemas/Error' - PrivacySettings: - type: object - additionalProperties: false - required: - - result - properties: - result: - type: boolean - description: > - `true` if the request is from a privacy aware browser (e.g. Tor) or - from a browser in which fingerprinting is blocked. Otherwise - `false`. - ProductPrivacySettings: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/PrivacySettings' - error: - $ref: '#/components/schemas/Error' - VirtualMachine: - type: object - additionalProperties: false - required: - - result - properties: - result: - type: boolean - description: > - `true` if the request came from a browser running inside a virtual - machine (e.g. VMWare), `false` otherwise. - ProductVirtualMachine: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/VirtualMachine' - error: - $ref: '#/components/schemas/Error' - ProductRawDeviceAttributes: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/RawDeviceAttributes' - error: - $ref: '#/components/schemas/Error' - HighActivity: - type: object - additionalProperties: false - required: - - result - properties: - result: - type: boolean - description: Flag indicating if the request came from a high-activity visitor. - dailyRequests: - type: integer - format: int64 - minimum: 1 - description: Number of requests from the same visitor in the previous day. - ProductHighActivity: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/HighActivity' - error: - $ref: '#/components/schemas/Error' - LocationSpoofing: - type: object - additionalProperties: false - required: - - result - properties: - result: - type: boolean - description: >- - Flag indicating whether the request came from a mobile device with - location spoofing enabled. - ProductLocationSpoofing: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/LocationSpoofing' - error: - $ref: '#/components/schemas/Error' - SuspectScore: - type: object - additionalProperties: false - required: - - result - properties: - result: - type: integer - description: > - Suspect Score is an easy way to integrate Smart Signals into your - fraud protection work flow. It is a weighted representation of all - Smart Signals present in the payload that helps identify suspicious - activity. The value range is [0; S] where S is sum of all Smart - Signals weights. See more details here: - https://dev.fingerprint.com/docs/suspect-score - ProductSuspectScore: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/SuspectScore' - error: - $ref: '#/components/schemas/Error' - RemoteControl: - type: object - deprecated: true - description: | - This signal is deprecated. - additionalProperties: false - required: - - result - properties: - result: + Confidence score (`0.0 - 1.0`) for tampering detection: + * Values above `0.5` indicate tampering. + * Values below `0.5` indicate genuine browsers. + anti_detect_browser: type: boolean + x-platforms: + - browser description: > - `true` if the request came from a machine being remotely controlled - (e.g. TeamViewer), `false` otherwise. - ProductRemoteControl: - type: object - deprecated: true - description: | - This product is deprecated. - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/RemoteControl' - error: - $ref: '#/components/schemas/Error' - VelocityIntervals: + True if the identified browser resembles an "anti-detect" browser, + such as Incognition, which attempts to evade identification by + manipulating its fingerprint. + VelocityData: type: object description: > Is absent if the velocity data could not be generated for the visitor - ID. + Id. additionalProperties: false required: - - 5m - - 1h + - 5_minutes + - 1_hour properties: - 5m: + 5_minutes: type: integer - 1h: + description: > + Count for the last 5 minutes of velocity data, from the time of the + event. + 1_hour: type: integer - 24h: + description: > + Count for the last 1 hour of velocity data, from the time of the + event. + 24_hours: type: integer description: > - The `24h` interval of `distinctIp`, `distinctLinkedId`, - `distinctCountry`, `distinctIpByLinkedId` and - `distinctVisitorIdByLinkedId` will be omitted if the number of - `events`` for the visitor ID in the last 24 hours - (`events.intervals.['24h']`) is higher than 20.000. - VelocityData: - type: object - additionalProperties: false - properties: - intervals: - $ref: '#/components/schemas/VelocityIntervals' + The `24_hours` interval of `distinct_ip`, `distinct_linked_id`, + `distinct_country`, `distinct_ip_by_linked_id` and + `distinct_visitor_id_by_linked_id` will be omitted if the number of + `events` for the visitor Id in the last 24 hours + (`events.['24_hours']`) is higher than 20.000. Velocity: type: object description: > - Sums key data points for a specific `visitorId`, `ipAddress` and - `linkedId` at three distinct time + Sums key data points for a specific `visitor_id`, `ip_address` and + `linked_id` at three distinct time intervals: 5 minutes, 1 hour, and 24 hours as follows: - - Number of distinct IP addresses associated to the visitor ID. + - Number of distinct IP addresses associated to the visitor Id. - - Number of distinct linked IDs associated with the visitor ID. + - Number of distinct linked Ids associated with the visitor Id. - - Number of distinct countries associated with the visitor ID. + - Number of distinct countries associated with the visitor Id. - - Number of identification events associated with the visitor ID. + - Number of identification events associated with the visitor Id. - Number of identification events associated with the detected IP address. - Number of distinct IP addresses associated with the provided linked - ID. + Id. - - Number of distinct visitor IDs associated with the provided linked ID. + - Number of distinct visitor Ids associated with the provided linked Id. - The `24h` interval of `distinctIp`, `distinctLinkedId`, - `distinctCountry`, + The `24h` interval of `distinct_ip`, `distinct_linked_id`, + `distinct_country`, - `distinctIpByLinkedId` and `distinctVisitorIdByLinkedId` will be - omitted + `distinct_ip_by_linked_id` and `distinct_visitor_id_by_linked_id` will + be omitted - if the number of `events` for the visitor ID in the last 24 + if the number of `events` for the visitor Id in the last 24 - hours (`events.intervals.['24h']`) is higher than 20.000. + hours (`events.['24h']`) is higher than 20.000. + + + All will not necessarily be returned in a response, some may be omitted + if the + + associated event does not have the required data, such as a linked_id. additionalProperties: false - required: - - distinctIp - - distinctLinkedId - - distinctCountry - - events - - ipEvents - - distinctIpByLinkedId - - distinctVisitorIdByLinkedId properties: - distinctIp: + distinct_ip: $ref: '#/components/schemas/VelocityData' - distinctLinkedId: + distinct_linked_id: $ref: '#/components/schemas/VelocityData' - distinctCountry: + distinct_country: $ref: '#/components/schemas/VelocityData' events: $ref: '#/components/schemas/VelocityData' - ipEvents: + ip_events: $ref: '#/components/schemas/VelocityData' - distinctIpByLinkedId: + distinct_ip_by_linked_id: $ref: '#/components/schemas/VelocityData' - distinctVisitorIdByLinkedId: + distinct_visitor_id_by_linked_id: $ref: '#/components/schemas/VelocityData' - ProductVelocity: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/Velocity' - error: - $ref: '#/components/schemas/Error' - DeveloperTools: + VirtualMachine: + type: boolean + description: > + `true` if the request came from a browser running inside a virtual + machine (e.g. VMWare), `false` otherwise. + Vpn: + type: boolean + description: | + VPN or other anonymizing service has been used when sending the request. + VpnConfidence: + type: string + enum: + - low + - medium + - high + description: >- + A confidence rating for the VPN detection result — "low", "medium", or + "high". Depends on the combination of results returned from all VPN + detection methods. + VpnOriginTimezone: + type: string + description: | + Local timezone which is used in timezone_mismatch method. + VpnOriginCountry: + type: string + description: > + Country of the request (only for Android SDK version >= 2.4.0, ISO 3166 + format or unknown). + VpnMethods: type: object additionalProperties: false - required: - - result properties: - result: + timezone_mismatch: type: boolean - description: > - `true` if the browser is Chrome with DevTools open or Firefox with - Developer Tools open, `false` otherwise. - ProductDeveloperTools: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/DeveloperTools' - error: - $ref: '#/components/schemas/Error' - MitMAttack: - type: object - additionalProperties: false - required: - - result - properties: - result: + x-platforms: + - android + - ios + - browser + description: >- + The browser timezone doesn't match the timezone inferred from the + request IP address. + public_vpn: type: boolean - description: > - * `true` - When requests made from your users' mobile devices to - Fingerprint servers have been intercepted and potentially modified. - - * `false` - Otherwise or when the request originated from a browser. - - See [MitM Attack - Detection](https://dev.fingerprint.com/docs/smart-signals-reference#mitm-attack-detection) - to learn more about this Smart Signal. - ProductMitMAttack: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/MitMAttack' - error: - $ref: '#/components/schemas/Error' - Proximity: + x-platforms: + - android + - ios + - browser + description: >- + Request IP address is owned and used by a public VPN service + provider. + auxiliary_mobile: + type: boolean + x-platforms: + - android + - ios + - browser + description: >- + This method applies to mobile devices only. Indicates the result of + additional methods used to detect a VPN in mobile devices. + os_mismatch: + type: boolean + x-platforms: + - browser + description: >- + The browser runs on a different operating system than the operating + system inferred from the request network signature. + relay: + type: boolean + x-platforms: + - android + - ios + - browser + description: > + Request IP address belongs to a relay service provider, indicating + the use of relay services like [Apple Private + relay](https://support.apple.com/en-us/102602) or [Cloudflare + Warp](https://developers.cloudflare.com/warp-client/). + + + * Like VPNs, relay services anonymize the visitor's true IP address. + + * Unlike traditional VPNs, relay services don't let visitors spoof + their location by choosing an exit node in a different country. + + + This field allows you to differentiate VPN users and relay service + users in your fraud prevention logic. + HighActivity: + type: boolean + description: Flag indicating if the request came from a high-activity visitor. + FontPreferences: type: object description: > - Proximity ID represents a fixed geographical zone in a discrete global - grid within which the device is observed. + Baseline measurement of canonical fonts rendered on the device. Numeric + width metrics, in CSS pixels, for the canonical fonts collected by the + agent. additionalProperties: false - required: - - id - - precisionRadius - - confidence properties: - id: - type: string - description: | - A stable privacy-preserving identifier for a given proximity zone. - precisionRadius: - type: integer - format: int32 - enum: - - 10 - - 25 - - 65 - - 175 - - 450 - - 1200 - - 3300 - - 8500 - - 22500 - description: | - The radius of the proximity zone’s precision level, in meters. - confidence: + default: type: number - format: float - minimum: 0 - maximum: 1 - description: > - A value between `0` and `1` representing the likelihood that the - true device location lies within the mapped proximity zone. - * Scores closer to `1` indicate high confidence that the location is inside the mapped proximity zone. - * Scores closer to `0` indicate lower confidence, suggesting the true location may fall in an adjacent zone. - ProductProximity: - type: object - additionalProperties: false - properties: - data: - $ref: '#/components/schemas/Proximity' - error: - $ref: '#/components/schemas/Error' - Products: - type: object - description: >- - Contains all information about the request identified by `requestId`, - depending on the pricing plan (Pro, Pro Plus, Enterprise) - additionalProperties: false - properties: - identification: - $ref: '#/components/schemas/ProductIdentification' - botd: - $ref: '#/components/schemas/ProductBotd' - rootApps: - $ref: '#/components/schemas/ProductRootApps' - emulator: - $ref: '#/components/schemas/ProductEmulator' - ipInfo: - $ref: '#/components/schemas/ProductIPInfo' - ipBlocklist: - $ref: '#/components/schemas/ProductIPBlocklist' - tor: - $ref: '#/components/schemas/ProductTor' - vpn: - $ref: '#/components/schemas/ProductVPN' - proxy: - $ref: '#/components/schemas/ProductProxy' - incognito: - $ref: '#/components/schemas/ProductIncognito' - tampering: - $ref: '#/components/schemas/ProductTampering' - clonedApp: - $ref: '#/components/schemas/ProductClonedApp' - factoryReset: - $ref: '#/components/schemas/ProductFactoryReset' - jailbroken: - $ref: '#/components/schemas/ProductJailbroken' - frida: - $ref: '#/components/schemas/ProductFrida' - privacySettings: - $ref: '#/components/schemas/ProductPrivacySettings' - virtualMachine: - $ref: '#/components/schemas/ProductVirtualMachine' - rawDeviceAttributes: - $ref: '#/components/schemas/ProductRawDeviceAttributes' - highActivity: - $ref: '#/components/schemas/ProductHighActivity' - locationSpoofing: - $ref: '#/components/schemas/ProductLocationSpoofing' - suspectScore: - $ref: '#/components/schemas/ProductSuspectScore' - remoteControl: - $ref: '#/components/schemas/ProductRemoteControl' - velocity: - $ref: '#/components/schemas/ProductVelocity' - developerTools: - $ref: '#/components/schemas/ProductDeveloperTools' - mitmAttack: - $ref: '#/components/schemas/ProductMitMAttack' - proximity: - $ref: '#/components/schemas/ProductProximity' - EventsGetResponse: - type: object - description: >- - Contains results from all activated products - Fingerprint Pro, Bot - Detection, and others. - additionalProperties: false - required: - - products - properties: - products: - $ref: '#/components/schemas/Products' - ErrorResponse: - type: object - additionalProperties: false - required: - - error - properties: - error: - $ref: '#/components/schemas/Error' - EventsUpdateRequest: - type: object - properties: - linkedId: - type: string - description: LinkedID value to assign to the existing event - tag: - $ref: '#/components/schemas/Tag' - suspect: - type: boolean - description: Suspect flag indicating observed suspicious or fraudulent event - x-go-force-pointer: true - SearchEventsResponse: + format: double + serif: + type: number + format: double + sans: + type: number + format: double + mono: + type: number + format: double + apple: + type: number + format: double + min: + type: number + format: double + system: + type: number + format: double + Emoji: type: object - description: >- - Contains a list of all identification events matching the specified - search criteria. + description: Bounding box metrics describing how the emoji glyph renders. additionalProperties: false properties: - events: - type: array - items: - type: object - description: Device intelligence results for the identification event. - required: - - products - properties: - products: - $ref: '#/components/schemas/Products' - paginationKey: + font: type: string - description: >- - Use this value in the `pagination_key` parameter to request the next - page of search results. - Visit: + description: Font family reported by the browser when drawing the emoji. + width: + type: number + format: double + height: + type: number + format: double + top: + type: number + format: double + bottom: + type: number + format: double + left: + type: number + format: double + right: + type: number + format: double + x: + type: number + format: double + 'y': + type: number + format: double + Fonts: + type: array + description: List of fonts detected on the device. + items: + type: string + example: + - Arial Unicode MS + - Gill Sans + - Helvetica Neue + - Menlo + DeviceMemory: + type: integer + format: int32 + minimum: 0 + example: 8 + description: Rounded amount of RAM (in gigabytes) reported by the browser. + Timezone: + type: string + description: Timezone identifier detected on the client. + Canvas: type: object + description: Canvas fingerprint containing winding flag plus geometry/text hashes. additionalProperties: false - required: - - requestId - - browserDetails - - incognito - - ip - - timestamp - - time - - url - - tag - - visitorFound - - firstSeenAt - - lastSeenAt properties: - requestId: - type: string - description: Unique identifier of the user's request. - browserDetails: - $ref: '#/components/schemas/BrowserDetails' - incognito: + winding: type: boolean - description: Flag if user used incognito session. - ip: - type: string - description: IP address of the requesting browser or bot. - ipLocation: - $ref: '#/components/schemas/DeprecatedGeolocation' - linkedId: + geometry: type: string - description: A customer-provided id that was sent with the request. - timestamp: - type: integer - format: int64 - description: Timestamp of the event with millisecond precision in Unix time. - time: + description: Hash of geometry rendering output or `unsupported` markers. + text: type: string - format: date-time - x-ogen-time-format: 2006-01-02T15:04:05Z07:00 - description: >- - Time expressed according to ISO 8601 in UTC format, when the request - from the client agent was made. We recommend to treat requests that - are older than 2 minutes as malicious. Otherwise, request replay - attacks are possible. - url: + description: Hash of text rendering output or `unsupported` markers. + Languages: + type: array + description: > + Navigator languages reported by the agent including fallbacks. Each + inner array represents ordered language preferences reported by + different APIs. + items: + type: array + items: type: string - description: Page URL from which the request was sent. - tag: - $ref: '#/components/schemas/Tag' - confidence: - $ref: '#/components/schemas/IdentificationConfidence' - visitorFound: - type: boolean - description: Attribute represents if a visitor had been identified before. - firstSeenAt: - $ref: '#/components/schemas/IdentificationSeenAt' - lastSeenAt: - $ref: '#/components/schemas/IdentificationSeenAt' - components: - $ref: '#/components/schemas/RawDeviceAttributes' - VisitorsGetResponse: + WebGlExtensions: type: object - description: >- - Pagination-related fields `lastTimestamp` and `paginationKey` are - included if you use a pagination parameter like `limit` or `before` and - there is more data available on the next page. + description: Hashes of WebGL context attributes and extension support. additionalProperties: false - required: - - visitorId - - visits properties: - visitorId: + context_attributes: type: string - visits: - type: array - items: - $ref: '#/components/schemas/Visit' - lastTimestamp: - deprecated: true - type: integer - format: int64 - description: > - ⚠️ Deprecated paging attribute, please use `paginationKey` instead. - Timestamp of the last visit in the current page of results. - paginationKey: + parameters: type: string - description: >- - Request ID of the last visit in the current page of results. Use - this value in the following request as the `paginationKey` parameter - to get the next page of results. - ErrorPlainResponse: - type: object - additionalProperties: false - required: - - error - properties: - error: + shader_precisions: type: string - RelatedVisitor: - type: object - additionalProperties: false - required: - - visitorId - properties: - visitorId: + extensions: type: string - description: >- - Visitor ID of a browser that originates from the same mobile device - as the input visitor ID. - RelatedVisitorsResponse: - type: object - additionalProperties: false - required: - - relatedVisitors - properties: - relatedVisitors: + extension_parameters: + type: string + unsupported_extensions: type: array items: - $ref: '#/components/schemas/RelatedVisitor' - WebhookRootApps: - type: object - additionalProperties: false - properties: - result: - type: boolean - description: > - Android specific root management apps detection. There are 2 - values: - * `true` - Root Management Apps detected (e.g. Magisk). - * `false` - No Root Management Apps detected or the client isn't Android. - WebhookEmulator: - type: object - additionalProperties: false - properties: - result: - type: boolean - description: | - Android specific emulator detection. There are 2 values: - * `true` - Emulated environment detected (e.g. launch inside of AVD). - * `false` - No signs of emulated environment detected or the client is not Android. - WebhookIPInfo: - type: object - description: >- - Details about the request IP address. Has separate fields for v4 and v6 - IP address versions. - additionalProperties: false - properties: - v4: - $ref: '#/components/schemas/IPInfoV4' - v6: - $ref: '#/components/schemas/IPInfoV6' - WebhookIPBlocklist: - type: object - additionalProperties: false - properties: - result: - type: boolean - description: > - `true` if request IP address is part of any database that we use to - search for known malicious actors, `false` otherwise. - details: - $ref: '#/components/schemas/IPBlocklistDetails' - WebhookTor: - type: object - additionalProperties: false - properties: - result: - type: boolean - description: > - `true` if the request IP address is a known tor exit node, `false` - otherwise. - WebhookVPN: + type: string + WebGlBasics: type: object + description: Render and vendor strings reported by the WebGL context. additionalProperties: false properties: - result: - type: boolean - description: >- - VPN or other anonymizing service has been used when sending the - request. - confidence: - $ref: '#/components/schemas/VPNConfidence' - originTimezone: + version: type: string - description: Local timezone which is used in timezoneMismatch method. - originCountry: + vendor: type: string - description: >- - Country of the request (only for Android SDK version >= 2.4.0, ISO - 3166 format or unknown). - methods: - $ref: '#/components/schemas/VPNMethods' - WebhookProxy: - type: object - additionalProperties: false - properties: - result: - type: boolean - description: > - IP address was used by a public proxy provider or belonged to a - known recent residential proxy - confidence: - $ref: '#/components/schemas/ProxyConfidence' - details: - $ref: '#/components/schemas/ProxyDetails' - WebhookTampering: + vendor_unmasked: + type: string + renderer: + type: string + renderer_unmasked: + type: string + shading_language_version: + type: string + ScreenResolution: + type: array + description: Current screen resolution. + minItems: 2 + maxItems: 2 + items: + type: integer + format: int32 + TouchSupport: type: object + description: Browser-reported touch capabilities. additionalProperties: false properties: - result: - type: boolean - description: > - Indicates if an identification request from a browser or an Android - SDK has been tampered with. Not supported in the iOS SDK, is always - `false` for iOS requests. - * `true` - If the request meets either of the following conditions: - * Contains anomalous browser or device attributes that could not have been legitimately produced by the JavaScript agent or the Android SDK (see `anomalyScore`). - * Originated from an anti-detect browser like Incognition (see `antiDetectBrowser`). - * `false` - If the request is considered genuine or was generated by the iOS SDK. - anomalyScore: - type: number - format: double - minimum: 0 - maximum: 1 - description: > - A score that indicates the extent of anomalous data in the request. - This field applies to requests originating from **both** browsers - and Android SDKs. - * Values above `0.5` indicate that the request has been tampered with. - * Values below `0.5` indicate that the request is genuine. - antiDetectBrowser: + touch_event: type: boolean - description: > - Anti-detect browsers try to evade identification by masking or - manipulating their fingerprint to imitate legitimate browser - configurations. This field does not apply to requests originating - from mobile SDKs. - * `true` - The browser resembles a known anti-detect browser, for example, Incognition. - * `false` - The browser does not resemble an anti-detect browser or the request originates from a mobile SDK. - WebhookClonedApp: - type: object - additionalProperties: false - properties: - result: + touch_start: type: boolean - description: | - Android specific cloned application detection. There are 2 values: - * `true` - Presence of app cloners work detected (e.g. fully cloned application found or launch of it inside of a not main working profile detected). - * `false` - No signs of cloned application detected or the client is not Android. - WebhookFactoryReset: - type: object - additionalProperties: false - properties: - time: - type: string - format: date-time - description: > - Indicates the time (in UTC) of the most recent factory reset that - happened on the **mobile device**. - - When a factory reset cannot be detected on the mobile device or when - the request is initiated from a browser, this field will correspond - to the *epoch* time (i.e 1 Jan 1970 UTC). - - See [Factory Reset - Detection](https://dev.fingerprint.com/docs/smart-signals-overview#factory-reset-detection) - to learn more about this Smart Signal. - timestamp: + max_touch_points: type: integer format: int64 - description: > - This field is just another representation of the value in the `time` - field. - - The time of the most recent factory reset that happened on the - **mobile device** is expressed as Unix epoch time. - WebhookJailbroken: - type: object - additionalProperties: false - properties: - result: - type: boolean - description: | - iOS specific jailbreak detection. There are 2 values: - * `true` - Jailbreak detected. - * `false` - No signs of jailbreak or the client is not iOS. - WebhookFrida: - type: object - additionalProperties: false - properties: - result: - type: boolean - description: > - [Frida](https://frida.re/docs/) detection for Android and iOS - devices. There are 2 values: - * `true` - Frida detected - * `false` - No signs of Frida or the client is not a mobile device. - WebhookPrivacySettings: - type: object - additionalProperties: false - properties: - result: - type: boolean - description: > - `true` if the request is from a privacy aware browser (e.g. Tor) or - from a browser in which fingerprinting is blocked. Otherwise - `false`. - WebhookVirtualMachine: - type: object - additionalProperties: false - properties: - result: - type: boolean - description: > - `true` if the request came from a browser running inside a virtual - machine (e.g. VMWare), `false` otherwise. - WebhookRawDeviceAttributes: + Oscpu: + type: string + description: Navigator `oscpu` string. + Architecture: + type: integer + format: int32 + description: Integer representing the CPU architecture exposed by the browser. + CookiesEnabled: + type: boolean + description: Whether the cookies are enabled in the browser. + HardwareConcurrency: + type: integer + format: int32 + minimum: 1 + description: Number of logical CPU cores reported by the browser. + DateTimeLocale: + type: string + description: > + Locale derived from the Intl.DateTimeFormat API. Negative values + indicate known error states. The negative statuses can be: - "-1": A + permanent status for browsers that don't support Intl API. - "-2": A + permanent status for browsers that don't supportDateTimeFormat + constructor. - "-3": A permanent status for browsers in which + DateTimeFormat locale is undefined or null. + Vendor: + type: string + description: Navigator vendor string. + ColorDepth: + type: integer + format: int32 + description: Screen color depth in bits. + Platform: + type: string + description: Navigator platform string. + SessionStorage: + type: boolean + description: Whether sessionStorage is available. + LocalStorage: + type: boolean + description: Whether localStorage is available. + Audio: + type: number + format: double + description: > + AudioContext fingerprint or negative status when unavailable. The + negative statuses can be: - -1: A permanent status for those browsers + which are known to always suspend audio context - -2: A permanent status + for browsers that don't support the signal - -3: A temporary status that + means that an unexpected timeout has happened + Plugins: + type: array + description: Browser plugins reported by `navigator.plugins`. + items: + type: object + additionalProperties: false + properties: + name: + type: string + description: + type: string + mimeTypes: + type: array + items: + type: object + additionalProperties: false + properties: + type: + type: string + suffixes: + type: string + description: + type: string + required: + - name + IndexedDb: + type: boolean + description: Whether IndexedDB is available. + Math: + type: string + description: Hash of Math APIs used for entropy collection. + RawDeviceAttributes: type: object description: > - It includes 35+ raw browser identification attributes to provide - Fingerprint users with even more information than our standard visitor - ID provides. This enables Fingerprint users to not have to run our - open-source product in conjunction with Fingerprint Pro Plus and - Enterprise to get those additional attributes. - - Warning: The raw signals data can change at any moment as we improve the - product. We cannot guarantee the internal shape of raw device attributes - to be stable, so typical semantic versioning rules do not apply here. - Use this data with caution without assuming a specific structure beyond - the generic type provided here. - additionalProperties: - $ref: '#/components/schemas/RawDeviceAttribute' - WebhookHighActivity: + A curated subset of raw browser/device attributes that the API surface + exposes. Each property contains a value or object with the data for the + collected signal. + additionalProperties: false + properties: + font_preferences: + $ref: '#/components/schemas/FontPreferences' + emoji: + $ref: '#/components/schemas/Emoji' + fonts: + $ref: '#/components/schemas/Fonts' + device_memory: + $ref: '#/components/schemas/DeviceMemory' + timezone: + $ref: '#/components/schemas/Timezone' + canvas: + $ref: '#/components/schemas/Canvas' + languages: + $ref: '#/components/schemas/Languages' + webgl_extensions: + $ref: '#/components/schemas/WebGlExtensions' + webgl_basics: + $ref: '#/components/schemas/WebGlBasics' + screen_resolution: + $ref: '#/components/schemas/ScreenResolution' + touch_support: + $ref: '#/components/schemas/TouchSupport' + oscpu: + $ref: '#/components/schemas/Oscpu' + architecture: + $ref: '#/components/schemas/Architecture' + cookies_enabled: + $ref: '#/components/schemas/CookiesEnabled' + hardware_concurrency: + $ref: '#/components/schemas/HardwareConcurrency' + date_time_locale: + $ref: '#/components/schemas/DateTimeLocale' + vendor: + $ref: '#/components/schemas/Vendor' + color_depth: + $ref: '#/components/schemas/ColorDepth' + platform: + $ref: '#/components/schemas/Platform' + session_storage: + $ref: '#/components/schemas/SessionStorage' + local_storage: + $ref: '#/components/schemas/LocalStorage' + audio: + $ref: '#/components/schemas/Audio' + plugins: + $ref: '#/components/schemas/Plugins' + indexed_db: + $ref: '#/components/schemas/IndexedDb' + math: + $ref: '#/components/schemas/Math' + Event: type: object + description: >- + Contains results from Fingerprint Identification and all active Smart + Signals. additionalProperties: false required: - - result - properties: - result: - type: boolean - description: Flag indicating if the request came from a high-activity visitor. - dailyRequests: - type: integer - format: int64 - minimum: 1 - description: Number of requests from the same visitor in the previous day. - WebhookLocationSpoofing: - type: object - additionalProperties: false - properties: - result: - type: boolean - description: >- - Flag indicating whether the request came from a mobile device with - location spoofing enabled. - WebhookSuspectScore: - type: object - additionalProperties: false - properties: - result: - type: integer - description: > - Suspect Score is an easy way to integrate Smart Signals into your - fraud protection work flow. It is a weighted representation of all - Smart Signals present in the payload that helps identify suspicious - activity. The value range is [0; S] where S is sum of all Smart - Signals weights. See more details here: - https://dev.fingerprint.com/docs/suspect-score - WebhookRemoteControl: - type: object - deprecated: true - description: | - This signal is deprecated. - additionalProperties: false + - event_id + - timestamp properties: - result: - type: boolean - description: > - `true` if the request came from a machine being remotely controlled - (e.g. TeamViewer), `false` otherwise. - WebhookVelocity: - type: object + event_id: + $ref: '#/components/schemas/EventId' + x-platforms: + - android + - ios + - browser + timestamp: + $ref: '#/components/schemas/Timestamp' + x-platforms: + - android + - ios + - browser + linked_id: + $ref: '#/components/schemas/LinkedId' + x-platforms: + - android + - ios + - browser + environment_id: + $ref: '#/components/schemas/EnvironmentId' + x-platforms: + - android + - ios + - browser + suspect: + $ref: '#/components/schemas/Suspect' + x-platforms: + - android + - ios + - browser + sdk: + $ref: '#/components/schemas/SDK' + x-platforms: + - android + - ios + - browser + replayed: + $ref: '#/components/schemas/Replayed' + x-platforms: + - android + - ios + - browser + identification: + $ref: '#/components/schemas/Identification' + x-platforms: + - android + - ios + - browser + supplementary_id_high_recall: + $ref: '#/components/schemas/SupplementaryIDHighRecall' + x-platforms: + - android + - ios + - browser + tags: + $ref: '#/components/schemas/Tags' + x-platforms: + - android + - ios + - browser + url: + $ref: '#/components/schemas/Url' + x-platforms: + - browser + bundle_id: + $ref: '#/components/schemas/BundleId' + x-platforms: + - ios + package_name: + $ref: '#/components/schemas/PackageName' + x-platforms: + - android + ip_address: + $ref: '#/components/schemas/IpAddress' + x-platforms: + - android + - ios + - browser + user_agent: + $ref: '#/components/schemas/UserAgent' + x-platforms: + - android + - ios + - browser + client_referrer: + $ref: '#/components/schemas/ClientReferrer' + x-platforms: + - browser + browser_details: + $ref: '#/components/schemas/BrowserDetails' + x-platforms: + - browser + proximity: + $ref: '#/components/schemas/Proximity' + x-platforms: + - android + - ios + bot: + $ref: '#/components/schemas/BotResult' + x-platforms: + - browser + bot_type: + $ref: '#/components/schemas/BotType' + x-platforms: + - browser + bot_info: + $ref: '#/components/schemas/BotInfo' + x-platforms: + - browser + cloned_app: + $ref: '#/components/schemas/ClonedApp' + x-platforms: + - android + developer_tools: + $ref: '#/components/schemas/DeveloperTools' + x-platforms: + - browser + emulator: + $ref: '#/components/schemas/Emulator' + x-platforms: + - android + factory_reset_timestamp: + $ref: '#/components/schemas/FactoryReset' + x-platforms: + - android + - ios + frida: + $ref: '#/components/schemas/Frida' + x-platforms: + - android + - ios + ip_blocklist: + $ref: '#/components/schemas/IPBlockList' + x-platforms: + - android + - ios + - browser + ip_info: + $ref: '#/components/schemas/IPInfo' + x-platforms: + - android + - ios + - browser + proxy: + $ref: '#/components/schemas/Proxy' + x-platforms: + - android + - ios + - browser + proxy_confidence: + $ref: '#/components/schemas/ProxyConfidence' + x-platforms: + - android + - ios + - browser + proxy_details: + $ref: '#/components/schemas/ProxyDetails' + x-platforms: + - android + - ios + - browser + incognito: + $ref: '#/components/schemas/Incognito' + x-platforms: + - browser + jailbroken: + $ref: '#/components/schemas/Jailbroken' + x-platforms: + - ios + location_spoofing: + $ref: '#/components/schemas/LocationSpoofing' + x-platforms: + - android + - ios + mitm_attack: + $ref: '#/components/schemas/MitMAttack' + x-platforms: + - android + - ios + privacy_settings: + $ref: '#/components/schemas/PrivacySettings' + x-platforms: + - browser + root_apps: + $ref: '#/components/schemas/RootApps' + x-platforms: + - android + rule_action: + $ref: '#/components/schemas/EventRuleAction' + suspect_score: + $ref: '#/components/schemas/SuspectScore' + x-platforms: + - android + - ios + - browser + tampering: + $ref: '#/components/schemas/Tampering' + x-platforms: + - android + - ios + - browser + tampering_details: + $ref: '#/components/schemas/TamperingDetails' + x-platforms: + - android + - ios + - browser + velocity: + $ref: '#/components/schemas/Velocity' + x-platforms: + - android + - ios + - browser + virtual_machine: + $ref: '#/components/schemas/VirtualMachine' + x-platforms: + - browser + vpn: + $ref: '#/components/schemas/Vpn' + x-platforms: + - android + - ios + - browser + vpn_confidence: + $ref: '#/components/schemas/VpnConfidence' + x-platforms: + - android + - ios + - browser + vpn_origin_timezone: + $ref: '#/components/schemas/VpnOriginTimezone' + x-platforms: + - android + - ios + - browser + vpn_origin_country: + $ref: '#/components/schemas/VpnOriginCountry' + x-platforms: + - android + - ios + vpn_methods: + $ref: '#/components/schemas/VpnMethods' + x-platforms: + - android + - ios + - browser + high_activity_device: + $ref: '#/components/schemas/HighActivity' + x-platforms: + - android + - ios + - browser + raw_device_attributes: + $ref: '#/components/schemas/RawDeviceAttributes' + x-platforms: + - browser + ErrorCode: + type: string + enum: + - request_cannot_be_parsed + - secret_api_key_required + - secret_api_key_not_found + - public_api_key_required + - public_api_key_not_found + - subscription_not_active + - wrong_region + - feature_not_enabled + - request_not_found + - visitor_not_found + - too_many_requests + - state_not_ready + - failed + - event_not_found + - missing_module + - payload_too_large + - service_unavailable + - ruleset_not_found description: > - Sums key data points for a specific `visitorId`, `ipAddress` and - `linkedId` at three distinct time + Error code: - intervals: 5 minutes, 1 hour, and 24 hours as follows: + * `request_cannot_be_parsed` - The query parameters or JSON payload + contains some errors + that prevented us from parsing it (wrong type/surpassed limits). + * `secret_api_key_required` - secret API key in header is missing or + empty. + * `secret_api_key_not_found` - No Fingerprint workspace found for + specified secret API key. - - Number of distinct IP addresses associated to the visitor ID. + * `public_api_key_required` - public API key in header is missing or + empty. - - Number of distinct linked IDs associated with the visitor ID. + * `public_api_key_not_found` - No Fingerprint workspace found for + specified public API key. - - Number of distinct countries associated with the visitor ID. + * `subscription_not_active` - Fingerprint workspace is not active. - - Number of identification events associated with the visitor ID. + * `wrong_region` - Server and workspace region differ. - - Number of identification events associated with the detected IP - address. + * `feature_not_enabled` - This feature (for example, Delete API) is not + enabled for your workspace. - - Number of distinct IP addresses associated with the provided linked - ID. + * `request_not_found` - The specified event ID was not found. It never + existed, expired, or it has been deleted. - - Number of distinct visitor IDs associated with the provided linked ID. + * `visitor_not_found` - The specified visitor ID was not found. It never + existed or it may have already been deleted. + * `too_many_requests` - The limit on secret API key requests per second + has been exceeded. - The `24h` interval of `distinctIp`, `distinctLinkedId`, - `distinctCountry`, + * `state_not_ready` - The event specified with event ID is + not ready for updates yet. Try again. + This error happens in rare cases when update API is called immediately + after receiving the event ID on the client. In case you need to send + information right away, we recommend using the JS agent API instead. + * `failed` - Internal server error. - `distinctIpByLinkedId` and `distinctVisitorIdByLinkedId` will be - omitted + * `event_not_found` - The specified event ID was not found. It never + existed, expired, or it has been deleted. - if the number of `events` for the visitor ID in the last 24 + * `missing_module` - The request is invalid because it is missing a + required module. - hours (`events.intervals.['24h']`) is higher than 20.000. - additionalProperties: false - properties: - distinctIp: - $ref: '#/components/schemas/VelocityData' - distinctLinkedId: - $ref: '#/components/schemas/VelocityData' - distinctCountry: - $ref: '#/components/schemas/VelocityData' - events: - $ref: '#/components/schemas/VelocityData' - ipEvents: - $ref: '#/components/schemas/VelocityData' - distinctIpByLinkedId: - $ref: '#/components/schemas/VelocityData' - distinctVisitorIdByLinkedId: - $ref: '#/components/schemas/VelocityData' - WebhookDeveloperTools: - type: object - additionalProperties: false - properties: - result: - type: boolean - description: > - `true` if the browser is Chrome with DevTools open or Firefox with - Developer Tools open, `false` otherwise. - WebhookMitMAttack: - type: object - additionalProperties: false - properties: - result: - type: boolean - description: > - * `true` - When requests made from your users' mobile devices to - Fingerprint servers have been intercepted and potentially modified. + * `payload_too_large` - The request payload is too large and cannot be + processed. - * `false` - Otherwise or when the request originated from a browser. + * `service_unavailable` - The service was unable to process the request. - See [MitM Attack - Detection](https://dev.fingerprint.com/docs/smart-signals-overview#mitm-attack-detection) - to learn more about this Smart Signal. - SupplementaryID: + * `ruleset_not_found` - The specified ruleset was not found. It never + existed or it has been deleted. + Error: type: object additionalProperties: false + required: + - code + - message properties: - visitorId: + code: + $ref: '#/components/schemas/ErrorCode' + message: type: string - description: >- - String of 20 characters that uniquely identifies the visitor's - browser or mobile device. - visitorFound: - type: boolean - description: Attribute represents if a visitor had been identified before. - confidence: - $ref: '#/components/schemas/IdentificationConfidence' - firstSeenAt: - $ref: '#/components/schemas/IdentificationSeenAt' - lastSeenAt: - $ref: '#/components/schemas/IdentificationSeenAt' - WebhookSupplementaryIDs: + ErrorResponse: type: object - description: Other identities that have been established for a given Visitor. + additionalProperties: false required: - - standard - - highRecall + - error properties: - standard: - $ref: '#/components/schemas/SupplementaryID' - highRecall: - $ref: '#/components/schemas/SupplementaryID' - WebhookProximity: + error: + $ref: '#/components/schemas/Error' + EventUpdate: type: object - description: > - Proximity ID represents a fixed geographical zone in a discrete global - grid within which the device is observed. - additionalProperties: false - required: - - id - - precisionRadius - - confidence properties: - id: + linked_id: type: string - description: | - A stable privacy-preserving identifier for a given proximity zone. - precisionRadius: - type: integer - format: int32 - enum: - - 10 - - 25 - - 65 - - 175 - - 450 - - 1200 - - 3300 - - 8500 - - 22500 - description: | - The radius of the proximity zone’s precision level, in meters. - confidence: - type: number - format: float - minimum: 0 - maximum: 1 - description: > - A value between `0` and `1` representing the likelihood that the - true device location lies within the mapped proximity zone. - * Scores closer to `1` indicate high confidence that the location is inside the mapped proximity zone. - * Scores closer to `0` indicate lower confidence, suggesting the true location may fall in an adjacent zone. - Webhook: + description: Linked Id value to assign to the existing event + tags: + type: object + description: >- + A customer-provided value or an object that was sent with the + identification request or updated later. + additionalProperties: true + suspect: + type: boolean + description: Suspect flag indicating observed suspicious or fraudulent event + x-go-force-pointer: true + EventSearch: type: object + description: >- + Contains a list of all identification events matching the specified + search criteria. + additionalProperties: false required: - - requestId - - url - - ip - - time - - timestamp - - sdk + - events properties: - requestId: - type: string - description: Unique identifier of the user's request. - url: - type: string - description: Page URL from which the request was sent. - ip: - type: string - description: IP address of the requesting browser or bot. - environmentId: - type: string - description: Environment ID of the event. - tag: - $ref: '#/components/schemas/Tag' - time: + events: + type: array + items: + $ref: '#/components/schemas/Event' + pagination_key: type: string - format: date-time - x-ogen-time-format: 2006-01-02T15:04:05.999Z07:00 description: >- - Time expressed according to ISO 8601 in UTC format, when the request - from the JS agent was made. We recommend to treat requests that are - older than 2 minutes as malicious. Otherwise, request replay attacks - are possible. - timestamp: + Use this value in the `pagination_key` parameter to request the next + page of search results. + total_hits: type: integer format: int64 - description: Timestamp of the event with millisecond precision in Unix time. - ipLocation: - $ref: '#/components/schemas/DeprecatedGeolocation' - linkedId: - type: string - description: A customer-provided id that was sent with the request. - visitorId: - type: string description: >- - String of 20 characters that uniquely identifies the visitor's - browser or mobile device. - visitorFound: - type: boolean - description: Attribute represents if a visitor had been identified before. - confidence: - $ref: '#/components/schemas/IdentificationConfidence' - firstSeenAt: - $ref: '#/components/schemas/IdentificationSeenAt' - lastSeenAt: - $ref: '#/components/schemas/IdentificationSeenAt' - browserDetails: - $ref: '#/components/schemas/BrowserDetails' - incognito: - type: boolean - description: Flag if user used incognito session. - clientReferrer: - type: string - components: - $ref: '#/components/schemas/RawDeviceAttributes' - bot: - $ref: '#/components/schemas/BotdBot' - userAgent: - type: string - rootApps: - $ref: '#/components/schemas/WebhookRootApps' - emulator: - $ref: '#/components/schemas/WebhookEmulator' - ipInfo: - $ref: '#/components/schemas/WebhookIPInfo' - ipBlocklist: - $ref: '#/components/schemas/WebhookIPBlocklist' - tor: - $ref: '#/components/schemas/WebhookTor' - vpn: - $ref: '#/components/schemas/WebhookVPN' - proxy: - $ref: '#/components/schemas/WebhookProxy' - tampering: - $ref: '#/components/schemas/WebhookTampering' - clonedApp: - $ref: '#/components/schemas/WebhookClonedApp' - factoryReset: - $ref: '#/components/schemas/WebhookFactoryReset' - jailbroken: - $ref: '#/components/schemas/WebhookJailbroken' - frida: - $ref: '#/components/schemas/WebhookFrida' - privacySettings: - $ref: '#/components/schemas/WebhookPrivacySettings' - virtualMachine: - $ref: '#/components/schemas/WebhookVirtualMachine' - rawDeviceAttributes: - $ref: '#/components/schemas/WebhookRawDeviceAttributes' - highActivity: - $ref: '#/components/schemas/WebhookHighActivity' - locationSpoofing: - $ref: '#/components/schemas/WebhookLocationSpoofing' - suspectScore: - $ref: '#/components/schemas/WebhookSuspectScore' - remoteControl: - $ref: '#/components/schemas/WebhookRemoteControl' - velocity: - $ref: '#/components/schemas/WebhookVelocity' - developerTools: - $ref: '#/components/schemas/WebhookDeveloperTools' - mitmAttack: - $ref: '#/components/schemas/WebhookMitMAttack' - replayed: - type: boolean - description: > - `true` if we determined that this payload was replayed, `false` - otherwise. - sdk: - $ref: '#/components/schemas/SDK' - supplementaryIds: - $ref: '#/components/schemas/WebhookSupplementaryIDs' - proximity: - $ref: '#/components/schemas/WebhookProximity' + This value represents the total number of events matching the search + query, up to the limit provided in the `total_hits` query parameter. + Only present if the `total_hits` query parameter was provided. diff --git a/sync.sh b/sync.sh index f2ef8ba4..6fb2a1cd 100755 --- a/sync.sh +++ b/sync.sh @@ -2,60 +2,40 @@ set -euo pipefail defaultBaseUrl="https://fingerprintjs.github.io/fingerprint-pro-server-api-openapi" -schemaUrl="${1:-$defaultBaseUrl/schemas/fingerprint-server-api-compact.yaml}" +schemaUrl="${1:-$defaultBaseUrl/schemas/fingerprint-server-api-v4.yaml}" examplesBaseUrl="${2:-$defaultBaseUrl/examples}" mkdir -p ./res curl -fSL --retry 3 -o ./res/fingerprint-server-api.yaml "$schemaUrl" -examplesList=( - 'get_visits_200_limit_1.json' - 'get_visits_200_limit_500.json' - 'get_visits_403_error.json' - 'get_visits_429_too_many_requests_error.json' - 'webhook.json' - 'get_event_200.json' - 'get_event_200_all_errors.json' - 'get_event_200_extra_fields.json' - 'get_event_403_error.json' - 'get_event_404_error.json' - 'get_event_200_botd_failed_error.json' - 'get_event_200_botd_too_many_requests_error.json' - 'get_event_200_identification_failed_error.json' - 'get_event_200_identification_too_many_requests_error.json' - 'update_event_400_error.json' - 'update_event_403_error.json' - 'update_event_404_error.json' - 'update_event_409_error.json' -) - -sharedExamplesList=( - '400_error_empty_visitor_id.json' - '400_error_incorrect_visitor_id.json' - '403_error_feature_not_enabled.json' - '403_error_token_not_found.json' - '403_error_token_required.json' - '403_error_wrong_region.json' - '404_error_visitor_not_found.json' - '429_error_too_many_requests.json' +examples=( + 'events/search/get_event_search_200.json' + 'webhook/webhook_event.json' + 'events/get_event_200.json' + 'events/update_event_multiple_fields_request.json' + 'events/update_event_one_field_request.json' + 'errors/400_visitor_id_required.json' + 'errors/400_visitor_id_invalid.json' + 'errors/403_feature_not_enabled.json' + 'errors/403_secret_api_key_not_found.json' + 'errors/403_secret_api_key_required.json' + 'errors/403_wrong_region.json' + 'errors/404_visitor_not_found.json' + 'errors/429_too_many_requests.json' ) baseDestination="./test/mocks" mkdir -p "$baseDestination" -download_example() { - local subpath="$1" - shift - local examples=("$@") - - for example in "${examples[@]}"; do - echo "Downloading $example" - curl -fSL --retry 3 -o "$baseDestination/$example" "$examplesBaseUrl/$subpath$example" - done -} +for example in "${examples[@]}"; do + destinationPath="$baseDestination/$example" + destinationDir="$(dirname "$destinationPath")" + mkdir -p "$destinationDir" -download_example "" "${examplesList[@]}" -download_example "shared/" "${sharedExamplesList[@]}" + exampleUrl="$examplesBaseUrl/$example" + echo "Downloading $exampleUrl to $destinationPath" + curl -fSL --retry 3 -o "$destinationPath" "$exampleUrl" +done ./generate.sh diff --git a/test/mocks/errors/400_visitor_id_invalid.json b/test/mocks/errors/400_visitor_id_invalid.json index c204c568..ae7a3596 100644 --- a/test/mocks/errors/400_visitor_id_invalid.json +++ b/test/mocks/errors/400_visitor_id_invalid.json @@ -1,6 +1,6 @@ { "error": { - "code": "RequestCannotBeParsed", + "code": "request_cannot_be_parsed", "message": "invalid visitor id" } } diff --git a/test/mocks/errors/400_visitor_id_required.json b/test/mocks/errors/400_visitor_id_required.json index 6c5801a0..e144a892 100644 --- a/test/mocks/errors/400_visitor_id_required.json +++ b/test/mocks/errors/400_visitor_id_required.json @@ -1,6 +1,6 @@ { "error": { - "code": "RequestCannotBeParsed", + "code": "request_cannot_be_parsed", "message": "visitor id is required" } } diff --git a/test/mocks/errors/403_feature_not_enabled.json b/test/mocks/errors/403_feature_not_enabled.json index 9820a568..1478d51d 100644 --- a/test/mocks/errors/403_feature_not_enabled.json +++ b/test/mocks/errors/403_feature_not_enabled.json @@ -1,6 +1,6 @@ { "error": { - "code": "FeatureNotEnabled", + "code": "feature_not_enabled", "message": "feature not enabled" } } diff --git a/test/mocks/errors/403_secret_api_key_not_found.json b/test/mocks/errors/403_secret_api_key_not_found.json new file mode 100644 index 00000000..7cf7953b --- /dev/null +++ b/test/mocks/errors/403_secret_api_key_not_found.json @@ -0,0 +1,6 @@ +{ + "error": { + "code": "secret_api_key_not_found", + "message": "no fingerprint workspace found for specified secret API key" + } +} diff --git a/test/mocks/errors/403_secret_api_key_required.json b/test/mocks/errors/403_secret_api_key_required.json new file mode 100644 index 00000000..9ed2f958 --- /dev/null +++ b/test/mocks/errors/403_secret_api_key_required.json @@ -0,0 +1,6 @@ +{ + "error": { + "code": "secret_api_key_required", + "message": "secret API key in header is missing or empty" + } +} diff --git a/test/mocks/errors/403_token_not_found.json b/test/mocks/errors/403_token_not_found.json deleted file mode 100644 index 3936b530..00000000 --- a/test/mocks/errors/403_token_not_found.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "error": { - "code": "TokenNotFound", - "message": "secret key is not found" - } -} diff --git a/test/mocks/errors/403_token_required.json b/test/mocks/errors/403_token_required.json deleted file mode 100644 index 544d8714..00000000 --- a/test/mocks/errors/403_token_required.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "error": { - "code": "TokenRequired", - "message": "secret key is required" - } -} diff --git a/test/mocks/errors/403_wrong_region.json b/test/mocks/errors/403_wrong_region.json index 8acc9e01..3c5fe748 100644 --- a/test/mocks/errors/403_wrong_region.json +++ b/test/mocks/errors/403_wrong_region.json @@ -1,6 +1,6 @@ { "error": { - "code": "WrongRegion", + "code": "wrong_region", "message": "wrong region" } } diff --git a/test/mocks/errors/404_visitor_not_found.json b/test/mocks/errors/404_visitor_not_found.json index 11da4f3d..e4076f4f 100644 --- a/test/mocks/errors/404_visitor_not_found.json +++ b/test/mocks/errors/404_visitor_not_found.json @@ -1,6 +1,6 @@ { "error": { - "code": "VisitorNotFound", + "code": "visitor_not_found", "message": "visitor not found" } } diff --git a/test/mocks/errors/429_too_many_requests.json b/test/mocks/errors/429_too_many_requests.json index e38639aa..bbbc7c41 100644 --- a/test/mocks/errors/429_too_many_requests.json +++ b/test/mocks/errors/429_too_many_requests.json @@ -1,6 +1,6 @@ { "error": { - "code": "TooManyRequests", + "code": "too_many_requests", "message": "too many requests" } } diff --git a/test/mocks/events/get_event_200.json b/test/mocks/events/get_event_200.json new file mode 100644 index 00000000..8985aa0e --- /dev/null +++ b/test/mocks/events/get_event_200.json @@ -0,0 +1,282 @@ +{ + "linked_id": "somelinkedId", + "tags": {}, + "timestamp": 1708102555327, + "event_id": "1708102555327.NLOjmg", + "url": "https://www.example.com/login?hope{this{works[!", + "ip_address": "61.127.217.15", + "user_agent": "Mozilla/5.0 (Windows NT 6.1; Win64; x64) ....", + "client_referrer": "https://example.com/blog/my-article", + "browser_details": { + "browser_name": "Chrome", + "browser_major_version": "74", + "browser_full_version": "74.0.3729", + "os": "Windows", + "os_version": "7", + "device": "Other" + }, + "identification": { + "visitor_id": "Ibk1527CUFmcnjLwIs4A9", + "confidence": { + "score": 0.97, + "version": "1.1" + }, + "visitor_found": false, + "first_seen_at": 1708102555327, + "last_seen_at": 1708102555327 + }, + "supplementary_id_high_recall": { + "visitor_id": "3HNey93AkBW6CRbxV6xP", + "visitor_found": true, + "confidence": { + "score": 0.97, + "version": "1.1" + }, + "first_seen_at": 1708102555327, + "last_seen_at": 1708102555327 + }, + "proximity": { + "id": "w1aTfd4MCvl", + "precision_radius": 10, + "confidence": 0.95 + }, + "bot": "not_detected", + "root_apps": false, + "emulator": false, + "ip_info": { + "v4": { + "address": "94.142.239.124", + "geolocation": { + "accuracy_radius": 20, + "latitude": 50.05, + "longitude": 14.4, + "postal_code": "150 00", + "timezone": "Europe/Prague", + "city_name": "Prague", + "country_code": "CZ", + "country_name": "Czechia", + "continent_code": "EU", + "continent_name": "Europe", + "subdivisions": [ + { + "iso_code": "10", + "name": "Hlavni mesto Praha" + } + ] + }, + "asn": "7922", + "asn_name": "COMCAST-7922", + "asn_network": "73.136.0.0/13", + "asn_type": "isp", + "datacenter_result": true, + "datacenter_name": "DediPath" + }, + "v6": { + "address": "2001:db8:3333:4444:5555:6666:7777:8888", + "geolocation": { + "accuracy_radius": 5, + "latitude": 49.982, + "longitude": 36.2566, + "postal_code": "10112", + "timezone": "Europe/Berlin", + "city_name": "Berlin", + "country_code": "DE", + "country_name": "Germany", + "continent_code": "EU", + "continent_name": "Europe", + "subdivisions": [ + { + "iso_code": "BE", + "name": "Land Berlin" + } + ] + }, + "asn": "6805", + "asn_name": "Telefonica Germany", + "asn_network": "2a02:3100::/24", + "asn_type": "isp", + "datacenter_result": false, + "datacenter_name": "" + } + }, + "ip_blocklist": { + "email_spam": false, + "attack_source": false, + "tor_node": false + }, + "proxy": true, + "proxy_confidence": "low", + "proxy_details": { + "proxy_type": "residential", + "last_seen_at": 1708102555327, + "provider": "Massive" + }, + "vpn": false, + "vpn_confidence": "high", + "vpn_origin_timezone": "Europe/Berlin", + "vpn_origin_country": "unknown", + "vpn_methods": { + "timezone_mismatch": false, + "public_vpn": false, + "auxiliary_mobile": false, + "os_mismatch": false, + "relay": false + }, + "incognito": false, + "tampering": false, + "tampering_details": { + "anomaly_score": 0.1955, + "anti_detect_browser": false + }, + "cloned_app": false, + "factory_reset_timestamp": 0, + "jailbroken": false, + "frida": false, + "privacy_settings": false, + "virtual_machine": false, + "location_spoofing": false, + "velocity": { + "distinct_ip": { + "5_minutes": 1, + "1_hour": 1, + "24_hours": 1 + }, + "distinct_country": { + "5_minutes": 1, + "1_hour": 2, + "24_hours": 2 + }, + "events": { + "5_minutes": 1, + "1_hour": 5, + "24_hours": 5 + }, + "ip_events": { + "5_minutes": 1, + "1_hour": 5, + "24_hours": 5 + }, + "distinct_ip_by_linked_id": { + "5_minutes": 1, + "1_hour": 5, + "24_hours": 5 + }, + "distinct_visitor_id_by_linked_id": { + "5_minutes": 1, + "1_hour": 5, + "24_hours": 5 + } + }, + "developer_tools": false, + "mitm_attack": false, + "sdk": { + "platform": "js", + "version": "3.11.10", + "integrations": [ + { + "name": "fingerprint-pro-react", + "version": "3.11.10", + "subintegration": { + "name": "preact", + "version": "10.21.0" + } + } + ] + }, + "replayed": false, + "high_activity_device": false, + "raw_device_attributes": { + "math": "5f030fa7d2e5f9f757bfaf81642eb1a6", + "vendor": "Google Inc.", + "plugins": [ + { + "description": "Portable Document Format", + "mimeTypes": [ + { + "suffixes": "pdf", + "type": "application/pdf" + }, + { + "suffixes": "pdf", + "type": "text/pdf" + } + ], + "name": "PDF Viewer" + } + ], + "webgl_extensions": { + "context_attributes": "6b1ed336830d2bc96442a9d76373252a", + "extension_parameters": "86a8abb36f0cb30b5946dec0c761d042", + "extensions": "57233d7b10f89fcd1ff95e3837ccd72d", + "parameters": "ea118c48e308bc4b0677118bbb3019ec", + "shader_precisions": "f223dfbcd580cf142da156d93790eb83", + "unsupported_extensions": [] + }, + "cookies_enabled": true, + "webgl_basics": { + "renderer": "WebKit WebGL", + "renderer_unmasked": "ANGLE (Apple, ANGLE Metal Renderer: Apple M4, Unspecified Version)", + "shading_language_version": "WebGL GLSL ES 1.0 (OpenGL ES GLSL ES 1.0 Chromium)", + "vendor": "WebKit", + "vendor_unmasked": "Google Inc. (Apple)", + "version": "WebGL 1.0 (OpenGL ES 2.0 Chromium)" + }, + "canvas": { + "geometry": "db3c1462576a399a03ae93d0ab9eb5c4", + "text": "70c3d3f7eb4408dc37a6bf8af1c51029", + "winding": true + }, + "hardware_concurrency": 10, + "languages": [ + [ + "en-US" + ] + ], + "color_depth": 24, + "fonts": [ + "Arial Unicode MS", + "Gill Sans", + "Helvetica Neue", + "Menlo" + ], + "indexed_db": true, + "touch_support": { + "max_touch_points": 0, + "touch_event": false, + "touch_start": false + }, + "device_memory": 8, + "oscpu": "Windows NT 6.1; Win64; x64", + "architecture": 127, + "screen_resolution": [ + 1920, + 1080 + ], + "timezone": "America/Sao_Paulo", + "emoji": { + "bottom": 32, + "font": "Times", + "height": 18, + "left": 8, + "right": 1608, + "top": 14, + "width": 1600, + "x": 8, + "y": 14 + }, + "font_preferences": { + "apple": 147.5625, + "default": 147.5625, + "min": 9.234375, + "mono": 133.0625, + "sans": 144.015625, + "serif": 147.5625, + "system": 146.09375 + }, + "platform": "MacIntel", + "local_storage": true, + "session_storage": true, + "date_time_locale": "en-US", + "audio": 124.04347745512496 + } +} \ No newline at end of file diff --git a/test/mocks/events/search/get_event_search_200.json b/test/mocks/events/search/get_event_search_200.json new file mode 100644 index 00000000..2affda77 --- /dev/null +++ b/test/mocks/events/search/get_event_search_200.json @@ -0,0 +1,287 @@ +{ + "events": [ + { + "linked_id": "somelinkedId", + "tags": {}, + "timestamp": 1708102555327, + "event_id": "1708102555327.NLOjmg", + "url": "https://www.example.com/login?hope{this{works[!", + "ip_address": "61.127.217.15", + "user_agent": "Mozilla/5.0 (Windows NT 6.1; Win64; x64) ....", + "client_referrer": "https://example.com/blog/my-article", + "browser_details": { + "browser_name": "Chrome", + "browser_major_version": "74", + "browser_full_version": "74.0.3729", + "os": "Windows", + "os_version": "7", + "device": "Other" + }, + "identification": { + "visitor_id": "Ibk1527CUFmcnjLwIs4A9", + "confidence": { + "score": 0.97, + "version": "1.1" + }, + "visitor_found": false, + "first_seen_at": 1708102555327, + "last_seen_at": 1708102555327 + }, + "supplementary_id_high_recall": { + "visitor_id": "3HNey93AkBW6CRbxV6xP", + "visitor_found": true, + "confidence": { + "score": 0.97, + "version": "1.1" + }, + "first_seen_at": 1708102555327, + "last_seen_at": 1708102555327 + }, + "proximity": { + "id": "w1aTfd4MCvl", + "precision_radius": 10, + "confidence": 0.95 + }, + "bot": "not_detected", + "root_apps": false, + "emulator": false, + "ip_info": { + "v4": { + "address": "94.142.239.124", + "geolocation": { + "accuracy_radius": 20, + "latitude": 50.05, + "longitude": 14.4, + "postal_code": "150 00", + "timezone": "Europe/Prague", + "city_name": "Prague", + "country_code": "CZ", + "country_name": "Czechia", + "continent_code": "EU", + "continent_name": "Europe", + "subdivisions": [ + { + "iso_code": "10", + "name": "Hlavni mesto Praha" + } + ] + }, + "asn": "7922", + "asn_name": "COMCAST-7922", + "asn_network": "73.136.0.0/13", + "asn_type": "isp", + "datacenter_result": true, + "datacenter_name": "DediPath" + }, + "v6": { + "address": "2001:db8:3333:4444:5555:6666:7777:8888", + "geolocation": { + "accuracy_radius": 5, + "latitude": 49.982, + "longitude": 36.2566, + "postal_code": "10112", + "timezone": "Europe/Berlin", + "city_name": "Berlin", + "country_code": "DE", + "country_name": "Germany", + "continent_code": "EU", + "continent_name": "Europe", + "subdivisions": [ + { + "iso_code": "BE", + "name": "Land Berlin" + } + ] + }, + "asn": "6805", + "asn_name": "Telefonica Germany", + "asn_network": "2a02:3100::/24", + "asn_type": "isp", + "datacenter_result": false, + "datacenter_name": "" + } + }, + "ip_blocklist": { + "email_spam": false, + "attack_source": false, + "tor_node": false + }, + "proxy": true, + "proxy_confidence": "low", + "proxy_details": { + "proxy_type": "residential", + "last_seen_at": 1708102555327, + "provider": "Massive" + }, + "vpn": false, + "vpn_confidence": "high", + "vpn_origin_timezone": "Europe/Berlin", + "vpn_origin_country": "unknown", + "vpn_methods": { + "timezone_mismatch": false, + "public_vpn": false, + "auxiliary_mobile": false, + "os_mismatch": false, + "relay": false + }, + "incognito": false, + "tampering": false, + "tampering_details": { + "anomaly_score": 0.1955, + "anti_detect_browser": false + }, + "cloned_app": false, + "factory_reset_timestamp": 0, + "jailbroken": false, + "frida": false, + "privacy_settings": false, + "virtual_machine": false, + "location_spoofing": false, + "velocity": { + "distinct_ip": { + "5_minutes": 1, + "1_hour": 1, + "24_hours": 1 + }, + "distinct_country": { + "5_minutes": 1, + "1_hour": 2, + "24_hours": 2 + }, + "events": { + "5_minutes": 1, + "1_hour": 5, + "24_hours": 5 + }, + "ip_events": { + "5_minutes": 1, + "1_hour": 5, + "24_hours": 5 + }, + "distinct_ip_by_linked_id": { + "5_minutes": 1, + "1_hour": 5, + "24_hours": 5 + }, + "distinct_visitor_id_by_linked_id": { + "5_minutes": 1, + "1_hour": 5, + "24_hours": 5 + } + }, + "developer_tools": false, + "mitm_attack": false, + "sdk": { + "platform": "js", + "version": "3.11.10", + "integrations": [ + { + "name": "fingerprint-pro-react", + "version": "3.11.10", + "subintegration": { + "name": "preact", + "version": "10.21.0" + } + } + ] + }, + "replayed": false, + "high_activity_device": false, + "raw_device_attributes": { + "math": "5f030fa7d2e5f9f757bfaf81642eb1a6", + "vendor": "Google Inc.", + "plugins": [ + { + "description": "Portable Document Format", + "mimeTypes": [ + { + "suffixes": "pdf", + "type": "application/pdf" + }, + { + "suffixes": "pdf", + "type": "text/pdf" + } + ], + "name": "PDF Viewer" + } + ], + "webgl_extensions": { + "context_attributes": "6b1ed336830d2bc96442a9d76373252a", + "extension_parameters": "86a8abb36f0cb30b5946dec0c761d042", + "extensions": "57233d7b10f89fcd1ff95e3837ccd72d", + "parameters": "ea118c48e308bc4b0677118bbb3019ec", + "shader_precisions": "f223dfbcd580cf142da156d93790eb83", + "unsupported_extensions": [] + }, + "cookies_enabled": true, + "webgl_basics": { + "renderer": "WebKit WebGL", + "renderer_unmasked": "ANGLE (Apple, ANGLE Metal Renderer: Apple M4, Unspecified Version)", + "shading_language_version": "WebGL GLSL ES 1.0 (OpenGL ES GLSL ES 1.0 Chromium)", + "vendor": "WebKit", + "vendor_unmasked": "Google Inc. (Apple)", + "version": "WebGL 1.0 (OpenGL ES 2.0 Chromium)" + }, + "canvas": { + "geometry": "db3c1462576a399a03ae93d0ab9eb5c4", + "text": "70c3d3f7eb4408dc37a6bf8af1c51029", + "winding": true + }, + "hardware_concurrency": 10, + "languages": [ + [ + "en-US" + ] + ], + "color_depth": 24, + "fonts": [ + "Arial Unicode MS", + "Gill Sans", + "Helvetica Neue", + "Menlo" + ], + "indexed_db": true, + "touch_support": { + "max_touch_points": 0, + "touch_event": false, + "touch_start": false + }, + "device_memory": 8, + "oscpu": "Windows NT 6.1; Win64; x64", + "architecture": 127, + "screen_resolution": [ + 1920, + 1080 + ], + "timezone": "America/Sao_Paulo", + "emoji": { + "bottom": 32, + "font": "Times", + "height": 18, + "left": 8, + "right": 1608, + "top": 14, + "width": 1600, + "x": 8, + "y": 14 + }, + "font_preferences": { + "apple": 147.5625, + "default": 147.5625, + "min": 9.234375, + "mono": 133.0625, + "sans": 144.015625, + "serif": 147.5625, + "system": 146.09375 + }, + "platform": "MacIntel", + "local_storage": true, + "session_storage": true, + "date_time_locale": "en-US", + "audio": 124.04347745512496 + } + } + ], + "pagination_key": "1708102555327" +} \ No newline at end of file diff --git a/test/mocks/events/update_event_multiple_fields_request.json b/test/mocks/events/update_event_multiple_fields_request.json new file mode 100644 index 00000000..adcdb05f --- /dev/null +++ b/test/mocks/events/update_event_multiple_fields_request.json @@ -0,0 +1,7 @@ +{ + "linked_id": "some_username", + "tags": { + "my_tag": "some_value" + }, + "suspect": true +} diff --git a/test/mocks/events/update_event_one_field_request.json b/test/mocks/events/update_event_one_field_request.json new file mode 100644 index 00000000..e42988f5 --- /dev/null +++ b/test/mocks/events/update_event_one_field_request.json @@ -0,0 +1,3 @@ +{ + "linked_id": "some_username" +} diff --git a/test/mocks/get_event_200.json b/test/mocks/get_event_200.json deleted file mode 100644 index 7560b9a6..00000000 --- a/test/mocks/get_event_200.json +++ /dev/null @@ -1,354 +0,0 @@ -{ - "products": { - "identification": { - "data": { - "visitorId": "Ibk1527CUFmcnjLwIs4A9", - "requestId": "1708102555327.NLOjmg", - "incognito": true, - "linkedId": "somelinkedId", - "tag": {}, - "time": "2019-05-21T16:40:13Z", - "timestamp": 1582299576512, - "url": "https://www.example.com/login?hope{this{works[!", - "ip": "61.127.217.15", - "ipLocation": { - "accuracyRadius": 10, - "latitude": 49.982, - "longitude": 36.2566, - "postalCode": "61202", - "timezone": "Europe/Dusseldorf", - "city": { - "name": "Dusseldorf" - }, - "country": { - "code": "DE", - "name": "Germany" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "63", - "name": "North Rhine-Westphalia" - } - ] - }, - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "74", - "browserFullVersion": "74.0.3729", - "os": "Windows", - "osVersion": "7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Windows NT 6.1; Win64; x64) ...." - }, - "confidence": { - "score": 0.97 - }, - "visitorFound": false, - "firstSeenAt": { - "global": "2022-03-16T11:26:45.362Z", - "subscription": "2022-03-16T11:31:01.101Z" - }, - "lastSeenAt": { - "global": null, - "subscription": null - }, - "sdk": { - "platform": "js", - "version": "3.11.10" - }, - "replayed": false - } - }, - "botd": { - "data": { - "bot": { - "result": "notDetected" - }, - "url": "https://www.example.com/login?hope{this{works}[!", - "ip": "61.127.217.15", - "time": "2019-05-21T16:40:13Z", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 YaBrowser/24.1.0.0 Safari/537.36", - "requestId": "1708102555327.NLOjmg" - } - }, - "rootApps": { - "data": { - "result": false - } - }, - "emulator": { - "data": { - "result": false - } - }, - "ipInfo": { - "data": { - "v4": { - "address": "94.142.239.124", - "geolocation": { - "accuracyRadius": 20, - "latitude": 50.05, - "longitude": 14.4, - "postalCode": "150 00", - "timezone": "Europe/Prague", - "city": { - "name": "Prague" - }, - "country": { - "code": "CZ", - "name": "Czechia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "10", - "name": "Hlavni mesto Praha" - } - ] - }, - "asn": { - "asn": "7922", - "name": "COMCAST-7922", - "network": "73.136.0.0/13" - }, - "datacenter": { - "result": true, - "name": "DediPath" - } - }, - "v6": { - "address": "2001:db8:3333:4444:5555:6666:7777:8888", - "geolocation": { - "accuracyRadius": 5, - "latitude": 49.982, - "longitude": 36.2566, - "postalCode": "10112", - "timezone": "Europe/Berlin", - "city": { - "name": "Berlin" - }, - "country": { - "code": "DE", - "name": "Germany" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "BE", - "name": "Land Berlin" - } - ] - }, - "asn": { - "asn": "6805", - "name": "Telefonica Germany", - "network": "2a02:3100::/24" - }, - "datacenter": { - "result": false, - "name": "" - } - } - } - }, - "ipBlocklist": { - "data": { - "result": false, - "details": { - "emailSpam": false, - "attackSource": false - } - } - }, - "tor": { - "data": { - "result": false - } - }, - "vpn": { - "data": { - "result": false, - "confidence": "high", - "originTimezone": "Europe/Berlin", - "originCountry": "unknown", - "methods": { - "timezoneMismatch": false, - "publicVPN": false, - "auxiliaryMobile": false, - "osMismatch": false, - "relay": false - } - } - }, - "proxy": { - "data": { - "result": true, - "confidence": "high", - "details": { - "proxyType": "residential", - "lastSeenAt": "2025-08-12T13:00:00Z" - } - } - }, - "incognito": { - "data": { - "result": false - } - }, - "tampering": { - "data": { - "result": false, - "anomalyScore": 0.1955, - "antiDetectBrowser": false - } - }, - "clonedApp": { - "data": { - "result": false - } - }, - "factoryReset": { - "data": { - "time": "1970-01-01T00:00:00Z", - "timestamp": 0 - } - }, - "jailbroken": { - "data": { - "result": false - } - }, - "frida": { - "data": { - "result": false - } - }, - "privacySettings": { - "data": { - "result": false - } - }, - "virtualMachine": { - "data": { - "result": false - } - }, - "rawDeviceAttributes": { - "data": { - "architecture": { - "value": 127 - }, - "audio": { - "value": 35.73832903057337 - }, - "canvas": { - "value": { - "Winding": true, - "Geometry": "4dce9d6017c3e0c052a77252f29f2b1c", - "Text": "dd2474a56ff78c1de3e7a07070ba3b7d" - } - }, - "colorDepth": { - "value": 30 - }, - "colorGamut": { - "value": "p3" - }, - "contrast": { - "value": 0 - }, - "cookiesEnabled": { - "value": true - }, - "cpuClass": {}, - "fonts": { - "value": ["Arial Unicode MS", "Gill Sans", "Helvetica Neue", "Menlo"] - } - } - }, - "highActivity": { - "data": { - "result": false - } - }, - "locationSpoofing": { - "data": { - "result": false - } - }, - "velocity": { - "data": { - "distinctIp": { - "intervals": { - "5m": 1, - "1h": 1, - "24h": 1 - } - }, - "distinctLinkedId": {}, - "distinctCountry": { - "intervals": { - "5m": 1, - "1h": 2, - "24h": 2 - } - }, - "events": { - "intervals": { - "5m": 1, - "1h": 5, - "24h": 5 - } - }, - "ipEvents": { - "intervals": { - "5m": 1, - "1h": 5, - "24h": 5 - } - }, - "distinctIpByLinkedId": { - "intervals": { - "5m": 1, - "1h": 5, - "24h": 5 - } - }, - "distinctVisitorIdByLinkedId": { - "intervals": { - "5m": 1, - "1h": 5, - "24h": 5 - } - } - } - }, - "developerTools": { - "data": { - "result": false - } - }, - "mitmAttack": { - "data": { - "result": false - } - }, - "proximity": { - "data": { - "id": "w1aTfd4MCvl", - "precisionRadius": 10, - "confidence": 0.95 - } - } - } -} diff --git a/test/mocks/get_event_200_all_errors.json b/test/mocks/get_event_200_all_errors.json deleted file mode 100644 index 15ea2037..00000000 --- a/test/mocks/get_event_200_all_errors.json +++ /dev/null @@ -1,164 +0,0 @@ -{ - "products": { - "identification": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "botd": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "ipInfo": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "incognito": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "rootApps": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "clonedApp": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "factoryReset": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "jailbroken": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "frida": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "emulator": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "ipBlocklist": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "tor": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "vpn": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "proxy": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "privacySettings": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "virtualMachine": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "tampering": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "rawDeviceAttributes": { - "data": { - "audio": { - "error": { - "name": "Error", - "message": "internal server error" - } - }, - "canvas": { - "error": { - "name": "Error", - "message": "internal server error" - } - } - } - }, - "locationSpoofing": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "highActivity": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "suspectScore": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "velocity": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "developerTools": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "mitmAttack": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "proximity": { - "error": { - "code": "Failed", - "message": "internal server error" - } - } - } -} diff --git a/test/mocks/get_event_200_botd_failed_error.json b/test/mocks/get_event_200_botd_failed_error.json deleted file mode 100644 index 0afa5b79..00000000 --- a/test/mocks/get_event_200_botd_failed_error.json +++ /dev/null @@ -1,69 +0,0 @@ -{ - "products": { - "identification": { - "data": { - "visitorId": "Ibk1527CUFmcnjLwIs4A9", - "requestId": "0KSh65EnVoB85JBmloQK", - "incognito": true, - "linkedId": "somelinkedId", - "time": "2019-05-21T16:40:13Z", - "tag": {}, - "timestamp": 1582299576512, - "url": "https://www.example.com/login", - "ip": "61.127.217.15", - "ipLocation": { - "accuracyRadius": 10, - "latitude": 49.982, - "longitude": 36.2566, - "postalCode": "61202", - "timezone": "Europe/Dusseldorf", - "city": { - "name": "Dusseldorf" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "country": { - "code": "DE", - "name": "Germany" - }, - "subdivisions": [ - { - "isoCode": "63", - "name": "North Rhine-Westphalia" - } - ] - }, - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "74", - "browserFullVersion": "74.0.3729", - "os": "Windows", - "osVersion": "7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Windows NT 6.1; Win64; x64) ...." - }, - "confidence": { - "score": 0.97 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-03-16T11:26:45.362Z", - "subscription": "2022-03-16T11:31:01.101Z" - }, - "lastSeenAt": { - "global": "2022-03-16T11:28:34.023Z", - "subscription": null - }, - "replayed": false - } - }, - "botd": { - "error": { - "code": "Failed", - "message": "internal server error" - } - } - } -} diff --git a/test/mocks/get_event_200_extra_fields.json b/test/mocks/get_event_200_extra_fields.json deleted file mode 100644 index 5a56a1c7..00000000 --- a/test/mocks/get_event_200_extra_fields.json +++ /dev/null @@ -1,91 +0,0 @@ -{ - "products": { - "identification": { - "data": { - "visitorId": "Ibk1527CUFmcnjLwIs4A9", - "requestId": "0KSh65EnVoB85JBmloQK", - "incognito": true, - "linkedId": "somelinkedId", - "tag": {}, - "time": "2019-05-21T16:40:13Z", - "timestamp": 1582299576512, - "url": "https://www.example.com/login", - "ip": "61.127.217.15", - "ipLocation": { - "accuracyRadius": 10, - "latitude": 49.982, - "longitude": 36.2566, - "postalCode": "61202", - "timezone": "Europe/Dusseldorf", - "city": { - "name": "Dusseldorf" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "country": { - "code": "DE", - "name": "Germany" - }, - "subdivisions": [ - { - "isoCode": "63", - "name": "North Rhine-Westphalia" - } - ] - }, - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "74", - "browserFullVersion": "74.0.3729", - "os": "Windows", - "osVersion": "7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Windows NT 6.1; Win64; x64) ...." - }, - "confidence": { - "score": 0.97, - "revision": "v1.1" - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-03-16T11:26:45.362Z", - "subscription": "2022-03-16T11:31:01.101Z" - }, - "lastSeenAt": { - "global": "2022-03-16T11:28:34.023Z", - "subscription": null - }, - "replayed": false - } - }, - "botd": { - "data": { - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 YaBrowser/24.1.0.0 Safari/537.36", - "requestId": "1708102555327.NLOjmg", - "bot": { - "result": "notDetected" - }, - "url": "https://www.example.com/login", - "ip": "61.127.217.15", - "time": "2019-05-21T16:40:13Z" - } - }, - "product3": { - "data": { - "result": false - } - }, - "product4": { - "data": { - "result": true, - "details": { - "detail1": true, - "detail2": "detail description", - "detail3": 42 - } - } - } - } -} diff --git a/test/mocks/get_event_200_identification_failed_error.json b/test/mocks/get_event_200_identification_failed_error.json deleted file mode 100644 index 4739f36e..00000000 --- a/test/mocks/get_event_200_identification_failed_error.json +++ /dev/null @@ -1,23 +0,0 @@ -{ - "products": { - "identification": { - "error": { - "code": "Failed", - "message": "internal server error" - } - }, - "botd": { - "data": { - "bot": { - "result": "bad", - "type": "headlessChrome" - }, - "url": "https://example.com/login", - "ip": "94.60.143.223", - "time": "2024-02-23T10:20:25.287Z", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) HeadlessChrome/121.0.6167.57 Safari/537.36", - "requestId": "1708683625245.tuJ4nD" - } - } - } -} diff --git a/test/mocks/get_event_200_too_many_requests_error.json b/test/mocks/get_event_200_too_many_requests_error.json deleted file mode 100644 index 138aae72..00000000 --- a/test/mocks/get_event_200_too_many_requests_error.json +++ /dev/null @@ -1,16 +0,0 @@ -{ - "products": { - "identification": { - "error": { - "code": "429 Too Many Requests", - "message": "too many requests" - } - }, - "botd": { - "error": { - "code": "TooManyRequests", - "message": "too many requests" - } - } - } -} diff --git a/test/mocks/get_event_200_with_broken_format.json b/test/mocks/get_event_200_with_broken_format.json deleted file mode 100644 index 58081140..00000000 --- a/test/mocks/get_event_200_with_broken_format.json +++ /dev/null @@ -1,301 +0,0 @@ -{ - "products": { - "identification": { - "data": { - "visitorId": "Ibk1527CUFmcnjLwIs4A9", - "requestId": "1708102555327.NLOjmg", - "incognito": true, - "linkedId": { - "broken": "format" - }, - "tag": {}, - "time": "2019-05-21T16:40:13Z", - "timestamp": 1582299576512, - "url": "https://www.example.com/login?hope{this{works[!", - "ip": "61.127.217.15", - "ipLocation": { - "accuracyRadius": 10, - "latitude": 49.982, - "longitude": 36.2566, - "postalCode": "61202", - "timezone": "Europe/Dusseldorf", - "city": { - "name": "Dusseldorf" - }, - "country": { - "code": "DE", - "name": "Germany" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "63", - "name": "North Rhine-Westphalia" - } - ] - }, - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "74", - "browserFullVersion": "74.0.3729", - "os": "Windows", - "osVersion": "7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Windows NT 6.1; Win64; x64) ...." - }, - "confidence": { - "score": 0.97 - }, - "visitorFound": false, - "firstSeenAt": { - "global": "2022-03-16T11:26:45.362Z", - "subscription": "2022-03-16T11:31:01.101Z" - }, - "lastSeenAt": { - "global": null, - "subscription": null - }, - "replayed": false - } - }, - "botd": { - "data": { - "bot": { - "result": "notDetected" - }, - "url": "https://www.example.com/login?hope{this{works}[!", - "ip": "61.127.217.15", - "time": "2019-05-21T16:40:13Z", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 YaBrowser/24.1.0.0 Safari/537.36", - "requestId": "1708102555327.NLOjmg" - } - }, - "rootApps": { - "data": { - "result": false - } - }, - "emulator": { - "data": { - "result": false - } - }, - "ipInfo": { - "data": { - "v4": { - "address": "94.142.239.124", - "geolocation": { - "accuracyRadius": 20, - "latitude": 50.05, - "longitude": 14.4, - "postalCode": "150 00", - "timezone": "Europe/Prague", - "city": { - "name": "Prague" - }, - "country": { - "code": "CZ", - "name": "Czechia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "10", - "name": "Hlavni mesto Praha" - } - ] - }, - "asn": { - "asn": "7922", - "name": "COMCAST-7922", - "network": "73.136.0.0/13" - }, - "datacenter": { - "result": true, - "name": "DediPath" - } - }, - "v6": { - "address": "2001:db8:3333:4444:5555:6666:7777:8888", - "geolocation": { - "accuracyRadius": 5, - "latitude": 49.982, - "longitude": 36.2566, - "postalCode": "10112", - "timezone": "Europe/Berlin", - "city": { - "name": "Berlin" - }, - "country": { - "code": "DE", - "name": "Germany" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "BE", - "name": "Land Berlin" - } - ] - }, - "asn": { - "asn": "6805", - "name": "Telefonica Germany", - "network": "2a02:3100::/24" - }, - "datacenter": { - "result": false, - "name": "" - } - } - } - }, - "ipBlocklist": { - "data": { - "result": false, - "details": { - "emailSpam": false, - "attackSource": false - } - } - }, - "tor": { - "data": { - "result": false - } - }, - "vpn": { - "data": { - "result": false, - "originTimezone": "Europe/Berlin", - "originCountry": "unknown", - "methods": { - "timezoneMismatch": false, - "publicVPN": false, - "auxiliaryMobile": false - } - } - }, - "proxy": { - "data": { - "result": true, - "confidence": "high", - "details": { - "proxyType": "residential", - "lastSeenAt": "2025-08-12T13:00:00Z" - } - } - }, - "incognito": { - "data": { - "result": false - } - }, - "tampering": { - "data": { - "result": false, - "anomalyScore": 0.1955 - } - }, - "clonedApp": { - "data": { - "result": false - } - }, - "factoryReset": { - "data": { - "time": "1970-01-01T00:00:00Z", - "timestamp": 0 - } - }, - "jailbroken": { - "data": { - "result": false - } - }, - "frida": { - "data": { - "result": false - } - }, - "privacySettings": { - "data": { - "result": false - } - }, - "virtualMachine": { - "data": { - "result": false - } - }, - "rawDeviceAttributes": { - "data": { - "architecture": { - "value": 127 - }, - "audio": { - "value": 35.73832903057337 - }, - "canvas": { - "value": { - "Winding": true, - "Geometry": "4dce9d6017c3e0c052a77252f29f2b1c", - "Text": "dd2474a56ff78c1de3e7a07070ba3b7d" - } - }, - "colorDepth": { - "value": 30 - }, - "colorGamut": { - "value": "p3" - }, - "contrast": { - "value": 0 - }, - "cookiesEnabled": { - "value": true - }, - "cpuClass": {}, - "fonts": { - "value": [ - "Arial Unicode MS", - "Gill Sans", - "Helvetica Neue", - "Menlo" - ] - } - } - }, - "highActivity": { - "data": { - "result": false - } - }, - "locationSpoofing": { - "data": { - "result": false - } - }, - "mitmAttack": { - "data": { - "result": false - } - }, - "proximity": { - "data": { - "id": "w1aTfd4MCvl", - "precisionRadius": 10, - "confidence": 0.95 - } - } - } -} diff --git a/test/mocks/get_event_200_with_unknown_field.json b/test/mocks/get_event_200_with_unknown_field.json deleted file mode 100644 index 6af6ad63..00000000 --- a/test/mocks/get_event_200_with_unknown_field.json +++ /dev/null @@ -1,299 +0,0 @@ -{ - "unknown": "field", - "products": { - "unknown": "field", - "identification": { - "unknown": "field", - "data": { - "unknown": "field", - "visitorId": "Ibk1527CUFmcnjLwIs4A9", - "requestId": "1708102555327.NLOjmg", - "incognito": true, - "linkedId": "somelinkedId", - "tag": {}, - "time": "2019-05-21T16:40:13Z", - "timestamp": 1582299576512, - "url": "https://www.example.com/login?hope{this{works[!", - "ip": "61.127.217.15", - "ipLocation": { - "accuracyRadius": 10, - "latitude": 49.982, - "longitude": 36.2566, - "postalCode": "61202", - "timezone": "Europe/Dusseldorf", - "city": { - "name": "Dusseldorf" - }, - "country": { - "code": "DE", - "name": "Germany" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "63", - "name": "North Rhine-Westphalia" - } - ] - }, - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "74", - "browserFullVersion": "74.0.3729", - "os": "Windows", - "osVersion": "7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Windows NT 6.1; Win64; x64) ...." - }, - "confidence": { - "score": 0.97 - }, - "visitorFound": false, - "firstSeenAt": { - "global": "2022-03-16T11:26:45.362Z", - "subscription": "2022-03-16T11:31:01.101Z" - }, - "lastSeenAt": { - "global": null, - "subscription": null - }, - "replayed": false - } - }, - "botd": { - "data": { - "bot": { - "result": "notDetected" - }, - "url": "https://www.example.com/login?hope{this{works}[!", - "ip": "61.127.217.15", - "time": "2019-05-21T16:40:13Z", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 YaBrowser/24.1.0.0 Safari/537.36", - "requestId": "1708102555327.NLOjmg" - } - }, - "rootApps": { - "data": { - "result": false - } - }, - "emulator": { - "data": { - "result": false - } - }, - "ipInfo": { - "data": { - "v4": { - "address": "94.142.239.124", - "geolocation": { - "accuracyRadius": 20, - "latitude": 50.05, - "longitude": 14.4, - "postalCode": "150 00", - "timezone": "Europe/Prague", - "city": { - "name": "Prague" - }, - "country": { - "code": "CZ", - "name": "Czechia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "10", - "name": "Hlavni mesto Praha" - } - ] - }, - "asn": { - "asn": "7922", - "name": "COMCAST-7922", - "network": "73.136.0.0/13" - }, - "datacenter": { - "result": true, - "name": "DediPath" - } - }, - "v6": { - "address": "2001:db8:3333:4444:5555:6666:7777:8888", - "geolocation": { - "accuracyRadius": 5, - "latitude": 49.982, - "longitude": 36.2566, - "postalCode": "10112", - "timezone": "Europe/Berlin", - "city": { - "name": "Berlin" - }, - "country": { - "code": "DE", - "name": "Germany" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "BE", - "name": "Land Berlin" - } - ] - }, - "asn": { - "asn": "6805", - "name": "Telefonica Germany", - "network": "2a02:3100::/24" - }, - "datacenter": { - "result": false, - "name": "" - } - } - } - }, - "ipBlocklist": { - "data": { - "result": false, - "details": { - "emailSpam": false, - "attackSource": false - } - } - }, - "tor": { - "data": { - "result": false - } - }, - "vpn": { - "data": { - "result": false, - "originTimezone": "Europe/Berlin", - "originCountry": "unknown", - "methods": { - "timezoneMismatch": false, - "publicVPN": false, - "auxiliaryMobile": false - } - } - }, - "proxy": { - "data": { - "result": false, - "confidence": "high" - } - }, - "incognito": { - "data": { - "result": false - } - }, - "tampering": { - "data": { - "result": false, - "anomalyScore": 0.1955 - } - }, - "clonedApp": { - "data": { - "result": false - } - }, - "factoryReset": { - "data": { - "time": "1970-01-01T00:00:00Z", - "timestamp": 0 - } - }, - "jailbroken": { - "data": { - "result": false - } - }, - "frida": { - "data": { - "result": false - } - }, - "privacySettings": { - "data": { - "result": false - } - }, - "virtualMachine": { - "data": { - "result": false - } - }, - "rawDeviceAttributes": { - "data": { - "architecture": { - "value": 127 - }, - "audio": { - "value": 35.73832903057337 - }, - "canvas": { - "value": { - "Winding": true, - "Geometry": "4dce9d6017c3e0c052a77252f29f2b1c", - "Text": "dd2474a56ff78c1de3e7a07070ba3b7d" - } - }, - "colorDepth": { - "value": 30 - }, - "colorGamut": { - "value": "p3" - }, - "contrast": { - "value": 0 - }, - "cookiesEnabled": { - "value": true - }, - "cpuClass": {}, - "fonts": { - "value": [ - "Arial Unicode MS", - "Gill Sans", - "Helvetica Neue", - "Menlo" - ] - } - } - }, - "highActivity": { - "data": { - "result": false - } - }, - "locationSpoofing": { - "data": { - "result": false - } - }, - "mitmAttack": { - "data": { - "result": false - } - }, - "proximity": { - "data": { - "id": "w1aTfd4MCvl", - "precisionRadius": 10, - "confidence": 0.95 - } - } - } -} diff --git a/test/mocks/get_event_search_200.json b/test/mocks/get_event_search_200.json deleted file mode 100644 index 27b7848d..00000000 --- a/test/mocks/get_event_search_200.json +++ /dev/null @@ -1,354 +0,0 @@ -{ - "events": [ - { - "products": { - "identification": { - "data": { - "visitorId": "Ibk1527CUFmcnjLwIs4A9", - "requestId": "1708102555327.NLOjmg", - "incognito": true, - "linkedId": "somelinkedId", - "tag": {}, - "time": "2019-05-21T16:40:13Z", - "timestamp": 1582299576512, - "url": "https://www.example.com/login?hope{this{works[!", - "ip": "61.127.217.15", - "ipLocation": { - "accuracyRadius": 10, - "latitude": 49.982, - "longitude": 36.2566, - "postalCode": "61202", - "timezone": "Europe/Dusseldorf", - "city": { - "name": "Dusseldorf" - }, - "country": { - "code": "DE", - "name": "Germany" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "63", - "name": "North Rhine-Westphalia" - } - ] - }, - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "74", - "browserFullVersion": "74.0.3729", - "os": "Windows", - "osVersion": "7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Windows NT 6.1; Win64; x64) ...." - }, - "confidence": { - "score": 0.97 - }, - "visitorFound": false, - "firstSeenAt": { - "global": "2022-03-16T11:26:45.362Z", - "subscription": "2022-03-16T11:31:01.101Z" - }, - "lastSeenAt": { - "global": null, - "subscription": null - }, - "replayed": false - } - }, - "botd": { - "data": { - "bot": { - "result": "notDetected" - }, - "url": "https://www.example.com/login?hope{this{works}[!", - "ip": "61.127.217.15", - "time": "2019-05-21T16:40:13Z", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 YaBrowser/24.1.0.0 Safari/537.36", - "requestId": "1708102555327.NLOjmg" - } - }, - "rootApps": { - "data": { - "result": false - } - }, - "emulator": { - "data": { - "result": false - } - }, - "ipInfo": { - "data": { - "v4": { - "address": "94.142.239.124", - "geolocation": { - "accuracyRadius": 20, - "latitude": 50.05, - "longitude": 14.4, - "postalCode": "150 00", - "timezone": "Europe/Prague", - "city": { - "name": "Prague" - }, - "country": { - "code": "CZ", - "name": "Czechia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "10", - "name": "Hlavni mesto Praha" - } - ] - }, - "asn": { - "asn": "7922", - "name": "COMCAST-7922", - "network": "73.136.0.0/13" - }, - "datacenter": { - "result": true, - "name": "DediPath" - } - }, - "v6": { - "address": "2001:db8:3333:4444:5555:6666:7777:8888", - "geolocation": { - "accuracyRadius": 5, - "latitude": 49.982, - "longitude": 36.2566, - "postalCode": "10112", - "timezone": "Europe/Berlin", - "city": { - "name": "Berlin" - }, - "country": { - "code": "DE", - "name": "Germany" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "BE", - "name": "Land Berlin" - } - ] - }, - "asn": { - "asn": "6805", - "name": "Telefonica Germany", - "network": "2a02:3100::/24" - }, - "datacenter": { - "result": false, - "name": "" - } - } - } - }, - "ipBlocklist": { - "data": { - "result": false, - "details": { - "emailSpam": false, - "attackSource": false - } - } - }, - "tor": { - "data": { - "result": false - } - }, - "vpn": { - "data": { - "result": false, - "confidence": "high", - "originTimezone": "Europe/Berlin", - "originCountry": "unknown", - "methods": { - "timezoneMismatch": false, - "publicVPN": false, - "auxiliaryMobile": false, - "osMismatch": false, - "relay": false - } - } - }, - "proxy": { - "data": { - "result": false, - "confidence": "high", - "details": { - "proxyType": "residential", - "lastSeenAt": "2025-08-12T13:00:00Z" - } - } - }, - "incognito": { - "data": { - "result": false - } - }, - "tampering": { - "data": { - "result": false, - "anomalyScore": 0.1955, - "antiDetectBrowser": false - } - }, - "clonedApp": { - "data": { - "result": false - } - }, - "factoryReset": { - "data": { - "time": "1970-01-01T00:00:00Z", - "timestamp": 0 - } - }, - "jailbroken": { - "data": { - "result": false - } - }, - "frida": { - "data": { - "result": false - } - }, - "privacySettings": { - "data": { - "result": false - } - }, - "virtualMachine": { - "data": { - "result": false - } - }, - "rawDeviceAttributes": { - "data": { - "architecture": { - "value": 127 - }, - "audio": { - "value": 35.73832903057337 - }, - "canvas": { - "value": { - "Winding": true, - "Geometry": "4dce9d6017c3e0c052a77252f29f2b1c", - "Text": "dd2474a56ff78c1de3e7a07070ba3b7d" - } - }, - "colorDepth": { - "value": 30 - }, - "colorGamut": { - "value": "p3" - }, - "contrast": { - "value": 0 - }, - "cookiesEnabled": { - "value": true - }, - "cpuClass": {}, - "fonts": { - "value": ["Arial Unicode MS", "Gill Sans", "Helvetica Neue", "Menlo"] - } - } - }, - "highActivity": { - "data": { - "result": false - } - }, - "locationSpoofing": { - "data": { - "result": false - } - }, - "velocity": { - "data": { - "distinctIp": { - "intervals": { - "5m": 1, - "1h": 1, - "24h": 1 - } - }, - "distinctLinkedId": {}, - "distinctCountry": { - "intervals": { - "5m": 1, - "1h": 2, - "24h": 2 - } - }, - "events": { - "intervals": { - "5m": 1, - "1h": 5, - "24h": 5 - } - }, - "ipEvents": { - "intervals": { - "5m": 1, - "1h": 5, - "24h": 5 - } - }, - "distinctIpByLinkedId": { - "intervals": { - "5m": 1, - "1h": 5, - "24h": 5 - } - }, - "distinctVisitorIdByLinkedId": { - "intervals": { - "5m": 1, - "1h": 5, - "24h": 5 - } - } - } - }, - "developerTools": { - "data": { - "result": false - } - }, - "mitmAttack": { - "data": { - "result": false - } - }, - "proximity": { - "data": { - "id": "w1aTfd4MCvl", - "precisionRadius": 10, - "confidence": 0.95 - } - } - }} - ], - "paginationKey": "1655373953086" -} diff --git a/test/mocks/get_visitors_200_limit_1.json b/test/mocks/get_visitors_200_limit_1.json deleted file mode 100644 index f6357ea5..00000000 --- a/test/mocks/get_visitors_200_limit_1.json +++ /dev/null @@ -1,61 +0,0 @@ -{ - "visitorId": "AcxioeQKffpXF8iGQK3P", - "visits": [ - { - "requestId": "1655373953086.DDlfmP", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "102", - "browserFullVersion": "102.0.5005", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36" - }, - "incognito": false, - "ip": "82.118.30.68", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 50.0805, - "longitude": 14.467, - "postalCode": "130 00", - "timezone": "Europe/Prague", - "city": { - "name": "Prague" - }, - "country": { - "code": "CZ", - "name": "Czechia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "10", - "name": "Hlavni mesto Praha" - } - ] - }, - "timestamp": 1655373953094, - "time": "2022-06-16T10:05:53Z", - "url": "https://dashboard.fingerprint.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-06-16T10:03:00.912Z", - "subscription": "2022-06-16T10:03:00.912Z" - } - } - ], - "lastTimestamp": 1655373953086, - "paginationKey": "1655373953086.DDlfmP" -} diff --git a/test/mocks/get_visitors_200_limit_500.json b/test/mocks/get_visitors_200_limit_500.json deleted file mode 100644 index 3e3aceb0..00000000 --- a/test/mocks/get_visitors_200_limit_500.json +++ /dev/null @@ -1,3030 +0,0 @@ -{ - "visitorId": "AcxioeQKffpXF8iGQK3P", - "visits": [ - { - "requestId": "1655373780901.HhjRFX", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "102", - "browserFullVersion": "102.0.5005", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36" - }, - "incognito": false, - "ip": "188.242.36.107", - "ipLocation": { - "accuracyRadius": 5, - "latitude": 59.8983, - "longitude": 30.2618, - "postalCode": "190924", - "timezone": "Europe/Moscow", - "city": { - "name": "St Petersburg" - }, - "country": { - "code": "RU", - "name": "Russia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "SPE", - "name": "St.-Petersburg" - } - ] - }, - "timestamp": 1655373780912, - "time": "2022-06-16T10:03:00Z", - "url": "https://fingerprint.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-06-16T05:27:30.578Z", - "subscription": "2022-06-16T05:27:30.578Z" - } - }, - { - "requestId": "1655357250568.vqejDF", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "102", - "browserFullVersion": "102.0.5005", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36" - }, - "incognito": false, - "ip": "82.118.30.62", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 50.0805, - "longitude": 14.467, - "postalCode": "130 00", - "timezone": "Europe/Prague", - "city": { - "name": "Prague" - }, - "country": { - "code": "CZ", - "name": "Czechia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "10", - "name": "Hlavni mesto Praha" - } - ] - }, - "timestamp": 1655357250578, - "time": "2022-06-16T05:27:30Z", - "url": "https://fingerprint.com/", - "tag": {}, - "confidence": { - "score": 0.99 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-06-15T15:28:33.479Z", - "subscription": "2022-06-15T15:28:33.479Z" - } - }, - { - "requestId": "1655306913474.kFQsQx", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "102", - "browserFullVersion": "102.0.5005", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36" - }, - "incognito": false, - "ip": "82.118.30.68", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 50.0805, - "longitude": 14.467, - "postalCode": "130 00", - "timezone": "Europe/Prague", - "city": { - "name": "Prague" - }, - "country": { - "code": "CZ", - "name": "Czechia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "10", - "name": "Hlavni mesto Praha" - } - ] - }, - "timestamp": 1655306913479, - "time": "2022-06-15T15:28:33Z", - "url": "https://fingerprint.com/", - "tag": {}, - "confidence": { - "score": 0.99 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-06-15T08:47:34.677Z", - "subscription": "2022-06-15T08:47:34.677Z" - } - }, - { - "requestId": "1655282854672.vz4ZlN", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "102", - "browserFullVersion": "102.0.5005", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36" - }, - "incognito": false, - "ip": "82.118.30.91", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 50.0805, - "longitude": 14.467, - "postalCode": "130 00", - "timezone": "Europe/Prague", - "city": { - "name": "Prague" - }, - "country": { - "code": "CZ", - "name": "Czechia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "10", - "name": "Hlavni mesto Praha" - } - ] - }, - "timestamp": 1655282854677, - "time": "2022-06-15T08:47:34Z", - "url": "https://fingerprint.com/", - "tag": {}, - "confidence": { - "score": 0.99 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-06-14T14:19:42.753Z", - "subscription": "2022-06-14T14:19:42.753Z" - } - }, - { - "requestId": "1655216382743.RDRa4h", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "102", - "browserFullVersion": "102.0.5005", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36" - }, - "incognito": false, - "ip": "188.242.36.107", - "ipLocation": { - "accuracyRadius": 5, - "latitude": 59.8983, - "longitude": 30.2618, - "postalCode": "190924", - "timezone": "Europe/Moscow", - "city": { - "name": "St Petersburg" - }, - "country": { - "code": "RU", - "name": "Russia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "SPE", - "name": "St.-Petersburg" - } - ] - }, - "timestamp": 1655216382753, - "time": "2022-06-14T14:19:42Z", - "url": "https://fingerprint.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-06-13T07:53:19.878Z", - "subscription": "2022-06-13T07:53:19.878Z" - } - }, - { - "requestId": "1655106799870.C8m8hR", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "102", - "browserFullVersion": "102.0.5005", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.137", - "timestamp": 1655106799878, - "time": "2022-06-13T07:53:19Z", - "url": "https://fingerprint.com/", - "tag": {}, - "confidence": { - "score": 0.99 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-06-07T12:54:35.413Z", - "subscription": "2022-06-07T12:54:35.413Z" - } - }, - { - "requestId": "1654606475406.2uXCJx", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "102", - "browserFullVersion": "102.0.5005", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36" - }, - "incognito": false, - "ip": "89.38.224.157", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 44.804, - "longitude": 20.4651 - }, - "timestamp": 1654606475413, - "time": "2022-06-07T12:54:35Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 0.99 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-06-07T09:37:57.43Z", - "subscription": "2022-06-07T09:37:57.43Z" - } - }, - { - "requestId": "1654594677423.pCHmKJ", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "102", - "browserFullVersion": "102.0.5005", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36" - }, - "incognito": false, - "ip": "188.242.36.107", - "ipLocation": { - "timezone": "Europe/Moscow" - }, - "timestamp": 1654594677430, - "time": "2022-06-07T09:37:57Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 0.99 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-06-07T09:37:50.109Z", - "subscription": "2022-06-07T09:37:50.109Z" - } - }, - { - "requestId": "1654594670097.Lmodmj", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "102", - "browserFullVersion": "102.0.5005", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36" - }, - "incognito": false, - "ip": "188.242.36.107", - "ipLocation": { - "accuracyRadius": 5, - "latitude": 59.8983, - "longitude": 30.2618, - "postalCode": "190924", - "timezone": "Europe/Moscow", - "city": { - "name": "St Petersburg" - }, - "country": { - "code": "RU", - "name": "Russia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "SPE", - "name": "St.-Petersburg" - } - ] - }, - "timestamp": 1654594670109, - "time": "2022-06-07T09:37:50Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 0.99 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-06-07T08:31:31.9Z", - "subscription": "2022-06-07T08:31:31.9Z" - } - }, - { - "requestId": "1654590691894.aCYqYE", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "102", - "browserFullVersion": "102.0.5005", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36" - }, - "incognito": false, - "ip": "188.242.36.107", - "ipLocation": { - "accuracyRadius": 5, - "latitude": 59.8983, - "longitude": 30.2618, - "postalCode": "190924", - "timezone": "Europe/Moscow", - "city": { - "name": "St Petersburg" - }, - "country": { - "code": "RU", - "name": "Russia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "SPE", - "name": "St.-Petersburg" - } - ] - }, - "timestamp": 1654590691900, - "time": "2022-06-07T08:31:31Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 0.99 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-06-06T09:05:25.954Z", - "subscription": "2022-06-06T09:05:25.954Z" - } - }, - { - "requestId": "1654506325946.ijIwzu", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "102", - "browserFullVersion": "102.0.5005", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36" - }, - "incognito": false, - "ip": "89.38.224.165", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 44.804, - "longitude": 20.4651, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1654506325954, - "time": "2022-06-06T09:05:25Z", - "url": "https://fingerprintcom.netlify.app/blog/name-change/", - "tag": {}, - "confidence": { - "score": 0.99 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-06-02T16:58:53.635Z", - "subscription": "2022-06-02T16:58:53.635Z" - } - }, - { - "requestId": "1654189133629.0V1gtF", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "102", - "browserFullVersion": "102.0.5005", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36" - }, - "incognito": false, - "ip": "89.38.224.165", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 44.804, - "longitude": 20.4651, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1654189133635, - "time": "2022-06-02T16:58:53Z", - "url": "https://fingerprintcom.netlify.app/blog/name-change/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-06-02T16:58:51.483Z", - "subscription": "2022-06-02T16:58:51.483Z" - } - }, - { - "requestId": "1654189131472.r49Bbh", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "102", - "browserFullVersion": "102.0.5005", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36" - }, - "incognito": false, - "ip": "89.38.224.165", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 44.804, - "longitude": 20.4651, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1654189131483, - "time": "2022-06-02T16:58:51Z", - "url": "https://fingerprintcom.netlify.app/", - "tag": {}, - "confidence": { - "score": 0.95 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-05-27T14:52:26.624Z", - "subscription": "2022-05-27T14:52:26.624Z" - } - }, - { - "requestId": "1653663146617.o8KpJO", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "101", - "browserFullVersion": "101.0.4951", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/101.0.4951.64 Safari/537.36" - }, - "incognito": false, - "ip": "89.38.224.165", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 44.804, - "longitude": 20.4651, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1653663146624, - "time": "2022-05-27T14:52:26Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-05-20T09:50:06.7Z", - "subscription": "2022-05-20T09:50:06.7Z" - } - }, - { - "requestId": "1653040206694.Q5Csig", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "101", - "browserFullVersion": "101.0.4951", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/101.0.4951.54 Safari/537.36" - }, - "incognito": false, - "ip": "89.38.224.165", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 44.804, - "longitude": 20.4651, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1653040206700, - "time": "2022-05-20T09:50:06Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-05-19T16:27:38.029Z", - "subscription": "2022-05-19T16:27:38.029Z" - } - }, - { - "requestId": "1652977658020.xbfYhA", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "101", - "browserFullVersion": "101.0.4951", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/101.0.4951.54 Safari/537.36" - }, - "incognito": false, - "ip": "89.38.224.165", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 44.804, - "longitude": 20.4651, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1652977658029, - "time": "2022-05-19T16:27:38Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-05-17T15:09:32.666Z", - "subscription": "2022-05-17T15:09:32.666Z" - } - }, - { - "requestId": "1652800172657.xA22Pd", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "101", - "browserFullVersion": "101.0.4951", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/101.0.4951.54 Safari/537.36" - }, - "incognito": false, - "ip": "89.38.224.165", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 44.804, - "longitude": 20.4651, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1652800172666, - "time": "2022-05-17T15:09:32Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-05-17T14:18:17.631Z", - "subscription": "2022-05-17T14:18:17.631Z" - } - }, - { - "requestId": "1652797097626.faAMJO", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "101", - "browserFullVersion": "101.0.4951", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/101.0.4951.54 Safari/537.36" - }, - "incognito": false, - "ip": "89.38.224.165", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 44.804, - "longitude": 20.4651, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1652797097631, - "time": "2022-05-17T14:18:17Z", - "url": "https://fingerprintjs.com/careers/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-05-17T10:16:04.809Z", - "subscription": "2022-05-17T10:16:04.809Z" - } - }, - { - "requestId": "1652782564800.MWH0GO", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "101", - "browserFullVersion": "101.0.4951", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/101.0.4951.54 Safari/537.36" - }, - "incognito": false, - "ip": "89.38.224.165", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 44.804, - "longitude": 20.4651, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1652782564809, - "time": "2022-05-17T10:16:04Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-05-16T06:47:01.511Z", - "subscription": "2022-05-16T06:47:01.511Z" - } - }, - { - "requestId": "1652683621505.1tOjuc", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "101", - "browserFullVersion": "101.0.4951", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/101.0.4951.54 Safari/537.36" - }, - "incognito": false, - "ip": "217.150.54.233", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 59.8983, - "longitude": 30.2618, - "postalCode": "190924", - "timezone": "Europe/Moscow", - "city": { - "name": "St Petersburg" - }, - "country": { - "code": "RU", - "name": "Russia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "SPE", - "name": "St.-Petersburg" - } - ] - }, - "timestamp": 1652683621511, - "time": "2022-05-16T06:47:01Z", - "url": "https://fingerprintjs.com/products/bot-detection/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-05-16T06:45:49.586Z", - "subscription": "2022-05-16T06:45:49.586Z" - } - }, - { - "requestId": "1652683586557.67Faeg", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "101", - "browserFullVersion": "101.0.4951", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/101.0.4951.54 Safari/537.36" - }, - "incognito": true, - "ip": "217.150.54.233", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 59.8983, - "longitude": 30.2618, - "postalCode": "190924", - "timezone": "Europe/Moscow", - "city": { - "name": "St Petersburg" - }, - "country": { - "code": "RU", - "name": "Russia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "SPE", - "name": "St.-Petersburg" - } - ] - }, - "timestamp": 1652683586562, - "time": "2022-05-16T06:46:26Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 0.94 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-05-16T06:45:49.586Z", - "subscription": "2022-05-16T06:45:49.586Z" - } - }, - { - "requestId": "1652683549513.aVRqEP", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "101", - "browserFullVersion": "101.0.4951", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/101.0.4951.54 Safari/537.36" - }, - "incognito": false, - "ip": "217.150.54.233", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 59.8983, - "longitude": 30.2618, - "postalCode": "190924", - "timezone": "Europe/Moscow", - "city": { - "name": "St Petersburg" - }, - "country": { - "code": "RU", - "name": "Russia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "SPE", - "name": "St.-Petersburg" - } - ] - }, - "timestamp": 1652683549586, - "time": "2022-05-16T06:45:49Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-05-05T10:11:25.96Z", - "subscription": "2022-05-05T10:11:25.96Z" - } - }, - { - "requestId": "1651745485951.Oj68me", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "89.38.224.165", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 44.804, - "longitude": 20.4651, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1651745485960, - "time": "2022-05-05T10:11:25Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-05-05T09:33:40.155Z", - "subscription": "2022-05-05T09:33:40.155Z" - } - }, - { - "requestId": "1651743220004.W02rhx", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "89.38.224.165", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 44.804, - "longitude": 20.4651, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1651743220155, - "time": "2022-05-05T09:33:40Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-05-03T15:26:32.826Z", - "subscription": "2022-05-03T15:26:32.826Z" - } - }, - { - "requestId": "1651591592822.Is9u93", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "89.38.224.157", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 44.804, - "longitude": 20.4651, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1651591592826, - "time": "2022-05-03T15:26:32Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-29T13:23:37.049Z", - "subscription": "2022-04-29T13:23:37.049Z" - } - }, - { - "requestId": "1651238617044.rMVPGS", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "89.38.224.165", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 44.804, - "longitude": 20.4651, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1651238617049, - "time": "2022-04-29T13:23:37Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-29T10:37:53.333Z", - "subscription": "2022-04-29T10:37:53.333Z" - } - }, - { - "requestId": "1651228673329.QZI2Cu", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "188.242.36.107", - "ipLocation": { - "accuracyRadius": 5, - "latitude": 59.8983, - "longitude": 30.2618, - "postalCode": "190924", - "timezone": "Europe/Moscow", - "city": { - "name": "St Petersburg" - }, - "country": { - "code": "RU", - "name": "Russia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "SPE", - "name": "St.-Petersburg" - } - ] - }, - "timestamp": 1651228673333, - "time": "2022-04-29T10:37:53Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-28T13:58:06.323Z", - "subscription": "2022-04-28T13:58:06.323Z" - } - }, - { - "requestId": "1651154286221.YvuOCP", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "84.247.59.113", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 50.0971, - "longitude": 8.5952, - "postalCode": "65933", - "timezone": "Europe/Berlin", - "city": { - "name": "Frankfurt am Main" - }, - "country": { - "code": "DE", - "name": "Germany" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "HE", - "name": "Hesse" - } - ] - }, - "timestamp": 1651154286323, - "time": "2022-04-28T13:58:06Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-28T12:16:02.564Z", - "subscription": "2022-04-28T12:16:02.564Z" - } - }, - { - "requestId": "1651148162556.dySgif", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "84.247.59.113", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 50.0971, - "longitude": 8.5952, - "postalCode": "65933", - "timezone": "Europe/Berlin", - "city": { - "name": "Frankfurt am Main" - }, - "country": { - "code": "DE", - "name": "Germany" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "HE", - "name": "Hesse" - } - ] - }, - "timestamp": 1651148162564, - "time": "2022-04-28T12:16:02Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-28T11:57:13.267Z", - "subscription": "2022-04-28T11:57:13.267Z" - } - }, - { - "requestId": "1651147033260.SxmFvL", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "84.247.59.146", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 50.0971, - "longitude": 8.5952, - "postalCode": "65933", - "timezone": "Europe/Berlin", - "city": { - "name": "Frankfurt am Main" - }, - "country": { - "code": "DE", - "name": "Germany" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "HE", - "name": "Hesse" - } - ] - }, - "timestamp": 1651147033267, - "time": "2022-04-28T11:57:13Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-28T11:57:06.24Z", - "subscription": "2022-04-28T11:57:06.24Z" - } - }, - { - "requestId": "1651147026139.aAZ8TO", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "84.247.59.146", - "ipLocation": { - "accuracyRadius": 20, - "latitude": 50.0971, - "longitude": 8.5952, - "postalCode": "65933", - "timezone": "Europe/Berlin", - "city": { - "name": "Frankfurt am Main" - }, - "country": { - "code": "DE", - "name": "Germany" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "HE", - "name": "Hesse" - } - ] - }, - "timestamp": 1651147026240, - "time": "2022-04-28T11:57:06Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-26T14:10:31.908Z", - "subscription": "2022-04-26T14:10:31.908Z" - } - }, - { - "requestId": "1650982231903.eG0b6v", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.105", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650982231908, - "time": "2022-04-26T14:10:31Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-26T11:43:37.373Z", - "subscription": "2022-04-26T11:43:37.373Z" - } - }, - { - "requestId": "1650973417360.xupFFD", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.99", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650973417373, - "time": "2022-04-26T11:43:37Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-26T11:43:30.111Z", - "subscription": "2022-04-26T11:43:30.111Z" - } - }, - { - "requestId": "1650973410104.AQD4qu", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.99", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650973410111, - "time": "2022-04-26T11:43:30Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-26T11:22:34.148Z", - "subscription": "2022-04-26T11:22:34.148Z" - } - }, - { - "requestId": "1650972154133.lSWE8a", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.96", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650972154148, - "time": "2022-04-26T11:22:34Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-26T11:22:03.83Z", - "subscription": "2022-04-26T11:22:03.83Z" - } - }, - { - "requestId": "1650972123824.xk8MUR", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.96", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650972123830, - "time": "2022-04-26T11:22:03Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-25T09:46:15.458Z", - "subscription": "2022-04-25T09:46:15.458Z" - } - }, - { - "requestId": "1650879975452.kfuowM", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "188.242.36.107", - "ipLocation": { - "accuracyRadius": 5, - "latitude": 59.8983, - "longitude": 30.2618, - "postalCode": "190924", - "timezone": "Europe/Moscow", - "city": { - "name": "St Petersburg" - }, - "country": { - "code": "RU", - "name": "Russia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "SPE", - "name": "St.-Petersburg" - } - ] - }, - "timestamp": 1650879975458, - "time": "2022-04-25T09:46:15Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-22T16:51:44.816Z", - "subscription": "2022-04-22T16:51:44.816Z" - } - }, - { - "requestId": "1650646304808.xQbAju", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.227", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650646304816, - "time": "2022-04-22T16:51:44Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-21T11:43:33.116Z", - "subscription": "2022-04-21T11:43:33.116Z" - } - }, - { - "requestId": "1650541413105.leAPLz", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.89", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650541413116, - "time": "2022-04-21T11:43:33Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-20T17:11:54.717Z", - "subscription": "2022-04-20T17:11:54.717Z" - } - }, - { - "requestId": "1650474714710.M1IGsl", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.111", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650474714717, - "time": "2022-04-20T17:11:54Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-20T17:11:47.217Z", - "subscription": "2022-04-20T17:11:47.217Z" - } - }, - { - "requestId": "1650474707211.CEUuZk", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.111", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650474707217, - "time": "2022-04-20T17:11:47Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-20T17:11:12.076Z", - "subscription": "2022-04-20T17:11:12.076Z" - } - }, - { - "requestId": "1650474672071.Pz4WsK", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.111", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650474672076, - "time": "2022-04-20T17:11:12Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-19T12:29:06.692Z", - "subscription": "2022-04-19T12:29:06.692Z" - } - }, - { - "requestId": "1650371346684.1d7sgv", - "browserDetails": { - "browserName": "Chrome Mobile", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Android", - "osVersion": "6.0", - "device": "Nexus 5", - "userAgent": "Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Mobile Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.198", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650371346692, - "time": "2022-04-19T12:29:06Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-19T12:29:02.15Z", - "subscription": "2022-04-19T12:29:02.15Z" - } - }, - { - "requestId": "1650371342145.oWyfRx", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.198", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650371342150, - "time": "2022-04-19T12:29:02Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-19T11:35:14.729Z", - "subscription": "2022-04-19T11:35:14.729Z" - } - }, - { - "requestId": "1650368114723.YEXcHI", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.206", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650368114729, - "time": "2022-04-19T11:35:14Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-19T11:13:33.107Z", - "subscription": "2022-04-19T11:13:33.107Z" - } - }, - { - "requestId": "1650366813101.SvUZC1", - "browserDetails": { - "browserName": "Chrome Mobile", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Android", - "osVersion": "6.0", - "device": "Nexus 5", - "userAgent": "Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Mobile Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.204", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650366813107, - "time": "2022-04-19T11:13:33Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-19T11:13:28.453Z", - "subscription": "2022-04-19T11:13:28.453Z" - } - }, - { - "requestId": "1650366808426.Hy6j7v", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.204", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650366808453, - "time": "2022-04-19T11:13:28Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-19T11:07:05.19Z", - "subscription": "2022-04-19T11:07:05.19Z" - } - }, - { - "requestId": "1650366425184.xvYkdr", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.204", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650366425190, - "time": "2022-04-19T11:07:05Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-19T11:07:00.483Z", - "subscription": "2022-04-19T11:07:00.483Z" - } - }, - { - "requestId": "1650366420377.VR5pDX", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.204", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650366420483, - "time": "2022-04-19T11:07:00Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-19T10:37:45.279Z", - "subscription": "2022-04-19T10:37:45.279Z" - } - }, - { - "requestId": "1650364665274.qq31O4", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.172", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650364665279, - "time": "2022-04-19T10:37:45Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-19T10:22:58.87Z", - "subscription": "2022-04-19T10:22:58.87Z" - } - }, - { - "requestId": "1650363778864.tsVBjO", - "browserDetails": { - "browserName": "Chrome Mobile", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Android", - "osVersion": "6.0", - "device": "Nexus 5", - "userAgent": "Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Mobile Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.210", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650363778870, - "time": "2022-04-19T10:22:58Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-19T10:22:46.894Z", - "subscription": "2022-04-19T10:22:46.894Z" - } - }, - { - "requestId": "1650363766889.KuVDpm", - "browserDetails": { - "browserName": "Chrome Mobile", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Android", - "osVersion": "6.0", - "device": "Nexus 5", - "userAgent": "Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Mobile Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.210", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650363766894, - "time": "2022-04-19T10:22:46Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-19T10:07:01.528Z", - "subscription": "2022-04-19T10:07:01.528Z" - } - }, - { - "requestId": "1650362821521.dXH2Ce", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.180", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650362821528, - "time": "2022-04-19T10:07:01Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-19T10:02:42.46Z", - "subscription": "2022-04-19T10:02:42.46Z" - } - }, - { - "requestId": "1650362562448.a5cPLU", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.127 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.180", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650362562460, - "time": "2022-04-19T10:02:42Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-18T17:06:30.834Z", - "subscription": "2022-04-18T17:06:30.834Z" - } - }, - { - "requestId": "1650301590829.YXGX7h", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.75 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.195", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650301590834, - "time": "2022-04-18T17:06:30Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-18T12:23:30.446Z", - "subscription": "2022-04-18T12:23:30.446Z" - } - }, - { - "requestId": "1650284610441.lJrX4M", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.75 Safari/537.36" - }, - "incognito": false, - "ip": "45.86.200.179", - "ipLocation": { - "accuracyRadius": 1000, - "latitude": 52.3824, - "longitude": 4.8995, - "timezone": "Europe/Amsterdam", - "country": { - "code": "NL", - "name": "Netherlands" - }, - "continent": { - "code": "EU", - "name": "Europe" - } - }, - "timestamp": 1650284610446, - "time": "2022-04-18T12:23:30Z", - "url": "https://fingerprintjs.com/blog/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-04-06T14:53:00.526Z", - "subscription": "2022-04-06T14:53:00.526Z" - } - }, - { - "requestId": "1649256780522.WAXWf2", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.60 Safari/537.36" - }, - "incognito": false, - "ip": "109.245.35.200", - "ipLocation": { - "accuracyRadius": 50, - "latitude": 44.8166, - "longitude": 20.4721, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1649256780526, - "time": "2022-04-06T14:53:00Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-03-18T11:08:35.698Z", - "subscription": "2022-03-18T11:08:35.698Z" - } - }, - { - "requestId": "1649256780520.RRC4PR", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "100", - "browserFullVersion": "100.0.4896", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.60 Safari/537.36" - }, - "incognito": false, - "ip": "109.245.35.200", - "ipLocation": { - "accuracyRadius": 50, - "latitude": 44.8166, - "longitude": 20.4721, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1649256780525, - "time": "2022-04-06T14:53:00Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-03-18T11:08:35.698Z", - "subscription": "2022-03-18T11:08:35.698Z" - } - }, - { - "requestId": "1647601715689.iocXfW", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "98", - "browserFullVersion": "98.0.4758", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/98.0.4758.109 Safari/537.36" - }, - "incognito": false, - "ip": "178.223.21.183", - "ipLocation": { - "accuracyRadius": 50, - "latitude": 44.8166, - "longitude": 20.4721, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1647601715698, - "time": "2022-03-18T11:08:35Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-03-16T08:21:23.62Z", - "subscription": "2022-03-16T08:21:23.62Z" - } - }, - { - "requestId": "1647418883615.Vck2NA", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "98", - "browserFullVersion": "98.0.4758", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/98.0.4758.109 Safari/537.36" - }, - "incognito": false, - "ip": "87.116.165.97", - "ipLocation": { - "accuracyRadius": 50, - "latitude": 44.8166, - "longitude": 20.4721, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1647418883620, - "time": "2022-03-16T08:21:23Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-03-16T08:21:18.398Z", - "subscription": "2022-03-16T08:21:18.398Z" - } - }, - { - "requestId": "1647418878391.NZDmht", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "98", - "browserFullVersion": "98.0.4758", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/98.0.4758.109 Safari/537.36" - }, - "incognito": false, - "ip": "87.116.165.97", - "ipLocation": { - "accuracyRadius": 50, - "latitude": 44.8166, - "longitude": 20.4721, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1647418878398, - "time": "2022-03-16T08:21:18Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-03-15T11:46:51.858Z", - "subscription": "2022-03-15T11:46:51.858Z" - } - }, - { - "requestId": "1647344811836.RvNkL5", - "browserDetails": { - "browserName": "Chrome", - "browserMajorVersion": "98", - "browserFullVersion": "98.0.4758", - "os": "Mac OS X", - "osVersion": "10.15.7", - "device": "Other", - "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/98.0.4758.109 Safari/537.36" - }, - "incognito": false, - "ip": "87.116.165.97", - "ipLocation": { - "accuracyRadius": 50, - "latitude": 44.8166, - "longitude": 20.4721, - "timezone": "Europe/Belgrade", - "city": { - "name": "Belgrade" - }, - "country": { - "code": "RS", - "name": "Serbia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "00", - "name": "Belgrade" - } - ] - }, - "timestamp": 1647344811858, - "time": "2022-03-15T11:46:51Z", - "url": "https://fingerprintjs.com/", - "tag": {}, - "confidence": { - "score": 1 - }, - "visitorFound": true, - "firstSeenAt": { - "global": "2022-02-04T11:31:20Z", - "subscription": "2022-02-04T11:31:20Z" - }, - "lastSeenAt": { - "global": "2022-03-08T12:33:05.677Z", - "subscription": "2022-03-08T12:33:05.677Z" - } - } - ] -} diff --git a/test/mocks/get_visitors_400_bad_request.json b/test/mocks/get_visitors_400_bad_request.json deleted file mode 100644 index c2b6e295..00000000 --- a/test/mocks/get_visitors_400_bad_request.json +++ /dev/null @@ -1,3 +0,0 @@ -{ - "error": "bad request" -} diff --git a/test/mocks/get_visitors_403_forbidden.json b/test/mocks/get_visitors_403_forbidden.json deleted file mode 100644 index 8a886d18..00000000 --- a/test/mocks/get_visitors_403_forbidden.json +++ /dev/null @@ -1,3 +0,0 @@ -{ - "error": "Forbidden (HTTP 403)" -} diff --git a/test/mocks/get_visitors_429_too_many_requests.json b/test/mocks/get_visitors_429_too_many_requests.json deleted file mode 100644 index 00d00f2e..00000000 --- a/test/mocks/get_visitors_429_too_many_requests.json +++ /dev/null @@ -1,3 +0,0 @@ -{ - "error": "too many requests" -} diff --git a/test/mocks/related-visitors/get_related_visitors_200.json b/test/mocks/related-visitors/get_related_visitors_200.json deleted file mode 100644 index 7a46a69e..00000000 --- a/test/mocks/related-visitors/get_related_visitors_200.json +++ /dev/null @@ -1,10 +0,0 @@ -{ - "relatedVisitors": [ - { - "visitorId": "NtCUJGceWX9RpvSbhvOm" - }, - { - "visitorId": "25ee02iZwGxeyT0jMNkZ" - } - ] -} diff --git a/test/mocks/related-visitors/get_related_visitors_200_empty.json b/test/mocks/related-visitors/get_related_visitors_200_empty.json deleted file mode 100644 index 6c9b02c1..00000000 --- a/test/mocks/related-visitors/get_related_visitors_200_empty.json +++ /dev/null @@ -1,3 +0,0 @@ -{ - "relatedVisitors": [] -} diff --git a/test/mocks/update_event_multiple_fields_request.json b/test/mocks/update_event_multiple_fields_request.json deleted file mode 100644 index f85d2e75..00000000 --- a/test/mocks/update_event_multiple_fields_request.json +++ /dev/null @@ -1,7 +0,0 @@ -{ - "linkedId": "myNewLinkedId", - "tag": { - "myTag": "myNewValue" - }, - "suspect": true -} diff --git a/test/mocks/update_event_one_field_request.json b/test/mocks/update_event_one_field_request.json deleted file mode 100644 index 0ebd1549..00000000 --- a/test/mocks/update_event_one_field_request.json +++ /dev/null @@ -1,3 +0,0 @@ -{ - "linkedId": "myNewLinkedId" -} diff --git a/test/mocks/webhook.json b/test/mocks/webhook.json deleted file mode 100644 index 1180fcdc..00000000 --- a/test/mocks/webhook.json +++ /dev/null @@ -1,293 +0,0 @@ -{ - "requestId": "Px6VxbRC6WBkA39yeNH3", - "url": "https://banking.example.com/signup", - "ip": "216.3.128.12", - "tag": { - "requestType": "signup", - "yourCustomId": 45321 - }, - "time": "2019-10-12T07:20:50.52Z", - "timestamp": 1554910997788, - "ipLocation": { - "accuracyRadius": 1, - "city": { - "name": "Bolingbrook" - }, - "continent": { - "code": "NA", - "name": "North America" - }, - "country": { - "code": "US", - "name": "United States" - }, - "latitude": 41.12933, - "longitude": -88.9954, - "postalCode": "60547", - "subdivisions": [ - { - "isoCode": "IL", - "name": "Illinois" - } - ], - "timezone": "America/Chicago" - }, - "linkedId": "any-string", - "visitorId": "3HNey93AkBW6CRbxV6xP", - "visitorFound": true, - "confidence": { - "score": 0.97 - }, - "firstSeenAt": { - "global": "2022-03-16T11:26:45.362Z", - "subscription": "2022-03-16T11:31:01.101Z" - }, - "lastSeenAt": { - "global": "2022-03-16T11:28:34.023Z", - "subscription": null - }, - "browserDetails": { - "browserName": "Chrome", - "browserFullVersion": "73.0.3683.86", - "browserMajorVersion": "73", - "os": "Mac OS X", - "osVersion": "10.14.3", - "device": "Other", - "userAgent": "(Macintosh; Intel Mac OS X 10_14_3) Chrome/73.0.3683.86" - }, - "incognito": false, - "clientReferrer": "https://google.com?search=banking+services", - "bot": { - "result": "bad", - "type": "selenium" - }, - "userAgent": "(Macintosh; Intel Mac OS X 10_14_3) Chrome/73.0.3683.86", - "rootApps": { - "result": false - }, - "emulator": { - "result": false - }, - "ipInfo": { - "v4": { - "address": "94.142.239.124", - "geolocation": { - "accuracyRadius": 20, - "latitude": 50.05, - "longitude": 14.4, - "postalCode": "150 00", - "timezone": "Europe/Prague", - "city": { - "name": "Prague" - }, - "country": { - "code": "CZ", - "name": "Czechia" - }, - "continent": { - "code": "EU", - "name": "Europe" - }, - "subdivisions": [ - { - "isoCode": "10", - "name": "Hlavni mesto Praha" - } - ] - }, - "asn": { - "asn": "7922", - "name": "COMCAST-7922", - "network": "73.136.0.0/13" - }, - "datacenter": { - "result": true, - "name": "DediPath" - } - } - }, - "ipBlocklist": { - "result": false, - "details": { - "emailSpam": false, - "attackSource": false - } - }, - "tor": { - "result": false - }, - "vpn": { - "result": false, - "confidence": "high", - "originTimezone": "Europe/Berlin", - "originCountry": "unknown", - "methods": { - "timezoneMismatch": false, - "publicVPN": false, - "auxiliaryMobile": false, - "osMismatch": false, - "relay": false - } - }, - "proxy": { - "result": true, - "confidence": "high", - "details": { - "proxyType": "residential", - "lastSeenAt": "2025-08-12T13:00:00Z" - } - }, - "tampering": { - "result": false, - "anomalyScore": 0, - "antiDetectBrowser": false - }, - "clonedApp": { - "result": false - }, - "factoryReset": { - "time": "1970-01-01T00:00:00Z", - "timestamp": 0 - }, - "jailbroken": { - "result": false - }, - "frida": { - "result": false - }, - "privacySettings": { - "result": false - }, - "virtualMachine": { - "result": false - }, - "rawDeviceAttributes": { - "architecture": { - "value": 127 - }, - "audio": { - "value": 35.73832903057337 - }, - "canvas": { - "value": { - "Winding": true, - "Geometry": "4dce9d6017c3e0c052a77252f29f2b1c", - "Text": "dd2474a56ff78c1de3e7a07070ba3b7d" - } - }, - "colorDepth": { - "value": 30 - }, - "colorGamut": { - "value": "srgb" - }, - "contrast": { - "value": 0 - }, - "cookiesEnabled": { - "value": true - } - }, - "highActivity": { - "result": false - }, - "locationSpoofing": { - "result": true - }, - "suspectScore": { - "result": 0 - }, - "velocity": { - "distinctIp": { - "intervals": { - "5m": 1, - "1h": 1, - "24h": 1 - } - }, - "distinctLinkedId": {}, - "distinctCountry": { - "intervals": { - "5m": 1, - "1h": 2, - "24h": 2 - } - }, - "events": { - "intervals": { - "5m": 1, - "1h": 5, - "24h": 5 - } - }, - "ipEvents": { - "intervals": { - "5m": 1, - "1h": 5, - "24h": 5 - } - }, - "distinctIpByLinkedId": { - "intervals": { - "5m": 1, - "1h": 5, - "24h": 5 - } - }, - "distinctVisitorIdByLinkedId": { - "intervals": { - "5m": 1, - "1h": 5, - "24h": 5 - } - } - }, - "developerTools": { - "result": false - }, - "mitmAttack": { - "result": false - }, - "sdk": { - "platform": "js", - "version": "3.11.10" - }, - "replayed": false, - "supplementaryIds": { - "standard": { - "visitorId": "3HNey93AkBW6CRbxV6xP", - "visitorFound": true, - "confidence": { - "score": 0.97 - }, - "firstSeenAt": { - "global": "2022-03-16T11:26:45.362Z", - "subscription": "2022-03-16T11:31:01.101Z" - }, - "lastSeenAt": { - "global": "2022-03-16T11:28:34.023Z", - "subscription": "2022-03-16T11:28:34.023Z" - } - }, - "highRecall": { - "visitorId": "3HNey93AkBW6CRbxV6xP", - "visitorFound": true, - "confidence": { - "score": 0.97 - }, - "firstSeenAt": { - "global": "2022-03-16T11:26:45.362Z", - "subscription": "2022-03-16T11:31:01.101Z" - }, - "lastSeenAt": { - "global": "2022-03-16T11:28:34.023Z", - "subscription": "2022-03-16T11:28:34.023Z" - } - } - }, - "proximity": { - "id": "w1aTfd4MCvl", - "precisionRadius": 10, - "confidence": 0.95 - } -} diff --git a/test/mocks/webhook/webhook_event.json b/test/mocks/webhook/webhook_event.json new file mode 100644 index 00000000..d9e597b2 --- /dev/null +++ b/test/mocks/webhook/webhook_event.json @@ -0,0 +1,282 @@ +{ + "linked_id": "somelinkedId", + "tags": {}, + "timestamp": 1708102555327, + "event_id": "1708102555327.NLOjmg", + "url": "https://www.example.com/login?hope{this{works[!", + "ip_address": "61.127.217.15", + "user_agent": "Mozilla/5.0 (Windows NT 6.1; Win64; x64) ....", + "client_referrer": "https://example.com/blog/my-article", + "browser_details": { + "browser_name": "Chrome", + "browser_major_version": "74", + "browser_full_version": "74.0.3729", + "os": "Windows", + "os_version": "7", + "device": "Other" + }, + "identification": { + "visitor_id": "Ibk1527CUFmcnjLwIs4A9", + "confidence": { + "score": 0.97, + "version": "1.1" + }, + "visitor_found": false, + "first_seen_at": 1708102555327, + "last_seen_at": 1708102555327 + }, + "supplementary_id_high_recall": { + "visitor_id": "3HNey93AkBW6CRbxV6xP", + "visitor_found": true, + "confidence": { + "score": 0.97, + "version": "1.1" + }, + "first_seen_at": 1708102555327, + "last_seen_at": 1708102555327 + }, + "proximity": { + "id": "w1aTfd4MCvl", + "precision_radius": 10, + "confidence": 0.95 + }, + "bot": "not_detected", + "root_apps": false, + "emulator": false, + "ip_info": { + "v4": { + "address": "94.142.239.124", + "geolocation": { + "accuracy_radius": 20, + "latitude": 50.05, + "longitude": 14.4, + "postal_code": "150 00", + "timezone": "Europe/Prague", + "city_name": "Prague", + "country_code": "CZ", + "country_name": "Czechia", + "continent_code": "EU", + "continent_name": "Europe", + "subdivisions": [ + { + "iso_code": "10", + "name": "Hlavni mesto Praha" + } + ] + }, + "asn": "7922", + "asn_name": "COMCAST-7922", + "asn_network": "73.136.0.0/13", + "asn_type": "isp", + "datacenter_result": true, + "datacenter_name": "DediPath" + }, + "v6": { + "address": "2001:db8:3333:4444:5555:6666:7777:8888", + "geolocation": { + "accuracy_radius": 5, + "latitude": 49.982, + "longitude": 36.2566, + "postal_code": "10112", + "timezone": "Europe/Berlin", + "city_name": "Berlin", + "country_code": "DE", + "country_name": "Germany", + "continent_code": "EU", + "continent_name": "Europe", + "subdivisions": [ + { + "iso_code": "BE", + "name": "Land Berlin" + } + ] + }, + "asn": "6805", + "asn_name": "Telefonica Germany", + "asn_network": "2a02:3100::/24", + "asn_type": "isp", + "datacenter_result": false, + "datacenter_name": "" + } + }, + "ip_blocklist": { + "email_spam": false, + "attack_source": false, + "tor_node": false + }, + "proxy": true, + "proxy_confidence": "low", + "proxy_details": { + "proxy_type": "residential", + "last_seen_at": 1708102555327, + "provider": "Massive" + }, + "vpn": false, + "vpn_confidence": "high", + "vpn_origin_timezone": "Europe/Berlin", + "vpn_origin_country": "unknown", + "vpn_methods": { + "timezone_mismatch": false, + "public_vpn": false, + "auxiliary_mobile": false, + "os_mismatch": false, + "relay": false + }, + "incognito": false, + "tampering": false, + "tampering_details": { + "anomaly_score": 0.1955, + "anti_detect_browser": false + }, + "cloned_app": false, + "factory_reset_timestamp": 0, + "jailbroken": false, + "frida": false, + "privacy_settings": false, + "virtual_machine": false, + "location_spoofing": false, + "velocity": { + "distinct_ip": { + "5_minutes": 1, + "1_hour": 1, + "24_hours": 1 + }, + "distinct_country": { + "5_minutes": 1, + "1_hour": 2, + "24_hours": 2 + }, + "events": { + "5_minutes": 1, + "1_hour": 5, + "24_hours": 5 + }, + "ip_events": { + "5_minutes": 1, + "1_hour": 5, + "24_hours": 5 + }, + "distinct_ip_by_linked_id": { + "5_minutes": 1, + "1_hour": 5, + "24_hours": 5 + }, + "distinct_visitor_id_by_linked_id": { + "5_minutes": 1, + "1_hour": 5, + "24_hours": 5 + } + }, + "developer_tools": false, + "mitm_attack": false, + "sdk": { + "platform": "js", + "version": "3.11.10", + "integrations": [ + { + "name": "fingerprint-pro-react", + "version": "3.11.10", + "subintegration": { + "name": "preact", + "version": "10.21.0" + } + } + ] + }, + "replayed": false, + "high_activity_device": false, + "raw_device_attributes": { + "math": "5f030fa7d2e5f9f757bfaf81642eb1a6", + "vendor": "Google Inc.", + "plugins": [ + { + "description": "Portable Document Format", + "mimeTypes": [ + { + "suffixes": "pdf", + "type": "application/pdf" + }, + { + "suffixes": "pdf", + "type": "text/pdf" + } + ], + "name": "PDF Viewer" + } + ], + "webgl_extensions": { + "context_attributes": "6b1ed336830d2bc96442a9d76373252a", + "extension_parameters": "86a8abb36f0cb30b5946dec0c761d042", + "extensions": "57233d7b10f89fcd1ff95e3837ccd72d", + "parameters": "ea118c48e308bc4b0677118bbb3019ec", + "shader_precisions": "f223dfbcd580cf142da156d93790eb83", + "unsupported_extensions": [] + }, + "cookies_enabled": true, + "webgl_basics": { + "renderer": "WebKit WebGL", + "renderer_unmasked": "ANGLE (Apple, ANGLE Metal Renderer: Apple M4, Unspecified Version)", + "shading_language_version": "WebGL GLSL ES 1.0 (OpenGL ES GLSL ES 1.0 Chromium)", + "vendor": "WebKit", + "vendor_unmasked": "Google Inc. (Apple)", + "version": "WebGL 1.0 (OpenGL ES 2.0 Chromium)" + }, + "canvas": { + "geometry": "db3c1462576a399a03ae93d0ab9eb5c4", + "text": "70c3d3f7eb4408dc37a6bf8af1c51029", + "winding": true + }, + "hardware_concurrency": 10, + "languages": [ + [ + "en-US" + ] + ], + "color_depth": 24, + "fonts": [ + "Arial Unicode MS", + "Gill Sans", + "Helvetica Neue", + "Menlo" + ], + "indexed_db": true, + "touch_support": { + "max_touch_points": 0, + "touch_event": false, + "touch_start": false + }, + "device_memory": 8, + "oscpu": "Windows NT 6.1; Win64; x64", + "architecture": 127, + "screen_resolution": [ + 1920, + 1080 + ], + "timezone": "America/Sao_Paulo", + "emoji": { + "bottom": 32, + "font": "Times", + "height": 18, + "left": 8, + "right": 1608, + "top": 14, + "width": 1600, + "x": 8, + "y": 14 + }, + "font_preferences": { + "apple": 147.5625, + "default": 147.5625, + "min": 9.234375, + "mono": 133.0625, + "sans": 144.015625, + "serif": 147.5625, + "system": 146.09375 + }, + "platform": "MacIntel", + "local_storage": true, + "session_storage": true, + "date_time_locale": "en-US", + "audio": 124.04347745512496 + } +} \ No newline at end of file From 70b9d4db7a3059b022fc59a9da0fa80bdafbc2db Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Eray=20Ayd=C4=B1n?= Date: Sat, 7 Feb 2026 20:34:58 +0300 Subject: [PATCH 3/4] chore: update schema version Update `.schema-version` tracked OpenAPI schema version to `v3.0.1`. Related-Task: INTER-1795 --- .schema-version | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.schema-version b/.schema-version index a5db00c8..5e008de3 100644 --- a/.schema-version +++ b/.schema-version @@ -1 +1 @@ -v2.12.0 \ No newline at end of file +v3.0.1 \ No newline at end of file From b70a752b456d3a793327b7672f647a1cb19d96a6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Eray=20Ayd=C4=B1n?= Date: Thu, 19 Feb 2026 18:38:34 +0300 Subject: [PATCH 4/4] feat: update to latest OpenAPI schema Update `fingerprint-server-api.yaml` file to the latest OpenAPI schema. Related-Task: INTER-1795 --- res/fingerprint-server-api.yaml | 185 ++++++++++++++++---------------- 1 file changed, 90 insertions(+), 95 deletions(-) diff --git a/res/fingerprint-server-api.yaml b/res/fingerprint-server-api.yaml index 8da52a0c..7e23e15a 100644 --- a/res/fingerprint-server-api.yaml +++ b/res/fingerprint-server-api.yaml @@ -179,6 +179,7 @@ paths: tags: - Fingerprint operationId: searchEvents + x-dotnet-use-request-object: true summary: Search events description: > ## Search @@ -250,8 +251,9 @@ paths: When more results are available (e.g., you requested up to 100 results for your query using `limit`, but there are more than 100 events total matching your request), the `pagination_key` field is - added to the response. The key corresponds to the `timestamp` of the - last returned event. In the following request, use that value in the + added to the response. The pagination key is an arbitrary string + that should not be interpreted in any way and should be passed + as-is. In the following request, use that value in the `pagination_key` parameter to get the next page of results: @@ -273,20 +275,15 @@ paths: - name: bot in: query schema: - type: string - enum: - - all - - good - - bad - - none + $ref: '#/components/schemas/SearchEventsBot' description: > Filter events by the Bot Detection result, specifically: `all` - events where any kind of bot was detected. `good` - events where a good bot was detected. `bad` - events where a bad bot was detected. `none` - events where no bot was detected. - > Note: When using this parameter, only events with the `botd.bot` - property set to a valid value are returned. Events without a `botd` + > Note: When using this parameter, only events with the `bot` + property set to a valid value are returned. Events without a `bot` Smart Signal result are left out of the response. - name: ip_address in: query @@ -302,11 +299,11 @@ paths: in: query schema: type: string - description: > - Filter events by the ASN associated with the event's IP address. + description: > + Filter events by the ASN associated with the event's IP address. - This corresponds to the `ip_info.(v4|v6).asn` property in the - response. + This corresponds to the `ip_info.(v4|v6).asn` property in the + response. - name: linked_id in: query schema: @@ -507,11 +504,7 @@ paths: - name: vpn_confidence in: query schema: - type: string - enum: - - high, - - medium - - low + $ref: '#/components/schemas/SearchEventsVpnConfidence' description: > Filter events by VPN Detection result confidence level. @@ -590,11 +583,7 @@ paths: - name: sdk_platform in: query schema: - type: string - enum: - - js - - android - - ios + $ref: '#/components/schemas/SearchEventsSdkPlatform' description: > Filter events by the SDK Platform associated with the identification event (`sdk.platform` property) . @@ -805,7 +794,6 @@ components: endpoint](https://dev.fingerprint.com/reference/updateevent). Integration: type: object - additionalProperties: false properties: name: type: string @@ -815,7 +803,6 @@ components: description: The version of the specific integration, e.g. "3.11.10". subintegration: type: object - additionalProperties: false properties: name: type: string @@ -826,7 +813,6 @@ components: SDK: type: object description: Contains information about the SDK used to perform the request. - additionalProperties: false required: - platform - version @@ -853,26 +839,8 @@ components: description: > `true` if we determined that this payload was replayed, `false` otherwise. - TriggeredBy: - type: array - description: The rule(s) associated with triggering the webhook via rule engine. - items: - type: object - additionalProperties: false - required: - - id - - name - - description - properties: - id: - type: string - name: - type: string - description: - type: string IdentificationConfidence: type: object - additionalProperties: false required: - score properties: @@ -894,7 +862,6 @@ components: type: string Identification: type: object - additionalProperties: false required: - visitor_id - visitor_found @@ -925,7 +892,6 @@ components: Corresponding to Wed Sep 17 2025 00:41:46 GMT+0000 SupplementaryIDHighRecall: type: object - additionalProperties: false description: >- A supplementary browser identifier that prioritizes coverage over precision. The High Recall ID algorithm matches more generously, i.e., @@ -1000,7 +966,6 @@ components: `https://example.com/blog/my-article` BrowserDetails: type: object - additionalProperties: false required: - browser_name - browser_full_version @@ -1026,7 +991,6 @@ components: description: > Proximity ID represents a fixed geographical zone in a discrete global grid within which the device is observed. - additionalProperties: false required: - id - precision_radius @@ -1079,7 +1043,6 @@ components: BotInfo: type: object description: Extended bot information. - additionalProperties: false required: - category - provider @@ -1163,7 +1126,6 @@ components: * `false` - No signs of Frida or the client is not a mobile device. IPBlockList: type: object - additionalProperties: false properties: email_spam: type: boolean @@ -1176,7 +1138,6 @@ components: description: IP address was part of known TOR network activity. Geolocation: type: object - additionalProperties: false properties: accuracy_radius: type: integer @@ -1217,7 +1178,6 @@ components: type: array items: type: object - additionalProperties: false required: - iso_code - name @@ -1228,7 +1188,6 @@ components: type: string IPInfoV4: type: object - additionalProperties: false required: - address properties: @@ -1251,7 +1210,6 @@ components: type: string IPInfoV6: type: object - additionalProperties: false required: - address properties: @@ -1277,7 +1235,6 @@ components: description: >- Details about the request IP address. Has separate fields for v4 and v6 IP address versions. - additionalProperties: false properties: v4: $ref: '#/components/schemas/IPInfoV4' @@ -1300,7 +1257,6 @@ components: "high". ProxyDetails: type: object - additionalProperties: false description: Proxy detection details (present if `proxy` is `true`) required: - proxy_type @@ -1420,18 +1376,26 @@ components: items: $ref: '#/components/schemas/RuleActionHeaderField' EventRuleActionAllow: - type: object description: >- Informs the client that the request should be forwarded to the origin with optional request header modifications. - required: - - type + type: object properties: + ruleset_id: + $ref: '#/components/schemas/RulesetId' + rule_id: + $ref: '#/components/schemas/RuleId' + rule_expression: + $ref: '#/components/schemas/RuleExpression' type: - $ref: '#/components/schemas/RuleActionType' - const: allow + allOf: + - $ref: '#/components/schemas/RuleActionType' + - const: allow request_header_modifications: $ref: '#/components/schemas/RequestHeaderModifications' + required: + - ruleset_id + - type StatusCode: type: integer description: A valid HTTP status code. @@ -1439,16 +1403,21 @@ components: type: string description: The response body to send to the client. EventRuleActionBlock: - type: object description: >- Informs the client the request should be blocked using the response described by this rule action. - required: - - type + type: object properties: + ruleset_id: + $ref: '#/components/schemas/RulesetId' + rule_id: + $ref: '#/components/schemas/RuleId' + rule_expression: + $ref: '#/components/schemas/RuleExpression' type: - $ref: '#/components/schemas/RuleActionType' - const: block + allOf: + - $ref: '#/components/schemas/RuleActionType' + - const: block status_code: $ref: '#/components/schemas/StatusCode' headers: @@ -1458,6 +1427,9 @@ components: $ref: '#/components/schemas/RuleActionHeaderField' body: $ref: '#/components/schemas/RuleActionBody' + required: + - ruleset_id + - type EventRuleAction: type: object description: >- @@ -1465,23 +1437,14 @@ components: the ruleset that matched the event. When getting an event by event ID, the rule_action will only be included when the ruleset_id query parameter is specified. - required: - - ruleset_id - properties: - ruleset_id: - $ref: '#/components/schemas/RulesetId' - rule_id: - $ref: '#/components/schemas/RuleId' - rule_expression: - $ref: '#/components/schemas/RuleExpression' oneOf: - $ref: '#/components/schemas/EventRuleActionAllow' - $ref: '#/components/schemas/EventRuleActionBlock' discriminator: propertyName: type mapping: - allow: EventRuleActionAllow.yaml - block: EventRuleActionBlock.yaml + allow: '#/components/schemas/EventRuleActionAllow' + block: '#/components/schemas/EventRuleActionBlock' SuspectScore: type: integer description: > @@ -1499,7 +1462,6 @@ components: * The browser signature resembles an "anti-detect" browser specifically designed to evade fingerprinting (see `tampering_details.anti_detect_browser`). TamperingDetails: type: object - additionalProperties: false properties: anomaly_score: type: number @@ -1527,7 +1489,6 @@ components: description: > Is absent if the velocity data could not be generated for the visitor Id. - additionalProperties: false required: - 5_minutes - 1_hour @@ -1591,7 +1552,6 @@ components: if the associated event does not have the required data, such as a linked_id. - additionalProperties: false properties: distinct_ip: $ref: '#/components/schemas/VelocityData' @@ -1637,7 +1597,6 @@ components: format or unknown). VpnMethods: type: object - additionalProperties: false properties: timezone_mismatch: type: boolean @@ -1703,7 +1662,6 @@ components: Baseline measurement of canonical fonts rendered on the device. Numeric width metrics, in CSS pixels, for the canonical fonts collected by the agent. - additionalProperties: false properties: default: type: number @@ -1729,7 +1687,6 @@ components: Emoji: type: object description: Bounding box metrics describing how the emoji glyph renders. - additionalProperties: false properties: font: type: string @@ -1780,7 +1737,6 @@ components: Canvas: type: object description: Canvas fingerprint containing winding flag plus geometry/text hashes. - additionalProperties: false properties: winding: type: boolean @@ -1803,7 +1759,6 @@ components: WebGlExtensions: type: object description: Hashes of WebGL context attributes and extension support. - additionalProperties: false properties: context_attributes: type: string @@ -1822,7 +1777,6 @@ components: WebGlBasics: type: object description: Render and vendor strings reported by the WebGL context. - additionalProperties: false properties: version: type: string @@ -1847,7 +1801,6 @@ components: TouchSupport: type: object description: Browser-reported touch capabilities. - additionalProperties: false properties: touch_event: type: boolean @@ -1910,7 +1863,6 @@ components: description: Browser plugins reported by `navigator.plugins`. items: type: object - additionalProperties: false properties: name: type: string @@ -1920,7 +1872,6 @@ components: type: array items: type: object - additionalProperties: false properties: type: type: string @@ -1942,7 +1893,6 @@ components: A curated subset of raw browser/device attributes that the API surface exposes. Each property contains a value or object with the data for the collected signal. - additionalProperties: false properties: font_preferences: $ref: '#/components/schemas/FontPreferences' @@ -1999,7 +1949,6 @@ components: description: >- Contains results from Fingerprint Identification and all active Smart Signals. - additionalProperties: false required: - event_id - timestamp @@ -2337,7 +2286,6 @@ components: existed or it has been deleted. Error: type: object - additionalProperties: false required: - code - message @@ -2348,7 +2296,6 @@ components: type: string ErrorResponse: type: object - additionalProperties: false required: - error properties: @@ -2375,7 +2322,6 @@ components: description: >- Contains a list of all identification events matching the specified search criteria. - additionalProperties: false required: - events properties: @@ -2395,3 +2341,52 @@ components: This value represents the total number of events matching the search query, up to the limit provided in the `total_hits` query parameter. Only present if the `total_hits` query parameter was provided. + SearchEventsBot: + type: string + enum: + - all + - good + - bad + - none + description: > + Filter events by the Bot Detection result, specifically: + `all` - events where any kind of bot was detected. + `good` - events where a good bot was detected. + `bad` - events where a bad bot was detected. + `none` - events where no bot was detected. + > Note: When using this parameter, only events with the `bot` property + set to a valid value are returned. Events without a `bot` Smart Signal + result are left out of the response. + SearchEventsVpnConfidence: + type: string + enum: + - high + - medium + - low + description: > + Filter events by VPN Detection result confidence level. + + `high` - events with high VPN Detection confidence. + + `medium` - events with medium VPN Detection confidence. + + `low` - events with low VPN Detection confidence. + + > Note: When using this parameter, only events with the `vpn.confidence` + property set to a valid value are returned. Events without a `vpn` Smart + Signal result are left out of the response. + SearchEventsSdkPlatform: + type: string + enum: + - js + - android + - ios + description: > + Filter events by the SDK Platform associated with the identification + event (`sdk.platform` property) . + + `js` - Javascript agent (Web). + + `ios` - Apple iOS based devices. + + `android` - Android based devices.