| ♥ 0 | Tenho uma integração com o módulo de produção em que podem ser efectuados consumos de componentes previstos de uma OF.
Funciona tudo sem problemas, crio o documento SOF respectivo, com as devidas quantidades a consumir, e visto esse consumo não se reflectir automaticamente na OF, actualizo o valor de QtConsumida no respectivo componente na OF, que foi previamente criada com uma alternativa de uma ficha técnica do artigo. Até aqui tudo normal, e já está a funcionar assim desde a V9 sem problemas (há mais de 2 anos).
O que acontece agora muito esporadicamente na V10, e aparentemente sem nenhum padrão que eu tenha conseguido identificar, é lançada uma mensagem de erro ao chamar o método Actualiza das OrdensFabrico (PriEngine.BSO.Producao.OrdensFabrico.Actualiza(OFDestino) ) depois de actualizar a quantidade consumida de um componente com a seguinte mensagem: “A quantidade da ordem de fabrico não corresponde à soma das quantidades por artigo.”
Agradecia imenso se alguém me conseguisse explicar em que casos essa mensagem pode ser lançada.
Por exemplo, tenho um caso que ando a tentar descobrir em que o componente, que imaginemos tem o código CPX, já foi várias vezes consumido em OFs anteriores sem problemas nenhuns, tanto com a quantidade consumida igual à prevista, como superior e até inferior. Sempre com validação de stock existente em armazém, localização e lote seleccionados, pois se não houver stock nem deixa efectuar o consumo, portanto não será por uma questão de stock. E tendo já sido comprovado que o consumo pode ser superior ou inferior ao previsto (que faz todo o sentido), a mensagem de erro lançada ainda acaba por fazer menos sentido.
Imaginemos o seguinte cenário:
Exemplo de pseudocódigo (a OF, respectiva operação e operador já estão definidos ao chegar aqui): private void ProcessConsumption(GprBEOrdemFabrico OFDestino, GprBEOFOperacao OFOperacaoDestino, int operatorID)
{
try
{
// dados fictícios apenas para demonstração, pois já são seleccionados anteriormente com as devidas validações
// (existência em stock, lote, armazém, localização, se componente está previsto, etc...)
string componentCode = "CPX";
string warehouse = "A1";
string location = "Loc1";
string batch = "LT01";
double totQtToConsume = 1.1466;
int moComponentID = 9999; // devido à possibilidade de nos componentes poder existir várias vezes o mesmo código, é necessário garantir qual a linha através do ID
// criar documento interno de saída para ordem de fabrico
IntBEDocumentoInterno doc = new IntBEDocumentoInterno
{
Tipodoc = "SOF",
IdOrdemFabrico = OFDestino.IDOrdemFabrico,
IDOperadorGPR = operatorID
};
PriEngine.BSO.Internos.Documentos.PreencheDadosRelacionados(doc);
doc.DataVencimento = doc.Data;
PriEngine.BSO.Internos.Documentos.AdicionaLinha(doc, componentCode, warehouse, location, batch, Quantidade: totQtToConsume);
doc.Linhas.GetEdita(doc.Linhas.NumItens).IdLinhaOrdemFabrico = moComponentID; // relacionar linha do componente com linha do doc interno
// obter componente da ordem de fabrico para actualizar qt. consumida
GprBEOFComponente componente = OFOperacaoDestino.Componentes.FirstOrDefault(x => x.Componente == componentCode && x.IDOrdemFabricoComponente == moComponentID);
componente.QtConsumida += totQtToConsume; // adicionar quantidade a consumir neste processo, pois pode já ter alguma consumida
// efectuar gravações em transacção
PriEngine.BSO.IniciaTransaccao();
PriEngine.BSO.Producao.OrdensFabrico.Actualiza(OFDestino); // erro é lançado aqui, sem aparente padrão. e muito esporadicamente (média de uma vez por mês, ou menos ainda)
PriEngine.BSO.Internos.Documentos.Actualiza(doc);
PriEngine.BSO.TerminaTransaccao();
}
catch (Exception ex)
{
PriEngine.BSO.DesfazTransaccao();
// tratamento de mensagem de erro ao utilizador...
}
}Detalhes da mensagem de erro num caso real: STACK_TRACE: em GprBS100.GprBSOrdensFabrico.Actualiza(GprBEOrdemFabrico objBE, String strAvisos)
Muito agradecido desde já pela possível ajuda. Marcado como spam |
| Resposta privada Essa mensagem é apresentada quando a quantidade indicada no objeto da Ordem de Fabrico (QtOrdemFabrico) é diferente da soma das quantidades de todos os artigos a produzir (soma do campo QtOF do objeto OrdemFabricoArtigo). Por exemplo: vamos fabricar as dimensões "Azul" e "Branco" do artigo "A". Indicamos que vamos produzir 5 unidades de cada dimensão. Se no momento da gravação indicarmos um valor diferente de 10 no campo "QtOrdemFabrico" do objeto da Ordem de Fabrico, será apresentado o erro. Caso o artigo não tenha dimensões as quantidades são validadas da mesma forma. Marcado como spam Comentários Extremamente agradecido pela resposta. Pelo menos já me levou a chegar a algum lado.
Agora levantou-se outra questão. As OFs são totalmente criadas por integração, atribuindo o código do Artigo e a quantidade a produzir, e depois carregando a ficha técnica do mesmo com o método BSO.Producao.OrdensFabrico.SugereOperacoes, onde passo novamente o artigo, a mesma quantidade e a alternativa. Em nenhum sítio indico outro artigo a produzir, no entanto, e baseado na sua resposta em que muito me ajudou, verifiquei que no caso específico que estou a analisar, realmente na tabela GPR_OrdemFabricoArtigos, existem 2 artigos atribuídos à OF. A mensagem vem exactamente por causa disso. Na OF a Qt a produzir é de 42, mas depois na OrdemFabricoArtigos existem 2 artigos, os 2 com a quantidade 42. Ou seja, segundo a sua informação, na OF deveria estar 84, e assim já não lançaria a mensagem.
Até aí penso estar percebido, finalmente. A questão é, como foi o segundo artigo aparecer ali? Se em momento nenhum é atribuído, apenas é carregada a ficha técnica do primeiro artigo, e a própria também não tem referência nenhuma ao segundo, nem em componentes nem nada.
Poderá existir algum bug nos motores que causem esse problema? É que é muito esporádico e aleatório, e como referenciei na questão inicial, esse mesmo artigo já foi produzido antes em outra OFs, e neste momento até em OFs posteriores a essa, sempre usando o mesmo método, o mesmo código, e não teve problemas nenhums. A informação que fornece é escassa para poder responder a essa questão. No entanto, aqui fica um exemplo de código que funciona sem problemas: //Criar uma nova OF.
GprBEOrdemFabrico objOF = new GprBEOrdemFabrico(); objOF.OrdemFabrico = "2000017.00";
objOF.Artigo = "PA1";
objOF.Alternativa = "01";
objOF.QtOrdemFabrico = 10;
objOF.DataOrdemFabrico = DateTime.Now;
objOF.DataFimPrevista = objOF.DataOrdemFabrico.AddDays(2);
objOF.DataIniPrevista = objOF.DataOrdemFabrico.AddDays(1);
objOF.DataEntrega = objOF.DataOrdemFabrico.AddDays(3); //Criar artigo da OF
GprBEOFArtigo objOFArtigo = new GprBEOFArtigo(); objOFArtigo.EstadoRegisto = StdBE100.StdBETipos.EnumEstadoRegisto.erInserido;
objOFArtigo.ID = Guid.NewGuid().ToString();
objOFArtigo.Artigo = objOF.Artigo;
objOFArtigo.QtOF = objOF.QtOrdemFabrico; //Inserir artigo na OF
objOF.Artigos.Insere(objOFArtigo); BSO.Producao.OrdensFabrico.SugereOperacoes(ref objOF, "PA1", "01", 10, objOF.DataOrdemFabrico,
GprBEOrdemFabrico.EnumGPRTipoSugereOperacoes.DataInicio, false);
BSO.Producao.OrdensFabrico.Actualiza(objOF); |