Solução sem código: apresentar os dias desde a última alteração de um item de lista
Aplica-se A
por Justin Joyce, LANtek
Nota: Este artigo faz parte de uma coleção de publicações de quatro anos do blogue Obter o Ponto para utilizadores finais do SharePoint.
Descrição geral: Relatórios personalizados de envelhecimento sem código
Uma das partes funcionais frequentemente pedidas de um site do SharePoint é um relatório antigo para tarefas ou itens de lista. Por outras palavras, quantos dias/meses se passaram desde que este item de lista foi modificado pela última vez?
Na superfície, este parece ser um pedido muito simples. Afinal de contas, temos datas para itens criados e modificados, temos a capacidade de armazenar datas personalizadas quando determinadas alterações aos itens ocorrem através de recetores de eventos. Temos colunas calculadas onde podemos incluir fórmulas semelhantes ao Excel para trabalhar com as nossas informações. Esta parece ser uma proposta muito directa. Escolhemos um campo de data, criamos uma coluna calculada e, em seguida, fazemos uma fórmula de acordo com as linhas de [DateField] – [Hoje]. Mas não tão rápido! Como qualquer pessoa que tenha tentado esta tarefa "simples" sabe, tentar usar algo como [Hoje] numa coluna calculada causa problemas. Experimente inserir [Hoje] na caixa de fórmulas da coluna calculada para lhe dar uma mensagem de erro semelhante à seguinte:
Por que é isto? Bem, tem a ver com a forma como as colunas calculadas são calculadas.
Vamos utilizar uma fórmula simples como exemplo:
= SE( [Coluna1]<=[Coluna2], "OK", "Não OK")
Tudo isto indica que, se Coluna1 for menor ou igual a Coluna2, apresentar OK, caso contrário, apresentar Não OK. Esta é uma fórmula básica bastante típica para uma coluna calculada e faz uma suposição básica sobre o item de lista que contém estas colunas: os valores para Coluna1 e Coluna2 nunca poderão ser alterados sem um evento Atualizar no item de lista.
Isso mesmo, as colunas calculadas só serão recalculadas quando a lista for atualizada (ou criada), uma vez que assumem que as informações que está a calcular estão contidas no próprio item. Isto cria um problema quando está a tentar utilizar algo que muda independentemente dos campos do item, como a data atual.
Agora não estava na reunião em que decidiram que era assim que as colunas calculadas funcionariam, no entanto, se tivesse de fazer um palpite educado, assumiria que funcionam desta forma para o desempenho. Imagine que tinha uma lista de vários milhares de itens, cada um dos quais continha uma coluna calculada que precisava de uma atualização "em direto". Tal significaria que algum mecanismo, talvez uma tarefa de temporizador, teria de iterar através de cada item que continha essa coluna calculada de vez em quando e atualizar o seu valor. Isto pode ser extremamente taxativo em termos de desempenho, porque com implementações maiores esta tarefa pode estar constantemente em execução e a mudar as coisas. É só o meu palpite, mas faz muito sentido se pensares nisso.
Existem algumas sugestões para soluções semelhantes que envolvem enganar o SharePoint para aceitar um valor Hoje ao criar primeiro uma coluna com o nome Hoje e, em seguida, adicioná-la à sua fórmula e, em seguida, eliminá-la. Tudo isto é bom, mas lembre-se do que disse quando as colunas calculadas são atualizadas. Este valor só será alterado quando o item for atualizado, o que significa que os valores estarão incorretos em breve, especialmente no caso de um cálculo diário.
Já vi outros a utilizarem JavaScript inteligente para escrever os valores na página. Isto também funcionaria, mas sou praticamente categoricamente contra o script de cliente quando pode ser evitado.
Implementação:
Então, o que fazer? As colunas calculadas estão fora de questão para as chamadas funções "voláteis", como Hoje. É possível que possamos desenvolver algum código personalizado para tratar disto por nós, como uma Coluna Calculada, trabalho de temporizador ou processo agendado para aparecer e atualizar todos os itens que precisam deste cálculo efetuado. Isso leva-nos de volta ao problema de desempenho que mencionei no último parágrafo e, além disso, é uma solução frágil que seria altamente específica para o site/lista/coluna em questão. Além dessas duas preocupações, também terias de encontrar um tipo totó, como eu, que saiba codificar e persuadi-lo a desenvolver esta solução para ti. Mas há uma maneira mais fácil!
Se tiver direitos para criar campos e editar páginas no seu site e tiver um pouco de conhecimento sobre XSLT e criar vistas, pode criar um modelo XSL que pode ser incluído numa vista de lista e calculará fielmente o seu valor sempre que a página for pedida. Este cenário elimina a nossa preocupação com o desempenho e não requer que o código personalizado seja desenvolvido e implementado através de uma solução.
Perfeito. Então, como é que o fazemos?
-
Crie ou selecione o campo que funcionará como a nossa origem. Tem de ser um tipo de data.
-
Crie o nosso campo que funcionará como um marcador de posição para o valor que está a ser calculado.
-
Adicione ambos os campos a um tipo de conteúdo e adicione esse tipo de conteúdo a uma lista.
-
Crie uma vista dessa lista que contenha as colunas de origem e de marcador de posição.
-
Carregue o modelo XSL para a Biblioteca de Estilos.
-
Defina a propriedade "Ligação XSL" para a Peça Web Vista de Lista através da IU.
-
Êxito!
Vamos explorar um caso de utilização de exemplo e percorrer a implementação. O nosso cliente queria uma vista da lista principal que lhes indicasse há quanto tempo um determinado item de lista estava no seu estado. Esta lista continha um tipo de conteúdo de site personalizado derivado do tipo Item e adicionado à lista. Já havia um recetor de eventos no local que captura cada vez que o campo de estado no item de lista era alterado e guardado nessa data numa coluna chamada "Estado da Data Alterado". Toda esta cablagem não é necessária e pode ser feita com qualquer campo de data (acontece que esta é a nossa implementação, mas pode experimentar). O mínimo que irá precisar é do campo de data de origem e do campo de marcador de posição para manter o cálculo (mais sobre este no parágrafo seguinte) adicionado à sua lista, embora sugira que utilize colunas de site e tipos de conteúdo de site caso pretenda reutilizar esta solução noutros locais do seu site.
Portanto, temos a nossa data de origem que podemos utilizar no nosso cálculo em relação à data de hoje. Agora, podemos criar uma coluna de site personalizada para utilizar como um contentor para o nosso valor calculado. Neste caso, optei por utilizar uma coluna calculada, uma vez que não poderá ser alterada nos formulários de item novo ou editar, mas pode ser selecionada para apresentação nas vistas, uma vez que não queremos que os utilizadores introduzam valores arbitrários nesta coluna. Pode ser confuso saber por que motivo não está a ser apresentado nas vistas, etc.
Agora que temos a nossa coluna de site, podemos adicioná-la aos nossos tipos de conteúdo que serão utilizados na nossa lista. Em seguida, temos de criar a nossa vista que será posteriormente personalizada com o nosso XSLT. Certifique-se de que cria uma vista padrão que contém a coluna de data de origem e a nova coluna calculada que funcionará como um marcador de posição para o valor calculado.
Temos agora tudo em vigor que vamos precisar para apoiar o nosso relatório de envelhecimento personalizado. Tudo o que resta é criar o nosso modelo XSL, carregá-lo para a Biblioteca de Estilos do site e ligá-lo à nossa vista de lista. O modelo XSL que vamos utilizar irá conter algumas marcações normais geradas pelo SharePoint para gerar a vista, bem como a nossa própria marcação personalizada utilizada para substituir determinadas partes deste valor e calcular o valor pretendido por nós.
Dando crédito quando o crédito é devido, os modelos XSL para fazer os cálculos reais que estou a utilizar para esta solução foram graciosamente fornecidos por "swirch" nos fóruns do MSDN:http://social.msdn.microsoft.com/Forums/en-US/sharepointcustomization/thread/aeda905b-9bc6-40c4-bd22-21306c5cb0d2/
Transfira a folha de estilos XSL (aging.zip) que reuni aqui:https://OneDrive.live.com/?cid=c262e8e2d59a86d9&permissionsChanged=1&id=C262E8E2D59A86D9!104
Ao abrir isto no seu editor de texto favorito, verá uma grande quantidade de marcações XSL normais do SharePoint para compor as vistas. Se continuar a deslocar para baixo até à linha 357, verá o início dos modelos personalizados que adicionei à marcação, sendo o primeiro o modelo "DateDiff" seguido de "calculate-julian-day" e "FieldRef_printTableCell_EcbAllowed.Days_x0020_At_x0020_Status". Estes são os nossos três modelos que farão e apresentarão os nossos cálculos nas nossas vistas. Se estiver a utilizar nomes de campo diferentes dos especificados anteriormente neste artigo, terá de percorrer estes modelos e substituir quaisquer referências aos outros nomes. Lembre-se de que, para tal, vai querer utilizar o nome INTERNO do campo e não o nome a apresentar.
Assim que estiver satisfeito com o facto de o modelo estar pronto para ser executado, navegue para a Sua Biblioteca de Estilos e carregue-o na pasta "Folhas de Estilo XSL" e, em seguida, copie a ligação para o ficheiro. Isto irá permitir-nos efetuar facilmente alterações ao mesmo mais tarde ou adicioná-lo a diferentes partes do site conforme quisermos.
Em seguida, aceda à sua lista e selecione a vista que criou anteriormente neste artigo. No menu "Ações do Site", clique em "Editar Página".
Localize a Peça Web Vista de Lista na página e abra o menu Peça Web ao clicar na pequena seta para baixo no canto superior direito. Neste menu, selecione "Editar Peça Web".
Esta ação irá abrir o menu da Peça Web no lado direito da janela do browser.
Clique no + para a secção "Diversos" e localize a propriedade "Ligação XSL".
Cole a ligação para o ficheiro XSL na Biblioteca de Estilos que copiou anteriormente (pode ser uma ligação relativa ou absoluta).
Clique em "OK" para guardar as alterações e, em seguida, clique no botão "Parar Edição" no friso "Página" na parte superior da página.
Se tudo tiver sido configurado corretamente, deverá ver números na coluna "Dias no Estado".
E, finalmente, eis o aspeto que teria com alguns dados de teste de várias datas:
Resumo:
Aí está: uma forma bem formatada, robusta e com melhor desempenho para criar um relatório antigo no SharePoint., completada com uma implementação simples sem código. Isto tem bastantes aplicações potenciais para além do único caso de utilização que explorámos aqui. Outro cenário comum para este tipo de relatório é anexá-lo a uma lista de tarefas para que possa ver há quanto tempo passou desde que uma tarefa foi criada de relance.
Esperamos que goste!
--Justin
Justin Joyce
Comentários
Passos em falta 08/10/2012 3:51 Ok Segui os passos, mas tem de haver algo em falta- como é que o XSL saberá qual a data a utilizar ou em que campo adicionar os dias desde então? odeia-o quando os passos são perdidos.
Sem Código, acordado! 30/08/2012 12:12 Concordo- Não acho que isto realmente conte como "sem código".Curiosamente, através de algum erro do SharePoint, tenho uma coluna calculada funcional a utilizar Hoje... não sei como ou porquê porque não consigo fazê-lo novamente, mas o que ainda está lá e a trabalhar.
Fórmula para a Coluna Calculada "Dias no Estado"? 02/05/2012 07:39 Justin – Qual é a fórmula que utilizou para a coluna de site calculada "Dias no Estado" (coluna de marcador de posição)? Foi "=hoje"?
SharePoint 2007 2/12/2011 11:29 Atualmente, não tentei aplicar esta solução ao SharePoint 2007. No entanto, estou a analisá-la. Infelizmente, não existe nenhuma propriedade XslLink na peça Web através da IU.
Excelente Publicação 30/11/2011 9:53 Olá; Grande Post.Estou a utilizar o SharePoint 2007.Não tenho uma secção Misc, conforme indicado acima.Tem passos para uma configuração do SP2007? Obrigado.
Re: Solução sem código: apresentar os dias desde que um item de lista do SharePoint foi alterado pela última vez 11/10/2011 8:24 Olá Chris.grande descoberta! Vou ver o que publicou ainda hoje e ver se consigo tornar esta solução um pouco mais robusta.Ainda bem que gostou da mensagem e ainda bem que conseguiu encontrar uma solução para o formato de data europeu. :) -Justin
Solução para Formatos de Data Europeus 11/10/2011 6:45 Olá novamente Justin, Nota: encontrei uma solução para o problema que mencionei anteriormente nesta página;https://sharepointbydummies.wordpress.com/2011/07/13/possible-work-around-to-date-format-issue-sharepoint-2010/
Formatos de Data Europeus 07/10/2011 3:59 Olá Justin, Esta é uma solução muito boa, obrigado, e é o tipo de coisa que passei os últimos dois dias à procura! No entanto, estou a ter um pequeno problema com isso e esperava que me pudesses ajudar.Alterei ligeiramente o seu código para calculá-lo até que algo aconteça, em vez de o fazer desde então, ao mudar as variáveis na última linha da função "DateDiff"; <xsl:value-of select="$JulianToday - $JulianStartDate"></xsl:value-of> No entanto, só consigo fazê-lo agrupar a diferença corretamente metade do tempo. Por exemplo, com esta data (formatar dd/MM/aaaa); 12/30/2011 Calcula corretamente, mas com esta data (mesmo formato) 10/12/2011 Calcula como se fosse 10-Dez-2011 em vez de 12-Out-2011.Tentei mudar simplesmente as posições dos valores de dia e mês na variável "JulianStartDate", desta forma; <xsl:with-param name="Month" select="substring(ddwrt:FormatDateTime(string($StartDate), 1033, 'yyyyMMdd'),7,2)"/> <xsl:with-param name="Day" select="substring(ddwrt:FormatDateTime(string($StartDate), 1033, 'yyyyMMdd'),5,2)"/> E isto corrigiu o problema com a segunda data, no entanto estava então incorreto para a primeira data! Também tentei alterar as chamadas FormatDateTime para utilizar LCIDs europeus e várias alterações para o último parâmetro de FormatDateTime (por exemplo, ddMMyyyy, MMddyyyyy) com os ajustes adequados aos parâmetros posicionais de subcadeia sem êxito.Agradeço muito qualquer conselho que possa oferecer.Obrigado; Chris
Sem Código 21/09/2011 4:27 Não creio que o XSL se qualifique como uma solução "sem código", uma vez que compreender a linguagem XSL não é para todos - no entanto, não envolve programação. Além disso: Boa solução, obrigado!