PageModelManager

O PageModelManager A biblioteca é fornecida como um pacote NPM a ser usado por um projeto SPA. Ela acompanha o SPA e serve como um gerenciador de modelo de dados.

Em nome do SPA, ele abstrai a recuperação e o gerenciamento da estrutura JSON que representa a estrutura de conteúdo real. Também é responsável pela sincronização com o SPA para informá-lo quando deve renderizar novamente seus componentes.

Consulte o pacote NPM @adobe/aem-spa-page-model-manager

Ao inicializar o PageModelManager, a biblioteca primeiro carrega o modelo raiz fornecido do aplicativo (por meio do parâmetro , da meta propriedade ou do URL atual). Se a biblioteca identificar que o modelo da página atual não faz parte do modelo raiz, ele é buscado e inclui-o como o modelo de uma página secundária.

page_model_Consolidation

ComponentMapping

O ComponentMapping é fornecido como um pacote NPM para o projeto front-end. Ele armazena componentes de front-end e fornece uma maneira de o SPA mapear componentes de front-end para AEM tipos de recursos. Isso permite uma resolução dinâmica de componentes ao analisar o modelo JSON do aplicativo.

Cada item presente no modelo contém um :type que expõe um tipo de recurso AEM. Quando montado, o componente de front-end pode se renderizar usando o fragmento de modelo recebido das bibliotecas subjacentes.

Modelo dinâmico para mapeamento de componentes

Para obter detalhes sobre como o modelo dinâmico para mapeamento de componentes ocorre no Javascript SPA SDK para AEM, consulte o artigo Modelo dinâmico para mapeamento de componentes para SPA.

Camada específica da estrutura

Uma terceira camada deve ser implementada para cada estrutura de front-end. Essa terceira biblioteca é responsável por interagir com as bibliotecas subjacentes e fornecer uma série de pontos de entrada bem integrados e fáceis de usar para interagir com o modelo de dados.

O restante deste documento descreve os requisitos dessa camada específica da estrutura intermediária e aspira a ser independente da estrutura. Respeitando os requisitos a seguir, pode ser fornecida uma camada específica para a estrutura para que os componentes do projeto interajam com as bibliotecas subjacentes responsáveis pelo gerenciamento do modelo de dados.

Conceitos gerais

Modelo de página

A estrutura de conteúdo da página é armazenada em AEM. O modelo da página é usado para mapear e instanciar componentes SPA. Os desenvolvedores de SPA criam componentes SPA que mapeiam para AEM componentes. Para fazer isso, eles usam o tipo de recurso (ou o caminho para o componente de AEM) como uma chave exclusiva.

Os componentes do SPA devem estar sincronizados com o modelo da página e ser atualizados com qualquer alteração no conteúdo de acordo. Um padrão que aproveite componentes dinâmicos deve ser usado para instanciar os componentes dinamicamente de acordo com a estrutura do modelo de página fornecida.

Campos Meta

O modelo de página aproveita o Exportador de Modelo JSON, que se baseia no Modelo Sling API. Os modelos de sling exportáveis expõem a seguinte lista de campos para permitir que as bibliotecas subjacentes interpretem o modelo de dados:

  • :type: Tipo do recurso AEM (padrão = tipo de recurso)

  • :children: Filhos hierárquicos do recurso atual. Os filhos não fazem parte do conteúdo interno do recurso atual (pode ser encontrado em itens que representam uma página)

  • :hierarchyType: Tipo hierárquico de um recurso. O PageModelManager atualmente suporta o tipo de página

  • :items: Recursos de conteúdo filho do recurso atual (estrutura aninhada, presente somente em contêineres)

  • :itemsOrder: Lista ordenada dos filhos. O objeto de mapa JSON não garante a ordem de seus campos. Com o mapa e o array atual, o consumidor da API tem os benefícios de ambas as estruturas

  • :path: Caminho do conteúdo de um item (presente nos itens que representam uma página)

Consulte também Introdução aos AEM Content Services.

Módulo específico da estrutura

A separação de preocupações ajuda a facilitar a implementação do projeto. Por conseguinte, deve ser fornecido um pacote específico para as npm. Esse pacote é responsável pela agregação e exposição dos módulos, serviços e componentes básicos. Esses componentes devem encapsular a lógica de gerenciamento do modelo de dados e fornecer acesso aos dados que o componente do projeto espera. O módulo também é responsável por expor transitoriamente pontos de entrada úteis das bibliotecas subjacentes.

Para facilitar a interoperabilidade das bibliotecas, o Adobe aconselha o módulo específico da estrutura a agrupar as seguintes bibliotecas. Se necessário, a camada pode encapsular e adaptar as APIs subjacentes antes de expô-las ao projeto.

Implementações

Reagir

módulo npm: @adobe/aem-response-editable-components

Angular

módulo npm: @adobe/aem-angular-edititable-components

Principais serviços e componentes

