From cb780e83dc5483f7a4c91c7723a092abe9890017 Mon Sep 17 00:00:00 2001 From: Tomasz Poszytek <50657947+tposzytek@users.noreply.github.com> Date: Fri, 1 Jul 2022 19:51:41 +0200 Subject: [PATCH] Nationalize.io (Independent Publisher) (#1688) --- .../Nationalize.io/Readme.md | 20 +++ .../Nationalize.io/apiDefinition.swagger.json | 136 ++++++++++++++++++ .../Nationalize.io/apiProperties.json | 27 ++++ .../Nationalize.io/script.csx | 60 ++++++++ 4 files changed, 243 insertions(+) create mode 100644 independent-publisher-connectors/Nationalize.io/Readme.md create mode 100644 independent-publisher-connectors/Nationalize.io/apiDefinition.swagger.json create mode 100644 independent-publisher-connectors/Nationalize.io/apiProperties.json create mode 100644 independent-publisher-connectors/Nationalize.io/script.csx diff --git a/independent-publisher-connectors/Nationalize.io/Readme.md b/independent-publisher-connectors/Nationalize.io/Readme.md new file mode 100644 index 000000000..a3d8b19a9 --- /dev/null +++ b/independent-publisher-connectors/Nationalize.io/Readme.md @@ -0,0 +1,20 @@ +# Nationalize.io +Nationalize.io predicts the nationality of a person given their name. Use the API for analytics, ad segmenting, demographic statistics etc. The API is free for up to 1000 names/day. + +## Publisher: Tomasz Poszytek + +## Prerequisites +No prerequisites. + +## Supported Operations +### Check name(s) nationality +Action returns predicted nationalities for a given name or list of names. In case you want to check nationality for a list of names, provide them delimited with comma. Max. 10 names at a time! List will be truncated to first 10 items in case more names are provided. + +## Obtaining Credentials +If you would like to use the free version of API (up to 1000 names per day) just type **"none"** (w/o quotes) as the API key, when creating a connection. However, if you would like to check more than 1k names per month, please check subscription plans: https://store.nationalize.io/. + +## Known Issues and Limitations +No issues or limitations at the moment of api creation. + +## Getting Started +Visit https://nationalize.io/ to test the api on your own. diff --git a/independent-publisher-connectors/Nationalize.io/apiDefinition.swagger.json b/independent-publisher-connectors/Nationalize.io/apiDefinition.swagger.json new file mode 100644 index 000000000..06314263d --- /dev/null +++ b/independent-publisher-connectors/Nationalize.io/apiDefinition.swagger.json @@ -0,0 +1,136 @@ +{ + "swagger": "2.0", + "info": { + "title": "Nationalize_io", + "description": "Nationalize.io predicts the nationality of a person given their name. Use the API for analytics, ad segmenting, demographic statistics etc. The API is free for up to 1000 names/day.", + "version": "1.0", + "contact": { + "name": "Tomasz Poszytek", + "url": "https://aka.ms/poszytek", + "email": "tomasz@poszytek.eu" + } + }, + "x-ms-connector-metadata": [ + { + "propertyName": "Website", + "propertyValue": "https://nationalize.io/" + }, + { + "propertyName": "Privacy policy", + "propertyValue": "https://nationalize.io/" + }, + { + "propertyName": "Categories", + "propertyValue": "AI;Data" + } + ], + "host": "api.genderize.io", + "basePath": "/", + "schemes": [ + "https" + ], + "consumes": ["application/json"], + "produces": ["application/json"], + "paths": { + "/": { + "get": { + "responses": { + "200": { + "description": "200", + "schema": { + "type": "array", + "items": { + "type": "object", + "properties": { + "name": { + "type": "string", + "description": "Checked name.", + "title": "Name", + "x-ms-visibility": "important" + }, + "country": { + "type": "array", + "items": { + "type": "object", + "properties": { + "country_id": { + "type": "string", + "description": "Country ISO code.", + "title": "Name" + }, + "probability": { + "type": "number", + "format": "float", + "description": "The certainty of the assigned nationality.", + "title": "Probability" + } + } + }, + "description": "List of checked countries.", + "title": "Countries" + } + } + } + }, + "headers": { + "X-Rate-Limit-Limit": { + "description": "The amount of names available in the current time window", + "type": "integer", + "x-ms-visibility": "advanced" + }, + "X-Rate-Reset": { + "description": "The number of names left in the current time window ", + "type": "integer", + "x-ms-visibility": "advanced" + }, + "X-Rate-Limit-Remaining": { + "description": "Seconds remaining until a new time window opens", + "type": "integer", + "x-ms-visibility": "advanced" + } + } + } + }, + "summary": "Check name(s) nationality", + "description": "Check nationality of a single name or multiple names. For multiple names - separate them with comma.", + "operationId": "CheckNamesNationality", + "parameters": [ + { + "name": "name", + "in": "query", + "required": true, + "type": "string", + "description": "Name(s) to check the nationality. For multiple, separate with comma. Up to 10 names at a time.", + "x-ms-summary": "Name(s)", + "x-ms-visibility": "important" + }, + { + "name": "Accept", + "in": "header", + "required": true, + "type": "string", + "default": "application/json", + "x-ms-visibility": "internal" + } + ] + } + }, + "/m/": {} + }, + "definitions": {}, + "parameters": {}, + "responses": {}, + "securityDefinitions": { + "API Key": { + "type": "apiKey", + "in": "query", + "name": "apikey" + } + }, + "security": [ + { + "API Key": [] + } + ], + "tags": [] +} \ No newline at end of file diff --git a/independent-publisher-connectors/Nationalize.io/apiProperties.json b/independent-publisher-connectors/Nationalize.io/apiProperties.json new file mode 100644 index 000000000..2d391f66b --- /dev/null +++ b/independent-publisher-connectors/Nationalize.io/apiProperties.json @@ -0,0 +1,27 @@ +{ + "properties": { + "connectionParameters": { + "api_key": { + "type": "securestring", + "uiDefinition": { + "displayName": "Provide your API key. Type \"none\" if you are using free plan.", + "description": "Provide your API key. Type \"none\" if you are using free plan.", + "tooltip": "Provide your API key. Type \"none\" if you are using free plan.", + "constraints": { + "tabIndex": 2, + "clearText": false, + "required": "true" + } + } + } + }, + "iconBrandColor": "#da3b01", + "scriptOperations": [ + "CheckNamesNationality" + ], + "capabilities": [], + "policyTemplateInstances": [], + "publisher": "Tomasz Poszytek", + "stackOwner": "nationalize.io" + } +} \ No newline at end of file diff --git a/independent-publisher-connectors/Nationalize.io/script.csx b/independent-publisher-connectors/Nationalize.io/script.csx new file mode 100644 index 000000000..988aadbbc --- /dev/null +++ b/independent-publisher-connectors/Nationalize.io/script.csx @@ -0,0 +1,60 @@ +using System.Net; +using System.Web; + +public class Script : ScriptBase +{ + + public override async Task ExecuteAsync() + { + return await this.HandleForwardOperation().ConfigureAwait(false); + } + + private async Task HandleForwardOperation() + { + // get current request Uri + var strRequestUri = this.Context.Request.RequestUri.AbsoluteUri; + /* + * url?name=x&country_id=y&apikey=z + * after split: + * 0: url + * 1: name + * 2: apikey + */ + string[] parts = strRequestUri.ToString().Split(new char[] {'?','&'}); + + int noOfParts = parts.Count(); + + // init request Uri params + string reqName = ""; + string reqApiKey= ""; + + // build a request string for names + string[] reqNameParts = parts[1].Split('='); + string[] reqNames = (HttpUtility.UrlDecode(reqNameParts[1])).Split(','); + int loopNo = 0; + foreach (string reqNamePart in reqNames) + { + reqName = reqName + "name[]=" + reqNamePart.Trim() + "&"; + loopNo++; + // Max. 10 names + if (loopNo == 10) break; + } + // remove last & + reqName = reqName.Remove(reqName.Length-1); + + reqApiKey = "&"+parts[2]; + // if api key is none - remove it from the request URI, + // to make a free request, otherwise use apikey + string[] reqApiKeyParts = reqApiKey.Split('='); + if (reqApiKeyParts[1].Contains("none")) { + reqApiKey = ""; + } + + // change request Uri in the request object + this.Context.Request.RequestUri = new Uri($"https://api.nationalize.io/?{reqName+reqApiKey}"); + + // Use the context to an HTTP request + HttpResponseMessage response = await this.Context.SendAsync(this.Context.Request, this.CancellationToken).ConfigureAwait(continueOnCapturedContext: false); + return response; + } +} \ No newline at end of file