Skip to content

Instantly share code, notes, and snippets.

@arantesxyz
Last active June 18, 2025 22:26
Show Gist options
  • Select an option

  • Save arantesxyz/b78f00ac3589f93deeefa331e1f1fdb3 to your computer and use it in GitHub Desktop.

Select an option

Save arantesxyz/b78f00ac3589f93deeefa331e1f1fdb3 to your computer and use it in GitHub Desktop.
BCB PIX End To End Identification Generation in Golang.
package helpers
import (
"fmt"
"math/rand"
"time"
"unsafe"
)
const letterBytes = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ123456789"
const (
letterIdxBits = 6
letterIdxMask = 1<<letterIdxBits - 1
letterIdxMax = 63 / letterIdxBits
)
var src = rand.NewSource(time.Now().UnixNano())
// Receive a transaction type and ISPB and returns a 32 characters string.
// TransactionType should contain a single character.
// ISPB should be 8 characters.
func GenerateE2E(transactionType string, ispb string) (string) {
location := time.FixedZone("GMT-3", -3*60*60)
date := time.Now().In(location).Format("200601021504")
randString := randString(11)
return fmt.Sprintf("%s%s%s%s", transactionType, ispb, date, randString)
}
func randString(n int) string {
b := make([]byte, n)
for i, cache, remain := n-1, src.Int63(), letterIdxMax; i >= 0; {
if remain == 0 {
cache, remain = src.Int63(), letterIdxMax
}
if idx := int(cache & letterIdxMask); idx < len(letterBytes) {
b[i] = letterBytes[idx]
i--
}
cache >>= letterIdxBits
remain--
}
return *(*string)(unsafe.Pointer(&b))
}
@arantesxyz
Copy link
Author

arantesxyz commented Feb 8, 2024

PACS.008 <EndToEndId> description:

"Deve ser preenchido no formato padrão ExxxxxxxxyyyyMMddHHmmkkkkkkkkkkk (32 caracteres; “case sensitive”, isso é, diferencia letras maiúsculas e minúsculas), sendo:
•  “E” – fixo (1 caractere); 
• xxxxxxxx – identificação do agente que gerou o <EndToEndId>, podendo ser: o ISPB do participante direto, o ISPB do participante indireto ou os 8 primeiros dígitos do CNPJ do prestador de serviço de iniciação (8 caracteres numéricos [0-9]);
• yyyyMMddHHmm – data, hora e minuto (12 caracteres), seguindo o horário UTC, sendo: 
      • o momento de submissão da ordem de pagamento ao SPI, caso a liquidação seja prioritária, ou
      • o momento previsto para o envio da ordem ao SPI, caso seja realizado um agendamento, ou
      • conforme orientações contidas nos documentos que formalizam a convenção sobre padrões tecnológicos e procedimentos operacionais do Open Finance Brasil, caso a ordem de pagamento prioritária seja iniciada por meio do serviço de iniciação de transação de pagamento no Open Finance. 
(Obs.: em todos os casos, aceita-se o <EndToEndId> com uma tolerância máxima de 12 horas, para o futuro ou para o passado, em relação ao horário de efetivo processamento da ordem pelo SPI)

• kkkkkkkkkkk – sequencial criado pelo agente que gerou o <EndToEndId>  (11 caracteres alfanuméricos [a-z|A-Z|0-9]). Deve ser único dentro de cada “yyyyMMddHHmm”.
                               
No caso de iniciação de um Pix por meio de serviço de iniciação de transação de pagamento, o <EndToEndId> deve ser gerado pelo prestador de serviço de iniciação. Caso contrário, deve ser gerado pelo participante direto ou pelo participante indireto. Ele deve ser único, não podendo ser repetido em qualquer outra operação enviada ao SPI. "

Sendo que o primeiro caractere E pode ser substituído por D na PACS.004 no campo <RtrId>

Fonte: https://www.bcb.gov.br/estabilidadefinanceira/comunicacaodados

@arantesxyz
Copy link
Author

As mesmas instruções podem ser utilizadas para gerar o MessageIdentification MsgId, apenas a data e hora não são obrigatórios, mas não fazem diferença, BCB só irá validar se é único.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment