Class PageContentIndexingConnector

java.lang.Object
org.exoplatform.container.component.BaseComponentPlugin
org.exoplatform.commons.search.index.IndexingServiceConnector
org.exoplatform.commons.search.index.impl.ElasticIndexingServiceConnector
io.meeds.social.cms.storage.elasticsearch.PageContentIndexingConnector
All Implemented Interfaces:
org.exoplatform.container.component.ComponentPlugin

public class PageContentIndexingConnector extends org.exoplatform.commons.search.index.impl.ElasticIndexingServiceConnector
Indexes portal Pages for the unified search bar, as two kinds of documents sharing one index:
  • a content block document per block bound to the page through a CMSSetting whose type is backed by a registered PageContentBlockPlugin — generic across content-block types, no knowledge of any specific addon (e.g. Notes' Single Note View). A page can carry more than one block (e.g. several Single Note View blocks placed in different sections of the same page); each one is indexed as its own document, so that unified search returns one result per block rather than a single blended excerpt for the whole page. Its id is <page's storage id>_<block hash> (buildBlockId(java.lang.String, io.meeds.social.cms.model.CMSSetting, java.util.Map<java.lang.String, io.meeds.social.cms.storage.elasticsearch.PageContentIndexingConnector.ResolvedPage>)).
  • a bare page document — the page's title, name and site, no content — for a page carrying no live content block at all, so that a page like "Spaces" or "Tasks" can still be found by name by a user who doesn't know how to reach it. Its id is the page's storage id itself (page_<numeric DB id>), and it exists only while the page is reachable from a navigation node: a search result that leads nowhere is worse than none.
The two kinds are exclusive for a given page: the moment a live block appears, the block documents take over (they carry the same title, name and site fields, so the page stays findable by name) and the bare page document is removed — and a bare page document requested for a page that turns out to carry live blocks queues those blocks' own indexing instead (queueLiveBlockDocuments(org.exoplatform.portal.config.model.Page, java.util.List<io.meeds.social.cms.model.CMSSetting>, boolean)): every one of them on a creation, so that a full reindex started before the content-block plugins were registered (a reindex-on-upgrade runs at Kernel start, the plugins arrive with their addon's Spring context) still ends up with every block indexed; only the ones the index lacks on a refresh (update(java.lang.String)), so that a page saved outside the Layout addon gets its blocks indexed without a save through it indexing them twice. "Live" is a purely structural rule — a CMSSetting whose widget still sits on the page's layout, see PageContentBlockUtils — so that every path deciding what the index holds evaluates it identically, from layout alone. Its one blind spot: a page whose only block's widget is still there but whose content is gone (e.g. the note it displayed was deleted) has no document of either kind until the widget is removed from the page.

