Design e processamento de scripts do lado do cliente
Client scripts bem projetados podem reduzir o tempo que os usuários levam para preencher um formulário.
O processamento adequado do lado do cliente depende do carregamento do formulário primeiro. Fazer atualizações de registro antes do carregamento do formulário pode produzir resultados inesperados que ignoram o processamento do lado do cliente.
- Desabilite a edição de lista para a tabela.
- Crie regras de negócios apropriadas ou controles de acesso para edição de lista.
- Crie políticas de dados.
- Crie um client script onCellEdit separado.
Restringir a edição da lista
Se você criar políticas de IU ou client scripts para campos em um formulário, deverá usar outro método para garantir que os dados nesses campos sejam controlados de forma semelhante em uma lista.
- Desabilite a edição de lista para a tabela.
- Crie regras de negócios apropriadas ou controles de acesso para edição de lista.
- Crie políticas de dados.
- Crie um client script onCellEdit separado.
Minimizar pesquisas do servidor
Use os dados do cliente o máximo possível para eliminar a necessidade de pesquisas demoradas do servidor.
O client scripting usa dados disponíveis no cliente ou dados recuperados do servidor. As principais maneiras de obter informações do servidor são g_scratchpad e pesquisa assíncrona de GlideAjax.
A principal diferença entre esses métodos é que g_scratchpad é enviado uma vez quando um formulário é carregado (as informações são enviadas por push do servidor para o cliente), enquanto o GlideAjax é acionado dinamicamente quando o cliente solicita informações do servidor.
Recuperar dados do servidor usando g_scratchpad
O objeto g_scratchpad passa informações do servidor para o cliente, como quando o cliente requer informações não disponíveis no formulário.Por exemplo, se você tiver um client script que precisa acessar o campo u_retrieve e o campo não estiver no formulário, os dados não estarão disponíveis para o client script. Uma solução típica para essa situação é colocar o campo no formulário e sempre ocultá-lo com um script de cliente ou uma política de IU. Embora esta solução possa ser mais rápida de configurar, ela é mais lenta de executar.
Se você souber de quais informações o cliente precisa do servidor antes que o formulário seja carregado, uma regra de negócios de exibição pode criar propriedades g_scratchpad para manter essas informações. Theg_scratchpad é enviado para o cliente quando o formulário é solicitado, disponibilizando-o para todos os métodos de script do lado do cliente. Este é um meio muito eficiente de enviar informações do servidor para o cliente. No entanto, você só pode carregar dados dessa forma quando o formulário é carregado. A regra de negócios não pode ser acionada dinamicamente. Nesses casos, use uma chamada GlideAjax assíncrona.
- O valor da propriedade do sistema css.base.color
- Se o registro atual tem ou não anexos
- O nome do gerente do solicitante
g_scratchpad.css = gs.getProperty('css.base.color');
g_scratchpad.hasAttachments = current.hasAttachments();
g_scratchpad.managerName = current.caller_id.manager.getDisplayValue();// Check if the form has attachments
if (g_scratchpad.hasAttachments)
// do something interesting here
else
alert('You need to attach a form signed by ' + g_scratchpad.managerName);Recuperar dados do servidor usando GlideAjax assíncrono
O GlideAjax assíncrono permite que você solicite informações dinamicamente do servidor.
//Alert if the assignment groups name matches the support group
function onChange(control, oldValue, newValue, isLoading) {
if (isLoading)
return;
var ga = new GlideAjax('ciCheck');
ga.addParam('sysparm_name', 'getCiSupportGroup');
ga.addParam('sysparm_ci', g_form.getValue('cmdb_ci'));
ga.addParam('sysparm_ag', g_form.getValue('assignment_group'));
ga.getXML(doAlert); // Always try to use asynchronous (getXML) calls rather than synchronous (getXMLWait)
}
// Callback function to process the response returned from the server
function doAlert(response) {
var answer = response.responseXML.documentElement.getAttribute("answer");
alert(answer);
}var ciCheck = Class.create();
ciCheck.prototype = Object.extendsObject(AbstractAjaxProcessor, {
getCiSupportGroup: function() {
var retVal = ''; // Return value
var ciID = this.getParameter('sysparm_ci');
var agID = this.getParameter('sysparm_ag');
var ciRec = new GlideRecord('cmdb_ci');
// If we can read the record, check if the sys_ids match
if (ciRec.get(ciID)) {
if (ciRec.getValue('support_group') == agID)
retVal = 'CI support group and assignment group match';
else
retVal = 'CI support group and assignment group do not match';
// Can't read the CI, then they don't match
} else {
retVal = 'CI support group and assignment group do not match';
}
return retVal;
}
});Use o parâmetro displayValue setValue() para campos de referência
Ao usar setValue() em um campo de referência, inclua o parâmetro displayValue para evitar chamadas de servidor adicionais.
Ao usar setValue() em um campo de referência, certifique-se de incluir o valor de exibição do campo de referência como o terceiro parâmetro. Se você definir o valor sem o displayValue, a instância fará uma chamada síncrona para recuperar o valor de exibição do registro especificado. Essa ida e volta extra para o servidor pode afetar o desempenho.
var id = '5137153cc611227c000bbd1bd8cd2005';
g_form.setValue('assigned_to', id); // Client needs to go back to the server to
// fetch the name that goes with this IDvar id = '5137153cc611227c000bbd1bd8cd2005';
var name = 'Fred Luddy';
g_form.setValue('assigned_to', id, name); // No server call requiredUsar política de IU em vez de um client script
Quando possível, considere o uso de uma política de IU em vez de um client script.
- As políticas de IU têm um campo Ordem para permitir controle total sobre a ordem na qual as operações do lado do cliente ocorrem.
- As políticas de IU não exigem script para tornar um campo obrigatório, somente leitura ou visível.
Validar entrada usando client scripts
Um excelente uso para client scripts é a validação da entrada do usuário.
Essa validação melhora a experiência do usuário porque o usuário descobre se há problemas de dados antes de enviar as informações.
if (g_form.getValue('impact') == '3' && g_form.getValue('priority') == '1')
g_form.showFieldMsg('impact', getMessage('Low impact now allowed with High priority'), 'error');
Definir ordem do client script
Controle a ordem de execução dos seus client scripts usando o campo Ordem. Para evitar que dois ou mais client scripts sejam executados simultaneamente e entrem em conflito, você pode adicionar uma ordem para os scripts serem executados em.
Antes de Iniciar
Por Que e Quando Desempenhar Esta Tarefa
Procedimento
Evitar manipulação de DOM
Evite a manipulação do modelo de objeto de documento (DOM), se possível. Isso pode causar um problema de manutenção quando os navegadores são atualizados.
Em vez disso, use a API GlideForm ou considere uma abordagem diferente para a solução. Em geral, ao usar métodos de manipulação de DOM, você precisa fazer referência a um elemento no DOM por ID ou usando um seletor de CSS. Ao fazer referência a elementos DOM prontos para uso, há um risco de que o ID do elemento ou o posicionamento no DOM seja alterado, fazendo com que o código pare de funcionar e/ou gere erros. Use premeditação, cuidado e tenha uma compreensão total do risco que está incorrendo. Revise esses objetos e reduza o uso de métodos de manipulação de DOM o máximo possível.
Evite Client scripts globais
Um client script global é qualquer client script em que a tabela selecionada é global. Os client scripts globais não têm restrições de tabela, portanto, eles serão carregados em todas as páginas do sistema, introduzindo um atraso de carregamento do navegador no processo.
Não há nenhum benefício em carregar esse tipo de script em todas as páginas.
Como alternativa, e para uma abordagem mais modular e escalonável, considere mover os scripts do cliente para uma tabela base (como Tarefa [tarefa] ou Item de configuração [cmdb_ci]) que pode ser derivada de todas as tabelas secundárias/de extensão. Isso elimina o carregamento do sistema dos scripts em todos os formulários na IU, como páginas iniciais ou Catálogo de serviços, onde eles raramente (ou nunca) são necessários.
Incluir código em funções
Coloque o código em um client script dentro de uma função.
Client scripts sem uma função causam problemas com escopo de variável. Quando o código não está incluído em uma função, as variáveis e outros objetos ficam disponíveis e são compartilhados com todos os outros scripts do lado do cliente. Se você estiver usando os mesmos nomes de variáveis, é possível que eles colidam. Isso pode levar a consequências inesperadas que são difíceis de solucionar.
var state = "6";
function onSubmit() {
if(g_form.getValue('incident_state') == state) {
alert("This incident is Resolved");
}
}function onSubmit() {
var state = "6";
if(g_form.getValue('incident_state') == state) {
alert("This incident is Resolved");
}
}Esta solução é muito mais segura porque o escopo do estado da variável é limitado à função onSubmit(). Portanto, a variável de estado não entra em conflito com variáveis de estado em outros scripts do lado do cliente.
Executar somente scripts necessários
Para evitar a execução desnecessária de scripts demorados, certifique-se de que os scripts do cliente executem somente as tarefas necessárias.
Os exemplos a seguir demonstram melhorias na amostra de código inicial. Cada exemplo demonstra um aprimoramento específico do script para melhorar o desempenho e evitar chamadas desnecessárias.
Lembre-se de que os client scripts não têm um campo de Condição. Isso significa que os scripts onLoad() e onChange() são executados integralmente sempre que o formulário apropriado é carregado. Este exemplo é um client script onChange() ineficiente definido para ser executado quando o campo Item de configuração for alterado.
//Set Assignment Group to CI's support group if assignment group is empty
function onChange(control, oldValue, newValue, isLoading) {
var ciSupportGroup = g_form.getReference('cmdb_ci').support_group;
if (ciSupportGroup != '' && g_form.getValue('assignment_group) != '')
g_form.setValue('assignment_group', ciRec.support_group.sys_id);
}
Este exemplo aprimora o primeiro, substituindo a pesquisa getReference() ou GlideRecord por uma chamada assíncrona GlideAjax.
//Set Assignment Group to support group if assignment group is empty
function onChange(control, oldValue, newValue, isLoading) {
var ga = new GlideAjax('ciCheck');
ga.addParam('sysparm_name', 'getSupportGroup');
ga.addParam('sysparm_ci', g_form.getValue('cmdb_ci'));
ga.getXML(setAssignmentGroup);
}
function setAssignmentGroup(response) {
var answer = response.responseXML.documentElement.getAttribute("answer");
g_form.setValue('assignment_group', answer);
}
O sinalizador isLoading é a maneira mais simples de impedir que códigos desnecessários ocupem o tempo do navegador em scripts onChange. O sinalizador isLoading deve ser usado no início de qualquer script que não precise ser executado quando o formulário estiver sendo carregado. Não há necessidade de executar este script em um carregamento de formulário porque a lógica já teria sido executada quando o campo foi alterado pela última vez. Adicionar a verificação isLoading ao script impede que ele faça uma pesquisa cmdb_ci em cada carregamento de formulário.
O sinalizador isTemplate indica que um modelo está sendo carregado.
//Set Assignment Group to CI's support group if assignment group is empty
function onChange(control, oldValue, newValue, isLoading, isTemplate) {
if (isLoading)
return;
var ga = new GlideAjax('ciCheck');
ga.addParam('sysparm_name', 'getSupportGroup');
ga.addParam('sysparm_ci', g_form.getValue('cmdb_ci'));
ga.getXML(setAssignmentGroup);
}
function setAssignmentGroup(response) {
var answer = response.responseXML.documentElement.getAttribute("answer");
g_form.setValue('assignment_group', answer);
}
function onChange(control, oldValue, newValue, isLoading, isTemplate) {
if (isLoading) {}; // run during loading
// rest of script here
}//Set Assignment Group to CI's support group if assignment group is empty
function onChange(control, oldValue, newValue, isLoading, isTemplate) {
if (isLoading)
return;
if (newValue) {
var ga = new GlideAjax('ciCheck');
ga.addParam('sysparm_name', 'getSupportGroup');
ga.addParam('sysparm_ci', g_form.getValue('cmdb_ci'));
ga.getXML(setAssignmentGroup);
}
}
function setAssignmentGroup(response) {
var answer = response.responseXML.documentElement.getAttribute("answer");
g_form.setValue('assignment_group', answer);
}//Set Assignment Group to CI's support group if assignment group is empty
function onChange(control, oldValue, newValue, isLoading, isTemplate) {
if (isLoading)
return;
if (newValue) {
if (newValue != oldValue) {
var ga = new GlideAjax('ciCheck');
ga.addParam('sysparm_name', 'getSupportGroup');
ga.addParam('sysparm_ci', g_form.getValue('cmdb_ci'));
ga.getXML(setAssignmentGroup);
}
}
}
function setAssignmentGroup(response) {
var answer = response.responseXML.documentElement.getAttribute("answer");
g_form.setValue('assignment_group', answer);
}//Set Assignment Group to CI's support group if assignment group is empty
function onChange(control, oldValue, newValue, isLoading, isTemplate) {
if (isLoading)
return;
if (newValue) {
if (newValue != oldValue) {
if (g_form.getValue('assignment_group') == '') {
var ga = new GlideAjax('ciCheck');
ga.addParam('sysparm_name', 'getSupportGroup');
ga.addParam('sysparm_ci', g_form.getValue('cmdb_ci'));
ga.getXML(setAssignmentGroup);
}
}
}
}
function setAssignmentGroup(response) {
var answer = response.responseXML.documentElement.getAttribute("answer");
g_form.setValue('assignment_group', answer);
}