This is to tidy up the `author-packagse`, which currently duplicates a lot of the configuration in the main packages. We need to DRY this up so that we don't fall foul of a change in one being missed in the other.
		
			
				
	
	
		
			142 lines
		
	
	
		
			4.3 KiB
		
	
	
	
		
			JavaScript
		
	
	
	
	
	
			
		
		
	
	
			142 lines
		
	
	
		
			4.3 KiB
		
	
	
	
		
			JavaScript
		
	
	
	
	
	
'use strict';
 | 
						|
 | 
						|
var fs = require('fs');
 | 
						|
var path = require('canonical-path');
 | 
						|
 | 
						|
/**
 | 
						|
 * @dgProcessor generateKeywordsProcessor
 | 
						|
 * @description
 | 
						|
 * This processor extracts all the keywords from each document and creates
 | 
						|
 * a new document that will be rendered as a JavaScript file containing all
 | 
						|
 * this data.
 | 
						|
 */
 | 
						|
module.exports = function generateKeywordsProcessor(log, readFilesProcessor) {
 | 
						|
  return {
 | 
						|
    ignoreWordsFile: undefined,
 | 
						|
    propertiesToIgnore: [],
 | 
						|
    docTypesToIgnore: [],
 | 
						|
    outputFolder: '',
 | 
						|
    $validate: {
 | 
						|
      ignoreWordsFile: {},
 | 
						|
      docTypesToIgnore: {},
 | 
						|
      propertiesToIgnore: {},
 | 
						|
      outputFolder: {presence: true}
 | 
						|
    },
 | 
						|
    $runAfter: ['paths-computed'],
 | 
						|
    $runBefore: ['rendering-docs'],
 | 
						|
    $process: function(docs) {
 | 
						|
 | 
						|
      // Keywords to ignore
 | 
						|
      var wordsToIgnore = [];
 | 
						|
      var propertiesToIgnore;
 | 
						|
      var docTypesToIgnore;
 | 
						|
 | 
						|
      // Keywords start with "ng:" or one of $, _ or a letter
 | 
						|
      var KEYWORD_REGEX = /^((ng:|[$_a-z])[\w\-_]+)/;
 | 
						|
 | 
						|
      // Load up the keywords to ignore, if specified in the config
 | 
						|
      if (this.ignoreWordsFile) {
 | 
						|
        var ignoreWordsPath = path.resolve(readFilesProcessor.basePath, this.ignoreWordsFile);
 | 
						|
        wordsToIgnore = fs.readFileSync(ignoreWordsPath, 'utf8').toString().split(/[,\s\n\r]+/gm);
 | 
						|
 | 
						|
        log.debug('Loaded ignore words from "' + ignoreWordsPath + '"');
 | 
						|
        log.silly(wordsToIgnore);
 | 
						|
      }
 | 
						|
 | 
						|
      propertiesToIgnore = convertToMap(this.propertiesToIgnore);
 | 
						|
      log.debug('Properties to ignore', propertiesToIgnore);
 | 
						|
      docTypesToIgnore = convertToMap(this.docTypesToIgnore);
 | 
						|
      log.debug('Doc types to ignore', docTypesToIgnore);
 | 
						|
 | 
						|
      var ignoreWordsMap = convertToMap(wordsToIgnore);
 | 
						|
 | 
						|
      // If the title contains a name starting with ng, e.g. "ngController", then add the module
 | 
						|
      // name
 | 
						|
      // without the ng to the title text, e.g. "controller".
 | 
						|
      function extractTitleWords(title) {
 | 
						|
        var match = /ng([A-Z]\w*)/.exec(title);
 | 
						|
        if (match) {
 | 
						|
          title = title + ' ' + match[1].toLowerCase();
 | 
						|
        }
 | 
						|
        return title;
 | 
						|
      }
 | 
						|
 | 
						|
      function extractWords(text, words, keywordMap) {
 | 
						|
        var tokens = text.toLowerCase().split(/[.\s,`'"#]+/mg);
 | 
						|
        tokens.forEach(function(token) {
 | 
						|
          var match = token.match(KEYWORD_REGEX);
 | 
						|
          if (match) {
 | 
						|
            var key = match[1];
 | 
						|
            if (!keywordMap[key]) {
 | 
						|
              keywordMap[key] = true;
 | 
						|
              words.push(key);
 | 
						|
            }
 | 
						|
          }
 | 
						|
        });
 | 
						|
      }
 | 
						|
 | 
						|
 | 
						|
      const filteredDocs = docs
 | 
						|
          // We are not interested in some docTypes
 | 
						|
          .filter(function(doc) { return !docTypesToIgnore[doc.docType]; })
 | 
						|
          // Ignore internals and private exports (indicated by the ɵ prefix)
 | 
						|
          .filter(function(doc) { return !doc.internal && !doc.privateExport; });
 | 
						|
 | 
						|
      filteredDocs.forEach(function(doc) {
 | 
						|
 | 
						|
 | 
						|
        var words = [];
 | 
						|
        var keywordMap = Object.assign({}, ignoreWordsMap);
 | 
						|
        var members = [];
 | 
						|
        var membersMap = {};
 | 
						|
 | 
						|
        // Search each top level property of the document for search terms
 | 
						|
        Object.keys(doc).forEach(function(key) {
 | 
						|
          const value = doc[key];
 | 
						|
 | 
						|
          if (isString(value) && !propertiesToIgnore[key]) {
 | 
						|
            extractWords(value, words, keywordMap);
 | 
						|
          }
 | 
						|
 | 
						|
          if (key === 'methods' || key === 'properties' || key === 'events') {
 | 
						|
            value.forEach(function(member) { extractWords(member.name, members, membersMap); });
 | 
						|
          }
 | 
						|
        });
 | 
						|
 | 
						|
 | 
						|
        doc.searchTerms = {
 | 
						|
          titleWords: extractTitleWords(doc.title || doc.name),
 | 
						|
          keywords: words.sort().join(' '),
 | 
						|
          members: members.sort().join(' ')
 | 
						|
        };
 | 
						|
 | 
						|
      });
 | 
						|
 | 
						|
      var searchData =
 | 
						|
          filteredDocs.filter(function(page) { return page.searchTerms; }).map(function(page) {
 | 
						|
            return Object.assign(
 | 
						|
                {path: page.path, title: page.name || page.title, type: page.docType}, page.searchTerms);
 | 
						|
          });
 | 
						|
 | 
						|
      docs.push({
 | 
						|
        docType: 'json-doc',
 | 
						|
        id: 'search-data-json',
 | 
						|
        template: 'json-doc.template.json',
 | 
						|
        path: this.outputFolder + '/search-data.json',
 | 
						|
        outputPath: this.outputFolder + '/search-data.json',
 | 
						|
        data: searchData
 | 
						|
      });
 | 
						|
    }
 | 
						|
  };
 | 
						|
};
 | 
						|
 | 
						|
 | 
						|
function isString(value) {
 | 
						|
  return typeof value == 'string';
 | 
						|
}
 | 
						|
 | 
						|
function convertToMap(collection) {
 | 
						|
  const obj = {};
 | 
						|
  collection.forEach(key => { obj[key] = true; });
 | 
						|
  return obj;
 | 
						|
} |