Neither id is PageKey.format(), which can exceed the 50-character limit of the ES_INDEXING_QUEUE.ENTITY_ID column, nor the setting's own name, which can be arbitrarily long — and the page id portion stays stable across page/site renames, unlike the formatted key.

  • Field Summary

    Fields
    Modifier and Type
    Field
    Description
    static final String
    The ES field listing the language tags a block actually has content for (the default/no-language content isn't listed — it's always the content field).
    static final String
    The ES connector/entity type name for indexed page documents.

    Fields inherited from class org.exoplatform.commons.search.index.impl.ElasticIndexingServiceConnector

    currentIndex, indexAlias, mapping, previousIndex, previousIndices, reindexOnUpgrade, replicas, shards

    Fields inherited from class org.exoplatform.commons.search.index.IndexingServiceConnector

    connectorName, enable

    Fields inherited from class org.exoplatform.container.component.BaseComponentPlugin

    desc, name
  • Constructor Summary

    Constructors
    Constructor
    Description
    PageContentIndexingConnector(io.meeds.social.cms.service.PageContentBlockPluginService pluginService, PageContentSearchConnector searchConnector, io.meeds.social.cms.service.CMSService cmsService, org.exoplatform.portal.mop.service.LayoutService layoutService, org.exoplatform.services.resources.LocaleConfigService localeConfigService, io.meeds.social.cms.service.PageUrlResolverService urlResolverService, org.exoplatform.container.xml.InitParams initParams)
     
  • Method Summary

    Modifier and Type
    Method
    Description
    static String
    buildBlockId(String pageStorageId, String contentType, String settingName)
     
    static String
     
    org.exoplatform.commons.search.domain.Document
    Builds a document from scratch — a full reindex, or a page or site that just came to exist.
    getAllIds(int offset, int limit)
    Every content block id first, then the storage id of every page of the store — the two lists are laid end to end, so that a batch spanning the boundary still comes back full: ElasticIndexingOperationProcessor#reindexAll loops while the returned batch size equals the batch size it asked for, so a batch coming back even one id short — after it has already queued a DELETE_ALL — ends the reindex and leaves every remaining document unindexed.
     
     
    static boolean
    isDraftPage(org.exoplatform.portal.mop.page.PageKey pageKey)
    A page currently being edited as a draft is cloned by the Layout addon as either a whole draft site (SiteType.DRAFT) or, within the same site, a page named <original>_draft_<username> — neither is a published page and must not be indexed.
    static boolean
    isIndexableSite(org.exoplatform.portal.mop.SiteKey siteKey)
     
    static boolean
     
    static long
     
    org.exoplatform.commons.search.domain.Document
    Refreshes a document that a listener already knows about.

    Methods inherited from class org.exoplatform.commons.search.index.impl.ElasticIndexingServiceConnector

    delete, getAttachmentProcessor, getCurrentIndex, getIndexAlias, getPipelineName, getPreviousIndex, getPreviousIndices, getReindexPipelineName, getReplicas, getShards, isNeedIngestPipeline, isReindexOnUpgrade, setPreviousIndex, setReplicas, setShards

    Methods inherited from class org.exoplatform.commons.search.index.IndexingServiceConnector

    isEnable, setEnable

    Methods inherited from class org.exoplatform.container.component.BaseComponentPlugin

    getDescription, getName, setDescription, setName

    Methods inherited from class java.lang.Object

    clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait
  • Field Details

    • TYPE

      public static final String TYPE
      The ES connector/entity type name for indexed page documents.
      See Also:
    • CONTENT_LANGUAGES_FIELD

      public static final String CONTENT_LANGUAGES_FIELD
      The ES field listing the language tags a block actually has content for (the default/no-language content isn't listed — it's always the content field). Lets the search side apply its "only excerpt in the searching user's own language" rule without having to pull every language's full text back in _source.
      See Also:
  • Constructor Details

    • PageContentIndexingConnector

      public PageContentIndexingConnector(io.meeds.social.cms.service.PageContentBlockPluginService pluginService, PageContentSearchConnector searchConnector, io.meeds.social.cms.service.CMSService cmsService, org.exoplatform.portal.mop.service.LayoutService layoutService, org.exoplatform.services.resources.LocaleConfigService localeConfigService, io.meeds.social.cms.service.PageUrlResolverService urlResolverService, org.exoplatform.container.xml.InitParams initParams)
  • Method Details

    • getConnectorName

      public String getConnectorName()
      Specified by:
      getConnectorName in class org.exoplatform.commons.search.index.IndexingServiceConnector
    • getMapping

      public String getMapping()
      Overrides:
      getMapping in class org.exoplatform.commons.search.index.impl.ElasticIndexingServiceConnector
    • getAllIds

      public List<String> getAllIds(int offset, int limit)
      Every content block id first, then the storage id of every page of the store — the two lists are laid end to end, so that a batch spanning the boundary still comes back full: ElasticIndexingOperationProcessor#reindexAll loops while the returned batch size equals the batch size it asked for, so a batch coming back even one id short — after it has already queued a DELETE_ALL — ends the reindex and leaves every remaining document unindexed.

      The page portion is paged by the store itself, in its own deterministic order (site type, site name, page name), and is not filtered here: drafts, pages of sites nobody navigates, pages carrying content blocks or unreachable ones are all decided in create(String), which returns null for them. Filtering before paging would need the whole page table loaded on every batch call, filtering after it would shorten batches; a disqualified id costs one queued operation that indexes nothing, which is cheap.

      Specified by:
      getAllIds in class org.exoplatform.commons.search.index.IndexingServiceConnector
    • create

      public org.exoplatform.commons.search.domain.Document create(String id)
      Builds a document from scratch — a full reindex, or a page or site that just came to exist. Besides the document itself, a bare page document requested this way for a page that turns out to carry live content blocks queues every one of those blocks' own indexing (see queueLiveBlockDocuments(org.exoplatform.portal.config.model.Page, java.util.List<io.meeds.social.cms.model.CMSSetting>, boolean)): nothing else may ever reach them, and the index cannot be asked which ones it holds at that moment.
      Specified by:
      create in class org.exoplatform.commons.search.index.IndexingServiceConnector
    • update

      public org.exoplatform.commons.search.domain.Document update(String id)
      Refreshes a document that a listener already knows about. Unlike create(java.lang.String), a bare page document refreshed for a page carrying live blocks queues only the blocks the index does not hold yet (see queueLiveBlockDocuments(org.exoplatform.portal.config.model.Page, java.util.List<io.meeds.social.cms.model.CMSSetting>, boolean)): the ones it holds are being refreshed by the listener that owns them, or need no refresh at all.
      Specified by:
      update in class org.exoplatform.commons.search.index.IndexingServiceConnector
    • contentFieldName

      public static String contentFieldName(String lang)
      Parameters:
      lang - language tag, empty string for the default/no-language content
      Returns:
      the ES field name holding that language's content
    • isPageDocumentId

      public static boolean isPageDocumentId(String id)
      Parameters:
      id - an indexed document id
      Returns:
      whether id designates a bare page document (a page storage id carrying no block hash) rather than a content block one
    • isDraftPage

      public static boolean isDraftPage(org.exoplatform.portal.mop.page.PageKey pageKey)
      A page currently being edited as a draft is cloned by the Layout addon as either a whole draft site (SiteType.DRAFT) or, within the same site, a page named <original>_draft_<username> — neither is a published page and must not be indexed.
      Parameters:
      pageKey - the page key to check
      Returns:
      true if the page is a draft
    • isIndexableSite

      public static boolean isIndexableSite(org.exoplatform.portal.mop.SiteKey siteKey)
      Parameters:
      siteKey - a site key
      Returns:
      whether the site is one users reach through a navigation, i.e. whose pages may surface as bare page documents
    • buildBlockId

      public static String buildBlockId(String pageStorageId, String contentType, String settingName)
      Parameters:
      pageStorageId - the storage id of the page carrying the block
      contentType - the content block's content type
      settingName - the content block's setting name
      Returns:
      the document id for the content block named settingName (of type contentType) bound to the page whose storage id is pageStorageId.
    • parsePageId

      public static long parsePageId(String blockId)
      Parameters:
      blockId - a content block document id (buildBlockId) or a plain page storage id — either way, the leading page_<numeric DB id> portion is parsed out.
      Returns:
      the numeric storage id of the page carrying the block.