-
Posts
843 -
Joined
-
Last visited
-
Days Won
77
Posts posted by Jorge Andrade
-
-
galera.. preciso urgente de um xml com a tag cBenef
nao estou conseguindo validar isso
skype: wfinan
email: vitor.reis@terra.com.br
whats. (11) 9-7414-4341
Em SP ainda não tem,
-
Aê galera! Tô gostando de ver as manifestações de vcs. Vamos esperar o levantamento das informações pelo Mário Guará do grupo Windev e também do nosso amigo Marcelo (Marca), por ser da região dele, o contato direto com os pais será mais fácil e também com os clientes, que é extremamente necessário pra certificar que eles não estarão desamparados, e haverá continuidade no sistema.
Acredito que após essas confirmações e até por ideia de um colega aqui do grupo, alguém assumir de vez e ter participação nos recebimentos, desde de que não prejudique e comprometa demais os ganhos das outras partes (Pais e esposa e filho).
Agradeço as boas intenções de todos.
[]s,
-
O ideal seria algum assumir os clientes, negociando com a familia... De graça, por mais boa vontade que a pessoa tem, ela vai ajudar por um tempo, o sistema vai ficar meia boca e logo o cliente troca e todos perdem.
Seria importante alguem da região que tem empresa negociar com a familia essa situação, remunerar a familia em uma espécie de royalties pelo sistema e atender os clientes resolvendo os problemas e fazendo melhorias.
É apenas minha sugestão e até repetindo o que já foi dito por vc tb Jorge.
Aqui em minha região aconteceu algo parecido a um tempo atrás. O cara que me ensinou a programar faleceu e eu ajudei a esposa dele a atender os clientes inicialmente, no meu caso foi sem remuneração pois já era amigo da familia. Mas como falei, ela conseguiu atender por um tempo pois melhorias não eram feitas, apenas resolvia os problemas conforme iam acontecendo. Eu a ajudei na parte de clipper e um outro rapaz na parte do VFP pois ele tinha sistema em ambas as linguagens na época.
Toda sugestão é bem vinda. O Marcelo deverá contatar o Mário e a família e assim, achar uma solução que atenda bem a família e a quem vai ajudar.
[]s,
-
Que situação terrivel... Ninguem gosta de pensar nisso mas é importante que todos tenham um seguro de vida para pelo menos dar um respeito financeiro a familia em um momento como esse. Não podemos partir e deixar nossa familia desestruturada.
Portanto fica a dica, um seguro de vida que não é nada caro e que pelo menos em um momento dificil como a morte não vai deixar a familia desamparada logo de cara.
Sou do interior de SP, não sei como poderia ajudar mas se tiver algo me chamem no skype live:eduardo_107
Que Deus conforte a familia
Edú como frisei, se a gente ajudar de alguma forma tecnicamente, e tentar manter os sistemas dele funcionando, acredito que será uma grande ajuda.
-
Jorge. Sou de Petrópolis, região serrana do Rio. Eu tenho o celular do Alexandre e tentei contato algumas vezes sem sucesso.
Me disponho a ajudar nesta parte técnica sendo que não tenho nenhum contato com a família. Se quiser me chame no Skype marcelomarca pra ver se conseguimos de alguma maneira ajudar
Amigo, já te adicionei no skype e aqueles que quiserem participar de alguma forma é só me incluir fnlinf ou fnlinf@hotmail.com.
[]s,
-
Dá um retorno aí amigo se deu certo e o caminho das pedras.
-
Pessoal
Boa noite
Como vcs sabem, muitos trabalham sozinho e as vezes nem a família tem acesso aos nossos códigos para alguém não dar continuidade ao pequeno legado que deixamos. Não foi diferente para o nosso amigo Alexandre e as vezes a família depende exclusivamente ou boa parte dos recursos oriundos no nosso trabalho.
Essa semana no grupo de Windev, tivemos uma notícia que a esposa dele está passando por necessidades e com isso já pensaram em fazer uma força tarefa para ajudar financeiramente.
Após o seu falecimento, tentei contato com os pais dele e com a sua esposa sem sucesso, porém, essa semana consegui falar com eles e estes me passaram uma situação complicada, embora sem entrar no âmbito familiar, este me informou que um colega nosso (Mário Guará) do grupo de Windev entrou em contato, esteve na casa deles, onde ele teve acesso as informações relativas aos projetos Windev.
Conversei com o Mário que me relatou a situação. Além da dificuldades em contatar os clientes para que ele dê continuidade aos projetos e os pais e a esposa recebam as mensalidades, porém o Mário não tem conhecimento de Fivewin e para tal, irá necessitar da ajuda dos colegas que estiverem interessados em contribuir tecnicamente.
Seria interessante se algum colega do grupo que mora no RJ, de preferência em Nova Iguaçu (Onde ele residia), para facilitar contatos ou visitas aos clientes, afim de dar esta força para a família.
Vejam que não estou pedindo para ajudar financeiramente e sim dispor da capacidade técnica profissional em ajudar nos projetos relativos a Fivewin. Aqueles que tiverem tempo e desejarem ajudar, manifestem-se
[]s,
-
-
Olá,
Alguem sabe como no Terminal server nao aparecer a tela desktop do servidor windows server?
estou precisando que ao fazer o logon no windows server com o TS,
ele abra o sistema, e nao mostre a tela desktop do servidor,
e após sair do sistema ele feche o terminal server,
ou seja o TS vai ser so para acessar o sistema.
Desde já agradeço a quem puder me ajudar
Narlem
BH/MG
Se entendi, vc loga o TS, mas a tela da área de trabalho não aparece, bom, isso deve ser pq, na última sessão ficou alguma pendência, mas vc pode começar do zero. Independente se vc utilizar Calls para acesso ou somente os dois acessos padrão. Na sua cpu no (Regedit) registro existe um carinha de nome MSLICENSING, neste registro existe um contador de acesso, e tem duas pastas HARDWAREID e STORE. Delete as duas pastas na sua cpu e tente conectar novamente, que o contador irá iniciar do zero, isso pode liberar a pendência.
[]s,
-
Boa tarde pessoal
Estou com um problema com o update no postgresql, ocorreram poucas vezes este ano, mas causa um grande estrago.
o cliente altera um cadastro e no momento de salvar o postgresql salva todos os registros da tabela com o mesmo dado
eu estou usando o postgre 9.5 com sqlrdd, e costumo usar assim:
clSql := UPDATE "sup0007" SET ;
CodEmp = ::avCarrega[1]:cCodEmp ,;
NomEmp = ::avCarrega[1]:cNomEmp ,;
FanEmp = ::avCarrega[1]:cFanEmp ,;
EndEmp = ::avCarrega[1]:cEndEmp ,;
RedEmp = ::avCarrega[1]:cRedEmp ,;
NumCep = ::avCarrega[1]:cNumCep ,;
Bairro = ::avCarrega[1]:cBairro ,;
TelEmp = ::avCarrega[1]:cTelEmp ,;
TelEm2 = ::avCarrega[1]:cTelEm2 ,;
Ativar = clAtivar ,;
UltUsu = oCarVar:cUser ,;
UltMod = date() ,;
Operad = oCarVar:cUser ,;
Updated= date() ;
WHERE sr_recno = ?alParam := {::avCarrega[1]:SR_RECNO}
SR_BeginTransaction()
Try
oSql := SR_GetConnection()
apCode := SR_SQLParse( clSql, @nErr, @nPos )
cResu := SR_SQLCodeGen( apCode, alParam, oSql:nSystemID )
nErr := oSql:Exec( cResu )este é um exemplo usando a sqlrdd pra converter o codigo, mas tenho outro caso que uso o comando direto no oSql:Exec sem passar pelo sr_sqlcodegen e também deu o problema.
este comando acima, gera o comando abaixo para o postgre
UPDATE
"sup0007"
SET
"codemp" = E'3000286',
"nomemp" = E'CONTE COMIGO',
"fanemp" = E'CONTE',
"endemp" = E'RUA BEABA,98',
"redemp" = ' ',
"numcep" = E'89837-000',
"bairro" = E'CENTRO',
"telemp" = E'3999999',
"telem2" = E'89999427',
"ativar" = E'FF',
"ultusu" = E'AUGUSTO',
"ultmod" = E'2019-10-01',
"operad" = E'AUGUSTO',
"updated" = E'2019-10-01' WHERE "sr_recno" = 1595Não vejo erro no comando, isto ocorre muitas vezes em todo meu sistema, mas este erro ocorreu poucas vezes.
Alguém tem ideia do que pode ser? Algo na Tabela, no banco, etc.
Puts, sem erro fica dificil, mas substitui todos os dados ou cria vários registros iguais?
-
Giba, tem uma nota técnica que diz que este registro é dispensando, mas qqr forma, a UF tem que informar o código, vc já tem o código divulgado pela UF?
[]s,
-
As Dlls, estão disponíveis para clientes Sac. Para ser cliente Sac, basta se cadastrar no ACBR, pagar uma mensalidade (R$120,00) e vc poderá baixar tudo o que existe nas áreas de downloads disponíveis para usuários Sac, mas não é obrigado a pagar todos os meses, somente quando vc precisar e querer atualizar, diferentemente de outros que tem que pagar mensalmente e por CNPJ.
Nada contra, mas sempre preferi ser de certa forma independente e isso não significa que daqui há alguns anos o ACBR não passe a ser taxado também.
[]s,
-
ola a todos
alguem ja criou o registro E115 do Sped Fiscal e Pis/Cofins, q poderia postar em demo, por favor ?
desde ja agradeco a ajuda: MUITO OBRIGADO !!!
Gilberto
Giba, este registro é mesmo do contribuições? Qual data e versão do layout?
Ah! Agora entendi, registro E115 do IPI/ICMS.
Esse abaixo:
1) Introdução ao Registro E115:
Veremos neste capítulo do Guia Prático o layout do Registro E115 do Sped-Fiscal, que tem o objetivo de informar os valores declaratórios relativos ao ICMS, conforme definição da legislação Estadual pertinente.
Base Legal: Guia Prático da Escrituração Fiscal Digital - EFD-ICMS/IPI da Receita Federal do Brasil (Checado pela Valor Consulting em 19/01/16).
2) Layout:
Este Registro tem o objetivo de informar os valores declaratórios relativos ao ICMS, conforme definição da legislação Estadual pertinente. Esses valores são meramente declaratórios e não são computados na apuração do ICMS.
Nº Campo Descrição Tipo Tam. Dec. Obrig. 01 REG Texto fixo contendo "E115". C 004 - O 02 COD_INF_ADIC Código da informação adicional conforme Tabela a ser definida pelas Secretarias da Fazenda (Sefaz). C 008* - O 03 VL_INF_ADIC Valor referente à informação adicional. N - 02 O 04 DESCR_COMPL_AJ Descrição complementar do ajuste. C - - OC Observações:
- Nível hierárquico: 4;
- Ocorrência: 1:N;
- Coluna Entrada e/ou Saída: O "O" significa que o campo deve ser sempre preenchido (ou apresentado). Já o "OC" significa que o campo deve ser preenchido (ou apresentado) sempre que houver a informação a ser apresentada. Por fim, o "N" significa que o registro não pode ser preenchido (ou apresentado).
Base Legal: Guia Prático da Escrituração Fiscal Digital - EFD-ICMS/IPI da Receita Federal do Brasil.
2.1) Observações sobre o preenchimento:
* Campo 01 (REG): Valor Válido: [E115].
* Campo 02 (COD_INF_ADIC): Preenchimento: o código da informação adicional deve obedecer à Tabela definida pelas Sefazs dos Estados. Caso não haja publicação da referida Tabela, o Registro não deve ser apresentado.
Base Legal: Guia Prático da Escrituração Fiscal Digital - EFD-ICMS/IPI da Receita Federal do Brasil.
2.2) Alterações do layout:
Até a última atualização desta publicação no Portal Valor Consulting, foram processadas as seguintes alterações no layout do Registro E115 da EFD-ICMS/IPI (Sped-Fiscal), conforme Guia Prático EFD-ICMS/IPI publicado no Portal do Sistema Público de Escrituração Digital (Sped). É a Equipe Valor Consulting trazendo o que há de melhor para vocês, nossos estimados leitores.
Precisou de assessoria e/ou consultoria em EFD-ICMS/IPI, entre em contato com nossa equipe comercial através do nosso Fale Conosco. Faça como outras empresas e profissionais, seja um cliente de valor você também!
Versão Vigente a partir de Alteração Nº Data 2.0.10 06/2012 01/10/2012 Dispensa de preenchimento dos campos PIS e Cofins em toda a EFD-ICMS/IPI. 2.0.11 09/2012 10/10/2012 Os contribuintes que entregarem a EFD-Contribuições relativa ao mesmo período de apuração do registro 0000 estão dispensados do preenchimento dos campos referentes às contribuições para PIS/COFINS. 2.0.11 09/2012 10/10/2012 Inclusão da obrigatoriedade dos registros por perfis. Base Legal: Equipe Valor Consulting.
Informações Adicionais:Este material foi escrito no dia 05/12/2013 pela Equipe Técnica da Valor Consulting e está atualizado até a legislação vigente em 09/07/2019 (data da sua última atualização), sujeitando-se, portanto, às mudanças em decorrência das alterações legais.
Não é permitido a utilização dos materiais publicados pela Valor Consulting para fins comerciais, pois os mesmos estão protegidos por direitos autorais. Também não é permitido copiar os artigos, materias e arquivos do Portal Valor Consulting para outro site, sistema ou banco de dados para fins de divulgação em sites, revistas, jornais, etc de terceiros sem a autorização escrita dos proprietários do Portal Valor Consulting.
A utilização para fins exclusivamente educacionais é permitida desde que indicada a fonte:
- Valor Consulting. Registro E115 do Sped-Fiscal - Informações adicionais da Apuração - Valores declaratórios. Disponível em: https://www.valor.srv.br/guias/guiasIndex.php?idGuia=140. Acesso em: 18/09/2019.
[]s,
-
Ah! Pensei que vc gerava e tinha todo controle e não do banco, que por sinal não ia deixar de ganhar, pq ele ganha na baixa e na próxima liquidação do novo boleto., embora, se for realmente um novo boleto com outro vencimento, o banco está certo, pq mesmo que vc faça a prorrogação, é feita a baixa e uma nova emissão de boleto.
[]s,
-
Boa tarde, Pessoal
Tenho um cliente que gera o boleto do Itau pelo meu sistema e no final do dia mando a remessa para registro
Tudo funcionando perfeitamente
Agora o cliente quer fazer a 2 via do boleto pelo sistema
Eu percebi que quando vc gera a 2 via pelo site do itau ele gera outro boleto com outra Numeração
Alguem poderia me dar alguma dica de como gerar essa 2 via pelo sistema e se tambem tenho que registrar 2 via do boleto.
Edú, bom dia
Eu não entendi? Vc não emite o boleto pelo seu sistema? E pq ele não não mantêm o mesmo número?
[]s,
-
o erro acima remova o DEBUGGER.PRG da compilacao
Deu certo amigo?
-
Jorge eh que não entendi essa frase. por isso perguntei:
O ACBr lançará oficialmente amanhã uma biblioteca que pode ser agregada ao sistema sem a necessidade do uso do monitor. Acredito que, com ela, será possível o próprio sistema configurar as pastas dos arquivos e certificado digital que será utilizado por cada empresa sem a necessidade de se instalar vários monitores ACBrs.
e continuo sem entender
Te explico amigo. A partir do momento que vc passar a usar as DLL's, não será mais necessário vc ativar o monitor, pq ficará por sua conta enviar os comandos para a dll, então em tempo de execução ou dinamicamente vc invoca/carrega/load na dll e envia os comandos conforme a sua necessidade, como se estivesse enviando para o monitor e ela fizesse parte do seu sistema.
Os exemplos acima da dll sat, o Rafael Dias (Acbr) criou um classe em Harbour/Xharbour para facilitar o uso da dll, eu deixei uns exemplos acima de envio de comandos e ele fez um exemplo de geração e envio de uma venda sat, como se estivesse gerando um arquivo INI para o monitor.
Se quiser mais informações me chame no skype: fnlinf
-
-
Oscar, é a mesma que eu postei aqui, embora postei a classe criada pelo Rafael Dias, embora, o exemplo é para quem usa o INI.
[]s,
-
Classe do Sat:
#include "hbclass.ch"
#include "error.ch"#define DC_CALL_CDECL 0x0010 // __cdecl
#define DC_CALL_STD 0x0020 // __stdcall#ifdef __XHARBOUR__
#define ACBrLIBSat "ACBrSAT32.dll"
#define DLL_OSAPI DC_CALL_STD
#else
#ifdef __PLATFORM__WINDOWS ///#if defined( __PLATFORM__WINDOWS )
#define ACBrLIBSat "ACBrSAT32.dll"
#define DLL_OSAPI DC_CALL_STD
#else
#define ACBrLIBSat "ACBrSAT32.dll"A classe da Nfe ainda não tenho.
#define DLL_OSAPI DC_CALL_STD
#endif
#endif#define STR_LEN 256
CREATE CLASS ACBrSat
HIDDEN:
VAR hHandleMETHOD CheckResult(hResult)
METHOD ProcessResult(buffer, bufferLen)VISIBLE:
METHOD New() CONSTRUCTOR
METHOD New(eArqConfig, eChaveCrypt) CONSTRUCTOR
DESTRUCTOR DestroyMETHOD Nome
METHOD VersaoMETHOD ConfigLer(eArqConfig)
METHOD ConfigGravar(eArqConfig)
METHOD ConfigLerValor(eSessao, eChave)
METHOD ConfigGravarValor(eSessao, eChave, eValor)METHOD Inicializar
METHOD DesInicializarMETHOD AssociarAssinatura(CNPJvalue, assinaturaCNPJs)
METHOD BloquearSAT()
METHOD DesbloquearSAT()
METHOD TrocarCodigoDeAtivacao(codigoDeAtivacaoOuEmergencia, opcao, novoCodigo)
METHOD ConsultarSAT()
METHOD ConsultarStatusOperacional()
METHOD ConsultarNumeroSessao(cNumeroDeSessao)
METHOD AtualizarSoftwareSAT()
METHOD ComunicarCertificadoICPBRASIL(certificado)
METHOD ExtrairLogs(eArquivo)
METHOD TesteFimAFim(eArquivoXmlVenda)
METHOD GerarAssinaturaSAT(eCNPJSHW, eCNPJEmitente)METHOD CriarCFe(eArquivoIni)
METHOD CriarEnviarCFe(eArquivoIni)
METHOD EnviarCFe(eArquivoXml)
METHOD CancelarCFe(eArquivoXml)METHOD ImprimirExtratoVenda(eArqXMLVenda, eNomeImpressora)
METHOD ImprimirExtratoResumido(eArqXMLVenda, eNomeImpressora)
METHOD ImprimirExtratoCancelamento(eArqXMLVenda, eArqXMLCancelamento, eNomeImpressora)
METHOD GerarImpressaoFiscalMFe(eArqXMLVenda)
METHOD GerarPDFExtratoVenda(eArqXMLVenda, eNomeArquivo)
METHOD GerarPDFCancelamento(eArqXMLVenda, eArqXMLCancelamento, eNomeArquivo)
METHOD EnviarEmail(eArqXMLVenda, sPara, sAssunto, eNomeArquivo, sMensagem, sCC, eAnexos)
END CLASSMETHOD New(eArqConfig, eChaveCrypt) CLASS ACBrSat
local hResult, buffer, bufferLen, oErr::hHandle := DllLoad(ACBrLIBSat)
if ::hHandle = nil
oErr := ErrorNew()
oErr:Severity := ES_ERROR
oErr:Description := "Erro a carregar a dll [" + ACBrLIBSat + "]"
Throw(oErr)
endif
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_Inicializar", hb_StrToUTF8(eArqConfig), hb_StrToUTF8(eChaveCrypt))
::CheckResult(hResult)
RETURN SelfPROCEDURE Destroy CLASS ACBrSat
DllCall(::hHandle, DLL_OSAPI, "SAT_Finalizar")
DllUnload(::hHandle)
RETURNMETHOD CheckResult(hResult) CLASS ACBrSat
local buffer, bufferLen, oErr
if hResult >= 0
RETURN nil
endifbufferLen := STR_LEN
buffer := Space(bufferLen)DllCall(::hHandle, DLL_OSAPI, "SAT_UltimoRetorno", @buffer, @bufferLen)
if bufferLen > STR_LEN
buffer := Space(bufferLen)
DllCall(::hHandle, DLL_OSAPI, "SAT_UltimoRetorno", @buffer, @bufferLen)
endifoErr := ErrorNew()
oErr:Severity := ES_ERROR
oErr:Description := hb_UTF8ToStr(buffer)
Throw(oErr)
RETURN nilMETHOD ProcessResult(buffer, bufferLen) CLASS ACBrSat
if bufferLen > STR_LEN
buffer := Space(bufferLen)
DllCall(::hHandle, DLL_OSAPI, "SAT_UltimoRetorno", @buffer, @bufferLen)
endif
RETURN bufferMETHOD Nome CLASS ACBrSat
local hResult, buffer, bufferLen, ret
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_Nome", @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD Versao CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_Versao", @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD ConfigLer(eArqConfig) CLASS ACBrSat
local hResult
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_ConfigLer", hb_StrToUTF8(eArqConfig))
::CheckResult(hResult)
RETURN nilMETHOD ConfigGravar(eArqConfig) CLASS ACBrSat
local hResult
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_ConfigGravar", hb_StrToUTF8(eArqConfig))
::CheckResult(hResult)
RETURN nilMETHOD ConfigLerValor(eSessao, eChave) CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_ConfigLerValor", hb_StrToUTF8(eSessao), hb_StrToUTF8(eChave), @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD ConfigGravarValor(eSessao, eChave, eValor) CLASS ACBrSat
local hResult
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_ConfigGravarValor", hb_StrToUTF8(eSessao), hb_StrToUTF8(eChave), hb_StrToUTF8(eValor))
::CheckResult(hResult)
RETURN nilMETHOD Inicializar CLASS ACBrSat
local hResult
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_InicializarSAT")
::CheckResult(hResult)
RETURN nilMETHOD DesInicializar CLASS ACBrSat
local hResult
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_DesInicializar")
::CheckResult(hResult)
RETURN nilMETHOD AssociarAssinatura(CNPJvalue, assinaturaCNPJs) CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_AssociarAssinatura", hb_StrToUTF8(CNPJvalue), hb_StrToUTF8(assinaturaCNPJs), @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD BloquearSAT() CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_BloquearSAT", @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD DesbloquearSAT() CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_DesbloquearSAT", @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD TrocarCodigoDeAtivacao(codigoDeAtivacaoOuEmergencia, opcao, novoCodigo)
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_TrocarCodigoDeAtivacao", hb_StrToUTF8(codigoDeAtivacaoOuEmergencia), opcao, hb_StrToUTF8(novoCodigo), @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD ConsultarSAT() CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_ConsultarSAT", @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD ConsultarStatusOperacional() CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_ConsultarStatusOperacional", @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD ConsultarNumeroSessao(cNumeroDeSessao) CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_ConsultarNumeroSessao", cNumeroDeSessao, @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD AtualizarSoftwareSAT() CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_AtualizarSoftwareSAT", @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD ComunicarCertificadoICPBRASIL(certificado) CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_ComunicarCertificadoICPBRASIL", hb_StrToUTF8(certificado), @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD ExtrairLogs(eArquivo) CLASS ACBrSat
local hResult
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_ExtrairLogs", hb_StrToUTF8(eArquivo))
::CheckResult(hResult)
RETURN nilMETHOD TesteFimAFim(eArquivoXmlVenda) CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_TesteFimAFim", hb_StrToUTF8(eArquivoXmlVenda), @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD GerarAssinaturaSAT(eCNPJSHW, eCNPJEmitente) CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_GerarAssinaturaSAT", hb_StrToUTF8(eCNPJSHW), hb_StrToUTF8(eCNPJEmitente), @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD CriarCFe(eArquivoIni) CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_CriarCFe", hb_StrToUTF8(eArquivoIni), @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD CriarEnviarCFe(eArquivoIni) CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_CriarEnviarCFe", hb_StrToUTF8(eArquivoIni), @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD EnviarCFe(eArquivoXml) CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_EnviarCFe", hb_StrToUTF8(eArquivoXml), @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD CancelarCFe(eArquivoXml) CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_CancelarCFe", hb_StrToUTF8(eArquivoXml), @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD ImprimirExtratoVenda(eArqXMLVenda, eNomeImpressora) CLASS ACBrSat
local hResult
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_ImprimirExtratoVenda", hb_StrToUTF8(eArqXMLVenda), hb_StrToUTF8(eNomeImpressora))
::CheckResult(hResult)
RETURN nilMETHOD ImprimirExtratoResumido(eArqXMLVenda, eNomeImpressora) CLASS ACBrSat
local hResult
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_ImprimirExtratoResumido", hb_StrToUTF8(eArqXMLVenda), hb_StrToUTF8(eNomeImpressora))
::CheckResult(hResult)
RETURN nilMETHOD ImprimirExtratoCancelamento(eArqXMLVenda, eArqXMLCancelamento, eNomeImpressora) CLASS ACBrSat
local hResult
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_ImprimirExtratoCancelamento", hb_StrToUTF8(eArqXMLVenda), hb_StrToUTF8(eArqXMLCancelamento), hb_StrToUTF8(eNomeImpressora))
::CheckResult(hResult)
RETURN nilMETHOD GerarImpressaoFiscalMFe(eArqXMLVenda) CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_CancelarCFe", hb_StrToUTF8(eArqXMLVenda), @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD GerarPDFExtratoVenda(eArqXMLVenda, eNomeArquivo) CLASS ACBrSat
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_GerarPDFExtratoVenda", hb_StrToUTF8(eArqXMLVenda), hb_StrToUTF8(eNomeArquivo), @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD GerarPDFCancelamento(eArqXMLVenda, eArqXMLCancelamento, eNomeArquivo)
local hResult, buffer, bufferLen
bufferLen := STR_LEN
buffer := Space(bufferLen)
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_GerarPDFCancelamento", hb_StrToUTF8(eArqXMLVenda), hb_StrToUTF8(eArqXMLCancelamento), hb_StrToUTF8(eNomeArquivo), @buffer, @bufferLen)
::CheckResult(hResult)
RETURN ::ProcessResult(buffer, bufferLen)METHOD EnviarEmail(eArqXMLVenda, sPara, sAssunto, eNomeArquivo, sMensagem, sCC, eAnexos)
local hResult
hResult := DllCall(::hHandle, DLL_OSAPI, "SAT_EnviarEmail", hb_StrToUTF8(eArqXMLVenda), hb_StrToUTF8(sPara), hb_StrToUTF8(sAssunto), hb_StrToUTF8(eNomeArquivo), hb_StrToUTF8(sMensagem), hb_StrToUTF8(sCC), hb_StrToUTF8(eAnexos))
::CheckResult(hResult)
RETURN nilDemo para quem usar geração em TXT:
Function Main ()
local sat
local vendaRetorno, strIniVenda
local hIni, hIniVenda
LOCAL cSection
sat := ACBrSat():New("", "")
// Sessão Chave Valor
// Configurações de log da Lib
sat:ConfigGravarValor("Principal", "LogNivel", "4") // logParanoico
sat:ConfigGravarValor("Principal", "LogPath", hb_dirBase())//Configurações do Sat
sat:ConfigGravarValor("SAT", "Modelo", "1") // satDinamico_cdecl
sat:ConfigGravarValor("SAT", "NomeDLL", "C:\SAT\SAT.dll")
sat:ConfigGravarValor("SAT", "CodigoDeAtivacao", "sefaz1234")
sat:ConfigGravarValor("SAT", "SignAC", "111111111111122222222222222111111111111112222222222222211111111111111222222222222221111111111111122222222222222111111111111112222222222222211111111111111222222222222221111111111111122222222222222111111111111112222222222222211111111111111222222222222221111")
// Softhouse
sat:ConfigGravarValor("SATConfig", "infCFe_versaoDadosEnt", "0.07")
sat:ConfigGravarValor("SATConfig", "ide_CNPJ", "16716114000172")
sat:ConfigGravarValor("SATConfig", "ide_numeroCaixa", "0")// Emitente
sat:ConfigGravarValor("SATConfig", "emit_CNPJ", "14200166000166")
sat:ConfigGravarValor("SATConfig", "emit_IE", "111111111111")
sat:ConfigGravarValor("SATConfig", "emit_IM", "")
sat:ConfigGravarValor("SATConfig", "emit_cRegTrib", "0") // RTSimplesNacional
sat:ConfigGravarValor("SATConfig", "emit_cRegTribISSQN", "0") // RTISSMicroempresaMunicipal
sat:ConfigGravarValor("SATConfig", "emit_indRatISSQN", "0") // irSim// Extrato
sat:ConfigGravarValor("Extrato", "Tipo", "0") // teFortes
sat:ConfigGravarValor("Extrato", "MostraPreview", "1") // True// Salvando configurações
sat:ConfigGravar("")
?sat:Nome
?sat:Versao
sat:Inicializar()// Gerando ini venda
hIniVenda := Hash()
hIniVenda["infCFe"] := Hash()
hIniVenda["infCFe"]["versao"] := "0.07"hIniVenda["Destinatario"] := Hash()
hIniVenda["Destinatario"]["CNPJCPF"] := "05481336000137"
hIniVenda["Destinatario"]["xNome"] := "D.J. SYSTEM"hIniVenda["Entrega"] := Hash()
hIniVenda["Entrega"]["xLgr"] := "Rua Cel. Aureliano de Camargo"
hIniVenda["Entrega"]["nro"] := "973"
hIniVenda["Entrega"]["xCpl"] := ""
hIniVenda["Entrega"]["xBairro"] := "Centro"
hIniVenda["Entrega"]["xMun"] := "Tatui"
hIniVenda["Entrega"]["UF"] := "SP"hIniVenda["Produto001"] := Hash()
hIniVenda["Produto001"]["cProd"] := "1189"
hIniVenda["Produto001"]["infAdProd"] := "Teste de Produto"
hIniVenda["Produto001"]["cEAN"] := ""
hIniVenda["Produto001"]["xProd"] := "OVO VERMELHO"
hIniVenda["Produto001"]["NCM"] := "04072100"
hIniVenda["Produto001"]["CFOP"] := "5102"
hIniVenda["Produto001"]["uCom"] := "DZ"
hIniVenda["Produto001"]["Combustivel"] := "0"
hIniVenda["Produto001"]["qCom"] := "510"
hIniVenda["Produto001"]["vUnCom"] := "2,70"
hIniVenda["Produto001"]["indRegra"] := "A"
hIniVenda["Produto001"]["vDesc"] := "0"
hIniVenda["Produto001"]["vOutro"] := "0"
hIniVenda["Produto001"]["vItem12741"] := "137,00"hIniVenda["ObsFiscoDet001001"] := Hash()
hIniVenda["ObsFiscoDet001001"]["xCampoDet"] := "Teste"
hIniVenda["ObsFiscoDet001001"]["xTextoDet"] := "Texto Teste"hIniVenda["ICMS001"] := Hash()
hIniVenda["ICMS001"]["Origem"] := "0"
hIniVenda["ICMS001"]["CSOSN"] := "500"hIniVenda["PIS001"] := Hash()
hIniVenda["PIS001"]["CST"] := "01"hIniVenda["COFINS001"] := Hash()
hIniVenda["COFINS001"]["CST"] := "01"hIniVenda["Total"] := Hash()
hIniVenda["Total"]["vCFeLei12741"] := "137,00"hIniVenda["DescAcrEntr"] := Hash()
hIniVenda["DescAcrEntr"]["vDescSubtot"] := "7,00"hIniVenda["Pagto001"] := Hash()
hIniVenda["Pagto001"]["cMP"] := "01"
hIniVenda["Pagto001"]["vMP"] := "1400"hIniVenda["DadosAdicionais"] := Hash()
hIniVenda["DadosAdicionais"]["infCpl"] := "Teste emissao CFe/SAT"hIniVenda["ObsFisco001"] := Hash()
hIniVenda["ObsFisco001"]["xCampo"] := "ObsFisco 1"
hIniVenda["ObsFisco001"]["xTexto"] := "Teste ObsFisco 1"strIniVenda := hb_iniWriteStr(hIniVenda)
// Venda
?"Ini Venda"
?strIniVenda
?""
?"-------------------------------------------------------------------------------------------------------------"
?""
vendaRetorno := sat:CriarEnviarCFe(strIniVenda)
?vendaRetorno
?""
?"-------------------------------------------------------------------------------------------------------------"
?""
hIni := hb_iniReadStr(vendaRetorno)
cSection := hIni["ENVIO"]if cSection["CodigoDeRetorno"] != "6000"
?cSection["Resultado"]
else
?"Impressão Preview"
sat:ImprimirExtratoVenda(cSection["XML"], "")
?"Impressão PDF"
?sat:GerarPDFExtratoVenda(cSection["XML"], "")
end ifsat:DesInicializar()
sat := nil
return NILExemplos:
sat := ACBrSat():New("", "")
sat:ConfigGravarValor("Principal", "LogNivel", "4")
sat:ConfigGravarValor("SAT", "Modelo", "2")sat:ConfigGravarValor("SAT", "ArqLog", "C:\windows\temp\satlog")
sat:ConfigGravarValor("SAT", "NomeDLL", "C:\ACBrMonitorPLUS\SAT\elgin\dllsat.dll")
sat:ConfigGravarValor("SAT", "CodigoDeAtivacao", "123456789")
sat:ConfigGravarValor("SAT", "SignAC", "SGR-SAT SISTEMA DE GESTAO E RETAGUARDA DO SAT")
sat:ConfigGravarValor("SATConfig", "ide_numeroCaixa", "3") //ide_numeroCaixa Define o numero de caixa padrão da CFe.
sat:ConfigGravarValor("SATConfig", "ide_tpAmb", "0") //ide_tpAmb taProducao = 0 taHomologacao = 1
sat:ConfigGravarValor("SATConfig", "EhUTF8", "") //EhUTF8 Define se devemos utilizar codificação UTF8 ao se comunicar com o SAT.
sat:ConfigGravarValor("SATConfig", "infCFe_versaoDadosEnt", "0,07") //infCFe_versaoDadosEnt Define qual será a versão do CFe utilizada.Ex.: 0,07 ou 0,08
sat:ConfigGravarValor("SATConfig", "PaginaDeCodigo", "0") //PaginaDeCodigo Define a pagina de código que se deve utilizar ao se comunicar com o SAT.sat:ConfigGravarValor("SATConfigArquivos", "PastaCFeVenda", "X:\acbr\NFESAI\AUTORIZA\59") //PastaCFeVenda Define o caminho onde será salvos os arquivos de venda.
sat:ConfigGravarValor("SATConfigArquivos", "SalvarCFe","0" ) //SalvarCFe Define se será salvo o arquivo de venda.
sat:ConfigGravarValor("SATConfigArquivos", "SalvarCFeCanc", "0") //SalvarCFeCanc Define se será salvo o arquivo de cancelamento.
sat:ConfigGravarValor("SATConfigArquivos", "SalvarEnvio", "0") //SalvarEnvio Define se será salvo o arquivo de envio para o sat.//sat:ConfigGravarValor("SATConfigArquivos", "SepararPorCNPJ", "0") //SepararPorCNPJ Define se deverá separar os arquivos por CNPJ.
//sat:ConfigGravarValor("SATConfigArquivos", "SepararPorModelo", "0") //SepararPorModelo Define se deverá separar os arquivos por modelo.
//sat:ConfigGravarValor("SATConfigArquivos", "SepararPorAno", "0") //SepararPorAno Define se deverá separar os arquivos por ano.
//sat:ConfigGravarValor("SATConfigArquivos", "SepararPorMes", "0") //SepararPorMes Define se deverá separar os arquivos por mês.
//sat:ConfigGravarValor("SATConfigArquivos", "SepararPorDia", "0") //SepararPorDia Define se deverá separar os arquivos por dia.sat:ConfigGravarValor("SATConfig", "ide_CNPJ", "14200166000166") //ide_CNPJ Exemplo da elgin: 16716114000172 Define o padrão CNPJ do emitente da CFe.
sat:ConfigGravarValor("SATConfig", "emit_IE", "144842258111") //emit_IE Define o IE padrão do emitente do CFe.
//sat:ConfigGravarValor("SATConfig", "emit_IM", "inscricao municipal do emitente") //emit_IM Define o IM padrão do emitente do CFe.
sat:ConfigGravarValor("SATConfig", "emit_cRegTrib","0") //emit_cRegTrib RTSimplesNacional = 0 RTRegimeNormal = 1
sat:ConfigGravarValor("SATConfig", "emit_cRegTribISSQN", "6") //emit_cRegTribISSQN RTISS MicroempresaMunicipal = 0
sat:ConfigGravarValor("SATConfig", "emit_indRatISSQN", "0") //emit_indRatISSQN Define indicador de rateio do desconto sobre subtotal entre itens sujeitos asat:ConfigGravarValor("SATConfig", "emit_CNPJ", "16716114000172") //emit_CNPJ Exemplo da elgin: 14200166000166 Define o CNPJ padrão do emitente da CFe.
sat:ConfigGravarValor("SATRede", "tipoInter", "0") //0 = infETHE
sat:ConfigGravarValor("SATRede", "tipoLan", "0")
sat:ConfigGravarValor("Extrato", "LarguraBobina", "302") //LarguraBobina Define a largura da bobina.
sat:ConfigGravarValor("Extrato", "MargemSuperior", "2") //MargemSuperior Define a margem superior da impressão.
sat:ConfigGravarValor("Extrato", "MargemInferior", "4") //MargemInferior Define a margem inferior da impressão.
sat:ConfigGravarValor("Extrato", "MargemEsquerda", "2") //MargemEsquerda Define a margem esquerda da impressão.
sat:ConfigGravarValor("Extrato", "MargemDireita", "2") //MargemDireita Define a margem direita da impressão.
sat:ConfigGravarValor("Extrato", "Tipo", "0") //TipoDefine o tipo de impressão a ser utilizada.tpFortes = 0 tpEscPos = 1
//sat:ConfigGravarValor("Extrato", "Impressora", "nome a impressora para emissão do cupom") //Impressora Define o nome da impressora padrão a ser utilizada pela impressão.
sat:ConfigGravarValor("Extrato", "ImprimeChaveEmUmaLinha", "0") //ImprimeChaveEmUma Define se deve imprimir a chave do CFe em apenas uma linha.Dll's Necessárias , a quais podems ser baixadas por qualquer usuário Sac do Acbr.
ACBrSAT32.dll
ACBrSAT64.dlllibeay32.dll
libexslt.dll
libiconv.dll
libxml2.dll
libxslt.dll
msvcr120.dll
ssleay32.dllObs: A classe da NF-e ainda não tenho.
[]s,
-
Jfaguiar, a Tmysql não é uma classe?
/*
* $Id: tmysql.prg,v 1.17 2007/07/17 21:01:17 andresreyesh Exp $
*//*
* Harbour Project source code:
* MySQL DBMS classes.
* These classes try to emulate clipper dbXXXX functions on a SQL query
*
* Copyright 2000 Maurilio Longo <maurilio.longo@libero.it>
* www - http://www.harbour-project.org
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this software; see the file COPYING. If not, write to
* the Free Software Foundation, Inc., 59 Temple Place, Suite 330,
* Boston, MA 02111-1307 USA (or visit the web site http://www.gnu.org/).
*
* As a special exception, the Harbour Project gives permission for
* additional uses of the text contained in its release of Harbour.
*
* The exception is that, if you link the Harbour libraries with other
* files to produce an executable, this does not by itself cause the
* resulting executable to be covered by the GNU General Public License.
* Your use of that executable is in no way restricted on account of
* linking the Harbour library code into it.
*
* This exception does not however invalidate any other reasons why
* the executable file might be covered by the GNU General Public License.
*
* This exception applies only to the code released by the Harbour
* Project under the name Harbour. If you copy code from other
* Harbour Project or Free Software Foundation releases into a copy of
* Harbour, as the General Public License permits, the exception does
* not apply to the code that you add in this way. To avoid misleading
* anyone as to the status of such modified files, you must delete
* this exception notice from them.
*
* If you write modifications of your own for Harbour, it is your choice
* whether to permit this exception to apply to your modifications.
* If you do not wish that, delete this exception notice.
*
*//*
2002-01-28 21:30 UTC+0100 Patrick Mast <email@patrickmast.com>
* contrib/mysql/tmysql
+ Added DateTime field
* Added more info on Alert message for Unknown type
* Modified ClipValue2SQL() to process empty strings
*//*
2002-02-18 07:30 UTC+0100 Srdjan Dragojlovic <digikv@yahoo.com>
* contrib/mysql/tmysql
+ Bug in GOTO Method
*/
#include "hbclass.ch"
#include "common.ch"
#include "dbstruct.ch"
#include "mysql.ch"// Every single row of an answer
CLASS TMySQLRowDATA aRow // a single row of answer
DATA aDirty // array of booleans set to .T. if corresponding field of aRow has been changed
DATA aOldValue // If aDirty[n] is .T. aOldValue[n] keeps a copy of changed value if aRow[n] is part of a primary keyDATA aFieldStruct // type of each field
DATA cTable // Name of table containing this row, empty if TMySQLQuery returned this rowMETHOD New( aRow, aFStruct, cTableName ) // Create a new Row object
METHOD FieldGet( cnField ) // Same as clipper ones, but FieldGet() and FieldPut() accept a string as
METHOD FieldPut( cnField, Value ) // field identifier, not only a number
METHOD FieldName( nNum )
METHOD FieldPos( cFieldName )METHOD FieldLen( nNum ) // Length of field N
METHOD FieldDec( nNum ) // How many decimals in field N
METHOD FieldType( nNum ) // Clipper type of field NMETHOD MakePrimaryKeyWhere() // returns a WHERE x=y statement which uses primary key (if available)
ENDCLASS
METHOD New( aRow, aFStruct, cTableName ) CLASS TMySQLRowdefault cTableName to ""
default aFStruct to {}::aRow := aRow
::aFieldStruct := aFStruct
::cTable := cTableName::aDirty := Array( Len( ::aRow ) )
::aOldValue := Array( Len( ::aRow ) )AFill( ::aDirty, .F. )
return Self
METHOD FieldGet( cnField ) CLASS TMySQLRowlocal nNum
if ValType( cnField ) == "C"
nNum := ::FieldPos( cnField )
else
nNum := cnField
endifif nNum > 0 .AND. nNum <= Len( ::aRow )
// Char fields are padded with spaces since a real .dbf field would be
if ::FieldType( nNum ) == "C"
return PadR( ::aRow[ nNum ], ::aFieldStruct[ nNum ][ MYSQL_FS_LENGTH ])
else
return ::aRow[ nNum ]
endifendif
return nil
METHOD FieldPut( cnField, Value ) CLASS TMySQLRowlocal nNum
if ValType( cnField ) == "C"
nNum := ::FieldPos( cnField )
else
nNum := cnField
endifif nNum > 0 .AND. nNum <= Len( ::aRow )
if Valtype( Value ) == Valtype( ::aRow[ nNum ] ) .OR. ::aRow[ nNum ] == NIL // .OR. Empty(::aRow[nNum])
// if it is a char field remove trailing spaces
if ValType( Value ) == "C"
Value := RTrim( Value )
endif// Save starting value for this field
if !::aDirty[ nNum ]
::aOldValue[ nNum ] := ::aRow[ nNum ]
::aDirty[ nNum ] := .T.
endif::aRow[ nNum ] := Value
return Value
endif
endifreturn nil
// Given a field name returns it's position
METHOD FieldPos( cFieldName ) CLASS TMySQLRowlocal cUpperName, nPos
cUpperName := Upper( cFieldName )
nPos := AScan( ::aFieldStruct, {| aItem | Upper( aItem[ MYSQL_FS_NAME ] ) == cUpperName } )
return nPos
// Returns name of field N
METHOD FieldName( nNum ) CLASS TMySQLRowif nNum >= 1 .AND. nNum <= Len( ::aFieldStruct )
return ::aFieldStruct[ nNum ][ MYSQL_FS_NAME ]
endifreturn ""
METHOD FieldLen(nNum) CLASS TMySQLRowif nNum >= 1 .AND. nNum <= Len( ::aFieldStruct )
return ::aFieldStruct[ nNum ][ MYSQL_FS_LENGTH ]
endifreturn 0
METHOD FieldDec( nNum ) CLASS TMySQLRowif nNum >= 1 .AND. nNum <= Len( ::aFieldStruct )
return ::aFieldStruct[ nNum ][ MYSQL_FS_DECIMALS ]
endifreturn 0
METHOD FieldType( nNum ) CLASS TMySQLRowif nNum >= 1 .AND. nNum <= Len( ::aFieldStruct )
Return SQL2ClipType( ::aFieldStruct[ nNum ][ MYSQL_FS_TYPE ] )
endifreturn "U"
// returns a WHERE x=y statement which uses primary key (if available)
METHOD MakePrimaryKeyWhere() CLASS TMySQLRowlocal cWhere := " WHERE ", aField
for each aField in ::aFieldStruct
// search for fields part of a primary key
if ( sqlAND( aField[ MYSQL_FS_FLAGS ], PRI_KEY_FLAG ) == PRI_KEY_FLAG ) .OR.;
( sqlAND( aField[ MYSQL_FS_FLAGS ], MULTIPLE_KEY_FLAG ) == MULTIPLE_KEY_FLAG )cWhere += aField[ MYSQL_FS_NAME ] + "="
// if a part of a primary key has been changed, use original value
if ::aDirty[ HB_EnumIndex() ]
cWhere += ClipValue2SQL( ::aOldValue[ HB_EnumIndex() ], SQL2ClipType(aField[ MYSQL_FS_TYPE ]) )
else
cWhere += ClipValue2SQL( ::aRow[ HB_EnumIndex() ], SQL2ClipType(aField[ MYSQL_FS_TYPE ]) )
endifcWhere += " AND "
endifnext
// remove last " AND "
cWhere := Left( cWhere, Len( cWhere ) - 5 )return cWhere
/* ----------------------------------------------------------------------------------------*/
// Every single query submitted to MySQL server
CLASS TMySQLQueryDATA nSocket // connection handle to MySQL server
DATA nResultHandle // result handle received from MySQLDATA cQuery // copy of query that generated this object
DATA nNumRows // number of rows available on answer NOTE MySQL is 0 based
DATA nCurRow // I'm currently over row numberDATA nNumFields // how many fields per row
DATA aFieldStruct // type of each field, a copy is here a copy inside each row
DATA aRowDATA lError // .T. if last operation failed
DATA loRow // If return oRow in GetRow(),
METHOD New( nSocket, cQuery, loRow ) // New query object
METHOD Destroy() INLINE sqlFreeR( ::nResultHandle ), Self
// Free result handle and associated resources
METHOD End() INLINE ::Destroy()METHOD Refresh() // ReExecutes the query (cQuery) so that changes to table are visible
METHOD GetRow( nRow, loRow, lSkip ) // return Row n of answer
METHOD Skip( nRows ) // Same as clipper ones
METHOD Bof() INLINE ::lBof // ::nCurRow == 1
METHOD Eof() INLINE ::lEof // ::nCurRow == ::nNumRows
METHOD RecNo() INLINE ::nCurRow
METHOD LastRec() INLINE ::nNumRows
METHOD GoTop() INLINE ::GetRow( 1 )
METHOD GoBottom() INLINE ::GetRow( ::nNumRows ) //-1 )
METHOD GoTo( nRow ) INLINE ::GetRow( nRow )METHOD FCount() INLINE ::nNumFields
METHOD NetErr() INLINE ::lError // Returns .T. if something went wrong
METHOD Error() INLINE ::lError := .F., sqlGetErr(::nSocket)
// Returns textual description of last error and clears ::lErrorMETHOD ErrorNo() INLINE ::lError := .F., sqlGetErrNo(::nSocket)
// Returns number of last error and clears ::lErrorMETHOD FieldName( nNum )
METHOD FieldPos( cFieldName )
METHOD FieldGet( cnField )METHOD FieldLen( nNum ) // Length of field N
METHOD FieldDec( nNum ) // How many decimals in field N
METHOD FieldType( nNum ) // Clipper type of field NMETHOD Locate( cFieldName, Value, bPartialKey, bSoftSeek )
METHOD RecCount() INLINE ::nNumRows
PROTECTED:
DATA lEof
DATA lBofENDCLASS
METHOD New( nSocket, cQuery, loRow ) CLASS TMySQLQuerylocal nI, aField, rc, bBlock
Default loRow to .t.
::nSocket := nSocket
::cQuery := cQuery::lError := .F.
::aFieldStruct := {}
::nCurRow := 1
::nResultHandle := nil
::nNumFields := 0
::nNumRows := 0
::loRow := loRow
if ( rc := sqlQuery( nSocket, cQuery ) ) == 0// save result set
if ( ::nResultHandle := sqlStoreR( nSocket ) ) > 0::nNumRows := sqlNRows( ::nResultHandle )
::nNumFields := sqlNumFi( ::nResultHandle )::aFieldStruct := Array( ::nNumFields )
::aRow := Array( ::nNumFields )if ::nNumRows > 0
::lEof := .f.
::lBof := .f.
else
::lEof := .t.
::lBof := .t.
endiffor each aField in ::aFieldStruct
aField := sqlFetchF( ::nResultHandle )
bBlock := ArrayBlock( HB_EnumIndex() )
__objAddInline( Self, aField[ MYSQL_FS_NAME ], bBlock )
__objAddInline( Self, "_"+aField[ MYSQL_FS_NAME ], bBlock )next
::getRow( ::nCurRow )
else
// Should query have returned rows? (Was it a SELECT like query?)if ( ::nNumFields := sqlNumFi( nSocket ) ) == 0
// Was not a SELECT so reset ResultHandle changed by previous sqlStoreR()
::nResultHandle := nil
::lEof := .t.
::lBof := .t.
else
::lError := .T.endif
endifelse
::lError := .T.endif
return Self
METHOD Refresh() CLASS TMySQLQuerylocal rc
// free present result handle
sqlFreeR( ::nResultHandle )::lError := .F.
if ( rc := sqlQuery( ::nSocket, ::cQuery ) ) == 0
// save result set
::nResultHandle := sqlStoreR( ::nSocket )
::nNumRows := sqlNRows( ::nResultHandle )// NOTE: I presume that number of fields doesn't change (that is nobody alters this table) between
// successive refreshes of the same// But row number could very well change
if ::nCurRow > ::nNumRows
::nCurRow := ::nNumRows
endif::getRow( ::nCurRow )
else
::lError := .T.endif
return !::lError
METHOD Skip( nRows ) CLASS TMySQLQuery
Local nOldrow := ::nCurRow
// NOTE: MySQL row count starts from 0
default nRows to 1if ::nNumRows > 0
::lBof := .f.
::lEof := .f.
else
::lBof := .t.
::lEof := .t.
endifif nRows == 0
// No moveelseif nRows < 0
// Negative movement
if (::nCurRow += nRows) < 1
::nCurRow := 0
::lBof := .t.
endifelse
// positive movement
if (::nCurRow += nRows) > ::nNumRows
::nCurRow := ::nNumRows + 1
::lEof := .t.
endifendif
::getRow( ::nCurRow )
return ::nCurRow - nOldRow
// Get row n of a query and return it as a TMySQLRow object
METHOD GetRow( nRow, loRow, lSkip ) CLASS TMySQLQuerylocal cType, xField
// local cDateFormat := Lower( Set( 4 ) )default loRow to ::loRow
default nRow to ::nCurRow
default lSkip to .f.if ::nResultHandle <> NIL
if lSkip
nRow := ::nCurRow + 1
endifdo case
case ::nNumRows == 0
::lBof := .t.
::lEof := .t.
::nCurRow := 1
case nRow < 1
::lBof := .t.
::lEof := .t.
::nCurRow := ::nNumRows + 1
case nRow > 0 .and. nRow <= ::nNumRows //- 1
::lBof := .f.
::lEof := .f.
::nCurRow := nRow
case nRow > ::nNumRows
::lBof := .f.
::lEof := .t.
::nCurRow := ::nNumRows + 1
endcase
nRow := ::nCurRowif nRow > 0 .AND. nRow <= ::nNumRows
// NOTE: row count starts from 0
sqlDataS( ::nResultHandle, nRow - 1 )
::nCurRow := nRow
::aRow := sqlFetchR( ::nResultHandle )elseif nRow == ::nNumRows + 1
::aRow := Array( Len( ::aFieldStruct ) )
Afill( ::aRow, "" )else
::aRow := NIL
endif
if ::aRow <> NIL// Convert answer from text field to correct clipper types
for each xField in ::aRowcType := SQL2ClipType( ::aFieldStruct[ HB_EnumIndex() ][ MYSQL_FS_TYPE ] )
switch cType
case "L"
xField := !( Val( xField ) == 0 )
exitcase "N"
case "I"
case "T"
xField := Val( xField )
exitcase "D"
if Empty(xField)
xField := CToD( "" )
/*
elseif cDateFormat = 'mm-dd-yyyy' // USA
xField := ctod(substr(xField,6,2)+"-"+right(xField,2,0)+ "-" + Left(xField, 4))elseif cDateFormat = 'dd/mm/yyyy' .or. cDateFormat = 'dd/mm/yy' // BRITISH ou FRENCH
xField := ctod(right(xField,2,0)+ "/"+ substr(xField,6,2)+"/"+ Left(xField, 4))elseif cDateFormat = 'yyyy.mm.dd' // ANSI
xField := ctod(Left(xField, 4)+ "."+substr(xField,6,2)+"."+right(xField,2,0))elseif cDateFormat = 'dd.mm.yyyy' //GERMAN
xField :=ctod(right(xField,2,0)+ "."+ substr(xField,6,2)+"."+ Left(xField, 4 ))elseif cDateFormat = 'dd-mm-yyyy' //ITALIAN
xField :=ctod(right(xField,2,0)+ "-"+ substr(xField,6,2)+"-"+ Left(xField, 4))elseif cDateFormat = 'yyyy/mm/dd' //JAPAN
xField := ctod(Left(xField, 4)+ "/"+substr(xField,6,2)+"/"+right(xField,2,0))elseif cDateFormat = 'mm/dd/yyyy' // AMERICAN
xField := ctod(substr(xField,6,2)+"/"+right(xField,2,0)+ "/" + Left(xField, 4))
else
xField := "''"
*/
else
// MySQL Date format YYYY-MM-DD
xField := SToD( Left( xField, 4 ) + substr( xField, 6, 2 ) + right( xField, 2 ) )
endif
exitcase "C"
xField := PadR( xField , ::aFieldStruct[ HB_EnumIndex() ][ MYSQL_FS_LENGTH ] )
case "M"
case "B"
// Character or Memo field
exitdefault
// Alert("Unknown type from SQL Server Field: " + LTrim(Str(i))+" is type "+LTrim(Str(nType)))
end
// __objsetValuelist(Self,{{::aFieldStruct[MYSQL_FS_NAME],xField}})
next
if loRow
Return TMySQLRow():New( ::aRow, ::aFieldStruct )
endifendif
endif
return nil
// Given a field name returns it's position
METHOD FieldPos( cFieldName ) CLASS TMySQLQuerylocal cUpperName, nPos := 0
cUpperName := Upper( cFieldName )
nPos := AScan( ::aFieldStruct, {| aItem | Upper( aItem[ MYSQL_FS_NAME ] ) == cUpperName } )
return nPos
// Returns name of field N
METHOD FieldName( nNum ) CLASS TMySQLQueryif nNum >= 1 .AND. nNum <= Len( ::aFieldStruct )
return ::aFieldStruct[ nNum ][ MYSQL_FS_NAME ]
endifreturn ""
METHOD FieldGet(cnField) CLASS TMySQLQuery
local nNum, Value
if ValType( cnField ) == "C"
nNum := ::FieldPos( cnField )
else
nNum := cnField
endifif nNum > 0 .AND. nNum <= ::nNumfields
// Value := __objsendmsg(Self,::aFieldStruct[nNum][MYSQL_FS_NAME])
Value := ::aRow[ nNum ]// Char fields are padded with spaces since a real .dbf field would be
if ::FieldType( nNum ) == "C"
return PadR( Value, ::aFieldStruct[ nNum ][ MYSQL_FS_LENGTH ] )
else
return Value
endifendif
return nil
METHOD FieldLen(nNum) CLASS TMySQLQueryif nNum > 0 .AND. nNum <= ::nNumFields
return ::aFieldStruct[ nNum ][ MYSQL_FS_LENGTH ]
endifreturn 0
METHOD FieldDec( nNum ) CLASS TMySQLQueryif nNum > 0 .AND. nNum <= ::nNumFields
return ::aFieldStruct[ nNum ][ MYSQL_FS_DECIMALS ]
endifreturn 0
METHOD FieldType( nNum ) CLASS TMySQLQuerylocal cType := "U"
if nNum >= 1 .AND. nNum <= ::nNumFields
cType := SQL2ClipType( ::aFieldStruct[ nNum ][ MYSQL_FS_TYPE ] )
endif
return cType
METHOD Locate( cFieldName, Value, bPartialKey, bSoftSeek ) CLASS TMySQLQuery
local nRecPrec := ::recno(), bFound := .F.//bSoftSeek cause the record pointer to be moved to the next record
if bSoftSeek == NIL ; bSoftSeek := .F. ; endif
if bPartialKey == NIL ; bPartialKey := .T. ; endif::gotop()
while ! ::eof()
bFound := (::FieldGet(::FieldPos(cFieldName)) == Value) .or. ((::FieldGet(::FieldPos(cFieldName)) = Value) .and. bPartialKey)if !bFound .and. ((::FieldGet(::FieldPos(cFieldName)) > Value) .and. bSoftSeek)
bFound := .T.
endifif bFound
exit
endif::skip()
enddoif !bFound
::goto(nRecPrec)
endifreturn bFound
/* ----------------------------------------------------------------------------------------*/
// A Table is a query without joins; this way I can Insert() e Delete() rows.
// NOTE: it's always a SELECT result, so it will contain a full table only if
// SELECT * FROM ... was issued
CLASS TMySQLTable FROM TMySQLQueryDATA cTable // name of table
DATA aOldValue // keeps a copy of old valueMETHOD New( nSocket, cQuery, cTableName, loRow )
METHOD GetRow( nRow, loRow, lSkip )
METHOD Skip( nRow )METHOD Update( oRow ) // Gets an oRow and updates changed fields
METHOD Save( oRow ) INLINE ::Update( oRow )
METHOD Delete( oRow ) // Deletes passed row from table
METHOD Append( oRow ) // Inserts passed row into tableMETHOD GetBlankRow( loRow ) // Returns an empty row with all available fields empty
METHOD Blank( loRow ) INLINE ::GetBlankRow( loRow )METHOD FieldPut( cnField, Value ) // field identifier, not only a number
METHOD Refresh()
METHOD MakePrimaryKeyWhere() // returns a WHERE x=y statement which uses primary key (if available)ENDCLASS
METHOD New(nSocket, cQuery, cTableName, loRow) CLASS TMySQLTableLocal xValue
super:New(nSocket, AllTrim(cQuery), loRow)
::cTable := Lower(cTableName)
::aOldValue := Array( ::nNumFields )for each xValue in ::aOldValue
xValue := ::fieldget( HB_EnumIndex() )
nextreturn Self
METHOD GetRow( nRow, loRow, lSkip ) CLASS TMySQLTablelocal oRow := super:GetRow( nRow, loRow, lSkip ), xValue
if oRow <> NIL
oRow:cTable := ::cTable
endif::aOldvalue := Array( ::nNumFields )
for each xValue in ::aOldValue
xValue := ::fieldget( HB_EnumIndex() )
nextreturn oRow
METHOD Skip(nRow) CLASS TMySQLTable
Local xValue, nSkipRowsnSkipRows := super:skip(nRow)
for each xValue in ::aOldValue
xValue := ::fieldget( HB_EnumIndex() )
nextreturn nSkipRows
/* Creates an update query for changed fields and submits it to server */
METHOD Update( oRow ) CLASS TMySQLTablelocal cUpdateQuery := "UPDATE " + ::cTable + " SET "
local xValue::lError := .F.
// default Current row
if oRow == nilfor each xValue in ::aOldValue
if xValue == NIL .or. xValue <> ::FieldGet( HB_EnumIndex() )
cUpdateQuery += ::aFieldStruct[ HB_EnumIndex() ][MYSQL_FS_NAME] + "=" + ClipValue2SQL(::FieldGet( HB_EnumIndex() ),::FieldType( HB_EnumIndex() )) + ","
endif
next// no Change
if right(cUpdateQuery,4)=="SET "; return !::lError; end// remove last comma
cUpdateQuery := Left(cUpdateQuery, Len(cUpdateQuery) -1)
cUpdateQuery += ::MakePrimaryKeyWhere()// alert( cUpdateQuery )
if sqlQuery( ::nSocket, cUpdateQuery ) == 0
::refresh()
for each xValue in ::aOldValue
xValue := ::fieldget( HB_EnumIndex() )
nextelse
::lError := .T.endif
else
WITH OBJECT oRow
if :cTable == ::cTable
for each xValue in :aRow
if :aDirty[ HB_EnumIndex() ]
cUpdateQuery += :aFieldStruct[ HB_EnumIndex() ][ MYSQL_FS_NAME ] + "=" + ClipValue2SQL( :aRow[ HB_EnumIndex() ], :FieldType( HB_EnumIndex() ) ) + ","
endif
next// remove last comma
cUpdateQuery := Left( cUpdateQuery, Len(cUpdateQuery ) - 1 )cUpdateQuery += :MakePrimaryKeyWhere()
// alert( cUpdateQuery )
if sqlQuery( ::nSocket, cUpdateQuery ) == 0
// All values are commited
Afill( :aDirty , .F. )
Afill( :aOldValue, nil )else
::lError := .T.endif
endif
END // WITH
endifreturn !::lError
METHOD Delete( oRow ) CLASS TMySQLTablelocal cDeleteQuery := "DELETE FROM " + ::cTable, xValue
// is this a row of this table ?
if oRow == nil
cDeleteQuery += ::MakePrimaryKeyWhere()
if sqlQuery( ::nSocket, cDeleteQuery ) == 0
::lError := .F.
// ::nCurRow--
::refresh()for each xValue in ::aOldValue
xValue := ::fieldget( HB_EnumIndex() )
nextelse
::lError := .T.endif
else
WITH OBJECT oRow
if :cTable == ::cTablecDeleteQuery += :MakePrimaryKeyWhere()
if sqlQuery( ::nSocket, cDeleteQuery ) == 0
::lError := .F.else
::lError := .T.endif
endif
END // WITH
Endifreturn !::lError
// Adds a row with values passed into oRow
METHOD Append( oRow ) CLASS TMySQLTablelocal cInsertQuery := "INSERT INTO " + ::cTable + " ("
local xValue, lResult:= .F.// default Current row
if oRow == nil// field names
for each xValue in ::aFieldStruct
if xValue[ MYSQL_FS_FLAGS ] <> AUTO_INCREMENT_FLAG
cInsertQuery += xValue[ MYSQL_FS_NAME ] + ","
endif
next// remove last comma from list
cInsertQuery := Left( cInsertQuery, Len( cInsertQuery ) - 1 ) + ") VALUES ("// field values
for each xValue in ::aFieldStruct
if xValue[ MYSQL_FS_FLAGS ] <> AUTO_INCREMENT_FLAG
cInsertQuery += ClipValue2SQL( ::FieldGet(HB_EnumIndex() ), ::FieldType(HB_EnumIndex()) ) + ","
endif
next// remove last comma from list of values and add closing parenthesis
cInsertQuery := Left( cInsertQuery, Len(cInsertQuery) - 1 ) + ")"// alert( cInsertQuery )
if sqlQuery( ::nSocket, cInsertQuery ) == 0
::refresh()
for each xValue in ::aOldValue
xValue := ::fieldget( HB_EnumIndex() )
next
lResult:= .T.
else
::lError := .T.
endif
elseWITH OBJECT oRow
if :cTable == ::cTable// field names
for each xValue in :aFieldStruct
if xValue[ MYSQL_FS_FLAGS ] <> AUTO_INCREMENT_FLAG
cInsertQuery += xValue[ MYSQL_FS_NAME ] + ","
endif
next
// remove last comma from list
cInsertQuery := Left( cInsertQuery, Len( cInsertQuery ) - 1 ) + ") VALUES ("// field values
for each xValue in :aRow
if :aFieldStruct[ HB_EnumIndex() ][ MYSQL_FS_FLAGS ] <> AUTO_INCREMENT_FLAG
cInsertQuery += ClipValue2SQL( xValue, :FieldType(HB_EnumIndex()) ) + ","
endif
next// remove last comma from list of values and add closing parenthesis
cInsertQuery := Left( cInsertQuery, Len( cInsertQuery ) - 1 ) + ")"// alert( cInsertQuery )
if sqlQuery( ::nSocket, cInsertQuery ) == 0
lResult:= .T.
else
::lError := .T.
endifendif
END // WITH
Endif
return lResult
METHOD GetBlankRow( loRow ) CLASS TMySQLTablelocal cType
local xValueDefault loRow to ::loRow
for each xValue in ::aRow
cType := SQL2ClipType( ::aFieldStruct[ HB_EnumIndex() ][ MYSQL_FS_TYPE ] )
switch cType
case "C"
::aOldValue[ HB_EnumIndex() ] := xValue := SPACE(::aFieldStruct[ HB_EnumIndex() ][ MYSQL_FS_LENGTH ])
exit
case "M"
case "B"
::aOldValue[ HB_EnumIndex() ] := xValue := ""
exitcase "N"
case "I"
::aOldValue[ HB_EnumIndex() ] := xValue := 0
exitcase "L"
::aOldValue[ HB_EnumIndex() ] := xValue := .F.
exitcase "D"
::aOldValue[ HB_EnumIndex() ] := xValue := CToD("")
exitdefault
::aOldValue[ HB_EnumIndex() ] := xValue := nilend
next
if loRow
return TMySQLRow():New( ::aRow, ::aFieldStruct, ::cTable )
endifreturn nil
METHOD FieldPut( cnField, Value ) CLASS TMySQLTablelocal nNum
if ValType( cnField ) == "C"
nNum := ::FieldPos( cnField )
else
nNum := cnField
endifif nNum > 0 .AND. nNum <= ::nNumFields
// if Valtype( Value ) == Valtype( ::FieldGet( nNum ) ) .OR. ::Fieldget( nNum ) == NIL )
if Valtype( Value ) == Valtype( ::aRow[ nNum ] ) .OR. ::aRow[ nNum ] == NIL// if it is a char field remove trailing spaces
if ValType( Value ) == "C"
Value := RTrim( Value )
endif::aRow[ nNum ] := Value
return Value
endif
endifreturn nil
METHOD Refresh() CLASS TMySQLTABLE
local rc
// free present result handle
sqlFreeR( ::nResultHandle )::lError := .F.
if ( rc := sqlQuery( ::nSocket, ::cQuery ) ) == 0
// save result set
::nResultHandle := sqlStoreR( ::nSocket )
::nNumRows := sqlNRows( ::nResultHandle )// NOTE: I presume that number of fields doesn't change (that is nobody alters this table) between
// successive refreshes of the same// But row number could very well change
if ::nCurRow > ::nNumRows
::nCurRow := ::nNumRows
endif::getRow( ::nCurRow )
else
::lError := .T.endif
return !::lError
// returns a WHERE x=y statement which uses primary key (if available)
METHOD MakePrimaryKeyWhere() CLASS TMySQLTablelocal ni, cWhere := " WHERE ", aField
for each aField in ::aFieldStruct
// search for fields part of a primary key
if ( sqlAND( aField[ MYSQL_FS_FLAGS ], PRI_KEY_FLAG ) == PRI_KEY_FLAG ) .OR.;
( sqlAND( aField[ MYSQL_FS_FLAGS ], MULTIPLE_KEY_FLAG ) == MULTIPLE_KEY_FLAG )cWhere += aField[ MYSQL_FS_NAME ] + "="
// if a part of a primary key has been changed, use original value
cWhere += ClipValue2SQL( ::aOldValue[ HB_EnumIndex() ], ::FieldType(HB_EnumIndex()) )
cWhere += " AND "
endifnext
// remove last " AND "
cWhere := Left( cWhere, Len( cWhere ) - 5 )return cWhere
/* ----------------------------------------------------------------------------------------*/
// Every available MySQL server
CLASS TMySQLServerDATA nSocket // connection handle to server (currently pointer to a MYSQL structure)
DATA cServer // server name
DATA cDBName // Selected DB
DATA cUser // user accessing db
DATA cPassword // his/her password
DATA lError // .T. if occurred an error
DATA nPort
DATA nFlags
DATA cCreateQueryMETHOD New( cServer, cUser, cPassword, nPort, nFlags ) // Opens connection to a server, returns a server object
METHOD Destroy() INLINE sqlClose( ::nSocket ), Self
// Closes connection to serverMETHOD SelectDB( cDBName ) // Which data base I will use for subsequent queries
METHOD CreateDatabase( cDataBase ) // Create an New Mysql Database
METHOD ListDBs() INLINE sqlListDB(::nSocket)
// returns an array with list of data bases availableMETHOD DBExist( cDB ) INLINE ( cDB IN ::ListDBs() )
// return .T. if cTable exist in the databaseMETHOD CreateTable( cTable, aStruct, cPrimaryKey, cUniqueKey, cAuto)
// Create new table using the same syntax of dbCreate()METHOD DeleteTable( cTable ) // delete table
METHOD TableExist( cTable ) INLINE ( cTable IN ::ListTables() )
// return .T. if cTable exist in the databaseMETHOD ListTables() INLINE sqlListTbl(::nSocket)
// returns an array with list of available tables in current databaseMETHOD TableStruct( cTable ) // returns a structure array compatible with clipper's dbStruct() ones
METHOD CreateIndex( cName, cTable, aFNames, lUnique )
// Create an index (unique) on field name(s) passed as an array of strings aFNamesMETHOD DeleteIndex( cName, cTable ) // Delete index cName from cTable
METHOD Query( cQuery, loRow ) // Gets a textual query and returns a TMySQLQuery or TMySQLTable objectMETHOD NetErr() INLINE ::lError
// Returns .T. if something went wrongMETHOD Error() // Returns textual description of last error
ENDCLASS
METHOD New( cServer, cUser, cPassword, nPort, nFlags ) CLASS TMySQLServer::cServer := cServer
::cUser := cUser
::cPassword := cPassword
::nPort := nPort
::nFlags := nFlags
::nSocket := sqlConnect(cServer, cUser, cPassword, nPort, nFlags )
::lError := .F.if ::nSocket == 0
::lError := .T.
endifreturn Self
METHOD SelectDB( cDBName ) CLASS TMySQLServer::lError := .F.
if sqlSelectD( ::nSocket, cDBName ) != 0 // table not exist
::cDBName :=""
::lError := .T.
else // table exist
::cDBName := cDBName
::lError := .F.
return .T.
endifreturn .F.
METHOD CreateDatabase ( cDataBase ) CLASS TMySQLServer
local cCreateQuery := "CREATE DATABASE "+ lower( cDatabase )if sqlQuery( ::nSocket, cCreateQuery ) == 0
return .T.
endifreturn .F.
// NOTE: OS/2 port of MySQL is picky about table names, that is if you create a table with
// an upper case name you cannot alter it (for example) using a lower case name, this violates
// OS/2 case insensibility about names
METHOD CreateTable( cTable, aStruct, cPrimaryKey, cUniqueKey, cAuto ) CLASS TMySQLServer/* NOTE: all table names are created with lower case */
local aField
// returns NOT NULL if extended structure has DBS_NOTNULL field to true
local cNN := {| aArr | iif( Len( aArr ) > DBS_DEC, iif( aArr[ DBS_NOTNULL ], " NOT NULL ", "" ), "" ) }
::cCreateQuery := "CREATE TABLE " + Lower(cTable) + " ("
for each aField in aStructswitch aField[ DBS_TYPE ]
case "C"
::cCreateQuery += aField[ DBS_NAME ] + " char(" + AllTrim(Str(aField[DBS_LEN])) + ")" + Eval(cNN, aField)+ if(aField[DBS_NAME]==cPrimaryKey," NOT NULL ",'' )+ ","
exitcase "M"
::cCreateQuery += aField[ DBS_NAME ] + " text" + Eval(cNN, aField) + ","
exitcase "N"
if aField[ DBS_DEC ] == 0 .and. aField[ DBS_LEN ] <= 18
do case
case aField[ DBS_LEN ] <= 4
::cCreateQuery += aField[ DBS_NAME ] + " smallint(" + AllTrim( Str( aField[ DBS_LEN ] ) ) + ")"case aField[ DBS_LEN ] <= 6
::cCreateQuery += aField[ DBS_NAME ] + " mediumint(" + AllTrim( Str( aField[ DBS_LEN ] ) ) + ")"case aField[ DBS_LEN ] <= 9
::cCreateQuery += aField[ DBS_NAME ] + " int(" + AllTrim( Str( aField[ DBS_LEN ] ) ) + ")"otherwise
::cCreateQuery += aField[ DBS_NAME ] + " bigint(" + AllTrim( Str( aField[ DBS_LEN ] ) ) + ")"endcase
::cCreateQuery += Eval( cNN, aField ) + if( aField[ DBS_NAME ] == cPrimaryKey, " NOT NULL ", "" ) + if( aField[ DBS_NAME ] == cAuto, " auto_increment ", "" ) + ","
else
::cCreateQuery += aField[ DBS_NAME ] + " real(" + AllTrim( Str( aField[ DBS_LEN ] ) ) + "," + AllTrim( Str( aField[ DBS_DEC ] ) ) + ")" + Eval( cNN, aField ) + ","endif
exitcase "D"
::cCreateQuery += aField[ DBS_NAME ] + " date " + Eval( cNN, aField ) + ","
exitcase "L"
::cCreateQuery += aField[ DBS_NAME ] + " tinyint " + Eval( cNN, aField ) + ","
exitcase "B"
::cCreateQuery += aField[ DBS_NAME ] + " mediumblob " + Eval( cNN, aField ) + ","
exitcase "I"
::cCreateQuery += aField[ DBS_NAME ] + " mediumint " + Eval( cNN, aField ) + ","
exitcase "T"
::cCreateQuery += aField[ DBS_NAME ] + " timestamp(" + AllTrim( Str( aField[ DBS_LEN ] ) ) + ")" + Eval( cNN, aField ) + ","
exitdefault
::cCreateQuery += aField[ DBS_NAME ] + " char(" + AllTrim(Str(aField[DBS_LEN])) + ")" + Eval( cNN, aField ) + ","end
next
if cPrimarykey != NIL
::cCreateQuery += ' PRIMARY KEY (' + cPrimaryKey + '),'
endifif cUniquekey != NIL
::cCreateQuery += ' UNIQUE ' + cUniquekey + ' (' + cUniqueKey + '),'
endif// remove last comma from list
::cCreateQuery := Left( ::cCreateQuery, Len( ::cCreateQuery ) - 1 ) + ");"if sqlQuery( ::nSocket, ::cCreateQuery ) == 0
return .T.
else
::lError := .T.
endifreturn .F.
METHOD CreateIndex( cName, cTable, aFNames, lUnique ) CLASS TMySQLServerlocal cCreateQuery := "CREATE "
local cFielddefault lUnique to .F.
if lUnique
cCreateQuery += "UNIQUE INDEX "
else
cCreateQuery += "INDEX "
endifcCreateQuery += cName + " ON " + Lower( cTable ) + " ("
for each cField in aFNames
cCreateQuery += cField + ","
next// remove last comma from list
cCreateQuery := Left( cCreateQuery, Len( cCreateQuery ) - 1 ) + ")"if sqlQuery( ::nSocket, cCreateQuery ) == 0
return .T.
endifreturn .F.
METHOD DeleteIndex( cName, cTable ) CLASS TMySQLServerlocal cDropQuery := "DROP INDEX " + cName + " FROM " + Lower( cTable )
if sqlQuery( ::nSocket, cDropQuery ) == 0
return .T.
endifreturn .F.
METHOD DeleteTable( cTable ) CLASS TMySQLServerlocal cDropQuery := "DROP TABLE " + Lower( cTable )
if sqlQuery( ::nSocket, cDropQuery ) == 0
return .T.endif
return .F.
METHOD Query( cQuery, loRow ) CLASS TMySQLServerlocal oQuery, cTableName, i, cUpperQuery, nNumTables, cToken
default cQuery to ""
cUpperQuery := Upper( AllTrim( cQuery ) )
i := 1
nNumTables := 1while (cToken := __StrToken( cUpperQuery, i++, " " ) ) <> "FROM" .AND. !Empty( cToken )
enddo// first token after "FROM" is a table name
// NOTE: SubSelects ?
cTableName := __StrToken( cUpperQuery, i++, " " )while ( cToken := __StrToken( cUpperQuery, i++, " " ) ) <> "WHERE" .AND. !Empty( cToken )
// do we have more than one table referenced ?
if cToken == "," .OR. cToken == "JOIN"
nNumTables++
endif
enddoif nNumTables == 1
oQuery := TMySQLTable():New( ::nSocket, cQuery, cTableName, loRow )
else
oQuery := TMySQLQuery():New(::nSocket, cQuery, loRow )
endifif oQuery:NetErr()
::lError := .T.
endifreturn oQuery
METHOD Error() CLASS TMySQLServer::lError := .F.
return iif(::nSocket > 0, sqlGetErr(::nSocket), "No connection to server")
/* TOFIX: Conversion creates a .dbf with fields of wrong dimension (often) */
METHOD TableStruct( cTable ) CLASS TMySQLServerlocal nRes, aField, aStruct, aSField, i
aStruct := {}/* TODO: rewrite for MySQL */
nRes := sqlListF( ::nSocket, cTable )if nRes > 0
for i := 1 to sqlNumFi( nRes )aField := sqlFetchF( nRes )
aSField := Array( DBS_DEC )// don't count indexes as real fields
// if aField[ MYSQL_FS_TYPE ] <= MYSQL_LAST_REAL_TYPEaSField[ DBS_NAME ] := Left( aField[ MYSQL_FS_NAME ], 10 )
aSField[ DBS_DEC ] := 0asField[ DBS_TYPE ] := SQL2ClipType( aField[ MYSQL_FS_TYPE ] )
switch aField[ MYSQL_FS_TYPE ]
case MYSQL_TINY_TYPE
aSField[ DBS_TYPE ] := "L"
aSField[ DBS_LEN ] := 1
exitcase MYSQL_SHORT_TYPE
aSField[ DBS_TYPE ] := "N"
aSField[ DBS_LEN ] := Min( 6, aField[ MYSQL_FS_LENGTH ] )
exitcase MYSQL_INT24_TYPE
aSField[ DBS_TYPE ] := "N"
aSField[ DBS_LEN ] := Min( 8, aField[ MYSQL_FS_LENGTH ] )
exitcase MYSQL_LONG_TYPE
aSField[ DBS_TYPE ] := "N"
aSField[ DBS_LEN ] := Min( 11, aField[ MYSQL_FS_LENGTH ] )
exitcase MYSQL_LONGLONG_TYPE
aSField[ DBS_TYPE ] := "N"
aSField[ DBS_LEN ] := Min( 20, aField[ MYSQL_FS_LENGTH ] )
exitcase MYSQL_FLOAT_TYPE
case MYSQL_DOUBLE_TYPE
case MYSQL_DECIMAL_TYPE
aSField[ DBS_TYPE ] := "N"
aSField[ DBS_LEN ] := aField[ MYSQL_FS_LENGTH ]
aSFIeld[ DBS_DEC ] := aField[ MYSQL_FS_DECIMALS ]
exit/* case FIELD_TYPE_INT24
aSField[ DBS_TYPE ] := "I"
aSField[ DBS_LEN ] := aField[ MYSQL_FS_LENGTH ]
aSFIeld[ DBS_DEC ] := aField[ MYSQL_FS_DECIMALS ]
exit */case MYSQL_STRING_TYPE
case MYSQL_VAR_STRING_TYPE
case MYSQL_DATETIME_TYPE
case MYSQL_TIME_TYPE
aSField[ DBS_TYPE ] := "C"
aSField[ DBS_LEN ] := aField[ MYSQL_FS_LENGTH ]
exitcase MYSQL_DATE_TYPE
aSField[ DBS_TYPE ] := "D"
aSField[ DBS_LEN ] := 8
exitcase MYSQL_MEDIUM_BLOB_TYPE
aSField[ DBS_TYPE ] := "B"
aSField[ DBS_LEN ] := aField[ MYSQL_FS_LENGTH ]
exitcase MYSQL_BLOB_TYPE
aSField[ DBS_TYPE ] := "M"
aSField[ DBS_LEN ] := 10
exitcase MYSQL_TIMESTAMP_TYPE
aSField[ DBS_TYPE ] := "N"
aSField[ DBS_LEN ] := aField[ MYSQL_FS_LENGTH ]
exitdefault
aSField[ DBS_TYPE ] := "C"
aSField[ DBS_LEN ] := aField[ MYSQL_FS_LENGTH ]end
AAdd( aStruct, aSField )
// endif
nextsqlFreeR( nRes )
endif
return aStruct
// Returns an SQL string with clipper value converted ie. Date() -> "'YYYY-MM-DD'"
static function ClipValue2SQL(Value, cType)local cValue := ""
// local cDateFormat := Lower( Set( 4 ) )Default cType to ValType( Value )
switch cType
case "N"
case "I"
cValue := AllTrim( Str( Value ) )
exitcase "D"
if !Empty( Value )
// MySQL dates are like YYYY-MM-DD or YYYYMMDD
cValue := "'" + Transform( Dtos( Value ), "@R 9999-99-99" ) + "'"
/*
if cDateFormat == 'mm-dd-yyyy' // USA
cValue := "'"+PadL(Month(Value), 2, "0") + '-'+ PadL(Day(Value), 2, "0") + "-" + Str(Year(Value), 4) + "'"
elseif cDateFormat == 'dd/mm/yyyy' // BRITISH ou FRENCH
//cValue := "'"+PadL(Day(Value), 2, "0") + "/" + PadL(Month(Value), 2, "0") + "/" + Str(Year(Value), 4) + "'"
cValue := "'"+Str(Year(Value), 4) + "-" + PadL(Month(Value), 2, "0") + "-" + PadL(Day(Value), 2, "0") + "'"
elseif cDateFormat == 'yyyy.mm.dd' // ANSI
cValue := "'"+Str(Year(Value), 4) + "." + PadL(Month(Value), 2, "0") + "." + PadL(Day(Value), 2, "0") + "'"
elseif cDateFormat == 'dd.mm.yyyy' //GERMAN
cValue := "'"+PadL(Day(Value), 2, "0") + "." + PadL(Month(Value), 2, "0") + "." + Str(Year(Value), 4) + "'"
elseif cDateFormat == 'dd-mm-yyyy' //ITALIAN
cValue := "'"+PadL(Day(Value), 2, "0") + "-" + PadL(Month(Value), 2, "0") + "-" + Str(Year(Value), 4) + "'"
elseif cDateFormat == 'yyyy/mm/dd' //JAPAN
cValue := "'"+Str(Year(Value), 4) + "/" + PadL(Month(Value), 2, "0") + "/" + PadL(Day(Value), 2, "0") + "'"
elseif cDateFormat == 'mm/dd/yyyy' // AMERICAN
cValue := "'"+Str(Year(Value), 4) + "/" + PadL(Month(Value), 2, "0") + "/" + PadL(Day(Value), 2, "0") + "'"
endif
*/
else
cValue := "''"
endif
exitcase "C"
case "M"
case "B"
IF Empty( Value)
cValue := "''"
ELSE
cValue := "'" + DATATOSQL( value ) + "'"
ENDIF
exitcase "L"
cValue := AllTrim( Str( iif(Value, 1, 0 ) ) )
exitcase "T"
cValue := iif( Value < 0, "NULL", Alltrim( str( Value ) ) )
exitdefault
cValue := "''" // NOTE: Here we lose values we cannot convertend
return cValue
static function SQL2ClipType( nType )switch nType
case MYSQL_TINY_TYPE
Return "L"case MYSQL_SHORT_TYPE
case MYSQL_LONG_TYPE
case MYSQL_LONGLONG_TYPE
case MYSQL_FLOAT_TYPE
case MYSQL_DOUBLE_TYPE
case MYSQL_DECIMAL_TYPE
Return "N"case MYSQL_DATE_TYPE
Return "D"case MYSQL_BLOB_TYPE
Return "M"case MYSQL_VAR_STRING_TYPE
case MYSQL_STRING_TYPE
case MYSQL_DATETIME_TYPE
case MYSQL_TIME_TYPE
Return "C"case MYSQL_INT24_TYPE
Return "I"case MYSQL_MEDIUM_BLOB_TYPE
Return "B"case MYSQL_TIMESTAMP_TYPE
Return "T"end
Return "U"
/* Given a three letter month name gives back month number as two char string (ie. Apr -> 04) */
static function NMonth(cMonthValue)static cMonths := {"Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Ago", "Sep", "Oct", "Nov", "Dec" }
local nMonthnMonth := AScan(cMonths, cMonthValue)
return PadL(nMonth, 2, "0")
static function ARRAYBLOCK( nIndex )
Local bBlockbBlock := {|Self, x | iif( PCount() == 1, ::aRow[ nIndex ], ::aRow[ nIndex ] := x ) }
return bBlock
-
-
Novos Códigos de Rejeição – NT 2019.001
Rejeição 305 : Destinatário bloqueado na UF
Rejeição 306 : IE do destinatário não está ativa na UF
Rejeição 922: Contranota de Produtor só pode referenciar NF-e ou NF de Produtor Modelo 4
Rejeição 923: Referenciado documento de operação interna em operação interestadual ou com o exterior
Rejeição 924: Informado Cupom Fiscal referenciado.
Rejeição 925: NF-e com identificação de estrangeiro e inscrição estadual informada para destinatário
Rejeição 926: Operação com Exterior e país de destino igual a Brasil.
Rejeição 927: Número do item fora da ordem sequencial.
Rejeição 928: Informado código de benefício fiscal para CST sem benefício fiscal [nItem: nnn]
Rejeição 929: Informado CST de diferimento sem as informações de diferimento [nItem: nnn]
Rejeição 930 : CST com benefício fiscal e não informado o código de benefício fiscal [nItem: nnn]
Rejeição 931 : CST não corresponde ao tipo de código de benefício fiscal [nItem: nnn]
Rejeição 932: Informada modalidade de determinação da BC da ST como MVA e não informado o campo pMVAST [nItem: nnn]
Rejeição 933: Informada modalidade de determinação da BC da ST diferente de MVA e informado o campo pMVAST [nItem: nnn]
Rejeição 934: Não informado valor do ICMS desonerado ou o Motivo de desoneração [nItem: nnn]
Rejeição 935: Valor total da Base de Cálculo superior ao valor limite estabelecido [Valor Limite: R$ XXX.XXX,XX] (valor definido pela UF)
Rejeição 936: Razão Social do emitente diverge do informado no cadastro da SEFAZ.Mano, tem rejeição nesta lista que parece coisa de português, uma coisa é rejeitar na validação (Consistência na validação), ou é rejeitar no envio,. Parece até piada.
Rejeição 925: NF-e com identificação de estrangeiro e inscrição estadual informada para destinatário
Rejeição 926: Operação com Exterior e país de destino igual a Brasil.
Rejeição 936: Razão Social do emitente diverge do informado no cadastro da SEFAZ. - Essa chega a ser um absurdo, pois com tantas informações como Cnpj e IE e ainda vão criticar o nome da empresa.
[]s,
-
João, boa noite.
Este registro eu gerava em MG, quando havia diferença de alíquota (Famoso DIFAL de hoje), como o SPED FISCAL é exclusivo das UF's, então MG, criou há muito tempo a tabela de códigos para essa situação, como não faço mais O sped para o cliente de MG há muito tempo, então não sei como está e como será em relação ao campo cBenef do layout da NF-e 4.0.
Sei que algumas UF's havia divulgado as suas tabelas para isso, mas SP, até o tempo que eu gerava SPED's para os meus clientes não tinha.
O resultado deste registro é informado na apuração.
[]s,
Luto no grupo
in Programação
Posted
Bela atitude Valdir, melhor a gente realmente ir divulgando. No meu caso, sou meio eclético. Indústria de confecções, varejo de confecções, varejo produtos de limpeza, indústria de pranchas de surf, distribuições de vacinas humanas, e varejo em geral. Sobre os locais de atuação: São Paulo, capital e interior, Belo Horizonte, Goiânia e Salvador.