Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

TW-1251 Add API entries for permanent ads #140

Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
31 changes: 31 additions & 0 deletions src/advertising/slise.ts
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,29 @@ export interface SliseAdPlacesRule {
stylesOverrides?: SliseAdStylesOverrides[];
}

export interface PermanentSliseAdPlacesRule {
urlRegexes: string[];
adSelector: {
isMultiple: boolean;
cssString: string;
parentDepth: number;
};
parentSelector: {
isMultiple: boolean;
cssString: string;
parentDepth: number;
};
insertionIndex?: number;
insertBeforeSelector?: string;
insertAfterSelector?: string;
insertionsCount?: number;
shouldUseDivWrapper: boolean;
divWrapperStyle?: Record<StylePropName, string>;
elementToMeasureSelector?: string;
stylesOverrides?: SliseAdStylesOverrides[];
shouldHideOriginal?: boolean;
}

export interface SliseAdProvidersByDomainRule {
urlRegexes: string[];
providers: string[];
Expand All @@ -99,6 +122,7 @@ const SLISE_AD_PLACES_RULES_KEY = 'slise_ad_places_rules';
const SLISE_AD_PROVIDERS_BY_SITES_KEY = 'slise_ad_providers_by_sites';
const SLISE_AD_PROVIDERS_ALL_SITES_KEY = 'slise_ad_providers_all_sites';
const SLISE_AD_PROVIDERS_LIST_KEY = 'slise_ad_providers_list';
const PERMANENT_SLISE_AD_PLACES_RULES_KEY = 'permanent_slise_ad_places_rules';

const objectStorageMethodsFactory = <V>(storageKey: string, fallbackValue: V) => ({
getByKey: async (key: string): Promise<V> => {
Expand Down Expand Up @@ -145,6 +169,13 @@ export const {
removeValues: removeProviders
} = objectStorageMethodsFactory<string[]>(SLISE_AD_PROVIDERS_LIST_KEY, []);

export const {
getByKey: getPermanentSliseAdPlacesRulesByDomain,
getAllValues: getAllPermanentSliseAdPlacesRules,
upsertValues: upsertPermanentSliseAdPlacesRules,
removeValues: removePermanentSliseAdPlacesRules
} = objectStorageMethodsFactory<PermanentSliseAdPlacesRule[]>(PERMANENT_SLISE_AD_PLACES_RULES_KEY, []);

export const getSliseAdProvidersForAllSites = async () => redisClient.smembers(SLISE_AD_PROVIDERS_ALL_SITES_KEY);

export const addSliseAdProvidersForAllSites = async (providers: string[]) =>
Expand Down
257 changes: 256 additions & 1 deletion src/routers/slise-ad-rules/ad-places.ts
Original file line number Diff line number Diff line change
@@ -1,16 +1,26 @@
import { Router } from 'express';

import {
getAllPermanentSliseAdPlacesRules,
getAllSliseAdPlacesRules,
getPermanentSliseAdPlacesRulesByDomain,
getSliseAdPlacesRulesByDomain,
removePermanentSliseAdPlacesRules,
removeSliseAdPlacesRules,
upsertPermanentSliseAdPlacesRules,
upsertSliseAdPlacesRules
} from '../../advertising/slise';
import { addObjectStorageMethodsToRouter } from '../../utils/express-helpers';
import { hostnamesListSchema, sliseAdPlacesRulesDictionarySchema } from '../../utils/schemas';
import {
hostnamesListSchema,
permanentSliseAdPlacesRulesDictionarySchema,
sliseAdPlacesRulesDictionarySchema
} from '../../utils/schemas';

/**
* @swagger
* tags:
* name: Slise ad places
* components:
* schemas:
* SliseAdPlacesRuleSelector:
Expand Down Expand Up @@ -115,15 +125,254 @@ import { hostnamesListSchema, sliseAdPlacesRulesDictionarySchema } from '../../u
* cssString: 'div.left-container > app-pe-banner:nth-child(2)'
* parentDepth: 0
* shouldUseDivWrapper: true
* PermanentSliseAdPlacesRule:
* type: object
* description: >
* This object describes rules of replacing ads banners if they are found and inserting new ads banners if
* they are not found. Exactly one of `insertionIndex`, `insertBeforeSelector` and `insertAfterSelector`
* properties must be specified.
* required:
* - urlRegexes
* - adSelector
* - parentSelector
* - shouldUseDivWrapper
* properties:
* urlRegexes:
* type: array
* items:
* type: string
* format: regex
* adSelector:
* type: object
* description: >
* This object describes rules of selecting ads banners in the parents of new ads banners selected
* according to the rules described in the `parentSelector` property.
* required:
* - isMultiple
* - cssString
* - parentDepth
* properties:
* isMultiple:
* type: boolean
* description: Whether the selector should return multiple elements
* cssString:
* type: string
* description: CSS selector
* parentDepth:
* type: number
* min: 0
* integer: true
* description: >
* Indicates the depth of the parent element of the selected element, i. e. 0 means that the selected
* elements are ads banners themselves, 1 means that the selected elements are ads banners' direct
* children and so on.
* parentSelector:
* type: object
* required:
* - isMultiple
* - cssString
* - parentDepth
* properties:
* isMultiple:
* type: boolean
* description: Whether the selector should return multiple elements
* cssString:
* type: string
* description: CSS selector
* parentDepth:
* type: number
* min: 0
* integer: true
* description: >
* Indicates the depth of the parent element of the selected element, i. e. 0 means that the selected
* elements are parents of new ads banners themselves, 1 means that the selected elements are their
* direct children and so on.
* insertionIndex:
* type: number
* integer: true
* description: >
* Describes where to insert new ads banners in the selected parents of new ads banners in case if original
* ads banners are not found. If the value is negative, the insertion index will be calculated from the end.
* The counting starts from 0.
* insertBeforeSelector:
* type: string
* description: A selector for the element before which new ads banners should be inserted
* insertAfterSelector:
* type: string
* description: A selector for the element after which new ads banners should be inserted
* insertionsCount:
* type: number
* integer: true
* min: 1
* default: 1
* description: >
* Describes how many new ads banners should be inserted in case if original ads banners are not found.
* shouldUseDivWrapper:
* type: boolean
* description: Whether the Slise ads banner should be wrapped in a div
* divWrapperStyle:
* type: object
* description: Style of the div wrapper
* additionalProperties:
* type: string
* elementToMeasureSelector:
* type: string
* description: A selector of the element which should be measured to define banner size
* stylesOverrides:
* type: array
* items:
* $ref: '#/components/schemas/SliseAdStylesOverrides'
* shouldHideOriginal:
* type: boolean
* description: Whether original ads banners should be hidden but not removed
* default: false
* example:
* urlRegexes:
* - '^https://etherscan\.io/tx/'
* adSelector:
* isMultiple: false
* cssString: '.coinzilla'
* parentDepth: 0
* parentSelector:
* isMultiple: false
* cssString: '#ContentPlaceHolder1_maintable > * > .row:nth-child(8) > :nth-child(2) > * > *'
* parentDepth: 0
* insertionIndex: 0
* shouldUseDivWrapper: false
* PermanentSliseAdPlacesRulesDictionary:
* type: object
* additionalProperties:
* type: array
* items:
* $ref: '#/components/schemas/PermanentSliseAdPlacesRule'
* example:
* etherscan.io:
* - urlRegexes:
* - '^https://etherscan\.io/tx/'
* adSelector:
* isMultiple: false
* cssString: '.coinzilla'
* parentDepth: 0
* parentSelector:
* isMultiple: false
* cssString: '#ContentPlaceHolder1_maintable > * > .row:nth-child(8) > :nth-child(2) > * > *'
* parentDepth: 0
* insertionIndex: 0
* shouldUseDivWrapper: false
*/

export const sliseAdPlacesRulesRouter = Router();

/**
* @swagger
* /api/slise-ad-rules/ad-places/permanent/{domain}:
* get:
* summary: Get rules for permanent ads places for the specified domain
* tags:
* - Slise ad places
* parameters:
* - in: path
* name: domain
* required: true
* schema:
* type: string
* format: hostname
* example: 'etherscan.io'
* responses:
* '200':
* description: Rules list
* content:
* application/json:
* schema:
* type: array
* items:
* $ref: '#/components/schemas/PermanentSliseAdPlacesRule'
* '500':
* $ref: '#/components/responses/ErrorResponse'
* /api/slise-ad-rules/ad-places/permanent:
* get:
* summary: Get all rules for permanent ads places
* tags:
* - Slise ad places
* responses:
* '200':
* description: Domain - rules list dictionary
* content:
* application/json:
* schema:
* $ref: '#/components/schemas/PermanentSliseAdPlacesRulesDictionary'
* '500':
* $ref: '#/components/responses/ErrorResponse'
* post:
* summary: Add rules for permanent ads places. If rules for a domain already exist, they will be overwritten
* tags:
* - Slise ad places
* security:
* - basicAuth: []
* requestBody:
* description: Domain - rules list dictionary
* content:
* application/json:
* schema:
* $ref: '#/components/schemas/PermanentSliseAdPlacesRulesDictionary'
* responses:
* '200':
* $ref: '#/components/responses/SuccessResponse'
* '400':
* $ref: '#/components/responses/ErrorResponse'
* '401':
* $ref: '#/components/responses/UnauthorizedError'
* '500':
* $ref: '#/components/responses/ErrorResponse'
* delete:
* summary: Remove rules for permanent ads places
* tags:
* - Slise ad places
* security:
* - basicAuth: []
* requestBody:
* description: List of domain names to remove rules for
* content:
* application/json:
* schema:
* type: array
* items:
* type: string
* format: hostname
* example:
* - 'etherscan.io'
* responses:
* '200':
* $ref: '#/components/responses/SuccessResponse'
* '400':
* $ref: '#/components/responses/ErrorResponse'
* '401':
* $ref: '#/components/responses/UnauthorizedError'
* '500':
* $ref: '#/components/responses/ErrorResponse'
*/
addObjectStorageMethodsToRouter(
sliseAdPlacesRulesRouter,
'/permanent',
{
getByKey: getPermanentSliseAdPlacesRulesByDomain,
getAllValues: getAllPermanentSliseAdPlacesRules,
upsertValues: upsertPermanentSliseAdPlacesRules,
removeValues: removePermanentSliseAdPlacesRules
},
'domain',
permanentSliseAdPlacesRulesDictionarySchema,
hostnamesListSchema,
entriesCount => `${entriesCount} entries have been removed`
);

/**
* @swagger
* /api/slise-ad-rules/ad-places/{domain}:
* get:
* summary: Get rules for ads places for the specified domain
* tags:
* - Slise ad places
* parameters:
* - in: path
* name: domain
Expand All @@ -146,6 +395,8 @@ export const sliseAdPlacesRulesRouter = Router();
* /api/slise-ad-rules/ad-places:
* get:
* summary: Get all rules for ads places
* tags:
* - Slise ad places
* responses:
* '200':
* description: Domain - rules list dictionary
Expand All @@ -157,6 +408,8 @@ export const sliseAdPlacesRulesRouter = Router();
* $ref: '#/components/responses/ErrorResponse'
* post:
* summary: Add rules for ads places. If rules for a domain already exist, they will be overwritten
* tags:
* - Slise ad places
* security:
* - basicAuth: []
* requestBody:
Expand All @@ -176,6 +429,8 @@ export const sliseAdPlacesRulesRouter = Router();
* $ref: '#/components/responses/ErrorResponse'
* delete:
* summary: Remove rules for ads places
* tags:
* - Slise ad places
* security:
* - basicAuth: []
* requestBody:
Expand Down
Loading
Loading