Communication structurée européenne

Bonjour,
Comment mettre en place la (communication structurée européenne) et autres pays avec dolibarr ?
Comment Générer une communication structurée avec dolibarr ?
Comment générer une communication structurée belge en dolibarr ?
Comment Générer la communication structurée avec dolibarr ?
Comment générer la communication structurée belge en dolibarr ?
Comment générer la communication structurée belge avec dolibarr ?
Indiquer la communication structuré en dolibarr ?
Mettre en place la communication structuré dolibarr ?
Mettre en place une communication structuré européen avec dolibarr ?
Mettre en place une communication structuré belge en dolibarr ?

Pour simplifier la traçabilité et retracer une facture en Belgique et Europe nous devons indiquer la (communication structuré) sur les virements, qui est représenter en 12 chiffres, comme suivant +++123/1234/12345+++

Bonjour,
Un peu répétitif comme post !
Vous souhaitez avoir des numéro de pièces sur le format 000/0000/00000 mais que doit représenter chaque chiffre ?
Le millésime de l’année ? le n° du client ?
Si il y a un format officiel, la communauté vous sera reconnaissante de fournir la source officielle mais pas que je sache.
@+

Bonjour,

Voici l’explication de la communication structurée. Je suis moi aussi intéressé.

Une communication structurée comporte 12 positions numériques : 10 positions significatives et 2 positions de contrôle (les deux dernières). Elle est divisée en 3 séquences séparées par des slash : 123/1234/12345

Comme pour l’algorithme de vérification des codes bancaires belges, les 2 chiffres de contrôle se basent sur le principe du modulo 97 des 10 premiers chiffres, le résultat de l’opération donnant les deux derniers chiffres.

Voici comment procéder pour trouver ces deux chiffres. Imaginons que les dix premiers chiffres soient les suivants : 1013274810

Divisons ce nombre par 97. On obtient un nombre dont on ne garde que la partie entière, avant la virgule : 10446132
Multiplions ce résultat par 97 : 1013274804
Soustrayons enfin ce nombre du nombre de départ 1013274810-1013274804.
On obtient 6 qu’il suffit de coder sur deux positions, soit 06

Bonjour,

Voici un logiciel pour faire de la communication structurée

Cordialement,

XP

Salut Xavier et merci pour le lien.
En fait je ne comprend pas bien l’intérêt de la chose. Juste un masque de numérotation particulier ?
A quoi ce « numéro » va servir en particulier, j’avoue avoir déjà aperçu mais je ne me suis pas posé la question.
@+

Avec ce numéro la banque peu savoir le nom de la société, la date et le numéro de facture ainsi que son montant.

Bon, c’est vieux… mais vous pourriez tomber dessus à la recherche d’une réponse.
Sans garantie aucune — mais je m’en sert depuis quelques années, voici ce que j’ai fait :
:warning: Garder le code sous la main ⇒ Il est écrasé à chaque mise à jour.

Pour ajouter la communication structurée (belge) dans les factures