As seguintes entidades devem ser implementadas em conformidade com as orientações específicas de cada quadro. Com base na arquitetura da estrutura, a implementação pode variar amplamente, mas as funcionalidades descritas devem ser fornecidas.

O Provedor de Modelo

Os componentes do projeto devem delegar acesso aos fragmentos de um modelo em um Provedor de Modelo. O Provedor de Modelo é responsável por acompanhar as alterações feitas no fragmento especificado do modelo e retornar o modelo atualizado ao componente delegado.

Para fazer isso, o Provedor de Modelo deve se registrar no PageModelManager. Em seguida, quando ocorrer uma alteração, ele receberá e transmitirá os dados atualizados ao componente de delegação. Por convenção, a propriedade disponibilizada ao componente delegado que carregará o fragmento do modelo é nomeada cqModel. A implementação é gratuita para fornecer essa propriedade ao componente, mas deve considerar aspectos como a integração com a arquitetura da estrutura, a descoberta e a facilidade de uso.

O HTML do componente

O Component Decorator é responsável por decorar a HTML externa do elemento de cada instância de componente com uma série de atributos de dados e nomes de classe esperados pelo Editor de páginas.

Declaração de componente

Os metadados a seguir devem ser adicionados ao elemento HTML externo produzido pelo componente do projeto. Eles permitem que o Editor de páginas recupere a configuração de edição correspondente.

  • data-cq-data-path: Caminho para o recurso relativo ao jcr:content

Editar declaração de capacidade e espaço reservado

Os metadados e nomes de classe a seguir devem ser adicionados ao elemento HTML externo produzido pelo componente do projeto. Eles permitem que o Editor de páginas ofereça funcionalidades relacionadas.

  • cq-placeholder: Nome da classe que identifica o espaço reservado de um componente vazio
  • data-emptytext: Rótulo a ser exibido pela sobreposição quando uma instância de componente estiver vazia

Espaço reservado para componentes vazios

Cada componente deve ser estendido com uma funcionalidade que decorará o elemento HTML externo com atributos de dados e nomes de classe específicos para espaços reservados e sobreposições relacionadas quando o componente for identificado como vazio.

Sobre o vazamento de um componente

  • O componente está logicamente vazio?
  • Qual deve ser o rótulo exibido pela sobreposição quando o componente está vazio?

Contêiner

Um contêiner é um componente destinado a conter e renderizar componentes filhos. Para fazer isso, o contêiner repete a :itemsOrder, :items e :children propriedades do modelo.

O contêiner obtém dinamicamente os componentes filhos do armazenamento do ComponentMapping biblioteca. Em seguida, o contêiner estende o componente filho com os recursos do Provedor de modelo e, por fim, instanciá-lo.

Página

O Page estende o Container componente. Um contêiner é um componente destinado a conter e renderizar componentes filhos, incluindo páginas filhas. Para fazer isso, o contêiner repete a :itemsOrder, :itemse :children propriedades do modelo. O Page O componente obtém dinamicamente os componentes filhos do armazenamento do ComponentMapping biblioteca. O Page é responsável pela instanciação de componentes filhos.

Grade responsiva

O componente Grade responsiva é um contêiner. Ela contém uma variante específica do Provedor de Modelo que representa suas colunas. A Grade Responsiva e suas colunas são responsáveis por decorar o elemento HTML externo do componente do projeto com os nomes de classe específicos contidos no modelo.

O componente Grade responsiva deve vir pré-mapeado para sua AEM contraparte, pois esse componente é complexo e raramente personalizado.

Campos de modelo específicos

  • gridClassNames: Nomes de classe fornecidos para a grade responsiva
  • columnClassNames: Nomes de classe fornecidos para a coluna responsiva

Espaço reservado da grade responsiva

O componente de SPA é mapeado para um contêiner gráfico, como a Grade Responsiva, e deve adicionar um espaço reservado para filho virtual quando o conteúdo estiver sendo criado. Quando o conteúdo do SPA é criado pelo Editor de páginas, ele é incorporado ao editor usando um iframe e o data-cq-editor é adicionado ao nó do documento desse conteúdo. Quando a variável data-cq-editor estiver presente, o contêiner deverá incluir um HTMLElement para representar a área com a qual o autor interage ao inserir um novo componente na página.

Por exemplo:

<div data-cq-data-path={"path/to/the/responsivegrid/*"} className="new section aem-Grid-newComponent"/>
NOTE
Os nomes de classe usados no exemplo são atualmente exigidos pelo editor de páginas.
  • "new section": Indica que o elemento atual é o espaço reservado do contêiner
  • "aem-Grid-newComponent": Normaliza o componente para a criação de layout

Mapeamento de componentes

O Component Mapping biblioteca e sua MapTo pode ser encapsulada e estendida para fornecer as funcionalidades relativas à configuração de edição fornecida ao lado da classe de componente atual.

