UNPKG

yoastseo

Version:

Yoast client-side content analysis

181 lines (172 loc) 8 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.default = void 0; var _i18n = require("@wordpress/i18n"); var _lodash = require("lodash"); var _getSubheadings = require("../../../languageProcessing/helpers/html/getSubheadings"); var _assessment = _interopRequireDefault(require("../assessment")); var _shortlinker = require("../../../helpers/shortlinker"); var _inRange = require("../../helpers/assessments/inRange.js"); var _AssessmentResult = _interopRequireDefault(require("../../../values/AssessmentResult")); function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; } /** * Represents the assessment that checks if the keyword is present in one of the subheadings. */ class SubHeadingsKeywordAssessment extends _assessment.default { /** * Sets the identifier and the config. * * @param {object} config The configuration to use. * * @returns {void} */ constructor(config = {}) { super(); const defaultConfig = { parameters: { lowerBoundary: 0.3, upperBoundary: 0.75 }, scores: { noMatches: 3, tooFewMatches: 3, goodNumberOfMatches: 9, tooManyMatches: 3 }, urlTitle: (0, _shortlinker.createAnchorOpeningTag)("https://yoa.st/33m"), urlCallToAction: (0, _shortlinker.createAnchorOpeningTag)("https://yoa.st/33n") }; this.identifier = "subheadingsKeyword"; this._config = (0, _lodash.merge)(defaultConfig, config); } /** * Runs the matchKeywordInSubheadings research and based on this returns an assessment result. * * @param {Paper} paper The paper to use for the assessment. * @param {Researcher} researcher The researcher used for calling research. * * @returns {AssessmentResult} The assessment result. */ getResult(paper, researcher) { this._subHeadings = researcher.getResearch("matchKeywordInSubheadings"); const assessmentResult = new _AssessmentResult.default(); this._minNumberOfSubheadings = Math.ceil(this._subHeadings.count * this._config.parameters.lowerBoundary); this._maxNumberOfSubheadings = Math.floor(this._subHeadings.count * this._config.parameters.upperBoundary); const calculatedResult = this.calculateResult(); assessmentResult.setScore(calculatedResult.score); assessmentResult.setText(calculatedResult.resultText); return assessmentResult; } /** * Checks whether the paper has a subheadings. * * @param {Paper} paper The paper to use for the check. * * @returns {boolean} True when there is at least one subheading. */ hasSubheadings(paper) { const subheadings = (0, _getSubheadings.getSubheadingsTopLevel)(paper.getText()); return subheadings.length > 0; } /** * Checks whether the paper has a text and a keyword. * * @param {Paper} paper The paper to use for the assessment. * * @returns {boolean} True when there is text and a keyword. */ isApplicable(paper) { return paper.hasText() && paper.hasKeyword() && this.hasSubheadings(paper); } /** * Checks whether there are too few subheadings with the keyphrase. * * This is the case if the number of subheadings with the keyphrase is more than 0 but less than the specified * recommended minimum. * * @returns {boolean} Returns true if the keyphrase is included in too few subheadings. */ hasTooFewMatches() { return this._subHeadings.matches > 0 && this._subHeadings.matches < this._minNumberOfSubheadings; } /** * Checks whether there are too many subheadings with the keyphrase. * * The upper limit is only applicable if there is more than one subheading. If there is only one subheading with * the keyphrase this would otherwise always lead to a 100% match rate. * * @returns {boolean} Returns true if there is more than one subheading and if the keyphrase is included in less * subheadings than the recommended maximum. */ hasTooManyMatches() { return this._subHeadings.count > 1 && this._subHeadings.matches > this._maxNumberOfSubheadings; } /** * Checks whether there is only one higher-level subheading and this subheading includes the keyphrase. * * @returns {boolean} Returns true if there is exactly one higher-level subheading and this * subheading has a keyphrase match. */ isOneOfOne() { return this._subHeadings.count === 1 && this._subHeadings.matches === 1; } /** * Checks whether there is a good number of subheadings with the keyphrase. * * This is the case if there is only one subheading and that subheading includes the keyphrase or if the number of * subheadings with the keyphrase is within the specified recommended range. * * @returns {boolean} Returns true if the keyphrase is included in a sufficient number of subheadings. */ hasGoodNumberOfMatches() { return (0, _inRange.inRangeStartEndInclusive)(this._subHeadings.matches, this._minNumberOfSubheadings, this._maxNumberOfSubheadings); } /** * Determines the score and the Result text for the subheadings. * * @returns {Object} The object with the calculated score and the result text. */ calculateResult() { if (this.hasTooFewMatches()) { return { score: this._config.scores.tooFewMatches, resultText: (0, _i18n.sprintf)(/* translators: %1$s and %2$s expand to a link on yoast.com, %3$s expands to the anchor end tag. */ (0, _i18n.__)("%1$sKeyphrase in subheading%3$s: %2$sUse more keyphrases or synonyms in your H2 and H3 subheadings%3$s!", "wordpress-seo"), this._config.urlTitle, this._config.urlCallToAction, "</a>") }; } if (this.hasTooManyMatches()) { return { score: this._config.scores.tooManyMatches, resultText: (0, _i18n.sprintf)(/* translators: %1$s and %2$s expand to a link on yoast.com, %3$s expands to the anchor end tag. */ (0, _i18n.__)("%1$sKeyphrase in subheading%3$s: More than 75%% of your H2 and H3 subheadings reflect the topic of your copy. That's too much. %2$sDon't over-optimize%3$s!", "wordpress-seo"), this._config.urlTitle, this._config.urlCallToAction, "</a>") }; } if (this.isOneOfOne()) { return { score: this._config.scores.goodNumberOfMatches, resultText: (0, _i18n.sprintf)( /* translators: %1$s expands to a link on yoast.com, %2$s expands to the anchor end tag, %3$d expands to the number of subheadings containing the keyphrase. */ (0, _i18n.__)("%1$sKeyphrase in subheading%2$s: Your H2 or H3 subheading reflects the topic of your copy. Good job!", "wordpress-seo"), this._config.urlTitle, "</a>", this._subHeadings.matches) }; } if (this.hasGoodNumberOfMatches()) { return { score: this._config.scores.goodNumberOfMatches, resultText: (0, _i18n.sprintf)( /* translators: %1$s expands to a link on yoast.com, %2$s expands to the anchor end tag, %3$d expands to the number of subheadings containing the keyphrase. */ (0, _i18n._n)("%1$sKeyphrase in subheading%2$s: %3$s of your H2 and H3 subheadings reflects the topic of your copy. Good job!", "%1$sKeyphrase in subheading%2$s: %3$s of your H2 and H3 subheadings reflect the topic of your copy. Good job!", this._subHeadings.matches, "wordpress-seo"), this._config.urlTitle, "</a>", this._subHeadings.matches) }; } return { score: this._config.scores.noMatches, resultText: (0, _i18n.sprintf)(/* translators: %1$s and %2$s expand to a link on yoast.com, %3$s expands to the anchor end tag. */ (0, _i18n.__)("%1$sKeyphrase in subheading%3$s: %2$sUse more keyphrases or synonyms in your H2 and H3 subheadings%3$s!", "wordpress-seo"), this._config.urlTitle, this._config.urlCallToAction, "</a>") }; } } exports.default = SubHeadingsKeywordAssessment; //# sourceMappingURL=SubHeadingsKeywordAssessment.js.map