Entity Extensions

Este documento descreve a implementação das extensões na Framework Elevation 300.

Modelo de Entidades

Entension - Modelo Entidades

POCOs

A classe que representa a entidade SalesItem tem como base a classe “ExtensionBusinessEntityBase” e implementa a interface “IEntityExtension”.

public class SalesItem : ExtensionBusinessEntityBase, IEntityExtension { }

Resources

A classe que representa a resource SalesItem tem como base a classe “ExtensionBusinessResourceBase”.

public partial class SalesItemResource : ExtensionBusinessResourceBase

ControllersApp

Create

O serviço de create da extensão recebe como parâmetro o id da base (parentId).

[Route("{parentId}/new")]
[HttpGet]
CreateSalesItemResource(Guid parentId)
{
}

Neste serviço é feita a validação se já existe um draft da extensão para a respetiva entidade base:

  • Se existir, é retornado esse draft;
  • Se não existir, é criado um novo draft para a extensão que referencia a respetiva entidade base.

Submit

O controllerApp da extensão implementa a interface ISupportsExtension.

public interface ISupportsExtension
{
    Task Submit(Guid id);
}

No momento do submit da entidade base, o DraftService é responsável por executar o submit de todas as extensões associadas.

Delete base and extensions

O manager da extensão implementa a interface ISupportsDelete.

public interface ISupportsDelete
{
    Task Delete(Guid id);
}

No momento do delete da entidade base, o DraftService é responsável por executar o delete de todas as extensões associadas.

Ativar e desativar extensão

O serviço de ativar e desativar extensão recebe como parâmetro o id da base (parentId) e o valor para ativar e desativar a extensão.

[Route("~/app/{tenantKey}/{orgKey}/simpleBusinessCore/customerParty/{baseId}/active")]
[HttpPut]
[ResponseType(typeof(bool))]
public virtual async Task<bool> UpdateExtensionState(Guid baseId, [FromBody] bool value)

O serviço é responsável por alterar o estado do draft para ativo ou não. No momento do submit o estado do draft da extensão é refletido na entidade e submetido na base de dados.

Nota: A rota é gerada com o nome da extensão (no exemplo “customerParty”) pois para cada extensão existe apenas um serviço e existe uma limitação na arquitetura atual que na construção dos tabuladores não é possível obter o nome do serviço para uma dada extensão.

DraftService

O draft da extensão tem uma referência para o draft base (ParentId) bem como o FullName da classe do respetivo controllerApp (que implementa a interface ISupportsExtension).

Draft Entity

DraftModel<TResource> GetExtension<TResource>(Guid id, Guid? schemaEntity)
Task ProcessExtensions(Guid parentId);
  • GetExtension: retorna o draft de uma extensão (schemaEntity) para uma determinada base (id),
  • ProcessExtensions: usado no momento de gravação da entidade base para gravar também as respetivas extensões.

Cliente

A view da extensão é modelada de forma independente da view da entidade base.

Quando o utilizador acede às operações da entidade base, é feita a validação se existem extensões, sendo estas incluídas em runtime.

Views

Sempre que uma entidade tem extensões associadas, são gerados no topo da view os respetivos tabuladores.

O tabulador da entidade base tem o nome “General”, sendo que o das extensões tem a caption definida no PresentationModel.

As extensões que não estão ativas aparecem no drop down.

Add Extension

Caso a extensão fique ativa é acrescentado um tab da extensão.

Active Extension

Caso se desative a extensão, o ‘Sales Item’ volta para a drop down, e o respetivo tab é removido. No entanto, se desativar uma extensão e voltar a ativá-la, a mesma fica com o estado prévio.

O HTML/Javascript da entidade base é carregado logo que se acede à operação.

Quanto ao HTML/Javascript da extensão, é carregado apenas no momento em que se acede ao respetivo tabulador.

A diretiva responsável por este comportamento:

<pri-extension-view statecreate="createState"
                    stateupdate="updateState"
…>
</pri-extension-view>

Config (state)

Cada extensão regista o respetivo estado no config do módulo onde é definida. Estes estados não têm parente definido.

$stateProvider
   .state('createExtensionSimpleBusinessCoreSalesItem', {
        parent: '',
        templateUrl: function ($stateParams) {…},
        params: { callback: null },
        controller: 'BusinessCore.SalesItemCreateSalesItemController',
        resolve: {
            promiseObj: function ($q, $rootScope) {…}
        }
    });