const EditConfig = {

    emptyLabel: 'My Component',

    isEmpty: function() {
        return !this.props || !this.props.cqModel || this.props.cqModel.isEmpty;
    }
};

class MyComponent extends Component {

    render() {
        return <div className={'my-component'}></div>;
    }
}

MapTo('component/resource/path')(MyComponent, EditConfig);

Na implementação acima, o componente do projeto é estendido com a funcionalidade vazia antes de ser realmente registrado na Mapeamento de componentes armazenar. Isso é feito encapsulando e estendendo o ComponentMapping para introduzir o suporte da EditConfig objeto de configuração:

/**
 * Configuration object in charge of providing the necessary data expected by the page editor to initiate the authoring. The provided data will be decorating the associated component
 *
 * @typedef {{}} EditConfig
 * @property {String} [dragDropName]       If defined, adds a specific class name enabling the drag and drop functionality
 * @property {String} emptyLabel           Label to be displayed by the placeholder when the component is empty. Optionally returns an empty text value
 * @property {function} isEmpty            Should the component be considered empty. The function is called using the context of the wrapper component giving you access to the component model
 */

/**
 * Map a React component with the given resource types. If an {@link EditConfig} is provided the <i>clazz</i> is wrapped to provide edition capabilities on the AEM Page Editor
 *
 * @param {string[]} resourceTypes                      - List of resource types for which to use the given <i>clazz</i>
 * @param {class} clazz                                 - Class to be instantiated for the given resource types
 * @param {EditConfig} [editConfig]                     - Configuration object for enabling the edition capabilities
 * @returns {class}                                     - The resulting decorated Class
 */
ComponentMapping.map = function map (resourceTypes, clazz, editConfig) {};

Contrato com o Editor de páginas

Os componentes do projeto devem gerar no mínimo os seguintes atributos de dados para permitir que o editor interaja com eles.

  • data-cq-data-path: O caminho relativo do componente, conforme fornecido pelo PageModel (por exemplo, "root/responsivegrid/image"). Esse atributo não deve ser adicionado às páginas.

Em resumo, para ser interpretado pelo editor de páginas como editável, um componente de projeto deve respeitar o seguinte contrato:

  • Forneça os atributos esperados para associar uma instância do componente front-end a um recurso AEM.
  • Forneça a série esperada de atributos e nomes de classe que permite a criação de espaços reservados vazios.
  • Forneça os nomes de classe esperados, permitindo o arrastar e soltar dos ativos.

Estrutura típica do elemento HTML

O fragmento a seguir ilustra a representação HTML típica de uma estrutura de conteúdo da página. Aqui estão alguns pontos importantes:

  • O elemento de grade responsiva contém nomes de classe prefixados com aem-Grid--
  • O elemento de coluna responsiva tem nomes de classe prefixados com aem-GridColumn--
  • Uma grade responsiva que também é a coluna de uma grade pai é encapsulada, como os dois prefixos anteriores, não aparecem no mesmo elemento
  • Os elementos correspondentes aos recursos editáveis carregam uma data-cq-data-path propriedade. Consulte a Contrato com o editor de páginas seção deste documento.
<div data-cq-data-path="/content/page">
    <div class="aem-Grid aem-Grid--12 aem-Grid--default--12">
        <div class="aem-container aem-GridColumn aem-GridColumn--default--12" data-cq-data-path="/content/page/jcr:content/root/responsivegrid">
            <div class="aem-Grid aem-Grid--12 aem-Grid--default--12">
                <div class="cmp-image cq-dd-image aem-GridColumn aem-GridColumn--default--12" data-cq-data-path="/root/responsivegrid/image">
                    <img src="/content/we-retail-spa-sample/react/jcr%3acontent/root/responsivegrid/image.img.jpeg/1512113734019.jpeg">
                </div>
            </div>
        </div>
    </div>
</div>

O aplicativo é o proprietário do roteamento. O desenvolvedor de front-end precisa primeiro implementar um componente de Navegação (mapeado para um componente de navegação de AEM). Esse componente renderizaria links de URL a serem usados junto com uma série de rotas que exibirão ou ocultarão fragmentos de conteúdo.

O PageModelManager biblioteca e sua ModelRouter módulo (habilitado por padrão) são responsáveis pela pré-busca e pelo fornecimento de acesso ao modelo associado a um determinado caminho de recurso.

As duas entidades estão relacionadas com a noção de encaminhamento, mas a ModelRouter é responsável apenas por ter a PageModelManager carregado com um modelo de dados estruturado em sincronia com o estado atual do aplicativo.

Veja o artigo Roteamento do Modelo de SPA para obter mais informações.

SPA em ação

Veja como um SPA simples funciona e experimente um SPA você mesmo continuando com o documento Introdução ao SPA no AEM.

Leitura adicional

Para obter mais informações sobre SPA no AEM, consulte os seguintes documentos:

Experience Manager