@studyportals/fawkes 8.2.1 → 8.2.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/src/programmes/policies/DisciplineArea.d.ts +1 -1
- package/dist/src/programmes/policies/DisciplineArea.js +1 -1
- package/dist/src/programmes/rules/ErasmusOrJointSpecialProgrammesRule.js +2 -2
- package/dist/src/structured-data/ScholarshipStructuredDataFactory.d.ts +17 -0
- package/dist/src/structured-data/ScholarshipStructuredDataFactory.js +63 -0
- package/dist/src/structured-data/SearchStructuredDataFactory.d.ts +16 -3
- package/dist/src/structured-data/SearchStructuredDataFactory.js +71 -7
- package/dist/src/structured-data/dto/EntityDTO.d.ts +2 -0
- package/dist/src/structured-data/dto/PaywallDTO.d.ts +14 -0
- package/dist/src/structured-data/dto/index.d.ts +1 -0
- package/dist/src/structured-data/dto/index.js +1 -0
- package/dist/src/structured-data/index.d.ts +1 -0
- package/dist/src/structured-data/index.js +1 -0
- package/package.json +3 -3
- package/dist/src/common/IPolicyMetaData.d.ts +0 -6
- package/dist/src/organisations/OrganisationsRuleBasedIndexabilityPolicy.d.ts +0 -11
- package/dist/src/organisations/OrganisationsRuleBasedIndexabilityPolicy.js +0 -19
- package/dist/src/organisations/rules/AtLeastTwoRankedResultsRule.d.ts +0 -13
- package/dist/src/organisations/rules/AtLeastTwoRankedResultsRule.js +0 -26
- package/dist/src/organisations/rules/OnlineAttendanceRule.d.ts +0 -6
- package/dist/src/organisations/rules/OnlineAttendanceRule.js +0 -14
- package/dist/src/programmes/IProgrammeSearchApplicationState.d.ts +0 -4
- package/dist/src/programmes/IProgrammeSearchApplicationState.js +0 -1
- package/dist/src/programmes/IProgrammeSearchDependencies.d.ts +0 -7
- package/dist/src/programmes/IProgrammeSearchDependencies.js +0 -1
- package/dist/src/programmes/IProgrammesSeoDependencies.d.ts +0 -2
- package/dist/src/programmes/IProgrammesSeoDependencies.js +0 -1
- package/dist/src/programmes/policies/DisciplineCountryDegree.d.ts +0 -16
- package/dist/src/programmes/policies/DisciplineCountryDegree.js +0 -53
- package/dist/src/programmes/rules/AtLeastSevenResultsRule.d.ts +0 -15
- package/dist/src/programmes/rules/AtLeastSevenResultsRule.js +0 -30
- package/dist/src/programmes/rules/DegreeAttendanceSpecificRule.d.ts +0 -10
- package/dist/src/programmes/rules/DegreeAttendanceSpecificRule.js +0 -42
- package/dist/src/programmes/rules/DegreeCountrySpecificRule.d.ts +0 -10
- package/dist/src/programmes/rules/DegreeCountrySpecificRule.js +0 -43
- package/dist/src/programmes/rules/DegreeCountryTuitionFeeRule.d.ts +0 -11
- package/dist/src/programmes/rules/DegreeCountryTuitionFeeRule.js +0 -40
- package/dist/src/programmes/rules/MBACountryAttendanceRule.d.ts +0 -11
- package/dist/src/programmes/rules/MBACountryAttendanceRule.js +0 -40
- package/dist/src/programmes/rules/MasterOfArtsDisciplineRule.d.ts +0 -10
- package/dist/src/programmes/rules/MasterOfArtsDisciplineRule.js +0 -41
- package/dist/src/programmes/rules/MasterOfEducationCountryDisciplineRule.d.ts +0 -11
- package/dist/src/programmes/rules/MasterOfEducationCountryDisciplineRule.js +0 -69
- package/dist/src/programmes/rules/MasterOfLawsCountryAttendanceRule.d.ts +0 -12
- package/dist/src/programmes/rules/MasterOfLawsCountryAttendanceRule.js +0 -43
- package/dist/src/programmes/rules/MasterOfLawsCountryTuitionFeeRule.d.ts +0 -12
- package/dist/src/programmes/rules/MasterOfLawsCountryTuitionFeeRule.js +0 -46
- package/dist/src/programmes/rules/MasterOfPhilosophyCountryAttendanceRule.d.ts +0 -12
- package/dist/src/programmes/rules/MasterOfPhilosophyCountryAttendanceRule.js +0 -43
- package/dist/src/programmes/rules/MasterOfScienceDisciplineRule.d.ts +0 -10
- package/dist/src/programmes/rules/MasterOfScienceDisciplineRule.js +0 -41
- package/dist/src/sitemap-generator/IPageNumberProvider.d.ts +0 -3
- package/dist/src/sitemap-generator/IPageNumberProvider.js +0 -1
- /package/dist/src/{common/IPolicyMetaData.js → structured-data/dto/PaywallDTO.js} +0 -0
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
1
|
+
import { FilterKey } from '@studyportals/search-filters/server-side';
|
|
2
2
|
import { OnlyFiltersSelectedRule } from '../../common/rules/OnlyFiltersSelectedRule';
|
|
3
3
|
import { SingleValueSelectedForFilterRule } from '../../common/rules/SingleValueSelectedForFilterRule';
|
|
4
4
|
import { FilterCombinations } from '../../enums/FilterCombinations';
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
1
|
+
import { FilterKey } from '@studyportals/search-filters/server-side';
|
|
2
2
|
import { OnlyFiltersSelectedRule } from '../../common/rules/OnlyFiltersSelectedRule';
|
|
3
3
|
import { SingleValueSelectedForFilterRule } from '../../common/rules/SingleValueSelectedForFilterRule';
|
|
4
4
|
import { FilterCombinations } from '../../enums/FilterCombinations';
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
2
|
-
import { SpecialProgrammesFilterOptionValue } from '@studyportals/search-filters';
|
|
1
|
+
import { FilterKey } from '@studyportals/search-filters/server-side';
|
|
2
|
+
import { SpecialProgrammesFilterOptionValue } from '@studyportals/search-filters/server-side';
|
|
3
3
|
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
4
|
export class ErasmusOrJointSpecialProgrammesRule extends BaseProgrammeRule {
|
|
5
5
|
forSearch(dependencies) {
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { MonetaryGrant } from "schema-dts";
|
|
2
|
+
import { StructuredDataCurrencyConversionService } from "./interface/StructuredDataCurrencyConversionService";
|
|
3
|
+
import { SearchStructuredDataFactory } from "./SearchStructuredDataFactory";
|
|
4
|
+
import { IScholarshipCard } from "@studyportals/domain-client";
|
|
5
|
+
import { EntityDTO, OfferDTO, PaywallDTO } from "./dto";
|
|
6
|
+
type MonetaryGrantWithPaywall = MonetaryGrant & {
|
|
7
|
+
isAccessibleForFree?: boolean;
|
|
8
|
+
};
|
|
9
|
+
export declare class ScholarshipStructuredDataFactory extends SearchStructuredDataFactory<IScholarshipCard> {
|
|
10
|
+
private currencyConversionService;
|
|
11
|
+
constructor(currencyConversionService: StructuredDataCurrencyConversionService);
|
|
12
|
+
protected buildStructuredDataForCard(entity: EntityDTO<IScholarshipCard>): Promise<MonetaryGrantWithPaywall | undefined>;
|
|
13
|
+
protected getOfferData(card: IScholarshipCard): Promise<OfferDTO | undefined>;
|
|
14
|
+
protected getPaywallData(): PaywallDTO | undefined;
|
|
15
|
+
private buildAmount;
|
|
16
|
+
}
|
|
17
|
+
export {};
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
import { SearchStructuredDataFactory } from "./SearchStructuredDataFactory";
|
|
2
|
+
export class ScholarshipStructuredDataFactory extends SearchStructuredDataFactory {
|
|
3
|
+
currencyConversionService;
|
|
4
|
+
constructor(currencyConversionService) {
|
|
5
|
+
super();
|
|
6
|
+
this.currencyConversionService = currencyConversionService;
|
|
7
|
+
}
|
|
8
|
+
async buildStructuredDataForCard(entity) {
|
|
9
|
+
const url = `https://${window.location.host}${entity.card.getScholarshipVirtualName()}`;
|
|
10
|
+
const amount = await this.buildAmount(entity.card);
|
|
11
|
+
const structuredData = {
|
|
12
|
+
"@type": "MonetaryGrant",
|
|
13
|
+
name: entity.card.getScholarshipTitle() || undefined,
|
|
14
|
+
description: entity.card.getDescriptionOfApplicationBasis() || undefined,
|
|
15
|
+
funder: entity.card.getProviderName() || undefined,
|
|
16
|
+
url,
|
|
17
|
+
amount
|
|
18
|
+
};
|
|
19
|
+
this.addPaywallToStructuredData(structuredData, entity.paywall);
|
|
20
|
+
return structuredData;
|
|
21
|
+
}
|
|
22
|
+
async getOfferData(card) {
|
|
23
|
+
const benefits = card.getDescriptionOfBenefits();
|
|
24
|
+
const hasMonetaryValue = benefits && !isNaN(Number(benefits.split(' ')[0]));
|
|
25
|
+
if (!hasMonetaryValue)
|
|
26
|
+
return;
|
|
27
|
+
const [amount, currency] = [Number(benefits.split(' ')[0]), benefits.split(' ')[1]];
|
|
28
|
+
return {
|
|
29
|
+
price: Math.round(await this.currencyConversionService.convert(amount, currency, 'USD')),
|
|
30
|
+
category: 'tuition',
|
|
31
|
+
validFrom: undefined
|
|
32
|
+
};
|
|
33
|
+
}
|
|
34
|
+
getPaywallData() {
|
|
35
|
+
return {
|
|
36
|
+
isAccessibleForFree: false,
|
|
37
|
+
cssSelector: '.Paywalled',
|
|
38
|
+
accessMode: 'registration'
|
|
39
|
+
};
|
|
40
|
+
}
|
|
41
|
+
async buildAmount(card) {
|
|
42
|
+
const benefits = card.getDescriptionOfBenefits();
|
|
43
|
+
const hasMonetaryValue = benefits && !isNaN(Number(benefits.split(' ')[0]));
|
|
44
|
+
let amount;
|
|
45
|
+
let currency;
|
|
46
|
+
if (hasMonetaryValue) {
|
|
47
|
+
[amount, currency] = [Number(benefits.split(' ')[0]), benefits.split(' ')[1]];
|
|
48
|
+
}
|
|
49
|
+
let value;
|
|
50
|
+
if (hasMonetaryValue) {
|
|
51
|
+
value = Math.round(await this.currencyConversionService.convert(amount, currency, 'USD'));
|
|
52
|
+
currency = 'USD';
|
|
53
|
+
}
|
|
54
|
+
else {
|
|
55
|
+
value = benefits || undefined;
|
|
56
|
+
}
|
|
57
|
+
return {
|
|
58
|
+
"@type": "MonetaryAmount",
|
|
59
|
+
value,
|
|
60
|
+
currency
|
|
61
|
+
};
|
|
62
|
+
}
|
|
63
|
+
}
|
|
@@ -1,12 +1,14 @@
|
|
|
1
|
-
import { SearchResultsPage, WithContext, Offer, AggregateRating, Thing, FAQPage } from 'schema-dts';
|
|
1
|
+
import { SearchResultsPage, WithContext, Offer, AggregateRating, Thing, FAQPage, WebPage } from 'schema-dts';
|
|
2
2
|
import { ReviewRatingDTO } from './dto/ReviewRatingDTO';
|
|
3
3
|
import { OfferDTO } from './dto/OfferDTO';
|
|
4
4
|
import { EntityDTO } from './dto/EntityDTO';
|
|
5
5
|
import { FAQItemDto } from './dto/FAQItemDto';
|
|
6
6
|
import { BreadcrumbDTO } from './dto/BreadcrumbDTO';
|
|
7
|
+
import { PaywallDTO } from './dto/PaywallDTO';
|
|
7
8
|
export declare abstract class SearchStructuredDataFactory<TCard> {
|
|
8
|
-
buildStructuredData(title: string, description: string, cards: TCard[], faqItems?: FAQItemDto[], breadcrumbs?: BreadcrumbDTO[]): Promise<WithContext<SearchResultsPage>>;
|
|
9
|
-
|
|
9
|
+
buildStructuredData(title: string, description: string, cards: TCard[], faqItems?: FAQItemDto[], breadcrumbs?: BreadcrumbDTO[], listItemStructure?: boolean): Promise<WithContext<SearchResultsPage | WebPage>>;
|
|
10
|
+
private generateMainEntities;
|
|
11
|
+
protected abstract buildStructuredDataForCard(entity: EntityDTO<TCard>): Promise<Thing | undefined> | Thing | undefined;
|
|
10
12
|
/**
|
|
11
13
|
* Get the rating for a card.
|
|
12
14
|
* This method should be overridden by subclasses to provide the specific rating logic.
|
|
@@ -25,10 +27,21 @@ export declare abstract class SearchStructuredDataFactory<TCard> {
|
|
|
25
27
|
* @protected
|
|
26
28
|
*/
|
|
27
29
|
protected getOfferData(card: TCard): Promise<OfferDTO | undefined>;
|
|
30
|
+
protected getPaywallData(): PaywallDTO | undefined;
|
|
28
31
|
private constructOptionalPageOffers;
|
|
29
32
|
protected constructOptionalFaqPage(faqItems: FAQItemDto[]): FAQPage | undefined;
|
|
33
|
+
private constructOptionalPageParts;
|
|
30
34
|
private constructOptionalBreadcrumbs;
|
|
35
|
+
private constructPaywallElement;
|
|
31
36
|
protected constructAggregateRating(reviewRating?: ReviewRatingDTO): AggregateRating | undefined;
|
|
32
37
|
protected constructOffer(offerData?: OfferDTO): Offer | undefined;
|
|
38
|
+
/**
|
|
39
|
+
* Add paywall information to any structured data object
|
|
40
|
+
*
|
|
41
|
+
* @param structuredData The structured data object to enhance
|
|
42
|
+
* @param paywallData The paywall data to add
|
|
43
|
+
* @protected
|
|
44
|
+
*/
|
|
45
|
+
protected addPaywallToStructuredData(structuredData: Record<string, any>, paywallData?: PaywallDTO): void;
|
|
33
46
|
private stripHtmlWithListRetain;
|
|
34
47
|
}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
export class SearchStructuredDataFactory {
|
|
2
|
-
async buildStructuredData(title, description, cards, faqItems = [], breadcrumbs = []) {
|
|
2
|
+
async buildStructuredData(title, description, cards, faqItems = [], breadcrumbs = [], listItemStructure) {
|
|
3
3
|
const entities = [];
|
|
4
4
|
const ratings = [];
|
|
5
5
|
const offersData = [];
|
|
@@ -12,21 +12,45 @@ export class SearchStructuredDataFactory {
|
|
|
12
12
|
offersData.push(offer);
|
|
13
13
|
entities.push({ card, offer, reviewRating });
|
|
14
14
|
}
|
|
15
|
-
const mainEntities = entities
|
|
16
|
-
.map(entity => this.buildStructuredDataForCard(entity))
|
|
17
|
-
.filter(entity => entity !== undefined);
|
|
15
|
+
const mainEntities = await this.generateMainEntities(entities, listItemStructure);
|
|
18
16
|
const data = {
|
|
19
17
|
'@context': 'https://schema.org',
|
|
20
|
-
'@type': 'SearchResultsPage',
|
|
18
|
+
'@type': !listItemStructure ? 'SearchResultsPage' : 'WebPage',
|
|
21
19
|
'name': title,
|
|
22
20
|
description,
|
|
23
21
|
'mainEntity': mainEntities
|
|
24
22
|
};
|
|
23
|
+
const paywallData = this.getPaywallData();
|
|
25
24
|
data.offers = this.constructOptionalPageOffers(offersData);
|
|
26
|
-
data.hasPart = this.
|
|
25
|
+
data.hasPart = this.constructOptionalPageParts(faqItems, paywallData);
|
|
27
26
|
data.breadcrumb = this.constructOptionalBreadcrumbs(breadcrumbs);
|
|
27
|
+
if (paywallData) {
|
|
28
|
+
data.isAccessibleForFree = paywallData.isAccessibleForFree;
|
|
29
|
+
}
|
|
28
30
|
return data;
|
|
29
31
|
}
|
|
32
|
+
async generateMainEntities(entities, listItemStructure) {
|
|
33
|
+
const mainEntities = [];
|
|
34
|
+
for (const entity of entities) {
|
|
35
|
+
const structuredData = await this.buildStructuredDataForCard(entity);
|
|
36
|
+
if (!structuredData)
|
|
37
|
+
continue;
|
|
38
|
+
mainEntities.push(structuredData);
|
|
39
|
+
}
|
|
40
|
+
if (listItemStructure) {
|
|
41
|
+
const listItems = mainEntities.map((entity, index) => ({
|
|
42
|
+
'@type': 'ListItem',
|
|
43
|
+
'position': index + 1,
|
|
44
|
+
'item': entity
|
|
45
|
+
}));
|
|
46
|
+
return [{
|
|
47
|
+
'@type': 'ItemList',
|
|
48
|
+
'numberOfItems': mainEntities.length,
|
|
49
|
+
'itemListElement': listItems
|
|
50
|
+
}];
|
|
51
|
+
}
|
|
52
|
+
return mainEntities;
|
|
53
|
+
}
|
|
30
54
|
/**
|
|
31
55
|
* Get the rating for a card.
|
|
32
56
|
* This method should be overridden by subclasses to provide the specific rating logic.
|
|
@@ -48,7 +72,10 @@ export class SearchStructuredDataFactory {
|
|
|
48
72
|
* @protected
|
|
49
73
|
*/
|
|
50
74
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
51
|
-
|
|
75
|
+
getOfferData(card) {
|
|
76
|
+
return Promise.resolve(undefined);
|
|
77
|
+
}
|
|
78
|
+
getPaywallData() {
|
|
52
79
|
return undefined;
|
|
53
80
|
}
|
|
54
81
|
constructOptionalPageOffers(offersData) {
|
|
@@ -94,6 +121,21 @@ export class SearchStructuredDataFactory {
|
|
|
94
121
|
}))
|
|
95
122
|
};
|
|
96
123
|
}
|
|
124
|
+
constructOptionalPageParts(faqItems, paywallData) {
|
|
125
|
+
const parts = [];
|
|
126
|
+
const faqPage = this.constructOptionalFaqPage(faqItems);
|
|
127
|
+
if (faqPage) {
|
|
128
|
+
parts.push(faqPage);
|
|
129
|
+
}
|
|
130
|
+
if (paywallData && paywallData.cssSelector) {
|
|
131
|
+
parts.push(this.constructPaywallElement(paywallData));
|
|
132
|
+
}
|
|
133
|
+
if (parts.length === 0)
|
|
134
|
+
return undefined;
|
|
135
|
+
if (parts.length === 1 && parts[0]['@type'] === 'FAQPage')
|
|
136
|
+
return parts[0];
|
|
137
|
+
return parts;
|
|
138
|
+
}
|
|
97
139
|
constructOptionalBreadcrumbs(breadcrumbs) {
|
|
98
140
|
if (breadcrumbs.length <= 0)
|
|
99
141
|
return;
|
|
@@ -108,6 +150,16 @@ export class SearchStructuredDataFactory {
|
|
|
108
150
|
}))
|
|
109
151
|
};
|
|
110
152
|
}
|
|
153
|
+
constructPaywallElement(paywallData) {
|
|
154
|
+
const element = {
|
|
155
|
+
'@type': 'WebPageElement',
|
|
156
|
+
'isAccessibleForFree': paywallData.isAccessibleForFree
|
|
157
|
+
};
|
|
158
|
+
if (paywallData.cssSelector) {
|
|
159
|
+
element.cssSelector = paywallData.cssSelector;
|
|
160
|
+
}
|
|
161
|
+
return element;
|
|
162
|
+
}
|
|
111
163
|
constructAggregateRating(reviewRating) {
|
|
112
164
|
if (!reviewRating)
|
|
113
165
|
return;
|
|
@@ -131,6 +183,18 @@ export class SearchStructuredDataFactory {
|
|
|
131
183
|
'category': 'tuition'
|
|
132
184
|
};
|
|
133
185
|
}
|
|
186
|
+
/**
|
|
187
|
+
* Add paywall information to any structured data object
|
|
188
|
+
*
|
|
189
|
+
* @param structuredData The structured data object to enhance
|
|
190
|
+
* @param paywallData The paywall data to add
|
|
191
|
+
* @protected
|
|
192
|
+
*/
|
|
193
|
+
addPaywallToStructuredData(structuredData, paywallData) {
|
|
194
|
+
if (!paywallData)
|
|
195
|
+
return;
|
|
196
|
+
structuredData.isAccessibleForFree = paywallData.isAccessibleForFree;
|
|
197
|
+
}
|
|
134
198
|
stripHtmlWithListRetain(html) {
|
|
135
199
|
const tempDiv = document.createElement('div');
|
|
136
200
|
tempDiv.innerHTML = html;
|
|
@@ -1,7 +1,9 @@
|
|
|
1
1
|
import { OfferDTO } from "./OfferDTO";
|
|
2
2
|
import { ReviewRatingDTO } from "./ReviewRatingDTO";
|
|
3
|
+
import { PaywallDTO } from "./PaywallDTO";
|
|
3
4
|
export interface EntityDTO<TCard> {
|
|
4
5
|
card: TCard;
|
|
5
6
|
offer?: OfferDTO;
|
|
6
7
|
reviewRating?: ReviewRatingDTO;
|
|
8
|
+
paywall?: PaywallDTO;
|
|
7
9
|
}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
export interface PaywallDTO {
|
|
2
|
+
/**
|
|
3
|
+
* Whether the content is behind a paywall
|
|
4
|
+
*/
|
|
5
|
+
isAccessibleForFree: boolean;
|
|
6
|
+
/**
|
|
7
|
+
* CSS selector for the paywall element (optional)
|
|
8
|
+
*/
|
|
9
|
+
cssSelector?: string;
|
|
10
|
+
/**
|
|
11
|
+
* Type of access restriction
|
|
12
|
+
*/
|
|
13
|
+
accessMode?: 'subscription' | 'payment' | 'registration' | 'free';
|
|
14
|
+
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@studyportals/fawkes",
|
|
3
|
-
"version": "8.2.
|
|
3
|
+
"version": "8.2.3",
|
|
4
4
|
"description": "A package to centralize SEO related logic for SBLP and Sitemap Generator.",
|
|
5
5
|
"files": [
|
|
6
6
|
"./dist"
|
|
@@ -99,7 +99,7 @@
|
|
|
99
99
|
"@rollup/rollup-linux-x64-gnu": "4.24.0"
|
|
100
100
|
},
|
|
101
101
|
"engines": {
|
|
102
|
-
"node": ">=18 <=
|
|
103
|
-
"npm": ">=8 <=
|
|
102
|
+
"node": ">=18 <=22",
|
|
103
|
+
"npm": ">=8 <=10"
|
|
104
104
|
}
|
|
105
105
|
}
|
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
import { PortalType } from '@studyportals/domain-client';
|
|
2
|
-
import { IOrganisationsSeoDependencies } from './types/IOrganisationsSeoDependencies';
|
|
3
|
-
import { SortingOptions } from '../enums/SortingOptions';
|
|
4
|
-
import { BaseSeoIndexabilityPolicy } from '../common/policies/BaseSeoIndexabilityPolicy';
|
|
5
|
-
export declare abstract class OrganisationsRuleBasedIndexabilityPolicy extends BaseSeoIndexabilityPolicy<IOrganisationsSeoDependencies> {
|
|
6
|
-
protected readonly indexablePortalTypes: PortalType[];
|
|
7
|
-
protected abstract readonly sortingOption: SortingOptions;
|
|
8
|
-
constructor(dependencies: IOrganisationsSeoDependencies);
|
|
9
|
-
protected isIndexable(): Promise<boolean>;
|
|
10
|
-
private matchesSortingOption;
|
|
11
|
-
}
|
|
@@ -1,19 +0,0 @@
|
|
|
1
|
-
import { PortalType } from '@studyportals/domain-client';
|
|
2
|
-
import { BaseSeoIndexabilityPolicy } from '../common/policies/BaseSeoIndexabilityPolicy';
|
|
3
|
-
export class OrganisationsRuleBasedIndexabilityPolicy extends BaseSeoIndexabilityPolicy {
|
|
4
|
-
indexablePortalTypes = [PortalType.MASTER];
|
|
5
|
-
constructor(dependencies) {
|
|
6
|
-
super(dependencies);
|
|
7
|
-
}
|
|
8
|
-
async isIndexable() {
|
|
9
|
-
const isIndexable = await super.isIndexable();
|
|
10
|
-
if (!isIndexable) {
|
|
11
|
-
return false;
|
|
12
|
-
}
|
|
13
|
-
return this.indexablePortalTypes.includes(this.dependencies.portalType) && this.matchesSortingOption();
|
|
14
|
-
}
|
|
15
|
-
matchesSortingOption() {
|
|
16
|
-
const dependencies = this.dependencies;
|
|
17
|
-
return dependencies.sortingState.getSelectedOption() === this.sortingOption;
|
|
18
|
-
}
|
|
19
|
-
}
|
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
import { IRule } from '../../common/IRule';
|
|
2
|
-
import { IOrganisationSearchDependencies } from '../types/IOrganisationSearchDependencies';
|
|
3
|
-
import { FilterKeyValuesMap } from '../../common/FilterKeyValuesMap';
|
|
4
|
-
import { IRankingApiClient } from '../../sitemap-generator/IRankingApiClient';
|
|
5
|
-
export declare class AtLeastTwoRankedResultsRule implements IRule {
|
|
6
|
-
private readonly minimumRankedResultsCount;
|
|
7
|
-
private readonly rankingApiClient?;
|
|
8
|
-
constructor(rankingApiClient?: IRankingApiClient);
|
|
9
|
-
forSearch(dependencies: IOrganisationSearchDependencies): Promise<boolean>;
|
|
10
|
-
forSitemapGenerator(filterKeyValues: FilterKeyValuesMap): Promise<boolean>;
|
|
11
|
-
getName(): string;
|
|
12
|
-
getDescription(): string;
|
|
13
|
-
}
|
|
@@ -1,26 +0,0 @@
|
|
|
1
|
-
import { DependencyMissingError } from '../../errors/DependencyMissingError';
|
|
2
|
-
export class AtLeastTwoRankedResultsRule {
|
|
3
|
-
minimumRankedResultsCount = 2;
|
|
4
|
-
rankingApiClient;
|
|
5
|
-
constructor(rankingApiClient) {
|
|
6
|
-
this.rankingApiClient = rankingApiClient;
|
|
7
|
-
}
|
|
8
|
-
forSearch(dependencies) {
|
|
9
|
-
const { applicationState } = dependencies;
|
|
10
|
-
const rankedResultsCount = applicationState.getRankedResultsCount();
|
|
11
|
-
return Promise.resolve(rankedResultsCount >= this.minimumRankedResultsCount);
|
|
12
|
-
}
|
|
13
|
-
async forSitemapGenerator(filterKeyValues) {
|
|
14
|
-
if (!this.rankingApiClient) {
|
|
15
|
-
throw new DependencyMissingError('RankingApiClient');
|
|
16
|
-
}
|
|
17
|
-
const rankedResultsCount = await this.rankingApiClient.getRankedOrganisationCount(filterKeyValues);
|
|
18
|
-
return rankedResultsCount >= this.minimumRankedResultsCount;
|
|
19
|
-
}
|
|
20
|
-
getName() {
|
|
21
|
-
return 'AtLeastTwoRankedResultsRule';
|
|
22
|
-
}
|
|
23
|
-
getDescription() {
|
|
24
|
-
return `At least ${this.minimumRankedResultsCount} ranked results are available`;
|
|
25
|
-
}
|
|
26
|
-
}
|
|
@@ -1,14 +0,0 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
2
|
-
import { BaseFilterKeyValueRule } from '../../common/rules/BaseFilterKeyValueRule';
|
|
3
|
-
export class OnlineAttendanceRule extends BaseFilterKeyValueRule {
|
|
4
|
-
constructor() {
|
|
5
|
-
const filterKeyValues = new Map([[FilterKey.DELIVERY_METHOD, ['online']]]);
|
|
6
|
-
super(filterKeyValues);
|
|
7
|
-
}
|
|
8
|
-
getName() {
|
|
9
|
-
return 'OnlineAttendanceRule';
|
|
10
|
-
}
|
|
11
|
-
getDescription() {
|
|
12
|
-
return 'Indexable if attendance is online';
|
|
13
|
-
}
|
|
14
|
-
}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export {};
|
|
@@ -1,7 +0,0 @@
|
|
|
1
|
-
import { ISearchDependencies } from '../common/ISearchDependencies';
|
|
2
|
-
import { IProgrammeSearchApplicationState } from './IProgrammeSearchApplicationState';
|
|
3
|
-
import { PortalType } from '@studyportals/domain-client';
|
|
4
|
-
export interface IProgrammeSearchDependencies extends ISearchDependencies {
|
|
5
|
-
portalType: PortalType;
|
|
6
|
-
applicationState: IProgrammeSearchApplicationState;
|
|
7
|
-
}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export {};
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export {};
|
|
@@ -1,16 +0,0 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
2
|
-
import { OnlyFiltersSelectedRule } from '../../common/rules/OnlyFiltersSelectedRule';
|
|
3
|
-
import { SingleValueSelectedForFilterRule } from '../../common/rules/SingleValueSelectedForFilterRule';
|
|
4
|
-
import { FilterCombinations } from '../../enums/FilterCombinations';
|
|
5
|
-
import { IndexableDegreeRule } from '../rules/IndexableDegreeRule';
|
|
6
|
-
import { ProgrammesBaseIndexabilityPolicy } from '../ProgrammesBaseIndexabilityPolicy';
|
|
7
|
-
import { IProgrammeSeoDependencies } from '../types/IProgrammeSeoDependencies';
|
|
8
|
-
export declare class DisciplineCountryDegree extends ProgrammesBaseIndexabilityPolicy {
|
|
9
|
-
readonly name: string;
|
|
10
|
-
readonly description: string;
|
|
11
|
-
readonly filterKeys: FilterKey[];
|
|
12
|
-
protected readonly rules: (SingleValueSelectedForFilterRule | OnlyFiltersSelectedRule | IndexableDegreeRule)[];
|
|
13
|
-
constructor(dependencies: IProgrammeSeoDependencies);
|
|
14
|
-
protected generateUrls(): Promise<string[]>;
|
|
15
|
-
get filterCombination(): FilterCombinations;
|
|
16
|
-
}
|
|
@@ -1,53 +0,0 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
2
|
-
import { OnlyFiltersSelectedRule } from '../../common/rules/OnlyFiltersSelectedRule';
|
|
3
|
-
import { SingleValueSelectedForFilterRule } from '../../common/rules/SingleValueSelectedForFilterRule';
|
|
4
|
-
import { FilterCombinations } from '../../enums/FilterCombinations';
|
|
5
|
-
import { IndexableDegreeRule } from '../rules/IndexableDegreeRule';
|
|
6
|
-
import { ProgrammesBaseIndexabilityPolicy } from '../ProgrammesBaseIndexabilityPolicy';
|
|
7
|
-
import { DisciplinePresenter } from '../../presenters/DisciplinePresenter';
|
|
8
|
-
import { CountryPresenter } from '../../presenters/CountryPresenter';
|
|
9
|
-
import { DegreePresenter } from '../../presenters/DegreePresenter';
|
|
10
|
-
export class DisciplineCountryDegree extends ProgrammesBaseIndexabilityPolicy {
|
|
11
|
-
name = 'Discipline Country Degree Policy';
|
|
12
|
-
description = `Determines indexing rules for pages filtered by discipline,
|
|
13
|
-
country, and degree type.`;
|
|
14
|
-
filterKeys = [FilterKey.DISCIPLINES, FilterKey.COUNTRY, FilterKey.DEGREE_TYPE];
|
|
15
|
-
rules = [
|
|
16
|
-
new SingleValueSelectedForFilterRule(FilterKey.DISCIPLINES),
|
|
17
|
-
new SingleValueSelectedForFilterRule(FilterKey.COUNTRY),
|
|
18
|
-
new SingleValueSelectedForFilterRule(FilterKey.DEGREE_TYPE),
|
|
19
|
-
new OnlyFiltersSelectedRule([FilterKey.DISCIPLINES, FilterKey.COUNTRY, FilterKey.DEGREE_TYPE]),
|
|
20
|
-
new IndexableDegreeRule()
|
|
21
|
-
];
|
|
22
|
-
constructor(dependencies) {
|
|
23
|
-
super(dependencies);
|
|
24
|
-
this.initateBaseRules();
|
|
25
|
-
}
|
|
26
|
-
async generateUrls() {
|
|
27
|
-
const disciplineFragments = DisciplinePresenter.getInstance().getFragments();
|
|
28
|
-
const countryFragments = CountryPresenter.getInstance().getFragments();
|
|
29
|
-
const degreeFragments = DegreePresenter.getInstance().getFragments();
|
|
30
|
-
const paths = [];
|
|
31
|
-
for (const pageNumber of this.indexablePageNumbers) {
|
|
32
|
-
for (const discipline of disciplineFragments) {
|
|
33
|
-
for (const country of countryFragments) {
|
|
34
|
-
for (const degree of degreeFragments) {
|
|
35
|
-
const filterKeyValues = new Map([
|
|
36
|
-
[FilterKey.DISCIPLINES, [discipline.id]],
|
|
37
|
-
[FilterKey.COUNTRY, [country.id]],
|
|
38
|
-
[FilterKey.DEGREE_TYPE, [degree.id]]
|
|
39
|
-
]);
|
|
40
|
-
const result = await this.checkRulesForSitemapWithPageNumber(filterKeyValues, pageNumber);
|
|
41
|
-
if (result) {
|
|
42
|
-
paths.push(this.getPathWithPageNumber(`${degree.path}/${discipline.path}/${country.path}`, pageNumber));
|
|
43
|
-
}
|
|
44
|
-
}
|
|
45
|
-
}
|
|
46
|
-
}
|
|
47
|
-
}
|
|
48
|
-
return paths;
|
|
49
|
-
}
|
|
50
|
-
get filterCombination() {
|
|
51
|
-
return FilterCombinations.DISCIPLINE_COUNTRY_DEGREE;
|
|
52
|
-
}
|
|
53
|
-
}
|
|
@@ -1,15 +0,0 @@
|
|
|
1
|
-
import { ISearchDependencies } from '../../common/ISearchDependencies';
|
|
2
|
-
import { FilterKeyValuesMap } from '../../common/FilterKeyValuesMap';
|
|
3
|
-
import { ISearchApiClient } from '../../sitemap-generator/ISearchApiClient';
|
|
4
|
-
import { IProgrammeRule } from '../IProgrammeRule';
|
|
5
|
-
export declare class AtLeastSevenResultsRule implements IProgrammeRule {
|
|
6
|
-
private readonly minimumResultsCount;
|
|
7
|
-
private readonly maximumPageSize;
|
|
8
|
-
private readonly searchApiClient?;
|
|
9
|
-
constructor(searchApiClient?: ISearchApiClient);
|
|
10
|
-
forSearch(dependencies: ISearchDependencies): Promise<boolean>;
|
|
11
|
-
forSitemapGeneratorWithPageNumber(filterKeyValues: FilterKeyValuesMap, pageNumber: number): Promise<boolean>;
|
|
12
|
-
forSitemapGenerator(): Promise<boolean>;
|
|
13
|
-
getName(): string;
|
|
14
|
-
getDescription(): string;
|
|
15
|
-
}
|
|
@@ -1,30 +0,0 @@
|
|
|
1
|
-
import { DependencyMissingError } from '../../errors/DependencyMissingError';
|
|
2
|
-
export class AtLeastSevenResultsRule {
|
|
3
|
-
minimumResultsCount = 7;
|
|
4
|
-
maximumPageSize = 20;
|
|
5
|
-
searchApiClient;
|
|
6
|
-
constructor(searchApiClient) {
|
|
7
|
-
this.searchApiClient = searchApiClient;
|
|
8
|
-
}
|
|
9
|
-
forSearch(dependencies) {
|
|
10
|
-
const { applicationState } = dependencies;
|
|
11
|
-
const resultCount = applicationState.getNumberOfResults();
|
|
12
|
-
return Promise.resolve(resultCount >= this.minimumResultsCount);
|
|
13
|
-
}
|
|
14
|
-
async forSitemapGeneratorWithPageNumber(filterKeyValues, pageNumber) {
|
|
15
|
-
if (!this.searchApiClient) {
|
|
16
|
-
throw new DependencyMissingError('SearchApiClient');
|
|
17
|
-
}
|
|
18
|
-
const count = await this.searchApiClient.getProgrammeCount(filterKeyValues);
|
|
19
|
-
return count >= (pageNumber - 1) * this.maximumPageSize + this.minimumResultsCount;
|
|
20
|
-
}
|
|
21
|
-
forSitemapGenerator() {
|
|
22
|
-
throw new Error('Method not implemented.');
|
|
23
|
-
}
|
|
24
|
-
getName() {
|
|
25
|
-
return 'AtLeastSevenResultsRule';
|
|
26
|
-
}
|
|
27
|
-
getDescription() {
|
|
28
|
-
return 'Is indexable if there are at least 7 results.';
|
|
29
|
-
}
|
|
30
|
-
}
|
|
@@ -1,10 +0,0 @@
|
|
|
1
|
-
import { ISearchDependencies } from '../../common/ISearchDependencies';
|
|
2
|
-
import { FilterKeyValuesMap } from '../../common/FilterKeyValuesMap';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export declare class DegreeAttendanceSpecificRule extends BaseProgrammeRule {
|
|
5
|
-
private readonly validCombinations;
|
|
6
|
-
getName(): string;
|
|
7
|
-
getDescription(): string;
|
|
8
|
-
forSearch(dependencies: ISearchDependencies): Promise<boolean>;
|
|
9
|
-
forSitemapGenerator(filterKeyValues: FilterKeyValuesMap): Promise<boolean>;
|
|
10
|
-
}
|
|
@@ -1,42 +0,0 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
2
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
3
|
-
export class DegreeAttendanceSpecificRule extends BaseProgrammeRule {
|
|
4
|
-
validCombinations = {
|
|
5
|
-
'master-of-science': ['online'], // MSc with online attendance
|
|
6
|
-
'master-of-arts': ['online'], // MA with online attendance
|
|
7
|
-
'master-of-business-administration': ['online'] // MBA with online attendance
|
|
8
|
-
};
|
|
9
|
-
getName() {
|
|
10
|
-
return 'DegreeAttendanceSpecificRule';
|
|
11
|
-
}
|
|
12
|
-
getDescription() {
|
|
13
|
-
return 'Indexes: master-of-science (online); master-of-arts (online); master-of-business-administration (online)';
|
|
14
|
-
}
|
|
15
|
-
forSearch(dependencies) {
|
|
16
|
-
const { seoInfoBase, filterState } = dependencies;
|
|
17
|
-
const degreeTypeValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DEGREE_TYPE, filterState);
|
|
18
|
-
const attendanceValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DELIVERY_METHOD, filterState);
|
|
19
|
-
if (!degreeTypeValue || !attendanceValue) {
|
|
20
|
-
return Promise.resolve(false);
|
|
21
|
-
}
|
|
22
|
-
const allowedAttendance = this.validCombinations[degreeTypeValue];
|
|
23
|
-
if (!allowedAttendance) {
|
|
24
|
-
return Promise.resolve(false);
|
|
25
|
-
}
|
|
26
|
-
return Promise.resolve(allowedAttendance.includes(attendanceValue));
|
|
27
|
-
}
|
|
28
|
-
forSitemapGenerator(filterKeyValues) {
|
|
29
|
-
const degreeTypeValues = filterKeyValues.get(FilterKey.DEGREE_TYPE);
|
|
30
|
-
const attendanceValues = filterKeyValues.get(FilterKey.DELIVERY_METHOD);
|
|
31
|
-
if (!degreeTypeValues?.length || !attendanceValues?.length) {
|
|
32
|
-
return Promise.resolve(false);
|
|
33
|
-
}
|
|
34
|
-
const degreeTypeValue = degreeTypeValues[0];
|
|
35
|
-
const attendanceValue = attendanceValues[0];
|
|
36
|
-
const allowedAttendance = this.validCombinations[degreeTypeValue];
|
|
37
|
-
if (!allowedAttendance) {
|
|
38
|
-
return Promise.resolve(false);
|
|
39
|
-
}
|
|
40
|
-
return Promise.resolve(allowedAttendance.includes(attendanceValue));
|
|
41
|
-
}
|
|
42
|
-
}
|
|
@@ -1,10 +0,0 @@
|
|
|
1
|
-
import { ISearchDependencies } from '../../common/ISearchDependencies';
|
|
2
|
-
import { FilterKeyValuesMap } from '../../common/FilterKeyValuesMap';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export declare class DegreeCountrySpecificRule extends BaseProgrammeRule {
|
|
5
|
-
private readonly validCombinations;
|
|
6
|
-
getName(): string;
|
|
7
|
-
getDescription(): string;
|
|
8
|
-
forSearch(dependencies: ISearchDependencies): Promise<boolean>;
|
|
9
|
-
forSitemapGenerator(filterKeyValues: FilterKeyValuesMap): Promise<boolean>;
|
|
10
|
-
}
|
|
@@ -1,43 +0,0 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
2
|
-
import { DegreeTypeFilterOptionValue } from '@studyportals/search-filters';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export class DegreeCountrySpecificRule extends BaseProgrammeRule {
|
|
5
|
-
validCombinations = {
|
|
6
|
-
[DegreeTypeFilterOptionValue.MSC]: ['82', '56', '11', '30'],
|
|
7
|
-
[DegreeTypeFilterOptionValue.MBA]: ['82', '30'],
|
|
8
|
-
[DegreeTypeFilterOptionValue.MED]: ['202', '56']
|
|
9
|
-
};
|
|
10
|
-
getName() {
|
|
11
|
-
return 'DegreeCountrySpecificRule';
|
|
12
|
-
}
|
|
13
|
-
getDescription() {
|
|
14
|
-
return 'Indexes: master-of-science (USA, Canada, Germany, UK); master-of-business-administration (USA, UK); master-of-education (Australia, Canada)';
|
|
15
|
-
}
|
|
16
|
-
forSearch(dependencies) {
|
|
17
|
-
const { seoInfoBase, filterState } = dependencies;
|
|
18
|
-
const degreeTypeValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DEGREE_TYPE, filterState);
|
|
19
|
-
const countryValue = seoInfoBase.getFilterOptionValueBy(FilterKey.COUNTRY, filterState);
|
|
20
|
-
if (!degreeTypeValue || !countryValue) {
|
|
21
|
-
return Promise.resolve(false);
|
|
22
|
-
}
|
|
23
|
-
const allowedCountries = this.validCombinations[degreeTypeValue];
|
|
24
|
-
if (!allowedCountries) {
|
|
25
|
-
return Promise.resolve(false);
|
|
26
|
-
}
|
|
27
|
-
return Promise.resolve(allowedCountries.includes(countryValue));
|
|
28
|
-
}
|
|
29
|
-
forSitemapGenerator(filterKeyValues) {
|
|
30
|
-
const degreeTypeValues = filterKeyValues.get(FilterKey.DEGREE_TYPE);
|
|
31
|
-
const countryValues = filterKeyValues.get(FilterKey.COUNTRY);
|
|
32
|
-
if (!degreeTypeValues?.length || !countryValues?.length) {
|
|
33
|
-
return Promise.resolve(false);
|
|
34
|
-
}
|
|
35
|
-
const degreeTypeValue = degreeTypeValues[0];
|
|
36
|
-
const countryValue = countryValues[0];
|
|
37
|
-
const allowedCountries = this.validCombinations[degreeTypeValue];
|
|
38
|
-
if (!allowedCountries) {
|
|
39
|
-
return Promise.resolve(false);
|
|
40
|
-
}
|
|
41
|
-
return Promise.resolve(allowedCountries.includes(countryValue));
|
|
42
|
-
}
|
|
43
|
-
}
|
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
import { ISearchDependencies } from '../../common/ISearchDependencies';
|
|
2
|
-
import { FilterKeyValuesMap } from '../../common/FilterKeyValuesMap';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export declare class DegreeCountryTuitionFeeRule extends BaseProgrammeRule {
|
|
5
|
-
private readonly degreeValue;
|
|
6
|
-
private readonly tuitionFeeValue;
|
|
7
|
-
getName(): string;
|
|
8
|
-
getDescription(): string;
|
|
9
|
-
forSearch(dependencies: ISearchDependencies): Promise<boolean>;
|
|
10
|
-
forSitemapGenerator(filterKeyValues: FilterKeyValuesMap): Promise<boolean>;
|
|
11
|
-
}
|
|
@@ -1,40 +0,0 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
2
|
-
import { TuitionFeeFilterOptionValue } from '@studyportals/search-filters';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export class DegreeCountryTuitionFeeRule extends BaseProgrammeRule {
|
|
5
|
-
degreeValue = 'master-of-business-administration';
|
|
6
|
-
tuitionFeeValue = TuitionFeeFilterOptionValue.ZERO_TO_TWO_THOUSAND_FIVE_HUNDRED;
|
|
7
|
-
getName() {
|
|
8
|
-
return 'DegreeCountryTuitionFeeRule';
|
|
9
|
-
}
|
|
10
|
-
getDescription() {
|
|
11
|
-
return 'Indexes: master-of-business-administration + all countries + affordable tuition (0-2500)';
|
|
12
|
-
}
|
|
13
|
-
forSearch(dependencies) {
|
|
14
|
-
const { seoInfoBase, filterState } = dependencies;
|
|
15
|
-
const degreeTypeValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DEGREE_TYPE, filterState);
|
|
16
|
-
const countryValue = seoInfoBase.getFilterOptionValueBy(FilterKey.COUNTRY, filterState);
|
|
17
|
-
const tuitionFeeValue = seoInfoBase.getFilterOptionValueBy(FilterKey.TUITION_FEE, filterState);
|
|
18
|
-
if (degreeTypeValue !== this.degreeValue) {
|
|
19
|
-
return Promise.resolve(true);
|
|
20
|
-
}
|
|
21
|
-
if (!countryValue || !tuitionFeeValue) {
|
|
22
|
-
return Promise.resolve(false);
|
|
23
|
-
}
|
|
24
|
-
return Promise.resolve(tuitionFeeValue === this.tuitionFeeValue);
|
|
25
|
-
}
|
|
26
|
-
forSitemapGenerator(filterKeyValues) {
|
|
27
|
-
const degreeTypeValues = filterKeyValues.get(FilterKey.DEGREE_TYPE);
|
|
28
|
-
const countryValues = filterKeyValues.get(FilterKey.COUNTRY);
|
|
29
|
-
const tuitionFeeValues = filterKeyValues.get(FilterKey.TUITION_FEE);
|
|
30
|
-
if (!degreeTypeValues?.length || !countryValues?.length || !tuitionFeeValues?.length) {
|
|
31
|
-
return Promise.resolve(false);
|
|
32
|
-
}
|
|
33
|
-
const degreeTypeValue = degreeTypeValues[0];
|
|
34
|
-
const tuitionFeeValue = tuitionFeeValues[0];
|
|
35
|
-
if (degreeTypeValue !== this.degreeValue) {
|
|
36
|
-
return Promise.resolve(true);
|
|
37
|
-
}
|
|
38
|
-
return Promise.resolve(tuitionFeeValue === this.tuitionFeeValue);
|
|
39
|
-
}
|
|
40
|
-
}
|
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
import { ISearchDependencies } from '../../common/ISearchDependencies';
|
|
2
|
-
import { FilterKeyValuesMap } from '../../common/FilterKeyValuesMap';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export declare class MbaCountryAttendanceRule extends BaseProgrammeRule {
|
|
5
|
-
private readonly degreeValue;
|
|
6
|
-
private readonly attendanceValue;
|
|
7
|
-
getName(): string;
|
|
8
|
-
getDescription(): string;
|
|
9
|
-
forSearch(dependencies: ISearchDependencies): Promise<boolean>;
|
|
10
|
-
forSitemapGenerator(filterKeyValues: FilterKeyValuesMap): Promise<boolean>;
|
|
11
|
-
}
|
|
@@ -1,40 +0,0 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
2
|
-
import { DegreeTypeFilterOptionValue } from '@studyportals/search-filters';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export class MbaCountryAttendanceRule extends BaseProgrammeRule {
|
|
5
|
-
degreeValue = DegreeTypeFilterOptionValue.MBA;
|
|
6
|
-
attendanceValue = 'online';
|
|
7
|
-
getName() {
|
|
8
|
-
return 'MbaCountryAttendanceRule';
|
|
9
|
-
}
|
|
10
|
-
getDescription() {
|
|
11
|
-
return 'Indexes: master-of-business-administration + all countries + online attendance';
|
|
12
|
-
}
|
|
13
|
-
forSearch(dependencies) {
|
|
14
|
-
const { seoInfoBase, filterState } = dependencies;
|
|
15
|
-
const degreeTypeValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DEGREE_TYPE, filterState);
|
|
16
|
-
const countryValue = seoInfoBase.getFilterOptionValueBy(FilterKey.COUNTRY, filterState);
|
|
17
|
-
const attendanceValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DELIVERY_METHOD, filterState);
|
|
18
|
-
if (degreeTypeValue !== this.degreeValue) {
|
|
19
|
-
return Promise.resolve(true);
|
|
20
|
-
}
|
|
21
|
-
if (!countryValue || !attendanceValue) {
|
|
22
|
-
return Promise.resolve(false);
|
|
23
|
-
}
|
|
24
|
-
return Promise.resolve(attendanceValue === this.attendanceValue);
|
|
25
|
-
}
|
|
26
|
-
forSitemapGenerator(filterKeyValues) {
|
|
27
|
-
const degreeTypeValues = filterKeyValues.get(FilterKey.DEGREE_TYPE);
|
|
28
|
-
const countryValues = filterKeyValues.get(FilterKey.COUNTRY);
|
|
29
|
-
const attendanceValues = filterKeyValues.get(FilterKey.DELIVERY_METHOD);
|
|
30
|
-
if (!degreeTypeValues?.length || !countryValues?.length || !attendanceValues?.length) {
|
|
31
|
-
return Promise.resolve(false);
|
|
32
|
-
}
|
|
33
|
-
const degreeTypeValue = degreeTypeValues[0];
|
|
34
|
-
const attendanceValue = attendanceValues[0];
|
|
35
|
-
if (degreeTypeValue !== this.degreeValue) {
|
|
36
|
-
return Promise.resolve(true);
|
|
37
|
-
}
|
|
38
|
-
return Promise.resolve(attendanceValue === this.attendanceValue);
|
|
39
|
-
}
|
|
40
|
-
}
|
|
@@ -1,10 +0,0 @@
|
|
|
1
|
-
import { ISearchDependencies } from '../../common/ISearchDependencies';
|
|
2
|
-
import { FilterKeyValuesMap } from '../../common/FilterKeyValuesMap';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export declare class MasterOfArtsDisciplineRule extends BaseProgrammeRule {
|
|
5
|
-
private readonly degreeValue;
|
|
6
|
-
getName(): string;
|
|
7
|
-
getDescription(): string;
|
|
8
|
-
forSearch(dependencies: ISearchDependencies): Promise<boolean>;
|
|
9
|
-
forSitemapGenerator(filterKeyValues: FilterKeyValuesMap): Promise<boolean>;
|
|
10
|
-
}
|
|
@@ -1,41 +0,0 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
2
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
3
|
-
export class MasterOfArtsDisciplineRule extends BaseProgrammeRule {
|
|
4
|
-
// Master of Arts accepts all disciplines
|
|
5
|
-
degreeValue = 'master-of-arts';
|
|
6
|
-
getName() {
|
|
7
|
-
return 'MasterOfArtsDisciplineRule';
|
|
8
|
-
}
|
|
9
|
-
getDescription() {
|
|
10
|
-
return 'Indexes: master-of-arts + all disciplines';
|
|
11
|
-
}
|
|
12
|
-
forSearch(dependencies) {
|
|
13
|
-
const { seoInfoBase, filterState } = dependencies;
|
|
14
|
-
const degreeTypeValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DEGREE_TYPE, filterState);
|
|
15
|
-
const disciplineValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DISCIPLINES, filterState);
|
|
16
|
-
// This rule only applies to Master of Arts
|
|
17
|
-
if (degreeTypeValue !== this.degreeValue) {
|
|
18
|
-
return Promise.resolve(true); // Rule doesn't apply to other degrees
|
|
19
|
-
}
|
|
20
|
-
// Must have a discipline selected
|
|
21
|
-
if (!disciplineValue) {
|
|
22
|
-
return Promise.resolve(false);
|
|
23
|
-
}
|
|
24
|
-
// Master of Arts accepts all disciplines
|
|
25
|
-
return Promise.resolve(true);
|
|
26
|
-
}
|
|
27
|
-
forSitemapGenerator(filterKeyValues) {
|
|
28
|
-
const degreeTypeValues = filterKeyValues.get(FilterKey.DEGREE_TYPE);
|
|
29
|
-
const disciplineValues = filterKeyValues.get(FilterKey.DISCIPLINES);
|
|
30
|
-
if (!degreeTypeValues?.length || !disciplineValues?.length) {
|
|
31
|
-
return Promise.resolve(false);
|
|
32
|
-
}
|
|
33
|
-
const degreeTypeValue = degreeTypeValues[0];
|
|
34
|
-
// This rule only applies to Master of Arts
|
|
35
|
-
if (degreeTypeValue !== this.degreeValue) {
|
|
36
|
-
return Promise.resolve(true); // Rule doesn't apply to other degrees
|
|
37
|
-
}
|
|
38
|
-
// Master of Arts accepts all disciplines
|
|
39
|
-
return Promise.resolve(true);
|
|
40
|
-
}
|
|
41
|
-
}
|
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
import { ISearchDependencies } from '../../common/ISearchDependencies';
|
|
2
|
-
import { FilterKeyValuesMap } from '../../common/FilterKeyValuesMap';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export declare class MasterOfEducationCountryDisciplineRule extends BaseProgrammeRule {
|
|
5
|
-
private readonly educationDisciplineIds;
|
|
6
|
-
private readonly allowedCountryIds;
|
|
7
|
-
getName(): string;
|
|
8
|
-
getDescription(): string;
|
|
9
|
-
forSearch(dependencies: ISearchDependencies): Promise<boolean>;
|
|
10
|
-
forSitemapGenerator(filterKeyValues: FilterKeyValuesMap): Promise<boolean>;
|
|
11
|
-
}
|
|
@@ -1,69 +0,0 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
2
|
-
import { DegreeTypeFilterOptionValue } from '@studyportals/search-filters';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export class MasterOfEducationCountryDisciplineRule extends BaseProgrammeRule {
|
|
5
|
-
educationDisciplineIds = [
|
|
6
|
-
'289', // Education & Training (main discipline)
|
|
7
|
-
'290', // Adult Education
|
|
8
|
-
'360', // Art Education
|
|
9
|
-
'291', // Coaching
|
|
10
|
-
'292', // School Counselling
|
|
11
|
-
'333', // Early Childhood Education
|
|
12
|
-
'8', // Education
|
|
13
|
-
'349', // Educational Leadership
|
|
14
|
-
'293', // Educational Psychology
|
|
15
|
-
'98', // Educational Research
|
|
16
|
-
'371', // Health Education
|
|
17
|
-
'363', // Higher Education
|
|
18
|
-
'355', // Instructional Design
|
|
19
|
-
'370', // Literacy Education
|
|
20
|
-
'348', // Primary Education
|
|
21
|
-
'97', // Special Education
|
|
22
|
-
'359', // Secondary Education
|
|
23
|
-
'345', // STEM Education
|
|
24
|
-
'295', // Teaching
|
|
25
|
-
'358' // Teaching English as a Foreign Language
|
|
26
|
-
];
|
|
27
|
-
// Australia (202), Canada (32)
|
|
28
|
-
allowedCountryIds = ['202', '32'];
|
|
29
|
-
getName() {
|
|
30
|
-
return 'MasterOfEducationCountryDisciplineRule';
|
|
31
|
-
}
|
|
32
|
-
getDescription() {
|
|
33
|
-
return 'Indexes: master-of-education (Australia, Canada) + education disciplines only';
|
|
34
|
-
}
|
|
35
|
-
forSearch(dependencies) {
|
|
36
|
-
const { seoInfoBase, filterState } = dependencies;
|
|
37
|
-
const degreeTypeValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DEGREE_TYPE, filterState);
|
|
38
|
-
const countryValue = seoInfoBase.getFilterOptionValueBy(FilterKey.COUNTRY, filterState);
|
|
39
|
-
const disciplineValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DISCIPLINES, filterState);
|
|
40
|
-
if (degreeTypeValue !== DegreeTypeFilterOptionValue.MED) {
|
|
41
|
-
return Promise.resolve(true);
|
|
42
|
-
}
|
|
43
|
-
if (!countryValue || !disciplineValue) {
|
|
44
|
-
return Promise.resolve(false);
|
|
45
|
-
}
|
|
46
|
-
if (!this.allowedCountryIds.includes(countryValue)) {
|
|
47
|
-
return Promise.resolve(false);
|
|
48
|
-
}
|
|
49
|
-
return Promise.resolve(this.educationDisciplineIds.includes(disciplineValue));
|
|
50
|
-
}
|
|
51
|
-
forSitemapGenerator(filterKeyValues) {
|
|
52
|
-
const degreeTypeValues = filterKeyValues.get(FilterKey.DEGREE_TYPE);
|
|
53
|
-
const countryValues = filterKeyValues.get(FilterKey.COUNTRY);
|
|
54
|
-
const disciplineValues = filterKeyValues.get(FilterKey.DISCIPLINES);
|
|
55
|
-
if (!degreeTypeValues?.length || !countryValues?.length || !disciplineValues?.length) {
|
|
56
|
-
return Promise.resolve(false);
|
|
57
|
-
}
|
|
58
|
-
const degreeTypeValue = degreeTypeValues[0];
|
|
59
|
-
const countryValue = countryValues[0];
|
|
60
|
-
const disciplineValue = disciplineValues[0];
|
|
61
|
-
if (degreeTypeValue !== DegreeTypeFilterOptionValue.MED.valueOf()) {
|
|
62
|
-
return Promise.resolve(true);
|
|
63
|
-
}
|
|
64
|
-
if (!this.allowedCountryIds.includes(countryValue)) {
|
|
65
|
-
return Promise.resolve(false);
|
|
66
|
-
}
|
|
67
|
-
return Promise.resolve(this.educationDisciplineIds.includes(disciplineValue));
|
|
68
|
-
}
|
|
69
|
-
}
|
|
@@ -1,12 +0,0 @@
|
|
|
1
|
-
import { ISearchDependencies } from '../../common/ISearchDependencies';
|
|
2
|
-
import { FilterKeyValuesMap } from '../../common/FilterKeyValuesMap';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export declare class MasterOfLawsCountryAttendanceRule extends BaseProgrammeRule {
|
|
5
|
-
private readonly degreeValue;
|
|
6
|
-
private readonly attendanceValue;
|
|
7
|
-
private readonly allowedCountryIds;
|
|
8
|
-
getName(): string;
|
|
9
|
-
getDescription(): string;
|
|
10
|
-
forSearch(dependencies: ISearchDependencies): Promise<boolean>;
|
|
11
|
-
forSitemapGenerator(filterKeyValues: FilterKeyValuesMap): Promise<boolean>;
|
|
12
|
-
}
|
|
@@ -1,43 +0,0 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
2
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
3
|
-
export class MasterOfLawsCountryAttendanceRule extends BaseProgrammeRule {
|
|
4
|
-
degreeValue = 'master-of-laws';
|
|
5
|
-
attendanceValue = 'online';
|
|
6
|
-
allowedCountryIds = ['82', '30', '32', '108'];
|
|
7
|
-
getName() {
|
|
8
|
-
return 'MasterOfLawsCountryAttendanceRule';
|
|
9
|
-
}
|
|
10
|
-
getDescription() {
|
|
11
|
-
return 'Indexes: master-of-laws (USA, UK, Canada, India) + online attendance';
|
|
12
|
-
}
|
|
13
|
-
forSearch(dependencies) {
|
|
14
|
-
const { seoInfoBase, filterState } = dependencies;
|
|
15
|
-
const degreeTypeValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DEGREE_TYPE, filterState);
|
|
16
|
-
const countryValue = seoInfoBase.getFilterOptionValueBy(FilterKey.COUNTRY, filterState);
|
|
17
|
-
const attendanceValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DELIVERY_METHOD, filterState);
|
|
18
|
-
if (degreeTypeValue !== this.degreeValue) {
|
|
19
|
-
return Promise.resolve(true);
|
|
20
|
-
}
|
|
21
|
-
if (!countryValue || !attendanceValue) {
|
|
22
|
-
return Promise.resolve(false);
|
|
23
|
-
}
|
|
24
|
-
return Promise.resolve(this.allowedCountryIds.includes(countryValue) &&
|
|
25
|
-
attendanceValue === this.attendanceValue);
|
|
26
|
-
}
|
|
27
|
-
forSitemapGenerator(filterKeyValues) {
|
|
28
|
-
const degreeTypeValues = filterKeyValues.get(FilterKey.DEGREE_TYPE);
|
|
29
|
-
const countryValues = filterKeyValues.get(FilterKey.COUNTRY);
|
|
30
|
-
const attendanceValues = filterKeyValues.get(FilterKey.DELIVERY_METHOD);
|
|
31
|
-
if (!degreeTypeValues?.length || !countryValues?.length || !attendanceValues?.length) {
|
|
32
|
-
return Promise.resolve(false);
|
|
33
|
-
}
|
|
34
|
-
const degreeTypeValue = degreeTypeValues[0];
|
|
35
|
-
const countryValue = countryValues[0];
|
|
36
|
-
const attendanceValue = attendanceValues[0];
|
|
37
|
-
if (degreeTypeValue !== this.degreeValue) {
|
|
38
|
-
return Promise.resolve(true);
|
|
39
|
-
}
|
|
40
|
-
return Promise.resolve(this.allowedCountryIds.includes(countryValue) &&
|
|
41
|
-
attendanceValue === this.attendanceValue);
|
|
42
|
-
}
|
|
43
|
-
}
|
|
@@ -1,12 +0,0 @@
|
|
|
1
|
-
import { ISearchDependencies } from '../../common/ISearchDependencies';
|
|
2
|
-
import { FilterKeyValuesMap } from '../../common/FilterKeyValuesMap';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export declare class MasterOfLawsCountryTuitionFeeRule extends BaseProgrammeRule {
|
|
5
|
-
private readonly degreeValue;
|
|
6
|
-
private readonly allowedCountryIds;
|
|
7
|
-
private readonly tuitionFeeValue;
|
|
8
|
-
getName(): string;
|
|
9
|
-
getDescription(): string;
|
|
10
|
-
forSearch(dependencies: ISearchDependencies): Promise<boolean>;
|
|
11
|
-
forSitemapGenerator(filterKeyValues: FilterKeyValuesMap): Promise<boolean>;
|
|
12
|
-
}
|
|
@@ -1,46 +0,0 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
2
|
-
import { TuitionFeeFilterOptionValue } from '@studyportals/search-filters';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export class MasterOfLawsCountryTuitionFeeRule extends BaseProgrammeRule {
|
|
5
|
-
degreeValue = 'master-of-laws';
|
|
6
|
-
allowedCountryIds = ['82', '30', '32', '108']; // USA, UK, Canada, India
|
|
7
|
-
tuitionFeeValue = TuitionFeeFilterOptionValue.ZERO_TO_TWO_THOUSAND_FIVE_HUNDRED;
|
|
8
|
-
getName() {
|
|
9
|
-
return 'MasterOfLawsCountryTuitionFeeRule';
|
|
10
|
-
}
|
|
11
|
-
getDescription() {
|
|
12
|
-
return 'Indexes: master-of-laws (USA, UK, Canada, India) + affordable tuition (0-2500)';
|
|
13
|
-
}
|
|
14
|
-
forSearch(dependencies) {
|
|
15
|
-
const { seoInfoBase, filterState } = dependencies;
|
|
16
|
-
const degreeTypeValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DEGREE_TYPE, filterState);
|
|
17
|
-
const countryValue = seoInfoBase.getFilterOptionValueBy(FilterKey.COUNTRY, filterState);
|
|
18
|
-
const tuitionFeeValue = seoInfoBase.getFilterOptionValueBy(FilterKey.TUITION_FEE, filterState);
|
|
19
|
-
if (degreeTypeValue !== this.degreeValue) {
|
|
20
|
-
return Promise.resolve(true);
|
|
21
|
-
}
|
|
22
|
-
if (!countryValue || !tuitionFeeValue) {
|
|
23
|
-
return Promise.resolve(false);
|
|
24
|
-
}
|
|
25
|
-
return Promise.resolve(this.allowedCountryIds.includes(countryValue) &&
|
|
26
|
-
tuitionFeeValue === this.tuitionFeeValue);
|
|
27
|
-
}
|
|
28
|
-
forSitemapGenerator(filterKeyValues) {
|
|
29
|
-
const degreeTypeValues = filterKeyValues.get(FilterKey.DEGREE_TYPE);
|
|
30
|
-
const countryValues = filterKeyValues.get(FilterKey.COUNTRY);
|
|
31
|
-
const tuitionFeeValues = filterKeyValues.get(FilterKey.TUITION_FEE);
|
|
32
|
-
if (!degreeTypeValues?.length || !countryValues?.length || !tuitionFeeValues?.length) {
|
|
33
|
-
return Promise.resolve(false);
|
|
34
|
-
}
|
|
35
|
-
const degreeTypeValue = degreeTypeValues[0];
|
|
36
|
-
const countryValue = countryValues[0];
|
|
37
|
-
const tuitionFeeValue = tuitionFeeValues[0];
|
|
38
|
-
// This rule only applies to Master of Laws
|
|
39
|
-
if (degreeTypeValue !== this.degreeValue) {
|
|
40
|
-
return Promise.resolve(true); // Rule doesn't apply to other degrees
|
|
41
|
-
}
|
|
42
|
-
// Must be in allowed countries and have affordable tuition
|
|
43
|
-
return Promise.resolve(this.allowedCountryIds.includes(countryValue) &&
|
|
44
|
-
tuitionFeeValue === this.tuitionFeeValue);
|
|
45
|
-
}
|
|
46
|
-
}
|
|
@@ -1,12 +0,0 @@
|
|
|
1
|
-
import { ISearchDependencies } from '../../common/ISearchDependencies';
|
|
2
|
-
import { FilterKeyValuesMap } from '../../common/FilterKeyValuesMap';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export declare class MasterOfPhilosophyCountryAttendanceRule extends BaseProgrammeRule {
|
|
5
|
-
private readonly degreeValue;
|
|
6
|
-
private readonly attendanceValue;
|
|
7
|
-
private readonly allowedCountryIds;
|
|
8
|
-
getName(): string;
|
|
9
|
-
getDescription(): string;
|
|
10
|
-
forSearch(dependencies: ISearchDependencies): Promise<boolean>;
|
|
11
|
-
forSitemapGenerator(filterKeyValues: FilterKeyValuesMap): Promise<boolean>;
|
|
12
|
-
}
|
|
@@ -1,43 +0,0 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
2
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
3
|
-
export class MasterOfPhilosophyCountryAttendanceRule extends BaseProgrammeRule {
|
|
4
|
-
degreeValue = 'master-of-philosophy';
|
|
5
|
-
attendanceValue = 'online';
|
|
6
|
-
allowedCountryIds = ['82', '30', '108']; // USA, UK, India
|
|
7
|
-
getName() {
|
|
8
|
-
return 'MasterOfPhilosophyCountryAttendanceRule';
|
|
9
|
-
}
|
|
10
|
-
getDescription() {
|
|
11
|
-
return 'Indexes: master-of-philosophy (USA, UK, India) + online attendance';
|
|
12
|
-
}
|
|
13
|
-
forSearch(dependencies) {
|
|
14
|
-
const { seoInfoBase, filterState } = dependencies;
|
|
15
|
-
const degreeTypeValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DEGREE_TYPE, filterState);
|
|
16
|
-
const countryValue = seoInfoBase.getFilterOptionValueBy(FilterKey.COUNTRY, filterState);
|
|
17
|
-
const attendanceValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DELIVERY_METHOD, filterState);
|
|
18
|
-
if (degreeTypeValue !== this.degreeValue) {
|
|
19
|
-
return Promise.resolve(true);
|
|
20
|
-
}
|
|
21
|
-
if (!countryValue || !attendanceValue) {
|
|
22
|
-
return Promise.resolve(false);
|
|
23
|
-
}
|
|
24
|
-
return Promise.resolve(this.allowedCountryIds.includes(countryValue) &&
|
|
25
|
-
attendanceValue === this.attendanceValue);
|
|
26
|
-
}
|
|
27
|
-
forSitemapGenerator(filterKeyValues) {
|
|
28
|
-
const degreeTypeValues = filterKeyValues.get(FilterKey.DEGREE_TYPE);
|
|
29
|
-
const countryValues = filterKeyValues.get(FilterKey.COUNTRY);
|
|
30
|
-
const attendanceValues = filterKeyValues.get(FilterKey.DELIVERY_METHOD);
|
|
31
|
-
if (!degreeTypeValues?.length || !countryValues?.length || !attendanceValues?.length) {
|
|
32
|
-
return Promise.resolve(false);
|
|
33
|
-
}
|
|
34
|
-
const degreeTypeValue = degreeTypeValues[0];
|
|
35
|
-
const countryValue = countryValues[0];
|
|
36
|
-
const attendanceValue = attendanceValues[0];
|
|
37
|
-
if (degreeTypeValue !== this.degreeValue) {
|
|
38
|
-
return Promise.resolve(true);
|
|
39
|
-
}
|
|
40
|
-
return Promise.resolve(this.allowedCountryIds.includes(countryValue) &&
|
|
41
|
-
attendanceValue === this.attendanceValue);
|
|
42
|
-
}
|
|
43
|
-
}
|
|
@@ -1,10 +0,0 @@
|
|
|
1
|
-
import { ISearchDependencies } from '../../common/ISearchDependencies';
|
|
2
|
-
import { FilterKeyValuesMap } from '../../common/FilterKeyValuesMap';
|
|
3
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
4
|
-
export declare class MasterOfScienceDisciplineRule extends BaseProgrammeRule {
|
|
5
|
-
private readonly degreeValue;
|
|
6
|
-
getName(): string;
|
|
7
|
-
getDescription(): string;
|
|
8
|
-
forSearch(dependencies: ISearchDependencies): Promise<boolean>;
|
|
9
|
-
forSitemapGenerator(filterKeyValues: FilterKeyValuesMap): Promise<boolean>;
|
|
10
|
-
}
|
|
@@ -1,41 +0,0 @@
|
|
|
1
|
-
import { FilterKey } from '@studyportals/search-filters';
|
|
2
|
-
import { BaseProgrammeRule } from '../BaseProgrammeRule';
|
|
3
|
-
export class MasterOfScienceDisciplineRule extends BaseProgrammeRule {
|
|
4
|
-
// Master of Science accepts all disciplines
|
|
5
|
-
degreeValue = 'master-of-science';
|
|
6
|
-
getName() {
|
|
7
|
-
return 'MasterOfScienceDisciplineRule';
|
|
8
|
-
}
|
|
9
|
-
getDescription() {
|
|
10
|
-
return 'Indexes: master-of-science + all disciplines';
|
|
11
|
-
}
|
|
12
|
-
forSearch(dependencies) {
|
|
13
|
-
const { seoInfoBase, filterState } = dependencies;
|
|
14
|
-
const degreeTypeValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DEGREE_TYPE, filterState);
|
|
15
|
-
const disciplineValue = seoInfoBase.getFilterOptionValueBy(FilterKey.DISCIPLINES, filterState);
|
|
16
|
-
// This rule only applies to Master of Science
|
|
17
|
-
if (degreeTypeValue !== this.degreeValue) {
|
|
18
|
-
return Promise.resolve(true); // Rule doesn't apply to other degrees
|
|
19
|
-
}
|
|
20
|
-
// Must have a discipline selected
|
|
21
|
-
if (!disciplineValue) {
|
|
22
|
-
return Promise.resolve(false);
|
|
23
|
-
}
|
|
24
|
-
// Master of Science accepts all disciplines
|
|
25
|
-
return Promise.resolve(true);
|
|
26
|
-
}
|
|
27
|
-
forSitemapGenerator(filterKeyValues) {
|
|
28
|
-
const degreeTypeValues = filterKeyValues.get(FilterKey.DEGREE_TYPE);
|
|
29
|
-
const disciplineValues = filterKeyValues.get(FilterKey.DISCIPLINES);
|
|
30
|
-
if (!degreeTypeValues?.length || !disciplineValues?.length) {
|
|
31
|
-
return Promise.resolve(false);
|
|
32
|
-
}
|
|
33
|
-
const degreeTypeValue = degreeTypeValues[0];
|
|
34
|
-
// This rule only applies to Master of Science
|
|
35
|
-
if (degreeTypeValue !== this.degreeValue) {
|
|
36
|
-
return Promise.resolve(true); // Rule doesn't apply to other degrees
|
|
37
|
-
}
|
|
38
|
-
// Master of Science accepts all disciplines
|
|
39
|
-
return Promise.resolve(true);
|
|
40
|
-
}
|
|
41
|
-
}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export {};
|
|
File without changes
|