Dans le document .php qui génère la facture (ex. htdocs/core/modules/facture/doc/pdf_crabe.php.
Perso., je l’ai mis — logiquement — dans les informations de paiement SI virement, donc
Cherchez les lignes

if (empty($object->mode_reglement_code) || $object->mode_reglement_code == 'VIR')
{
    if (! empty($object->mode_reglement_code) || ! empty($object->fk_bank) || ! empty($conf->global->FACTURE_RIB_NUMBER))
    {

et remplacer la ligne

$pdf->MultiCell(100,3, 'Communication:' . $outputlangs->convToOutputCharset($object->ref),0, 'L', 0);

par le code suivant :

//NIMAL 2018-09-22
switch (substr($object->ref,0,2))
                                  {
                                      case "FA":
                                          $n_type_code = '20'; //code des factures
                                          break;
                                      case "AC":
                                          $n_type_code = '21'; //code des acomptes
                                          break;
                                      case "FR":
                                          $n_type_code = '30'; //code des factures de remplacement
                                          break;
                                      case "NC":
                                          $n_type_code = '40'; //code des notes de crédit
                                          break;
                                      default:
                                          $n_type_code = '00';
                                  }
                                  $n_code = substr($object->ref,2,strlen($object->ref) - 2); //reprend la partie numérique de la référence du documment
                                  $n_code = explode("-",$n_code);                            //sépare la partie date de la séquence
                                  $n_size = strlen($n_code[0]) + strlen($n_code[1]);         //si je n’ai pas 8 caractères, j’ajoute des 0 à la séquence
                                  if ($n_size > 8)
                                  {
                                      $n_code[1] = substr($n_code[1],-($n_size-8));
                                  }
                                  $n_base = (float)($n_type_code . $n_code[0] . $n_code[1]); // calcul de la somme de controle
                                  $n_control = $n_base - floor($n_base / 97) * 97;
                                  if ($n_control == 0)
                                      $n_control = 97;
                                  $n_base_s = (string) $n_base;                              //repasse tout en string
                                  $n_control_s = (string) $n_control;                        //vérifie que la somme de controle est sur 2 caractères
                                  if ($control < 10)
                                      $control_s = "0" . $n_control_s;

                                  $n_count = 10 - strlen($n_base_s);                         //vérifie qu’on a 10 caractère pour la base
                                  for ($i=0; $i < $count; $i++)
                                  {
                                      $n_base_s = "0" . $n_base_s;
                                  }
                                  $n_com = $n_base_s . $n_control_s;                        //formatage
                                  $n_com = "+++" . substr($n_com,0,3) . "/" . substr($n_com,3,4) . "/" . substr($n_com,-5) . "+++";
                                  //affichage
                                  $dpf->MultiCell(100,3,'Communiaction: ' . $outputlangs->convToOutputCharset($n_com,0,'L',0);
                                  $posy+=2;

C’est la même chose pour les autres documents (AC, NC, …) le Switch… case «  » au début du code donne un nombre différent en fonction du type de document… vous pouvez naturellement changer ces valeurs ou les adapter à votre configuration.

Pour ajouter dans les mails __FACCOM_STRCT__ qui représente la communication structurée

Il y en a un peu plus, je vous le mets…
Les premières entrées⁽*⁾ n’ont rien à voir, mais permettent de mettre les infos élémentaires dans un mail également.
* ces éléments ne sont pas de moi, mais — mea culpa — je ne me souviens plus de l’auteur pour lui rendre hommage. Navré.
Edit : J’ai retrouvé. C’était Philazerty dans ce post. Merci à lui !

Dans le fichier htdocs/core/lib/functions.lib.php, ajouter dans la fonction getCommonSubstitutionArray(…)
vers la fin, avant le TODO foreign multicurrency et _TOTAL_TTC_ (vers la ligne 7000)

                  //NIMAL 2018-09-22
                  $substitutionarray['__FACDATE__']        = is_object($object)?(isset($object->date) ? dol_print_date($object->date, 'daytext', 0, $outputlangs) : '') : '';
                  $substitutionarray['__FACDATELIMREG__']        = is_object($object)?(isset($object->date) ? dol_print_date($object->date_lim_reglement, 'daytext', 0, $outputlangs) : '') : '';
                  $substitutionarray['__FACTOTALTTC_2D__'] = is_object($object)?number_format($object->total_ttc,2,',',' '):'';
                  $substitutionarray['__FACTOTALHT_2D__'] = is_object($object)?number_format($object->total_ht,2,',',' '):'';
                  $substitutionarray['__FACPAYE_2D__'] = is_object($object)?number_format($object->totalpaye,2,',',' '):'';
                  $substitutionarray['__FACREST_2D__'] = is_object($object)?number_format($object->total_ttc - $object->totalpaye,2,',',' '):'';
                  /**************************************************/
                                  // COMMUNICATION STRUCTURÉE:
                                  // <codeDoc><reference Doc><modulo 97>
                                  switch (substr($object->ref,0,2))
                                  {
                                      case "FA":
                                          $n_type_code = '20'; //code des factures
                                          break;
                                      case "AC":
                                          $n_type_code = '21'; //code des acomptes
                                          break;
                                      case "FR":
                                          $n_type_code = '30'; //code des factures de remplacement
                                          break;
                                      case "NC":
                                          $n_type_code = '40'; //code des notes de crédit
                                          break;
                                      default:
                                          $n_type_code = '00';
                                  }
                                  $n_code = substr($object->ref,2,strlen($object->ref) - 2); //reprend la partie numérique de la référence du documment
                                  $n_code = explode("-",$n_code);                            //sépare la partie date de la séquence
                                  $n_size = strlen($n_code[0]) + strlen($n_code[1]);         //si je n’ai pas 8 caractères, j’ajoute des 0 à la séquence
                                  if ($n_size > 8)
                                  {
                                      $n_code[1] = substr($n_code[1],-($n_size-8));
                                  }
                                  $n_base = (float)($n_type_code . $n_code[0] . $n_code[1]); // calcul de la somme de controle
                                  $n_control = $n_base - floor($n_base / 97) * 97;
                                  if ($n_control == 0)
                                      $n_control = 97;
                                  $n_base_s = (string) $n_base;                              //repasse tout en string
                                  $n_control_s = (string) $n_control;                        //vérifie que la somme de controle est sur 2 caractères
                                  if ($control < 10)
                                      $control_s = "0" . $n_control_s;

                                  $n_count = 10 - strlen($n_base_s);                         //vérifie qu’on a 10 caractère pour la base
                                  for ($i=0; $i < $count; $i++)
                                  {
                                      $n_base_s = "0" . $n_base_s;
                                  }
                                  $n_com = $n_base_s . $n_control_s;                        //formatage
                                  $n_com = "+++" . substr($n_com,0,3) . "/" . substr($n_com,3,4) . "/" . substr($n_com,-5) . "+++";
                                  $substitutionarray['__FACCOM_STRCT__'] = $n_com;

                  //END NIMAL
3 « J'aime »

Bonjour @GNL,

j’ai essayé d’intégrer votre code dans la version 16 de Dolibarr. Mais à chaque fois que je mets cette ligne dans le code. Le modèle crabe disparait de l’administration des modules

 $pdf->MultiCell(100,3,'Communiaction: ' . $outputlangs->convToOutputCharset($n_com,0,'L',0);

auriez-vous quelques conseils ou une version plus récente?

Drari

Salut les enfants,

Ne serait-il pas possible de l’inclure dans dolibarr ? un petit github ?

Car j’avoue que ça m’intéresse aussi.

Egalement à la recherche d’un module pour les communications structurées.
Ce serait bien de le voir apparaitre dans une des prochaines mises à jour.

Pierre

2 « J'aime »

Je serais également intéressé.

Bonjour à tous,

voici ma contribution quand à ce sujet qui touche principalement les Belges :wink:

J’ai solutionné ce problème en créant une fonction BuildCommStruct($numerofacture) que j’ai inclus dans le fichier htdocs/core/lib/function.lib.php.

voici le script utilisé:

/**
 * Génère une communication structurée au format belge avec contrôle modulo 97.
 * Le format final est +++XXX/XXXX/XXXXX+++.
 *
 * @param string $numeroFacture Le numéro de facture, qui doit contenir au moins 8 chiffres.
 * @return string La communication structurée au format "XXX/XXXX/XXXXX" avec contrôle modulo 97.
 * si le numéro de facture compte moins de 8 chiffres ajoute des 0 à la fin (surtout pour les factures en état "PROV".
 */

function BuildCommStruct($numeroFacture) {


 
    // Extraire uniquement les chiffres du numéro de facture
    $chiffres = preg_replace('/\D/', '', $numeroFacture);

    // Vérifier que le numéro contient au moins 8 chiffres
  /*  if (strlen($chiffres) < 8) {
        throw new Exception("Le numéro de facture doit contenir au moins 8 chiffres.");
    }
*/
    // On prend les 8 derniers chiffres du numéro pour générer la base de la référence
    $baseReference = substr('00000000'.$chiffres, -8);

    // Préfixer avec '20' pour avoir la base de la référence
    $numeroSansControle = '20' . $baseReference;

    // Calculer le chiffre de contrôle modulo 97
    $mod97 = intval($numeroSansControle) % 97;

    // Si le modulo est 0, on considère qu'il vaut 97
    $chiffreControle = ($mod97 === 0) ? 97 : $mod97;

    // Ajouter le chiffre de contrôle à la fin de la référence
    $referenceComplete = $numeroSansControle . str_pad($chiffreControle, 2, '0', STR_PAD_LEFT);

    // Formater la référence en XXX/XXXX/XXXXX
    $part1 = '+++'.substr($referenceComplete, 0, 3);
    $part2 = substr($referenceComplete, 3, 4);
    $part3 = substr($referenceComplete, 7, 5).'+++'; // Inclut les 3 derniers chiffres + les 2 chiffres de contrôle

    return "$part1/$part2/$part3";

}

Ensuite vous devez créer un extra champs personnalisé comme montré dans l’image suivante:

Et finalement vous retrouvez votre communication structurée dans votre facture

update pour l’ajouter à votre Facture PDF, dans mon cas je passe le numéro de facture (REF) dans la fonction qui génère le numéro structuré mais bien entendu vous êtes libre de mettre une autre référence

il faut ajouter les lignes suivante après le check du mode de paiement ‹ VIR › comme l’avait mentionné @GNL le fichier pdf_crabe_module.php:

			if (empty($object->mode_reglement_code) || $object->mode_reglement_code == 'VIR') {
				if ($object->fk_account > 0 || $object->fk_bank > 0 || getDolGlobalInt('FACTURE_RIB_NUMBER')) {
					$bankid = ($object->fk_account <= 0 ? $conf->global->FACTURE_RIB_NUMBER : $object->fk_account);
					if ($object->fk_bank > 0) {
						$bankid = $object->fk_bank; // For backward compatibility when object->fk_account is forced with object->fk_bank
					}
	**/**Lignes à ajouter pour inclure la communication structurée dans le bas de la facture**/**
**				    include_once DOL_DOCUMENT_ROOT.'/core/lib/functions.lib.php';**
**					$pdf->MultiCell(100,3, 'Communication:' . $outputlangs->convToOutputCharset(BuildCommStruct($object->ref)),0, 'L', 0);**

Bonne soirée à tous

3 « J'aime »

Bonjour et merci @drari
Il y a des chances pour je j’intègre la comm structurée dans mon module Rubis.
Merci pour ton travail :wink:
@+

1 « J'aime »

ce serait effectivemment une excellente nouvelle :wink:
Tout le monde l’attend tel le messi

Avec plaisir j’ai tellement galéré dessus que j’ai bloqué ma journée à chercher une solution et c’est pas fini

1 « J'aime »

Bonjour,

Je découvre ce besoin. Je ne savais pas que cela existait.

Une question, une fois la communication structurée générée pour une facture, est ce que ce numéro doit être précisé pour le prélèvement SEPA d’une facture afin qu’il apparaisse sur l’extrait bancaire ?

J’ai trouvé cette information sur le format SEPA, il existe un champ facultatif « Structuré » ( dans documents ci-dessous). Je ne sais pas si cela correspond au besoin. A priori, si disponible, le numéro structuré vient remplacer le champ non structuré utilisé par le France, l’Allemagne et les Pays Bas qui utilise simplement le numéro de la facture…

image

Documentation format SEPA - Oracle

ou si cela est plus clair ici :
Echange format SEPA - Microsoft

Merci par avance du retour

1 « J'aime »

Bien vu @aspangaro-Inovea Alex,
Il faut aussi réfléchir à la facture électronique dans ce cas.
Pourquoi ne pas mettre en place une numérotation "structurée " dans Dolibarr dans ce cas ?
@+

1 « J'aime »

Merci @Philazerty :kissing:

Je t’avoue ne pas voir le lien avec la facture électronique sauf si le fichier XML contient les informations de paiements…

Mais oui, en l’état, c’est intégrable dans le core à mon sens. Vite, il reste 15 jours pour la v21 !

Pour les domiciliations, ça dépend du fournisseur par exemple à la sécurité sociale ou la TVA nous avons un numéro structuré unique par « Client » donc on pourrait le mettre sans problème dans une domiciliation mais si celui-ci change à chaque facture, on pourrait effectivement le mettre mais ce n’est pas obligatoire (une référence suffit)

C’est le cas en Belgique, la communication structurée est envoyée dans le fichier XML et un champs à part entière dans le formulaire de création d’une facture électronique (sur Mercurius par exemple Le Chorus Belge)

Bonjour,

On va faire dans l’ordre, avant de s’occuper du côté facture électronique / module prélèvement, on va déjà afficher la communication structurée sur le pdf.

J’ai retravaillé le code communiqué ci-dessus.
Faut-il afficher la communication structurée ailleurs que sur les pdf des factures ?

P.S. : Pour les crédits sur le code, merci de communiquer un nom/prénom + email.

1 « J'aime »