ソースを参照

Initialisation

Mathieu Moulin 2 年 前
コミット
c4a7228601
51 ファイル変更3176 行追加0 行削除
  1. 24 0
      .editorconfig
  2. 23 0
      .gitattributes
  3. 621 0
      COPYING
  4. 5 0
      ChangeLog.md
  5. 86 0
      README.md
  6. 45 0
      accepted.php
  7. 29 0
      admin/about.php
  8. 53 0
      admin/setup.php
  9. 11 0
      build/makepack-mbietransactions.conf
  10. 44 0
      canceled.php
  11. 348 0
      class/actions_mbietransactions.class.php
  12. 369 0
      class/mmi_etransactions.class.php
  13. 166 0
      core/modules/modMBIETransactions.class.php
  14. 132 0
      core/triggers/interface_99_modMBIETransactions_ETransactionsSendMail.class.php
  15. 3 0
      env.inc.php
  16. 30 0
      gd/index.php
  17. BIN
      gd/png/Y6m6si8Pyrw1V7Ol4EM59NQK0e6mfUzX.png
  18. 0 0
      gd/png/wheregoesimg.txt
  19. BIN
      img/American-Express-Logo.png
  20. BIN
      img/amex.png
  21. BIN
      img/ca-e-transactions-bis-400px.png
  22. BIN
      img/ca-e-transactions-bis.png
  23. BIN
      img/ca-e-transactions-cb-visa-mastercard.jpg
  24. BIN
      img/ca-e-transactions-cb-visa-mastercard.png
  25. BIN
      img/ca-e-transactions-cb-visa-mastercard.png23688
  26. BIN
      img/ca-e-transactions.png
  27. BIN
      img/cb-visa-mastercard-paylib.png
  28. BIN
      img/cb-visa-mastercard-paypal-paylib-amex.png
  29. BIN
      img/cb-visa-mastercard.png
  30. BIN
      img/cb.png
  31. BIN
      img/e-transactions-transparent.png
  32. BIN
      img/object_logo.png
  33. BIN
      img/object_mmiprestasync.png
  34. BIN
      img/paylib.png
  35. BIN
      img/paypal-logo.png
  36. BIN
      img/paypal.png
  37. 103 0
      langs/en_US/mbietransactions.lang
  38. 116 0
      langs/fr_FR/mbietransactions.lang
  39. 57 0
      lib/create_link.lib.php
  40. 38 0
      lib/mbietransactions.lib.php
  41. 38 0
      main_load.inc.php
  42. 3 0
      modulebuilder.txt
  43. 52 0
      payment.css
  44. 331 0
      payment.php
  45. 45 0
      refused.php
  46. 222 0
      retour.php
  47. 19 0
      sql/llx_mbi_etransactions_hash.sql
  48. 22 0
      sql/llx_mbi_etransactions_return.sql
  49. 24 0
      sql/llx_paiement_extrafields.sql
  50. 28 0
      sql/llx_paiement_object.sql
  51. 89 0
      style.css

+ 24 - 0
.editorconfig

@@ -0,0 +1,24 @@
+# EditorConfig is awesome: http://EditorConfig.org
+
+# top-most EditorConfig file
+root = true
+
+# Unix-style newlines with a newline ending every file
+[*]
+charset = utf-8
+end_of_line = lf
+insert_final_newline = true
+
+[*.php]
+indent_style = tab
+indent_size = 4
+trim_trailing_whitespace = true
+insert_final_newline = true
+[*.js]
+indent_style = tab
+[*.css]
+indent_style = tab
+[*.xml]
+indent_style = tab
+[*.md]
+trim_trailing_whitespace = false

+ 23 - 0
.gitattributes

@@ -0,0 +1,23 @@
+# Set default behaviour, in case users don't have core.autocrlf set.
+* text=auto
+
+
+# Explicitly declare text files we want to always be normalized and converted 
+# to native line endings on checkout.
+*.php text eol=lf
+*.sql text eol=lf
+*.htm text eol=lf
+*.html text eol=lf
+*.js text eol=lf
+*.css text eol=lf
+*.lang text eol=lf
+*.txt text eol=lf
+*.md text eol=lf
+*.bat text eol=lf
+
+# Denote all files that are truly binary and should not be modified.
+*.ico binary
+*.png binary
+*.jpg binary
+*.odt binary
+*.odf binary

+ 621 - 0
COPYING

@@ -0,0 +1,621 @@
+                    GNU GENERAL PUBLIC LICENSE
+                       Version 3, 29 June 2007
+
+ Copyright (C) 2007 Free Software Foundation, Inc. <http://fsf.org/>
+ Everyone is permitted to copy and distribute verbatim copies
+ of this license document, but changing it is not allowed.
+
+                            Preamble
+
+  The GNU General Public License is a free, copyleft license for
+software and other kinds of works.
+
+  The licenses for most software and other practical works are designed
+to take away your freedom to share and change the works.  By contrast,
+the GNU General Public License is intended to guarantee your freedom to
+share and change all versions of a program--to make sure it remains free
+software for all its users.  We, the Free Software Foundation, use the
+GNU General Public License for most of our software; it applies also to
+any other work released this way by its authors.  You can apply it to
+your programs, too.
+
+  When we speak of free software, we are referring to freedom, not
+price.  Our General Public Licenses are designed to make sure that you
+have the freedom to distribute copies of free software (and charge for
+them if you wish), that you receive source code or can get it if you
+want it, that you can change the software or use pieces of it in new
+free programs, and that you know you can do these things.
+
+  To protect your rights, we need to prevent others from denying you
+these rights or asking you to surrender the rights.  Therefore, you have
+certain responsibilities if you distribute copies of the software, or if
+you modify it: responsibilities to respect the freedom of others.
+
+  For example, if you distribute copies of such a program, whether
+gratis or for a fee, you must pass on to the recipients the same
+freedoms that you received.  You must make sure that they, too, receive
+or can get the source code.  And you must show them these terms so they
+know their rights.
+
+  Developers that use the GNU GPL protect your rights with two steps:
+(1) assert copyright on the software, and (2) offer you this License
+giving you legal permission to copy, distribute and/or modify it.
+
+  For the developers' and authors' protection, the GPL clearly explains
+that there is no warranty for this free software.  For both users' and
+authors' sake, the GPL requires that modified versions be marked as
+changed, so that their problems will not be attributed erroneously to
+authors of previous versions.
+
+  Some devices are designed to deny users access to install or run
+modified versions of the software inside them, although the manufacturer
+can do so.  This is fundamentally incompatible with the aim of
+protecting users' freedom to change the software.  The systematic
+pattern of such abuse occurs in the area of products for individuals to
+use, which is precisely where it is most unacceptable.  Therefore, we
+have designed this version of the GPL to prohibit the practice for those
+products.  If such problems arise substantially in other domains, we
+stand ready to extend this provision to those domains in future versions
+of the GPL, as needed to protect the freedom of users.
+
+  Finally, every program is threatened constantly by software patents.
+States should not allow patents to restrict development and use of
+software on general-purpose computers, but in those that do, we wish to
+avoid the special danger that patents applied to a free program could
+make it effectively proprietary.  To prevent this, the GPL assures that
+patents cannot be used to render the program non-free.
+
+  The precise terms and conditions for copying, distribution and
+modification follow.
+
+                       TERMS AND CONDITIONS
+
+  0. Definitions.
+
+  "This License" refers to version 3 of the GNU General Public License.
+
+  "Copyright" also means copyright-like laws that apply to other kinds of
+works, such as semiconductor masks.
+
+  "The Program" refers to any copyrightable work licensed under this
+License.  Each licensee is addressed as "you".  "Licensees" and
+"recipients" may be individuals or organizations.
+
+  To "modify" a work means to copy from or adapt all or part of the work
+in a fashion requiring copyright permission, other than the making of an
+exact copy.  The resulting work is called a "modified version" of the
+earlier work or a work "based on" the earlier work.
+
+  A "covered work" means either the unmodified Program or a work based
+on the Program.
+
+  To "propagate" a work means to do anything with it that, without
+permission, would make you directly or secondarily liable for
+infringement under applicable copyright law, except executing it on a
+computer or modifying a private copy.  Propagation includes copying,
+distribution (with or without modification), making available to the
+public, and in some countries other activities as well.
+
+  To "convey" a work means any kind of propagation that enables other
+parties to make or receive copies.  Mere interaction with a user through
+a computer network, with no transfer of a copy, is not conveying.
+
+  An interactive user interface displays "Appropriate Legal Notices"
+to the extent that it includes a convenient and prominently visible
+feature that (1) displays an appropriate copyright notice, and (2)
+tells the user that there is no warranty for the work (except to the
+extent that warranties are provided), that licensees may convey the
+work under this License, and how to view a copy of this License.  If
+the interface presents a list of user commands or options, such as a
+menu, a prominent item in the list meets this criterion.
+
+  1. Source Code.
+
+  The "source code" for a work means the preferred form of the work
+for making modifications to it.  "Object code" means any non-source
+form of a work.
+
+  A "Standard Interface" means an interface that either is an official
+standard defined by a recognized standards body, or, in the case of
+interfaces specified for a particular programming language, one that
+is widely used among developers working in that language.
+
+  The "System Libraries" of an executable work include anything, other
+than the work as a whole, that (a) is included in the normal form of
+packaging a Major Component, but which is not part of that Major
+Component, and (b) serves only to enable use of the work with that
+Major Component, or to implement a Standard Interface for which an
+implementation is available to the public in source code form.  A
+"Major Component", in this context, means a major essential component
+(kernel, window system, and so on) of the specific operating system
+(if any) on which the executable work runs, or a compiler used to
+produce the work, or an object code interpreter used to run it.
+
+  The "Corresponding Source" for a work in object code form means all
+the source code needed to generate, install, and (for an executable
+work) run the object code and to modify the work, including scripts to
+control those activities.  However, it does not include the work's
+System Libraries, or general-purpose tools or generally available free
+programs which are used unmodified in performing those activities but
+which are not part of the work.  For example, Corresponding Source
+includes interface definition files associated with source files for
+the work, and the source code for shared libraries and dynamically
+linked subprograms that the work is specifically designed to require,
+such as by intimate data communication or control flow between those
+subprograms and other parts of the work.
+
+  The Corresponding Source need not include anything that users
+can regenerate automatically from other parts of the Corresponding
+Source.
+
+  The Corresponding Source for a work in source code form is that
+same work.
+
+  2. Basic Permissions.
+
+  All rights granted under this License are granted for the term of
+copyright on the Program, and are irrevocable provided the stated
+conditions are met.  This License explicitly affirms your unlimited
+permission to run the unmodified Program.  The output from running a
+covered work is covered by this License only if the output, given its
+content, constitutes a covered work.  This License acknowledges your
+rights of fair use or other equivalent, as provided by copyright law.
+
+  You may make, run and propagate covered works that you do not
+convey, without conditions so long as your license otherwise remains
+in force.  You may convey covered works to others for the sole purpose
+of having them make modifications exclusively for you, or provide you
+with facilities for running those works, provided that you comply with
+the terms of this License in conveying all material for which you do
+not control copyright.  Those thus making or running the covered works
+for you must do so exclusively on your behalf, under your direction
+and control, on terms that prohibit them from making any copies of
+your copyrighted material outside their relationship with you.
+
+  Conveying under any other circumstances is permitted solely under
+the conditions stated below.  Sublicensing is not allowed; section 10
+makes it unnecessary.
+
+  3. Protecting Users' Legal Rights From Anti-Circumvention Law.
+
+  No covered work shall be deemed part of an effective technological
+measure under any applicable law fulfilling obligations under article
+11 of the WIPO copyright treaty adopted on 20 December 1996, or
+similar laws prohibiting or restricting circumvention of such
+measures.
+
+  When you convey a covered work, you waive any legal power to forbid
+circumvention of technological measures to the extent such circumvention
+is effected by exercising rights under this License with respect to
+the covered work, and you disclaim any intention to limit operation or
+modification of the work as a means of enforcing, against the work's
+users, your or third parties' legal rights to forbid circumvention of
+technological measures.
+
+  4. Conveying Verbatim Copies.
+
+  You may convey verbatim copies of the Program's source code as you
+receive it, in any medium, provided that you conspicuously and
+appropriately publish on each copy an appropriate copyright notice;
+keep intact all notices stating that this License and any
+non-permissive terms added in accord with section 7 apply to the code;
+keep intact all notices of the absence of any warranty; and give all
+recipients a copy of this License along with the Program.
+
+  You may charge any price or no price for each copy that you convey,
+and you may offer support or warranty protection for a fee.
+
+  5. Conveying Modified Source Versions.
+
+  You may convey a work based on the Program, or the modifications to
+produce it from the Program, in the form of source code under the
+terms of section 4, provided that you also meet all of these conditions:
+
+    a) The work must carry prominent notices stating that you modified
+    it, and giving a relevant date.
+
+    b) The work must carry prominent notices stating that it is
+    released under this License and any conditions added under section
+    7.  This requirement modifies the requirement in section 4 to
+    "keep intact all notices".
+
+    c) You must license the entire work, as a whole, under this
+    License to anyone who comes into possession of a copy.  This
+    License will therefore apply, along with any applicable section 7
+    additional terms, to the whole of the work, and all its parts,
+    regardless of how they are packaged.  This License gives no
+    permission to license the work in any other way, but it does not
+    invalidate such permission if you have separately received it.
+
+    d) If the work has interactive user interfaces, each must display
+    Appropriate Legal Notices; however, if the Program has interactive
+    interfaces that do not display Appropriate Legal Notices, your
+    work need not make them do so.
+
+  A compilation of a covered work with other separate and independent
+works, which are not by their nature extensions of the covered work,
+and which are not combined with it such as to form a larger program,
+in or on a volume of a storage or distribution medium, is called an
+"aggregate" if the compilation and its resulting copyright are not
+used to limit the access or legal rights of the compilation's users
+beyond what the individual works permit.  Inclusion of a covered work
+in an aggregate does not cause this License to apply to the other
+parts of the aggregate.
+
+  6. Conveying Non-Source Forms.
+
+  You may convey a covered work in object code form under the terms
+of sections 4 and 5, provided that you also convey the
+machine-readable Corresponding Source under the terms of this License,
+in one of these ways:
+
+    a) Convey the object code in, or embodied in, a physical product
+    (including a physical distribution medium), accompanied by the
+    Corresponding Source fixed on a durable physical medium
+    customarily used for software interchange.
+
+    b) Convey the object code in, or embodied in, a physical product
+    (including a physical distribution medium), accompanied by a
+    written offer, valid for at least three years and valid for as
+    long as you offer spare parts or customer support for that product
+    model, to give anyone who possesses the object code either (1) a
+    copy of the Corresponding Source for all the software in the
+    product that is covered by this License, on a durable physical
+    medium customarily used for software interchange, for a price no
+    more than your reasonable cost of physically performing this
+    conveying of source, or (2) access to copy the
+    Corresponding Source from a network server at no charge.
+
+    c) Convey individual copies of the object code with a copy of the
+    written offer to provide the Corresponding Source.  This
+    alternative is allowed only occasionally and noncommercially, and
+    only if you received the object code with such an offer, in accord
+    with subsection 6b.
+
+    d) Convey the object code by offering access from a designated
+    place (gratis or for a charge), and offer equivalent access to the
+    Corresponding Source in the same way through the same place at no
+    further charge.  You need not require recipients to copy the
+    Corresponding Source along with the object code.  If the place to
+    copy the object code is a network server, the Corresponding Source
+    may be on a different server (operated by you or a third party)
+    that supports equivalent copying facilities, provided you maintain
+    clear directions next to the object code saying where to find the
+    Corresponding Source.  Regardless of what server hosts the
+    Corresponding Source, you remain obligated to ensure that it is
+    available for as long as needed to satisfy these requirements.
+
+    e) Convey the object code using peer-to-peer transmission, provided
+    you inform other peers where the object code and Corresponding
+    Source of the work are being offered to the general public at no
+    charge under subsection 6d.
+
+  A separable portion of the object code, whose source code is excluded
+from the Corresponding Source as a System Library, need not be
+included in conveying the object code work.
+
+  A "User Product" is either (1) a "consumer product", which means any
+tangible personal property which is normally used for personal, family,
+or household purposes, or (2) anything designed or sold for incorporation
+into a dwelling.  In determining whether a product is a consumer product,
+doubtful cases shall be resolved in favor of coverage.  For a particular
+product received by a particular user, "normally used" refers to a
+typical or common use of that class of product, regardless of the status
+of the particular user or of the way in which the particular user
+actually uses, or expects or is expected to use, the product.  A product
+is a consumer product regardless of whether the product has substantial
+commercial, industrial or non-consumer uses, unless such uses represent
+the only significant mode of use of the product.
+
+  "Installation Information" for a User Product means any methods,
+procedures, authorization keys, or other information required to install
+and execute modified versions of a covered work in that User Product from
+a modified version of its Corresponding Source.  The information must
+suffice to ensure that the continued functioning of the modified object
+code is in no case prevented or interfered with solely because
+modification has been made.
+
+  If you convey an object code work under this section in, or with, or
+specifically for use in, a User Product, and the conveying occurs as
+part of a transaction in which the right of possession and use of the
+User Product is transferred to the recipient in perpetuity or for a
+fixed term (regardless of how the transaction is characterized), the
+Corresponding Source conveyed under this section must be accompanied
+by the Installation Information.  But this requirement does not apply
+if neither you nor any third party retains the ability to install
+modified object code on the User Product (for example, the work has
+been installed in ROM).
+
+  The requirement to provide Installation Information does not include a
+requirement to continue to provide support service, warranty, or updates
+for a work that has been modified or installed by the recipient, or for
+the User Product in which it has been modified or installed.  Access to a
+network may be denied when the modification itself materially and
+adversely affects the operation of the network or violates the rules and
+protocols for communication across the network.
+
+  Corresponding Source conveyed, and Installation Information provided,
+in accord with this section must be in a format that is publicly
+documented (and with an implementation available to the public in
+source code form), and must require no special password or key for
+unpacking, reading or copying.
+
+  7. Additional Terms.
+
+  "Additional permissions" are terms that supplement the terms of this
+License by making exceptions from one or more of its conditions.
+Additional permissions that are applicable to the entire Program shall
+be treated as though they were included in this License, to the extent
+that they are valid under applicable law.  If additional permissions
+apply only to part of the Program, that part may be used separately
+under those permissions, but the entire Program remains governed by
+this License without regard to the additional permissions.
+
+  When you convey a copy of a covered work, you may at your option
+remove any additional permissions from that copy, or from any part of
+it.  (Additional permissions may be written to require their own
+removal in certain cases when you modify the work.)  You may place
+additional permissions on material, added by you to a covered work,
+for which you have or can give appropriate copyright permission.
+
+  Notwithstanding any other provision of this License, for material you
+add to a covered work, you may (if authorized by the copyright holders of
+that material) supplement the terms of this License with terms:
+
+    a) Disclaiming warranty or limiting liability differently from the
+    terms of sections 15 and 16 of this License; or
+
+    b) Requiring preservation of specified reasonable legal notices or
+    author attributions in that material or in the Appropriate Legal
+    Notices displayed by works containing it; or
+
+    c) Prohibiting misrepresentation of the origin of that material, or
+    requiring that modified versions of such material be marked in
+    reasonable ways as different from the original version; or
+
+    d) Limiting the use for publicity purposes of names of licensors or
+    authors of the material; or
+
+    e) Declining to grant rights under trademark law for use of some
+    trade names, trademarks, or service marks; or
+
+    f) Requiring indemnification of licensors and authors of that
+    material by anyone who conveys the material (or modified versions of
+    it) with contractual assumptions of liability to the recipient, for
+    any liability that these contractual assumptions directly impose on
+    those licensors and authors.
+
+  All other non-permissive additional terms are considered "further
+restrictions" within the meaning of section 10.  If the Program as you
+received it, or any part of it, contains a notice stating that it is
+governed by this License along with a term that is a further
+restriction, you may remove that term.  If a license document contains
+a further restriction but permits relicensing or conveying under this
+License, you may add to a covered work material governed by the terms
+of that license document, provided that the further restriction does
+not survive such relicensing or conveying.
+
+  If you add terms to a covered work in accord with this section, you
+must place, in the relevant source files, a statement of the
+additional terms that apply to those files, or a notice indicating
+where to find the applicable terms.
+
+  Additional terms, permissive or non-permissive, may be stated in the
+form of a separately written license, or stated as exceptions;
+the above requirements apply either way.
+
+  8. Termination.
+
+  You may not propagate or modify a covered work except as expressly
+provided under this License.  Any attempt otherwise to propagate or
+modify it is void, and will automatically terminate your rights under
+this License (including any patent licenses granted under the third
+paragraph of section 11).
+
+  However, if you cease all violation of this License, then your
+license from a particular copyright holder is reinstated (a)
+provisionally, unless and until the copyright holder explicitly and
+finally terminates your license, and (b) permanently, if the copyright
+holder fails to notify you of the violation by some reasonable means
+prior to 60 days after the cessation.
+
+  Moreover, your license from a particular copyright holder is
+reinstated permanently if the copyright holder notifies you of the
+violation by some reasonable means, this is the first time you have
+received notice of violation of this License (for any work) from that
+copyright holder, and you cure the violation prior to 30 days after
+your receipt of the notice.
+
+  Termination of your rights under this section does not terminate the
+licenses of parties who have received copies or rights from you under
+this License.  If your rights have been terminated and not permanently
+reinstated, you do not qualify to receive new licenses for the same
+material under section 10.
+
+  9. Acceptance Not Required for Having Copies.
+
+  You are not required to accept this License in order to receive or
+run a copy of the Program.  Ancillary propagation of a covered work
+occurring solely as a consequence of using peer-to-peer transmission
+to receive a copy likewise does not require acceptance.  However,
+nothing other than this License grants you permission to propagate or
+modify any covered work.  These actions infringe copyright if you do
+not accept this License.  Therefore, by modifying or propagating a
+covered work, you indicate your acceptance of this License to do so.
+
+  10. Automatic Licensing of Downstream Recipients.
+
+  Each time you convey a covered work, the recipient automatically
+receives a license from the original licensors, to run, modify and
+propagate that work, subject to this License.  You are not responsible
+for enforcing compliance by third parties with this License.
+
+  An "entity transaction" is a transaction transferring control of an
+organization, or substantially all assets of one, or subdividing an
+organization, or merging organizations.  If propagation of a covered
+work results from an entity transaction, each party to that
+transaction who receives a copy of the work also receives whatever
+licenses to the work the party's predecessor in interest had or could
+give under the previous paragraph, plus a right to possession of the
+Corresponding Source of the work from the predecessor in interest, if
+the predecessor has it or can get it with reasonable efforts.
+
+  You may not impose any further restrictions on the exercise of the
+rights granted or affirmed under this License.  For example, you may
+not impose a license fee, royalty, or other charge for exercise of
+rights granted under this License, and you may not initiate litigation
+(including a cross-claim or counterclaim in a lawsuit) alleging that
+any patent claim is infringed by making, using, selling, offering for
+sale, or importing the Program or any portion of it.
+
+  11. Patents.
+
+  A "contributor" is a copyright holder who authorizes use under this
+License of the Program or a work on which the Program is based.  The
+work thus licensed is called the contributor's "contributor version".
+
+  A contributor's "essential patent claims" are all patent claims
+owned or controlled by the contributor, whether already acquired or
+hereafter acquired, that would be infringed by some manner, permitted
+by this License, of making, using, or selling its contributor version,
+but do not include claims that would be infringed only as a
+consequence of further modification of the contributor version.  For
+purposes of this definition, "control" includes the right to grant
+patent sublicenses in a manner consistent with the requirements of
+this License.
+
+  Each contributor grants you a non-exclusive, worldwide, royalty-free
+patent license under the contributor's essential patent claims, to
+make, use, sell, offer for sale, import and otherwise run, modify and
+propagate the contents of its contributor version.
+
+  In the following three paragraphs, a "patent license" is any express
+agreement or commitment, however denominated, not to enforce a patent
+(such as an express permission to practice a patent or covenant not to
+sue for patent infringement).  To "grant" such a patent license to a
+party means to make such an agreement or commitment not to enforce a
+patent against the party.
+
+  If you convey a covered work, knowingly relying on a patent license,
+and the Corresponding Source of the work is not available for anyone
+to copy, free of charge and under the terms of this License, through a
+publicly available network server or other readily accessible means,
+then you must either (1) cause the Corresponding Source to be so
+available, or (2) arrange to deprive yourself of the benefit of the
+patent license for this particular work, or (3) arrange, in a manner
+consistent with the requirements of this License, to extend the patent
+license to downstream recipients.  "Knowingly relying" means you have
+actual knowledge that, but for the patent license, your conveying the
+covered work in a country, or your recipient's use of the covered work
+in a country, would infringe one or more identifiable patents in that
+country that you have reason to believe are valid.
+
+  If, pursuant to or in connection with a single transaction or
+arrangement, you convey, or propagate by procuring conveyance of, a
+covered work, and grant a patent license to some of the parties
+receiving the covered work authorizing them to use, propagate, modify
+or convey a specific copy of the covered work, then the patent license
+you grant is automatically extended to all recipients of the covered
+work and works based on it.
+
+  A patent license is "discriminatory" if it does not include within
+the scope of its coverage, prohibits the exercise of, or is
+conditioned on the non-exercise of one or more of the rights that are
+specifically granted under this License.  You may not convey a covered
+work if you are a party to an arrangement with a third party that is
+in the business of distributing software, under which you make payment
+to the third party based on the extent of your activity of conveying
+the work, and under which the third party grants, to any of the
+parties who would receive the covered work from you, a discriminatory
+patent license (a) in connection with copies of the covered work
+conveyed by you (or copies made from those copies), or (b) primarily
+for and in connection with specific products or compilations that
+contain the covered work, unless you entered into that arrangement,
+or that patent license was granted, prior to 28 March 2007.
+
+  Nothing in this License shall be construed as excluding or limiting
+any implied license or other defenses to infringement that may
+otherwise be available to you under applicable patent law.
+
+  12. No Surrender of Others' Freedom.
+
+  If conditions are imposed on you (whether by court order, agreement or
+otherwise) that contradict the conditions of this License, they do not
+excuse you from the conditions of this License.  If you cannot convey a
+covered work so as to satisfy simultaneously your obligations under this
+License and any other pertinent obligations, then as a consequence you may
+not convey it at all.  For example, if you agree to terms that obligate you
+to collect a royalty for further conveying from those to whom you convey
+the Program, the only way you could satisfy both those terms and this
+License would be to refrain entirely from conveying the Program.
+
+  13. Use with the GNU Affero General Public License.
+
+  Notwithstanding any other provision of this License, you have
+permission to link or combine any covered work with a work licensed
+under version 3 of the GNU Affero General Public License into a single
+combined work, and to convey the resulting work.  The terms of this
+License will continue to apply to the part which is the covered work,
+but the special requirements of the GNU Affero General Public License,
+section 13, concerning interaction through a network will apply to the
+combination as such.
+
+  14. Revised Versions of this License.
+
+  The Free Software Foundation may publish revised and/or new versions of
+the GNU General Public License from time to time.  Such new versions will
+be similar in spirit to the present version, but may differ in detail to
+address new problems or concerns.
+
+  Each version is given a distinguishing version number.  If the
+Program specifies that a certain numbered version of the GNU General
+Public License "or any later version" applies to it, you have the
+option of following the terms and conditions either of that numbered
+version or of any later version published by the Free Software
+Foundation.  If the Program does not specify a version number of the
+GNU General Public License, you may choose any version ever published
+by the Free Software Foundation.
+
+  If the Program specifies that a proxy can decide which future
+versions of the GNU General Public License can be used, that proxy's
+public statement of acceptance of a version permanently authorizes you
+to choose that version for the Program.
+
+  Later license versions may give you additional or different
+permissions.  However, no additional obligations are imposed on any
+author or copyright holder as a result of your choosing to follow a
+later version.
+
+  15. Disclaimer of Warranty.
+
+  THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY
+APPLICABLE LAW.  EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT
+HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY
+OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO,
+THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+PURPOSE.  THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM
+IS WITH YOU.  SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF
+ALL NECESSARY SERVICING, REPAIR OR CORRECTION.
+
+  16. Limitation of Liability.
+
+  IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
+WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS
+THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY
+GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE
+USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF
+DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD
+PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS),
+EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF
+SUCH DAMAGES.
+
+  17. Interpretation of Sections 15 and 16.
+
+  If the disclaimer of warranty and limitation of liability provided
+above cannot be given local legal effect according to their terms,
+reviewing courts shall apply local law that most closely approximates
+an absolute waiver of all civil liability in connection with the
+Program, unless a warranty or assumption of liability accompanies a
+copy of the Program in return for a fee.
+
+                     END OF TERMS AND CONDITIONS

+ 5 - 0
ChangeLog.md

@@ -0,0 +1,5 @@
+# CHANGELOG MBIETRANSACTIONS FOR [DOLIBARR ERP CRM](https://www.dolibarr.org)
+
+## 1.0
+
+Initial version

+ 86 - 0
README.md

@@ -0,0 +1,86 @@
+# MBIETRANSACTIONS FOR [DOLIBARR ERP CRM](https://www.dolibarr.org)
+
+## Features
+
+Description...
+
+<!--
+![Screenshot mbietransactions](img/screenshot_mbietransactions.png?raw=true "MBIETransactions"){imgmd}
+-->
+
+Other modules are available on [Dolistore.com](https://www.dolistore.com).
+
+## Translations
+
+Translations can be define manually by editing files into directories *langs*.
+
+<!--
+This module contains also a sample configuration for Transifex, under the hidden directory [.tx](.tx), so it is possible to manage translation using this service.
+
+For more informations, see the [translator's documentation](https://wiki.dolibarr.org/index.php/Translator_documentation).
+
+There is a [Transifex project](https://transifex.com/projects/p/dolibarr-module-template) for this module.
+-->
+
+<!--
+
+## Installation
+
+### From the ZIP file and GUI interface
+
+- If you get the module in a zip file (like when downloading it from the market place [Dolistore](https://www.dolistore.com)), go into
+menu ```Home - Setup - Modules - Deploy external module``` and upload the zip file.
+
+Note: If this screen tell you there is no custom directory, check your setup is correct:
+
+- In your Dolibarr installation directory, edit the ```htdocs/conf/conf.php``` file and check that following lines are not commented:
+
+    ```php
+    //$dolibarr_main_url_root_alt ...
+    //$dolibarr_main_document_root_alt ...
+    ```
+
+- Uncomment them if necessary (delete the leading ```//```) and assign a sensible value according to your Dolibarr installation
+
+    For example :
+
+    - UNIX:
+        ```php
+        $dolibarr_main_url_root_alt = '/custom';
+        $dolibarr_main_document_root_alt = '/var/www/Dolibarr/htdocs/custom';
+        ```
+
+    - Windows:
+        ```php
+        $dolibarr_main_url_root_alt = '/custom';
+        $dolibarr_main_document_root_alt = 'C:/My Web Sites/Dolibarr/htdocs/custom';
+        ```
+
+### From a GIT repository
+
+- Clone the repository in ```$dolibarr_main_document_root_alt/mbietransactions```
+
+```sh
+cd ....../custom
+git clone git@github.com:gitlogin/mbietransactions.git mbietransactions
+```
+
+### <a name="final_steps"></a>Final steps
+
+From your browser:
+
+  - Log into Dolibarr as a super-administrator
+  - Go to "Setup" -> "Modules"
+  - You should now be able to find and enable the module
+
+-->
+
+## Licenses
+
+### Main code
+
+GPLv3 or (at your option) any later version. See file COPYING for more information.
+
+### Documentation
+
+All texts and readmes are licensed under GFDL.

+ 45 - 0
accepted.php

@@ -0,0 +1,45 @@
+<?php
+
+// Copyright (C) 2020      MB Informatique      <info@mb-informatique.fr>
+
+if (!defined('NOLOGIN')) define("NOLOGIN", 1); // This means this output page does not require to be logged.
+if (!defined('NOCSRFCHECK')) define("NOCSRFCHECK", 1); // We accept to go on this page from external web site.
+
+global $db, $conf, $langs;
+
+try {
+	if (!file_exists('../../main.inc.php'))
+		throw new Exception ('Does not exist');
+	else
+		require '../../main.inc.php';
+	$path = "/custom";
+}
+catch(Exception $e) {
+	require '../main.inc.php';
+	$path = "";
+}
+
+$langs->loadLangs(array("mbietransactions@mbietransactions"));
+
+echo "<head><meta name='robots' content='noindex,nofollow'><title>" . $langs->trans("MBIETransactionsPaymentPageTitle") . "</title>";
+echo "<link rel='stylesheet' type='text/css' href='" .  DOL_URL_ROOT . $conf->css . "?lang=" . $langs->defaultlang . "'>";
+echo "<link rel='stylesheet' type='text/css' href='" . DOL_URL_ROOT . $path . "/mbietransactions/style.css'></head>";
+echo "<div id='logo'>";
+if (!empty($mysoc->logo)) {
+	echo "<img width='150px;' id='paymentlogo' title='" . $conf->global->MAIN_INFO_SOCIETE_NOM . "' src='" . DOL_URL_ROOT . "/viewimage.php?modulepart=mycompany&amp;file=" . urlencode('logos/'.$mysoc->logo) ."'>";
+}
+echo "</div>";
+
+echo "<div id='payment-content'>
+<h1 style='font-size: 1.6em;'>" . $langs->trans("MBIETransactionsPaymentPageH1") . "</h1>
+<p style='font-size: 1.2em;'>" . $langs->trans("MBIETransactionsPaymentAccepted") . "<strong> " . $conf->global->MAIN_INFO_SOCIETE_NOM . "</strong> " . $langs->trans("MBIETransactionsPaymentAccepted2") . "</p>
+<p style='font-size: 1.2em;'>" . $langs->trans("MBIETransactionsPaymentAccepted3") . "</p>
+</div>";
+
+?>
+
+<br><br>
+<div>
+	<img style="width:250px" src="<?php echo DOL_URL_ROOT . $path . "/mbietransactions/img/ca-e-transactions-cb-visa-mastercard.jpg"; ?>" />
+	<p><?php echo $conf->global->MAIN_INFO_SOCIETE_NOM; ?> © <?php echo date('Y') ?><br><small><?php if ($conf->global->MAIN_INFO_SIRET) { echo "SIRET: " . $conf->global->MAIN_INFO_SIRET; } ?><br><?php echo $conf->global->MAIN_INFO_SOCIETE_ADDRESS; ?> <?php echo $conf->global->MAIN_INFO_SOCIETE_ZIP; ?> <?php echo $conf->global->MAIN_INFO_SOCIETE_TOWN; ?> - <?php echo $conf->global->MAIN_INFO_SOCIETE_TEL; ?></small></p>
+</div>

+ 29 - 0
admin/about.php

@@ -0,0 +1,29 @@
+<?php
+/* Copyright (C) 2004-2017 Laurent Destailleur  <eldy@users.sourceforge.net>
+ * Copyright (C) 2020      MB Informatique      <info@mb-informatique.fr>
+ *
+ * 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 3 of the License, 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 program.  If not, see <https://www.gnu.org/licenses/>.
+ */
+
+/**
+ * \file    mbietransactions/admin/about.php
+ * \ingroup mbietransactions
+ * \brief   About page of module MBIETransactions.
+ */
+
+// Load Dolibarr environment
+require_once '../env.inc.php';
+require_once '../main_load.inc.php';
+
+require_once('../../mmicommon/admin/mmiabout_1.inc.php');

+ 53 - 0
admin/setup.php

@@ -0,0 +1,53 @@
+<?php
+/* Copyright (C) 2004-2017 Laurent Destailleur  <eldy@users.sourceforge.net>
+ * Copyright (C) 2020      MB Informatique      <info@mb-informatique.fr>
+ *
+ * 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 3 of the License, 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 program.  If not, see <https://www.gnu.org/licenses/>.
+ */
+
+/**
+ * \file    mbietransactions/admin/setup.php
+ * \ingroup mbietransactions
+ * \brief   MBIETransactions setup page.
+ */
+
+// Load Dolibarr environment
+require_once '../env.inc.php';
+require_once '../main_load.inc.php';
+
+$arrayofparameters = array(
+	'MBIETRANSACTIONS_TEST'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_TEST_RANK'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_TEST_ID'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_TEST_SHOP_ID'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_TEST_KEY'=>array('css'=>'minwidth500', 'enabled'=>1),
+	
+	'MBIETRANSACTIONS_RANK'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_ID'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_SHOP_ID'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_KEY'=>array('css'=>'minwidth500', 'enabled'=>1),
+	
+	'MBIETRANSACTIONS_DELIVERY_RECEIPT_EMAIL'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_CC_EMAILS'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_NOTIFICATION_FROM_EMAIL'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_NOTIFICATION_EMAIL'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_WEBSITE_CONTACT_URL'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_BANK_ACCOUNT'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_SUBJECT_PAYMENT_MAIL'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_TEMPLATE_PAYMENT_MAIL'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_SUBJECT_PAID_INVOICE_MAIL'=>array('css'=>'minwidth500', 'enabled'=>1),
+	'MBIETRANSACTIONS_TEMPLATE_PAID_INVOICE_MAIL'=>array('css'=>'minwidth500', 'enabled'=>1)
+);
+
+require_once('../../mmicommon/admin/mmisetup_1.inc.php');

+ 11 - 0
build/makepack-mbietransactions.conf

@@ -0,0 +1,11 @@
+# Your module name here
+#
+# Goal:    Goal of module
+# Version: <version>
+# Author:  Copyright <year> - <name of author>
+# License: GPLv3
+# Install: Just unpack content of module package in Dolibarr directory.
+# Setup:   Go on Dolibarr setup - modules to enable module.
+#
+# Files in module
+mymodule/

+ 44 - 0
canceled.php

@@ -0,0 +1,44 @@
+<?php
+
+// Copyright (C) 2020      MB Informatique      <info@mb-informatique.fr>
+
+if (!defined('NOLOGIN')) define("NOLOGIN", 1); // This means this output page does not require to be logged.
+if (!defined('NOCSRFCHECK')) define("NOCSRFCHECK", 1); // We accept to go on this page from external web site.
+
+global $db, $conf, $langs;
+
+try {
+	if (!file_exists('../../main.inc.php'))
+		throw new Exception ('Does not exist');
+	else
+		require '../../main.inc.php';
+	$path = "/custom";
+}
+catch(Exception $e) {
+	require '../main.inc.php';
+	$path = "";
+}
+
+$langs->loadLangs(array("mbietransactions@mbietransactions"));
+
+echo "<head><meta name='robots' content='noindex,nofollow'><title>" . $langs->trans("MBIETransactionsPaymentPageTitle") . "</title>";
+echo "<link rel='stylesheet' type='text/css' href='" .  DOL_URL_ROOT . $conf->css . "?lang=" . $langs->defaultlang . "'>";
+echo "<link rel='stylesheet' type='text/css' href='" . DOL_URL_ROOT . $path . "/mbietransactions/style.css'></head>";
+echo "<div id='logo'>";
+if (!empty($mysoc->logo)) {
+	echo "<img width='150px;' id='paymentlogo' title='" . $conf->global->MAIN_INFO_SOCIETE_NOM . "' src='" . DOL_URL_ROOT . "/viewimage.php?modulepart=mycompany&amp;file=" . urlencode('logos/'.$mysoc->logo) ."'>";
+}
+echo "</div>";
+
+echo "<div id='payment-content'>
+<h1 style='font-size: 1.6em;'>" . $langs->trans("MBIETransactionsPaymentPageH1") . "</h1>
+<p style='font-size: 1.2em;'>" . $langs->trans("MBIETransactionsPaymentCanceled") . "</p>
+</div>";
+
+?>
+
+<br><br>
+<div>
+	<img style="width:250px" src="<?php echo DOL_URL_ROOT . $path . "/mbietransactions/img/ca-e-transactions-cb-visa-mastercard.jpg"; ?>" />
+	<p><?php echo $conf->global->MAIN_INFO_SOCIETE_NOM; ?> © <?php echo date('Y') ?><br><small><?php if ($conf->global->MAIN_INFO_SIRET) { echo "SIRET: " . $conf->global->MAIN_INFO_SIRET; } ?><br><?php echo $conf->global->MAIN_INFO_SOCIETE_ADDRESS; ?> <?php echo $conf->global->MAIN_INFO_SOCIETE_ZIP; ?> <?php echo $conf->global->MAIN_INFO_SOCIETE_TOWN; ?> - <?php echo $conf->global->MAIN_INFO_SOCIETE_TEL; ?></small></p>
+</div>

+ 348 - 0
class/actions_mbietransactions.class.php

@@ -0,0 +1,348 @@
+<?php
+/**
+ * Copyright (C) 2020       MB Informatique         <info@mb-informatique.fr>
+ * Copyright (C) 2022       Mathieu Moulin          <contact@iprospective.fr>
+ */
+
+dol_include_once('custom/mmicommon/class/mmi_actions.class.php');
+dol_include_once('/mbietransactions/class/mmi_etransactions.class.php');
+
+class ActionsMBIETransactions extends MMI_Actions_1_0
+{
+	const MOD_NAME = 'mbietransactions';
+
+	// Payment page
+
+	/**
+	 * Check Object OK
+	 */
+	function doCheckStatus($parameters, &$object, &$action, $hookmanager)
+	{
+		$objecttype = get_class($object);
+
+		if (in_array($objecttype, ['Propal'])) {
+			// Vérif devis ok, pas relié commande, etc.
+		}
+
+		return 0;
+	}
+
+	/**
+	 * Check Object OK
+	 */
+	function addOnlinePaymentMeans($parameters, &$object, &$action, $hookmanager)
+	{
+		$objecttype = get_class($object);
+
+		if (in_array($objecttype, ['Propal', 'Commande', 'Facture'])) {
+			$hookmanager->results['useonlinepayment'] = true;
+		}
+
+		return 0;
+	}
+	
+	// Boutons moyens de paiement
+	function doaddButton($parameters, &$object, &$action, $hookmanager)
+	{
+		global $db, $langs, $conf;
+
+		// var_dump($object);
+		// die();
+		$time = time();
+
+		$objecttype = get_class($object);
+		$deja = mmi_payments::total_regle($objecttype, $object->id);
+		//var_dump($deja);
+		$reste = ($deja>0 ?max(0, round($object->total_ttc-$deja, 2)) :$object->total_ttc);
+		//var_dump($object->fin_validite, $time, empty($object->fin_validite) || $object->fin_validite < $time);
+
+		print '<div style="width: 800px;">';
+		if ($objecttype=='Propal') {
+			$fin_validite = $object->fin_validite ?$object->fin_validite+86400 :0;
+			$ok = $fin_validite && $fin_validite > $time;
+			// if (!empty($object->ref_client))
+			// 	echo '<p><b>Référence du projet :</b> '.$object->ref_client.'</p>';
+			if (empty($deja) && $fin_validite && $fin_validite < $time)
+				echo '<p'.(!$ok ?' style="color: red;"' :'').'>Date de fin de validité de votre Devis : '.date('d/m/Y', $fin_validite).'</p>';
+			if (!$ok) {
+				$nok_message = '<b style="color: red;">Votre devis est échu, merci de contacter votre conseiller !</b>';
+			}
+		}
+		else {
+			$ok = true;
+		}
+		if ($ok) {
+			echo '<p><input type="checkbox" id="cgv" name="cgv" value="1" /> '."J'ai lu les <a href=\"https://www.pisceen.com/fr/a/3-conditions-generales-de-vente\" target=\"_blank\">conditions générales de vente</a> et j'y adhère sans réserve.".'</p>';
+		}
+		elseif (!empty($nok_message)) {
+			echo '<p>'.$nok_message.'</p>';
+		}
+		echo '</div>';
+		//var_dump($object); die();
+		echo '<div id="voile" class="voile"></div>';
+
+		print '<div style="width: 400px;"><img src="/custom/mbietransactions/img/ca-e-transactions-bis-400px.png" alt="E-Transactions Crédit Agricole" width="400px" /></div>';
+
+		// Acompte
+		// Une seule fois => si déjà alors pas acompte
+		if (empty($deja) && empty($parameters['amount']) && (!empty($object->array_options['options_acompte']) || !empty($object->array_options['options_acompte_val']))) {
+			if ($acompte = $object->array_options['options_acompte'])
+				$amount = round($reste*$acompte/100, 2);
+			else
+				$amount = round($object->array_options['options_acompte_val'], 2);
+			$link_acompte = mmi_etransactions::paymentlink($objecttype, $object->id, $amount, 1, true);
+			//var_dump($link); die();
+
+			print '<div class="button buttonpayment" id="div_dopayment_mbietransactions_acompte">
+			<input class="" type="submit" id="dopayment_mbietransactions_acompte" name="dopayment_mbietransactions" value="'.$langs->trans("MBIETransactionsDoPaymentAcompte", $amount.'€').'">';
+			print '<br />';
+			print '<span class="buttonpaymentsmall">
+			<img src="/custom/mbietransactions/img/cb-visa-mastercard.png" alt="CB Visa Mastercard" class="img_cb" />
+			<img src="/custom/mbietransactions/img/paypal.png" alt="Paypal" class="img_paypal" />
+			<img src="/custom/mbietransactions/img/amex.png" alt="Amex" class="img_amex" />
+			</span>';
+			print '</div>';
+		}
+
+		// Paiement normal complet
+		if (true) {
+			$amount = (!empty($parameters['amount']) ?$parameters['amount'] :$reste);
+			//var_dump(get_class($object), $object->id, $amount, 1, true);
+			$link = mmi_etransactions::paymentlink($objecttype, $object->id, $amount, 1, true);
+			//var_dump($link); die();
+
+			print '<div class="button buttonpayment" id="div_dopayment_mbietransactions">
+			<input class="" type="submit" id="dopayment_mbietransactions" name="dopayment_mbietransactions" value="'.$langs->trans("MBIETransactionsDoPayment").'">';
+			print '<br />';
+			print '<span class="buttonpaymentsmall">
+			<img src="/custom/mbietransactions/img/cb-visa-mastercard.png" alt="CB Visa Mastercard" class="img_cb" />
+			<img src="/custom/mbietransactions/img/paypal.png" alt="Paypal" class="img_paypal" />
+			<img src="/custom/mbietransactions/img/amex.png" alt="Amex" class="img_amex" />
+			</span>';
+			print '</div>';
+		}
+
+		// var_dump($parameters['amount']);
+		// var_dump($object->array_options['options_acompte']);
+		// var_dump($object->total_ttc);
+
+		// Multiple
+		if (empty($parameters['amount']) && ($reste>=300 || ($object->total_ttc>300 && $reste===NULL))) {
+			$multiple = 3;
+			$link_multiple = mmi_etransactions::paymentlink($objecttype, $object->id, $reste, $multiple, true);
+			//var_dump($link); die();
+
+			print '<div class="button buttonpayment" id="div_dopayment_mbietransactions_multiple">
+			<input class="" type="submit" id="dopayment_mbietransactions_multiple" name="dopayment_mbietransactions" value="'.$langs->trans("MBIETransactionsDoPaymentMultiple", $multiple).'">';
+			print '<br />';
+			print '<span class="buttonpaymentsmall">
+			<img src="/custom/mbietransactions/img/cb-visa-mastercard.png" alt="CB Visa Mastercard" class="img_cb" />
+			<img src="/custom/mbietransactions/img/amex.png" alt="Amex" class="img_amex" />
+			</span>';
+			print '</div>';
+		}
+
+		// Virement
+		if (true) {
+			require_once DOL_DOCUMENT_ROOT.'/compta/bank/class/account.class.php';
+			if($conf->global->PAYMENTBYBANKTRANSFER_ID_BANKACCOUNT) {
+				$account = new account($db);
+				$account->fetch($conf->global->PAYMENTBYBANKTRANSFER_ID_BANKACCOUNT);
+
+				echo '<div class="button buttonpayment" id="div_dopayment_transfer">
+				<input class="" type="submit" id="dopayment_transfer" name="dopayment_transfer" value="'.$langs->trans('MBIETransactionsDoPaymentTransfer').'" />';
+				echo '<div class="pay_infos">';
+				echo '<p>Il vous faudra transférer le montant de la facture sur notre compte bancaire.</p>
+				<p>Vous recevrez votre confirmation de commande par e-mail, comprenant nos coordonnées bancaires et le numéro de commande.</p>
+				<p>Nous traiterons votre commande dès la réception du paiement.</p>
+				<p class="small">Cliquer pour plus d\'informations</p>';
+				echo '</div>';
+				echo '</div>';
+			}
+		}
+
+		// Chèque
+		if (true) {
+			global $mysoc;
+			//var_dump($mysoc);
+			echo '<div class="button buttonpayment" id="div_dopayment_cheque">
+			<input class="" type="submit" id="dopayment_cheque" name="dopayment_cheque" value="'.$langs->trans('MBIETransactionsDoPaymentCheque').'" />';
+			echo '<div class="pay_infos">';
+			echo '<p>A l\'ordre de : <b>'.$mysoc->name.'</b></p>';
+			echo '<p>'.$mysoc->address.'<br />'.$mysoc->zip.' '.$mysoc->town.'</p>
+			<p class="small">Cliquer pour plus d\'informations</p>';
+			echo '</div>';
+			echo '</div>';
+		}
+
+		print '<script>
+			$( document ).ready(function() {
+				$("#cgv").click(function(e){
+					$("#voile").toggle();
+				});
+				$("#div_dopayment_mbietransactions").click(function(e){
+					document.location.href=\''.$link.'\';
+					$(this).css( \'cursor\', \'wait\' );
+					e.stopPropagation();
+					return false;
+				});
+				$("#div_dopayment_mbietransactions_acompte").click(function(e){
+					document.location.href=\''.$link_acompte.'\';
+					$(this).css( \'cursor\', \'wait\' );
+					e.stopPropagation();
+					return false;
+				});
+				$("#div_dopayment_mbietransactions_multiple").click(function(e){
+					document.location.href=\''.$link_multiple.'\';
+					$(this).css( \'cursor\', \'wait\' );
+					e.stopPropagation();
+					return false;
+				});
+				$("#div_dopayment_transfer input").click(function(e){
+					if (confirm("Je confirme ma commande avec obligation de paiement.")) {
+						$(this).css( \'cursor\', \'wait\' );
+						$(\'input\', this).submit();
+						return true;
+					}
+					else {
+						return false;
+					}
+				});
+				$("#div_dopayment_transfer p").click(function(e){
+					$("#div_dopayment_transfer input").click();
+				});
+				$("#div_dopayment_cheque input").click(function(e){
+					if (confirm("Je confirme ma commande avec obligation de paiement.")) {
+						$(this).css( \'cursor\', \'wait\' );
+						return true;
+					}
+					else {
+						return false;
+					}
+				});
+				$("#div_dopayment_cheque p").click(function(e){
+					$("#div_dopayment_cheque input").click();
+				});
+			});
+			</script>';
+
+		return 0;
+	}
+
+	// Payment means
+	function doValidatePayment($parameters, &$object, &$action, $hookmanager)
+	{
+		//var_dump($parameters); var_dump(get_class($object)); var_dump($action);
+		$parameters['validpaymentmethod']['mbietransactions'] = true;
+		$parameters['validpaymentmethod']['cheque'] = true;
+		$parameters['validpaymentmethod']['transfer'] = true;
+
+		return 0;
+	}
+
+	// This hook is used to show the embedded form to make payments with external payment modules (ie Payzen, ...)
+	function doPayment($parameters, &$object, &$action, $hookmanager)
+	{
+		global $db, $conf, $mysoc, $user;
+		//var_dump($mysoc); die();
+
+		require_once DOL_DOCUMENT_ROOT.'/compta/bank/class/account.class.php';
+
+		if(($client=$object->thirdparty) && $client->email) {
+			$mail_notif_to = [];
+			
+			if (!empty($conf->global->MBIETRANSACTIONS_NOTIFICATION_EMAIL))
+				$mail_notif_to[] = $conf->global->MBIETRANSACTIONS_NOTIFICATION_EMAIL;
+			$contacts = $object->liste_contact(-1, 'internal');
+			$contacts_ok = false;
+			foreach($contacts as $contact) {
+				$contacts_ok = true;
+				if (!empty($contact->email) && !in_array($contact->email, $mail_notif_to))
+					$mail_notif_to[] = $contact->email;
+			}
+			$contacts = $client->getSalesRepresentatives($user);
+			foreach($contacts as $contact) {
+				$contacts_ok = true;
+				if (!empty($contact['email']) && !in_array($contact['email'], $mail_notif_to))
+					$mail_notif_to[] = $contact['email'];
+			}
+			$to_email = $client->nom.' <'.$client->email.'>';
+			$from_email = $mysoc->name.' <'.$mysoc->email.'>';
+			$notif_email = (!empty($mail_notif_to) ?'Bcc: '.implode(',', $mail_notif_to)."\r\n" :'');
+			// @todo : $mailfile = new CMailFile($subject, $sendto, $from, $message, $filepath, $mimetype, $filename, $sendtocc, $sendtobcc, $deliveryreceipt, -1, '', '', $trackid, '', $sendcontext);
+		}
+
+		$object_class = get_class($object);
+		if ($object_class=='Propal')
+			$otype = 'Devis';
+		else
+			$otype = $object_class;
+
+		//var_dump($parameters);
+		if ($parameters['paymentmethod']=='transfer' && $conf->global->PAYMENTBYBANKTRANSFER_ID_BANKACCOUNT) {
+			mmi_etransactions::object_mode_reglement_set($object, 'VIR');
+
+			$account = new account($db);
+			$account->fetch($conf->global->PAYMENTBYBANKTRANSFER_ID_BANKACCOUNT);
+			//var_dump($account);
+			$info = '<h3 class="title">Vous avez choisi de payer par virement</h3>
+			<p>Votre demande a bien été prise en considération.</p>
+			<p>Merci de nous envoyer votre paiement par virement bancaire,</p>
+			<p>Montant du règlement : '.$parameters['amount'].'&nbsp;&euro;</p>
+			<p>Code Banque : '.$account->code_banque.'<br />
+			Code Guichet :  '.$account->code_guichet.'<br />
+			Numéro de compte : '.$account->number.'<br />
+			Clé RIB : '.$account->cle_rib.'<br />
+			IBAN : <b>'.$account->iban.'</b><br />
+			Code BIC / SWIFT : <b>'.$account->bic.'</b></p>
+			<p>Adresse de la banque / Domiciliation du compte :</p>
+			<p>'.str_replace("\r\n", '<br />', $account->domiciliation).'</p>
+			<p>N\'oubliez pas la référence de votre '.$otype.' dans la description du virement :<br /><b>'.$object->ref.'</b></p>'
+			.($object->thirdparty && $object->thirdparty->email ?'<p>Un e-mail contenant ces informations a été envoyé sur votre adresse :<br /><b>'.$object->thirdparty->email.'</b></p>' :'')
+			.'<p><b>Votre commande sera traitée dès réception de votre virement.</b></p>'
+			.($conf->global->MBIETRANSACTIONS_WEBSITE_CONTACT_URL ?'<p>Pour toute question ou information complémentaire,<br />
+			merci de contacter notre <a href="'.$conf->global->MBIETRANSACTIONS_WEBSITE_CONTACT_URL.'">support client</a>.</p>' :'');
+
+			echo '<table align="center" width="600"><tr><td><div style="width: 559px;border: 1px solid #aaa;padding: 20px;">
+			'.$info.'
+			</div></td></tr></table>';
+			if($object->thirdparty && $object->thirdparty->email) {
+				mail($to_email,
+					'=?utf-8?B?'.base64_encode('Votre '.$otype.' '.$object->ref.' en attente de réglement par virement bancaire').'?=',
+					$info,
+					"Content-Type: text/html; charset=\"UTF-8\";\r\nFrom: ".$from_email."\r\n".$notif_email);
+			}
+		}
+		elseif ($parameters['paymentmethod']=='cheque') {
+			mmi_etransactions::object_mode_reglement_set($object, 'CHQ');
+
+			$info = '<h3 class="title">Vous avez choisi de payer par chèque</h3>
+			<p>Votre demande a bien été prise en considération.</p>
+			<p>Merci de nous envoyer votre paiement par chèque,</p>
+			<p>- Montant du règlement : '.$parameters['amount'].'&nbsp;&euro;</p>
+			<p>- Payable à l\'ordre de : <b>'.$mysoc->name.'</b>,</p>
+			<p>- Envoyer à l\'adresse suivante :</p>
+			<p style="margin-left: 40px;"><b>'.$mysoc->address.'<br />'.$mysoc->zip.' '.$mysoc->town.'</b></p>
+			<p>- N\'oubliez pas la référence de votre '.$otype.' : <b>'.$object->ref.'</b></p>'
+			.($object->thirdparty && $object->thirdparty->email ?'<p>Un e-mail contenant ces informations a été envoyé sur votre adresse : '.$object->thirdparty->email.'</p>' :'')
+			.'<p><b>Votre commande sera traitée dès réception de votre chèque.</b></p>'
+			.($conf->global->MBIETRANSACTIONS_WEBSITE_CONTACT_URL ?'<p>Pour toute question ou information complémentaire,<br />
+			merci de contacter notre <a href="'.$conf->global->MBIETRANSACTIONS_WEBSITE_CONTACT_URL.'">support client</a>.</p>' :'');
+
+			echo '<table align="center" width="600"><tr><td><div style="width: 559px;border: 1px solid #aaa;padding: 20px;">
+			'.$info.'
+			</div></td></tr></table>';
+			if($object->thirdparty && $object->thirdparty->email) {
+				mail($to_email,
+					'=?utf-8?B?'.base64_encode('Votre '.$otype.' '.$object->ref.' en attente de réglement par chèque').'?=',
+					$info, 
+					"Content-Type: text/html; charset=\"UTF-8\";\r\nFrom: ".$from_email."\r\n".$notif_email);
+			}
+		}
+		//die('YO');
+
+		return 0;
+	}
+}
+
+ActionsMBIETransactions::__init();

+ 369 - 0
class/mmi_etransactions.class.php

@@ -0,0 +1,369 @@
+<?php
+
+dol_include_once('/custom/mmipayments/class/mmi_payments.class.php');
+
+class mmi_etransactions
+{
+
+public static function __init()
+{
+
+}
+
+public static function active($objecttype=NULL)
+{
+	global $conf;
+
+	if (is_string($objecttype) && in_array($objecttype, ['Facture', 'Commande', 'Propal', 'Client']))
+		return $conf->global->MBIETRANSACTIONS_TEST == "1" || (!empty($conf->global->MBIETRANSACTIONS_SHOP_ID) && !empty($conf->global->MBIETRANSACTIONS_RANK) && !empty($conf->global->MBIETRANSACTIONS_ID) && !empty($conf->global->MBIETRANSACTIONS_KEY) && !empty($conf->global->MBIETRANSACTIONS_BANK_ACCOUNT));
+	else
+		return false;
+}
+
+public static function payment_insert()
+{
+
+}
+
+public static function paymentlink($objecttype, $id, $amount=NULL, $multiple=NULL, $autosubmit=false)
+{
+	global $db;
+	
+	if ($amount===NULL) {
+		$total_regle = mmi_payments::total_regle($objecttype, $id);
+		$object = mmi_payments::loadobject($objecttype, $id);
+		$amount = round($object->total_ttc - $total_regle, 2);
+	}
+
+	$sql = "SELECT mh.`hash`
+		FROM ".MAIN_DB_PREFIX."mbi_etransactions_hash mh
+		LEFT JOIN ".MAIN_DB_PREFIX."mbi_etransactions_return mr
+			ON mr.fk_mbi_etransactions=mh.rowid
+		WHERE mr.`rowid` IS NULL
+			AND mh.`objecttype`='".$objecttype."' AND mh.`fk_object` = '" . $id . "'
+			AND mh.`amount`".(!empty($amount) && is_numeric($amount) ?'='.$amount :' IS NULL')."
+			AND mh.`multiple`".(is_numeric($multiple) && $multiple>1 ?'='.$multiple :' IS NULL');
+	//echo $sql;
+	$q = $db->query($sql);
+	//var_dump($q);
+	if ($q) {
+		if (!list($hash)=$q->fetch_row()) {
+			$hash = static::createhash();
+			$sql = "INSERT INTO " . MAIN_DB_PREFIX . "mbi_etransactions_hash
+				(objecttype, fk_object, amount, multiple, hash)
+				VALUES ('".$objecttype."', '" . $id . "', ".(!empty($amount) && is_numeric($amount) ?$amount :'NULL').", ".(is_numeric($multiple) && $multiple>1 ?$multiple :'NULL').", '" . $hash . "')";
+			$db->query($sql);
+			//echo $sql;
+		}
+		return dol_buildpath('/mbietransactions/payment.php', 2).'?hashp='.$hash.($autosubmit ?'&autosubmit' :'');
+	}
+}
+
+public static function query($hash)
+{
+	global $db;
+
+	$sql = "SELECT *
+		FROM ".MAIN_DB_PREFIX."mbi_etransactions_hash
+		WHERE `hash`='".$hash."'";
+	//echo $sql;
+	$resql = $db->query($sql);
+	if (!($resql && ($obj = $db->fetch_object($resql))))
+		return;
+
+	return $obj;
+}
+
+public static function info($hash)
+{
+	return static::query($hash);
+}
+
+public static function trans_query_nb($hash, $trans, $ok=true)
+{
+	global $db;
+
+	$sql = "SELECT COUNT(*)
+		FROM ".MAIN_DB_PREFIX."mbi_etransactions_return mr
+		INNER JOIN ".MAIN_DB_PREFIX."mbi_etransactions_hash mh ON mh.rowid=mr.fk_mbi_etransactions
+		WHERE mh.`hash`='".$hash."' AND mr.`trans`='".$trans."'".($ok ?" AND mr.`erreur`='00000'" :'');
+	//echo $sql;
+	$resql = $db->query($sql);
+	if (!$resql)
+		return;
+	if (!(list($nb) = $db->fetch_row($resql)))
+		return;
+
+	return $nb;
+}
+
+public static function trans_query($hash, $trans, $autorisation)
+{
+	global $db;
+
+	$sql = "SELECT mr.*
+		FROM ".MAIN_DB_PREFIX."mbi_etransactions_return mr
+		INNER JOIN ".MAIN_DB_PREFIX."mbi_etransactions_hash mh ON mh.rowid=mr.fk_mbi_etransactions
+		WHERE mh.`hash`='".$hash."' AND mr.`trans`='".$trans."' AND mr.`auto`='".$autorisation."'";
+	//echo $sql;
+	$resql = $db->query($sql);
+	if (!$resql)
+		return;
+	if (!($obj = $db->fetch_object($resql)))
+		return;
+
+	return $obj;
+}
+
+public static function trans_info($hash, $trans, $autorisation)
+{
+	return static::trans_query($hash, $trans, $autorisation);
+}
+
+public static function retrieve($hash)
+{
+	if (!($obj = static::info($hash)))
+		return;
+
+	$objecttype = $obj->objecttype;
+	$id = $obj->fk_object;
+
+	return mmi_payments::loadobject($objecttype, $id);
+}
+
+public static function createhash()
+{
+	include_once DOL_DOCUMENT_ROOT.'/core/lib/security2.lib.php';
+	$hashp = getRandomPassword(true);
+	return $hashp;
+}
+
+public static function notification_email($email_to, $subject, $message)
+{
+	global $conf, $mysoc;
+	
+	if (empty($email_to))
+		$email_to = (!empty($conf->global->MBIETRANSACTIONS_NOTIFICATION_EMAIL) ?$conf->global->MBIETRANSACTIONS_NOTIFICATION_EMAIL :$mysoc->email);
+	
+	$email_from = (!empty($conf->global->MBIETRANSACTIONS_NOTIFICATION_FROM_EMAIL) ?$conf->global->MBIETRANSACTIONS_NOTIFICATION_FROM_EMAIL :$mysoc->email);
+	
+	return mail($email_to,
+		$subject,
+		$message,
+		$email_headers = 'From: '.$email_from."\r\n"
+			.'Content-Type: text/plain; charset=UTF-8'."\r\n");
+}
+
+public static function object_mode_reglement_set($object, $code)
+{
+	global $db, $user;
+
+	$sql = 'SELECT id
+		FROM '.MAIN_DB_PREFIX.'c_paiement
+		WHERE code="'.$code.'"';
+	$q = $db->query($sql);
+	if ($q && (list($pid)=$db->fetch_row($q))) {
+		//echo $pid;
+		$object->mode_reglement_id = $pid;
+		//var_dump($object);
+		$object->update($user);
+	}
+}
+
+public static function error($code_error)
+{
+	switch ($code_error) {
+	  case '00000':
+		return 'Transaction approuvée. Opération réussie.';
+		break;
+	  case '00001':
+		return 'La connexion au centre d\'autorisation a échoué, ou le client a annulé.';
+		break;
+	  case '00003':
+		return 'Erreur de la plateforme bancaire.';
+		break;
+	  case '00004':
+		return 'Numéro de porteur ou cryptogramme visuel invalide.';
+		break;
+	  case '00006':
+		return 'Accès refusé.';
+		break;
+	  case '00008':
+		return 'Date de fin de validité incorrecte.';
+		break;
+	  case '00009':
+		return 'Erreur de création d\'un abonnement.';
+		break;
+	  case '00010':
+		return 'Devise inconnue.';
+		break;
+	  case '00011':
+		return 'Montant incorrect.';
+		break;
+	  case '00015':
+		return 'Paiement déjà effectué.';
+		break;
+	  case '00016':
+		return 'Abonnement déjà existant.';
+		break;
+	  case '00021':
+		return 'Carte non autorisée.';
+		break;
+	  case '00029':
+		return 'Carte non conforme.';
+		break;
+	  case '00030':
+		return 'Temps d\'attente de plus de 15 minutes sur la page de paiements.';
+		break;
+	  case '00033':
+		return 'Code pays de l\'adresse IP du navigateur de l\'acheteur non autorisé.';
+		break;
+	  case '00040':
+		return 'Opération sans authentification 3-DSecure, bloquée par le filtre.';
+		break;
+	  case '00100':
+		return 'Transaction approuvée ou traitée avec succès.';
+		break;
+	  case '00101':
+		return 'Contacter l\'émetteur de carte.';
+		break;
+	  case '00102':
+		return 'Contacter l\'émetteur de carte.';
+		break;
+	  case '00103':
+		return 'Commerçant invalide.';
+		break;
+	  case '00104':
+		return 'Conserver la carte.';
+		break;
+	  case '00105':
+		return 'Ne pas honorer.';
+		break;
+	  case '00107':
+		return 'Conserver la carte, conditions spéciales.';
+		break;
+	  case '00108':
+		return 'Approuver après identification du porteur.';
+		break;
+	  case '00112':
+		return 'Transaction invalide.';
+		break;
+	  case '00113':
+		return 'Montant invalide.';
+		break;
+	  case '00114':
+		return 'Numéro de porteur invalide.';
+		break;
+	  case '00115':
+		return 'Emetteur de carte inconnu.';
+		break;
+	  case '00117':
+		return 'Annulation client.';
+		break;
+	  case '00119':
+		return 'Répéter la transaction ultérieurement.';
+		break;
+	  case '00120':
+		return 'Réponse erronée (erreur dans le domaine serveur).';
+		break;
+	  case '00124':
+		return 'Mise à jour de fichier non supportée.';
+		break;
+	  case '00125':
+		return 'Impossible de localiser l\'enregistrement dans le fichier.';
+		break;
+	  case '00126':
+		return 'Enregistrement dupliqué, ancien enregistrement remplacé.';
+		break;
+	  case '00127':
+		return 'Erreur en « edit » sur champ de mise à jour fichier.';
+		break;
+	  case '00128':
+		return 'Accès interdit au fichier.';
+		break;
+	  case '00129':
+		return 'Mise à jour de fichier impossible.';
+		break;
+	  case '00130':
+		return 'Erreur de format.';
+		break;
+	  case '00133':
+		return 'Carte expirée.';
+		break;
+	  case '00138':
+		return 'Nombre d\'essais code confidentiel dépassé.';
+		break;
+	  case '00141':
+		return 'Carte perdue.';
+		break;
+	  case '00143':
+		return 'Carte volée.';
+		break;
+	  case '00151':
+		return 'Provision insuffisante ou crédit dépassé.';
+		break;
+	  case '00154':
+		return 'Date de validité de la carte dépassée.';
+		break;
+	  case '00155':
+		return 'Code confidentiel erroné.';
+		break;
+	  case '00156':
+		return 'Carte absente du fichier.';
+		break;
+	  case '00157':
+		return 'Transaction non permise à ce porteur.';
+		break;
+	  case '00158':
+		return 'Transaction interdite au terminal.';
+		break;
+	  case '00159':
+		return 'Suspicion de fraude.';
+		break;
+	  case '00160':
+		return 'L\'accepteur de carte doit contacter l\'acquéreur.';
+		break;
+	  case '00161':
+		return 'Dépasse la limite du montant de retrait.';
+		break;
+	  case '00163':
+		return 'Règles de sécurité non respectées.';
+		break;
+	  case '00168':
+		return 'Réponse non parvenue ou reçue trop tard.';
+		break;
+	  case '00175':
+		return 'Nombre d\'essais code confidentiel dépassé.';
+		break;
+	  case '00176':
+		return 'Porteur déjà en opposition, ancien enregistrement conservé.';
+		break;
+	  case '00189':
+		return 'Echec de l’authentification.';
+		break;
+	  case '00190':
+		return 'Arrêt momentané du système.';
+		break;
+	  case '00191':
+		return 'Emetteur de cartes inaccessible.';
+		break;
+	  case '00194':
+		return 'Demande dupliquée.';
+		break;
+	  case '00196':
+		return 'Mauvais fonctionnement du système.';
+		break;
+	  case '00197':
+		return 'Echéance de la temporisation de surveillance globale.';
+		break;
+	  case '99999':
+		return 'Opération en attente de validation par l\'émetteur du moyen de paiement.';
+		break;
+	  default:
+		return 'Erreur inconnue.';
+	}
+}
+
+}
+
+mmi_etransactions::__init();

+ 166 - 0
core/modules/modMBIETransactions.class.php

@@ -0,0 +1,166 @@
+<?php
+/**
+ * Copyright (C) 2004-2018  Laurent Destailleur     <eldy@users.sourceforge.net>
+ * Copyright (C) 2018-2019  Nicolas ZABOURI         <info@inovea-conseil.com>
+ * Copyright (C) 2019-2020  Frédéric France         <frederic.france@netlogic.fr>
+ * Copyright (C) 2020      	MB Informatique      	<info@mb-informatique.fr>
+ * Copyright (C) 2022       Mathieu Moulin          <contact@iprospective.fr>
+ */
+
+/**
+ * 	\defgroup   mbietransactions     Module MBIETransactions
+ *  \brief      MBIETransactions module descriptor.
+ *
+ *  \file       htdocs/mbietransactions/core/modules/modMBIETransactions.class.php
+ *  \ingroup    mbietransactions
+ *  \brief      Description and activation file for module MBIETransactions
+ */
+include_once DOL_DOCUMENT_ROOT.'/core/modules/DolibarrModules.class.php';
+
+/**
+ *  Description and activation class for module MBIETransactions
+ */
+class modMBIETransactions extends DolibarrModules
+{
+	/**
+	 * Constructor. Define names, constants, directories, boxes, permissions
+	 *
+	 * @param DoliDB $db Database handler
+	 */
+	public function __construct($db)
+	{
+		global $conf;
+		$this->db = $db;
+		$this->numero = 172370;
+		$this->rights_class = 'mbietransactions';
+		$this->family = "interface";
+		$this->module_position = '90';
+		$this->name = preg_replace('/^mod/i', '', get_class($this));
+		$this->description = "MBIETransactionsDescription";
+		$this->descriptionlong = "MBIETransactions description (Long)";
+		$this->editor_name = 'Mathieu Moulin iProspective';
+		$this->editor_url = 'https://www.iprospective.fr';
+		$this->version = '1.0.1';
+
+		$this->const_name = 'MAIN_MODULE_'.strtoupper($this->name);
+		$this->picto = 'logo@mbietransactions';
+		$this->module_parts = array(
+			'triggers' => 1,
+			'login' => 0,
+			'substitutions' => 0,
+			'menus' => 0,
+			'tpl' => 0,
+			'barcode' => 0,
+			'models' => 0,
+			'theme' => 0,
+			'css' => array(),
+			'js' => array(),
+			'hooks' => array('invoicecard', 'ordercard', 'propalcard', 'newpayment'),
+			'moduleforexternal' => 0,
+		);
+		$this->dirs = array("/mbietransactions/temp");
+		$this->config_page_url = array("setup.php@mbietransactions");
+		$this->hidden = false;
+		$this->depends = array('modMMICommon', 'modMMIPayments');
+		$this->requiredby = array();
+		$this->conflictwith = array();
+		$this->langfiles = array("mbietransactions@mbietransactions");
+		$this->phpmin = array(5, 5);
+		$this->need_dolibarr_version = array(8, 0);
+		$this->warnings_activation = array();
+		$this->warnings_activation_ext = array();
+		$this->const = array();
+
+		if (!isset($conf->mbietransactions) || !isset($conf->mbietransactions->enabled)) {
+			$conf->mbietransactions = new stdClass();
+			$conf->mbietransactions->enabled = 0;
+		}
+
+		$this->tabs = array();
+		$this->dictionaries = array();
+		$this->boxes = array();
+		$this->cronjobs = array();
+
+		// Permissions provided by this module
+		$this->rights = array();
+		$r = 0;
+		// Add here entries to declare new permissions
+		/* BEGIN MODULEBUILDER PERMISSIONS */
+		$this->rights[$r][0] = $this->numero + $r; // Permission id (must not be already used)
+		$this->rights[$r][1] = 'Read objects of MBIETransactions'; // Permission label
+		$this->rights[$r][4] = 'myobject'; // In php code, permission will be checked by test if ($user->rights->mbietransactions->level1->level2)
+		$this->rights[$r][5] = 'read'; // In php code, permission will be checked by test if ($user->rights->mbietransactions->level1->level2)
+		$r++;
+		$this->rights[$r][0] = $this->numero + $r; // Permission id (must not be already used)
+		$this->rights[$r][1] = 'Create/Update objects of MBIETransactions'; // Permission label
+		$this->rights[$r][4] = 'myobject'; // In php code, permission will be checked by test if ($user->rights->mbietransactions->level1->level2)
+		$this->rights[$r][5] = 'write'; // In php code, permission will be checked by test if ($user->rights->mbietransactions->level1->level2)
+		$r++;
+		$this->rights[$r][0] = $this->numero + $r; // Permission id (must not be already used)
+		$this->rights[$r][1] = 'Delete objects of MBIETransactions'; // Permission label
+		$this->rights[$r][4] = 'myobject'; // In php code, permission will be checked by test if ($user->rights->mbietransactions->level1->level2)
+		$this->rights[$r][5] = 'delete'; // In php code, permission will be checked by test if ($user->rights->mbietransactions->level1->level2)
+		$r++;
+		/* END MODULEBUILDER PERMISSIONS */
+
+		$this->menu = array();
+	}
+
+	/**
+	 *  Function called when module is enabled.
+	 *  The init function add constants, boxes, permissions and menus (defined in constructor) into Dolibarr database.
+	 *  It also creates data directories
+	 *
+	 *  @param      string  $options    Options when enabling module ('', 'noboxes')
+	 *  @return     int             	1 if OK, 0 if KO
+	 */
+	public function init($options = '')
+	{
+		global $conf, $langs;
+
+		$langs->loadLangs(array("mbietransactions@mbietransactions"));
+
+		$result = $this->_load_tables('/mbietransactions/sql/');
+		if ($result < 0) return -1; // Do not activate module if error 'not allowed' returned when loading module SQL queries (the _load_table run sql with run_sql with the error allowed parameter set to 'default')
+
+		// Create extrafields during init
+		include_once DOL_DOCUMENT_ROOT.'/core/class/extrafields.class.php';
+		$extrafields = new ExtraFields($this->db);
+		$extrafields->addExtraField('acompte', $langs->trans("MBIETransactionsAcompte"), 'double', 100, "4,2", 'propal', 0, 0, '', 0, true, '', -1, 0);
+		$extrafields->addExtraField('acompte_val', $langs->trans("MBIETransactionsAcompteVal"), 'price', 100, "8,2", 'propal', 0, 0, '', 0, true, '', -1, 0);
+		$extrafields->addExtraField('acompte', $langs->trans("MBIETransactionsAcompte"), 'double', 100, "4,2", 'commande', 0, 0, '', 0, true, '', -1, 0);
+		$extrafields->addExtraField('acompte_val', $langs->trans("MBIETransactionsAcompteVal"), 'price', 100, "8,2", 'commande', 0, 0, '', 0, true, '', -1, 0);
+		//$extrafields->addExtraField('mbi_payment_link', $langs->trans("MBIETransactionsPaymentLink"), 'text', 100, '2000', 'facture', 0, 0, '', '', 0, '', '1', '', '', $conf->entity, '', '1', 0, 0);
+		//$extrafields->addExtraField('mbi_image_link', $langs->trans("MBIETransactionsTrustImage"), 'text', 100, '2000', 'facture', 0, 0, '', '', 0, '', '1', '', '', $conf->entity, '', '1', 0, 0);
+		//$extrafields->addExtraField('mbi_payment_deposit', $langs->trans("MBIETransactionsAdvanceAmountTTC"), 'varchar', 100, '2000', 'facture', 0, 0, '', '', 1, '', '1', '', '', $conf->entity, '', '1', 0, 0);
+		//$extrafields->addExtraField('mbi_payment_multiple', $langs->trans("MBIETransactionsPaymentMultiple"), 'select', 100, '', 'facture', 0, 0, '', 'a:1:{s:7:"options";a:2:{i:2;s:1:"2";i:3;s:1:"3";}}', 1, '', '1', '', '', $conf->entity, '', '1', 0, 0);
+
+		// Permissions
+		$this->remove($options);
+
+		$sql = array(
+			"INSERT IGNORE INTO " . MAIN_DB_PREFIX . "c_paiement (entity, code, libelle, type, active, position) VALUES (" . $conf->entity . ", 'CBI', 'Carte internet', 2, 1, 0)",
+			//"INSERT IGNORE INTO " . MAIN_DB_PREFIX . "const (name, value) VALUES ('MBIETRANSACTIONS_TEMPLATE_PAYMENT_MAIL', '" . $langs->trans("MBIETRANSACTIONS_TEMPLATE_PAYMENT_MAIL_DEFAULT") . "')",
+			//"INSERT IGNORE INTO " . MAIN_DB_PREFIX . "const (name, value) VALUES ('MBIETRANSACTIONS_TEMPLATE_PAID_INVOICE_MAIL', '" . $langs->trans("MBIETRANSACTIONS_TEMPLATE_PAID_INVOICE_MAIL_DEFAULT") . "')",
+			"INSERT IGNORE INTO " . MAIN_DB_PREFIX . "const (name, value) VALUES ('MBIETRANSACTIONS_TEST', '1')",
+			//"INSERT IGNORE INTO " . MAIN_DB_PREFIX . "const (name, value) VALUES ('MBIETRANSACTIONS_SUBJECT_PAYMENT_MAIL', '" . $langs->trans("MBIETransactionsMailTitlePaymentLink") . "')",
+			//"INSERT IGNORE INTO " . MAIN_DB_PREFIX . "const (name, value) VALUES ('MBIETRANSACTIONS_SUBJECT_PAID_INVOICE_MAIL', '" . $langs->trans("MBIETransactionsMailTitlePaidInvoice") . "')"
+		);
+
+		return $this->_init($sql, $options);
+	}
+
+	/**
+	 *  Function called when module is disabled.
+	 *  Remove from database constants, boxes and permissions from Dolibarr database.
+	 *  Data directories are not deleted
+	 *
+	 *  @param      string	$options    Options when enabling module ('', 'noboxes')
+	 *  @return     int                 1 if OK, 0 if KO
+	 */
+	public function remove($options = '')
+	{
+		$sql = array();
+		return $this->_remove($sql, $options);
+	}
+}

+ 132 - 0
core/triggers/interface_99_modMBIETransactions_ETransactionsSendMail.class.php

@@ -0,0 +1,132 @@
+<?php
+/**
+ * Copyright (C) 2020       MB Informatique         <info@mb-informatique.fr>
+ * Copyright (C) 2022       MMI Mathieu Moulin      <contact@iprospective.fr>
+ */
+
+require_once DOL_DOCUMENT_ROOT.'/core/triggers/dolibarrtriggers.class.php';
+
+/**
+ *  Class of triggers for MyModule module
+ */
+class InterfaceEtransactionsSendMail extends DolibarrTriggers
+{
+	/**
+	 * @var DoliDB Database handler
+	 */
+	protected $db;
+
+	/**
+	 * Constructor
+	 *
+	 * @param DoliDB $db Database handler
+	 */
+	public function __construct($db)
+	{
+		$this->db = $db;
+
+		$this->name = preg_replace('/^Interface/i', '', get_class($this));
+		$this->family = "demo";
+		$this->description = "MBI ETransactions triggers";
+		$this->version = 'development';
+		$this->picto = 'mymodule@mymodule';
+	}
+
+	/**
+	 * Trigger name
+	 *
+	 * @return string Name of trigger file
+	 */
+	public function getName()
+	{
+		return $this->name;
+	}
+
+	/**
+	 * Trigger description
+	 *
+	 * @return string Description of trigger file
+	 */
+	public function getDesc()
+	{
+		return $this->description;
+	}
+
+	/**
+	 * Function called when a Dolibarrr business event is done.
+	 * All functions "runTrigger" are triggered if file
+	 * is inside directory core/triggers
+	 *
+	 * @param string 		$action 	Event action code
+	 * @param CommonObject 	$object 	Object
+	 * @param User 			$user 		Object user
+	 * @param Translate 	$langs 		Object langs
+	 * @param Conf 			$conf 		Object conf
+	 * @return int              		<0 if KO, 0 if no triggered ran, >0 if OK
+	 */
+	public function runTrigger($action, $object, User $user, Translate $langs, Conf $conf)
+	{
+		if (empty($conf->mbietransactions->enabled)) return 0;
+
+		global $db;
+		$langs->loadLangs(array("mbietransactions@mbietransactions"));
+		$extrafields = $object->array_options;
+		// Disabled by MMI
+        if (false && ($action == "BILL_PAYED" || $action == "BILL_SENTBYMAIL") && $object->mode_reglement_code == "CBI") {
+			require_once DOL_DOCUMENT_ROOT.'/core/class/CMailFile.class.php';
+			require_once DOL_DOCUMENT_ROOT.'/compta/facture/class/facture.class.php';
+            dol_syslog("Trigger 'MBIETransactions Send Mail' for action '$action' launched. id=".$object->id);
+			$facture = new Facture($db);
+			$facture->fetch($object->id);
+			$facture->fetch_thirdparty();
+			$totalttc = $facture->multicurrency_total_ttc;
+			$dejaregle = $facture->getSommePaiement(($conf->multicurrency->enabled && $facture->multicurrency_tx != 1) ? 1 : 0);
+			$resteapayer = price2num($totalttc - $dejaregle);
+
+			// Infos du mail
+
+			$outputlangs = $langs;
+
+			$substit= getCommonSubstitutionArray($outputlangs, 0, NULL, $object);
+			complete_substitutions_array($substit, $outputlangs, $object, array());
+
+			$substit['{REF}'] = $object->ref; // DEPRECATED -> USE __REF__ INSTEAD
+			$substit['{CLIENT}'] = $facture->thirdparty->name; // DEPRECATED -> USE __THIRDPARTY_NAME__ INSTEAD
+			$substit['{URL}'] =  $extrafields['options_mbi_payment_link'];
+			$substit['{IMG}'] = "<img src='" . $extrafields['options_mbi_image_link'] . "'>";
+
+            if ($action == "BILL_PAYED") {
+				$subject = $conf->global->MBIETRANSACTIONS_SUBJECT_PAID_INVOICE_MAIL;
+				$message = $conf->global->MBIETRANSACTIONS_TEMPLATE_PAID_INVOICE_MAIL;
+				$filepath = array(DOL_DATA_ROOT . "/facture/" . $facture->ref . "/" . $facture->ref . ".pdf");
+				$mimetype = array("application/pdf");
+				$filename = array($facture->ref . ".pdf");
+			} else if ($action == "BILL_SENTBYMAIL") {
+				$subject =  $conf->global->MBIETRANSACTIONS_SUBJECT_PAYMENT_MAIL;
+				$message = $conf->global->MBIETRANSACTIONS_TEMPLATE_PAYMENT_MAIL;
+				$filepath = array();
+				$mimetype = array();
+				$filename = array();
+			}
+			$sendto = $facture->thirdparty->email;
+			$from = $conf->global->MAIN_INFO_SOCIETE_MAIL;
+			$subject = make_substitutions($subject, $substit);
+            $message = make_substitutions($message, $substit);
+			$cc = !empty($conf->global->MBIETRANSACTIONS_CC_EMAILS) ? $conf->global->MBIETRANSACTIONS_CC_EMAILS : "";
+			$deliveryreceipt = $conf->global->MBIETRANSACTIONS_DELIVERY_RECEIPT_EMAIL == "1" ? 1 : 0;
+
+			// Génération du PDF
+
+			$hidedetails = !empty($conf->global->MAIN_GENERATE_DOCUMENTS_HIDE_DETAILS) ? 1 : 0;
+			$hidedesc = !empty($conf->global->MAIN_GENERATE_DOCUMENTS_HIDE_DESC) ? 1 : 0;
+			$hideref = !empty($conf->global->MAIN_GENERATE_DOCUMENTS_HIDE_REF) ? 1 : 0;
+			$facture->generateDocument("crabe", $langs, $hidedetails, $hidedesc, $hideref);
+
+			// Envoi du mail
+
+			$mailfile = new CMailFile($subject, $sendto, $from, $message, $filepath, $mimetype, $filename, $cc, "", $deliveryreceipt, 1);
+			$mailfile->sendfile();
+        }
+		return 0;
+	}
+}

+ 3 - 0
env.inc.php

@@ -0,0 +1,3 @@
+<?php
+
+$modulename = 'MBIETransactions';

+ 30 - 0
gd/index.php

@@ -0,0 +1,30 @@
+<?php
+
+// Copyright (C) 2020      MB Informatique        <info@mb-informatique.fr>
+
+function drawBorder(&$img, &$color, $thickness = 1)
+{
+    $x1 = 0;
+    $y1 = 0;
+    $x2 = ImageSX($img) - 1;
+    $y2 = ImageSY($img) - 1;
+
+    for($i = 0; $i < $thickness; $i++)
+    {
+        ImageRectangle($img, $x1++, $y1++, $x2--, $y2--, $color);
+    }
+}
+
+$image = imagecreate(186,50);
+$background_color = imagecolorallocate($image, 255, 255, 255);
+$color = imagecolorallocate($image, 0, 0, 0);
+$phone = $facture->thirdparty->phone;
+
+imagestring($image, 4, 35, 15, $phone, $color);
+
+drawBorder($image,$color, 4);
+
+$urlpng = DOL_DOCUMENT_ROOT. $path . "/gd/png/".$hashp.".png";
+
+imagepng($image, $urlpng);
+$image = imagecreatefrompng($urlpng);

BIN
gd/png/Y6m6si8Pyrw1V7Ol4EM59NQK0e6mfUzX.png


+ 0 - 0
gd/png/wheregoesimg.txt


BIN
img/American-Express-Logo.png


BIN
img/amex.png


BIN
img/ca-e-transactions-bis-400px.png


BIN
img/ca-e-transactions-bis.png


BIN
img/ca-e-transactions-cb-visa-mastercard.jpg


BIN
img/ca-e-transactions-cb-visa-mastercard.png


BIN
img/ca-e-transactions-cb-visa-mastercard.png23688


BIN
img/ca-e-transactions.png


BIN
img/cb-visa-mastercard-paylib.png


BIN
img/cb-visa-mastercard-paypal-paylib-amex.png


BIN
img/cb-visa-mastercard.png


BIN
img/cb.png


BIN
img/e-transactions-transparent.png


BIN
img/object_logo.png


BIN
img/object_mmiprestasync.png


BIN
img/paylib.png


BIN
img/paypal-logo.png


BIN
img/paypal.png


+ 103 - 0
langs/en_US/mbietransactions.lang

@@ -0,0 +1,103 @@
+# Copyright (C) 2020      	MB Informatique      	<info@mb-informatique.fr>
+#
+# 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 3 of the License, 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 program.  If not, see <https://www.gnu.org/licenses/>.
+
+#
+# Generic
+#
+# Module label 'ModuleMBIETransactionsName'
+ModuleMBIETransactionsName = MBI ETransactions
+# Module description 'ModuleMBIETransactionsDesc'
+ModuleMBIETransactionsDesc = MBI ETransactions description
+
+#
+# Admin page
+#
+MBIETransactionsSetup = MBI ETransactions setup
+Settings = Settings
+MBIETransactionsSetupPage = MBI ETransactions setup page
+MBIETRANSACTIONS_TEST = Test mode
+MBIETRANSACTIONS_RANK = Rank number
+MBIETRANSACTIONS_ID = E-Transactions/Paybox ID
+MBIETRANSACTIONS_SHOP_ID = Shop ID
+MBIETRANSACTIONS_KEY = Public key
+MBIETRANSACTIONS_DELIVERY_RECEIPT_EMAIL = Delivery receipt
+MBIETRANSACTIONS_CC_EMAILS = CC email addresses
+MBIETRANSACTIONS_CC_EMAILSTooltip = Comma separated
+MBIETRANSACTIONS_BANK_ACCOUNT = Bank account
+MBIETRANSACTIONS_TEMPLATE_PAYMENT_MAIL = Payment mail template
+MBIETRANSACTIONS_TEMPLATE_PAYMENT_MAIL_DEFAULT = Hello __THIRDPARTY_NAME__,<br>you can click on the secure link below to pay your invoice __REF__ to COMPANY via our bank payment interface.<br>{URL}<br>Security picture : You can trust this mail if your phone number is below.<br>{IMG}<br>COMPANY
+MBIETRANSACTIONS_TEMPLATE_PAYMENT_MAILTooltip = Mail template after sending the invoice. The variables {URL} (Payment link), {IMG} (Trust picture with customer phone number) and the other substitution variables can be used
+MBIETRANSACTIONS_TEMPLATE_PAID_INVOICE_MAIL = Paid invoice mail template
+MBIETRANSACTIONS_TEMPLATE_PAID_INVOICE_MAIL_DEFAULT = Hello __THIRDPARTY_NAME__, <br>thank you for your payment, there is nothing more to pay on invoice __REF__.
+MBIETRANSACTIONS_TEMPLATE_PAID_INVOICE_MAILTooltip = Mail template when the invoice is paid
+MBIETRANSACTIONS_SUBJECT_PAYMENT_MAIL = Payment mail subject
+MBIETRANSACTIONS_SUBJECT_PAID_INVOICE_MAIL = Paid invoice mail subject
+
+#
+# About page
+#
+About = About
+MBIETransactionsAbout = About MBIETransactions
+MBIETransactionsAboutPage = MBIETransactions about page
+
+#
+# Hooks
+#
+MBIETransactionsPaymentButton = Internet payment
+
+#
+# Pages de paiement
+#
+MBIETransactionsPaymentPageTitle = Payment Form
+MBIETransactionsPaymentPageH1 = Secured payment service
+MBIETransactionsPaymentAccepted = Accepted payment.
+MBIETransactionsPaymentAccepted2 = thanks you.
+MBIETransactionsPaymentAccepted3 = A confirmation mail has been sent to you, please keep it safe.
+MBIETransactionsPaymentCanceled = Payment canceled. You can always click of the payment link in the email to access your invoice payment.
+MBIETransactionsPaymentRefused = We are sorry, payment refused. We invite you to try again with the payment link in the email.
+MBIETransactionsPaymentRefused2 = If there is problem, please contact us to
+MBIETransactionsPaymentRefused3 = with the invoice reference.
+MBIETransactionsErrorConfig = We are sorry, there is a configuration problem into our payment service, please contact us to
+MBIETransactionsErrorConfigAlreadyPaid = Thank you, the payment was accepted. A confirmation mail has been sent to you, please keep it safe.
+MBIETransactionsPaymentRecapTitle = This screen allows you to make an online payment to
+MBIETransactionsPaymentRecapVerify = Please verify this informations below and click on 'Continue' to be connected to the secured payment server.
+MBIETransactionsPaymentRecapVerify2 = If there is an error, please send a mail to
+MBIETransactionsPaymentRecapVerify3 = with the invoice reference.
+MBIETransactionsPaymentRecapInfos = This is the informations about the payment :
+MBIETransactionsPaymentRecapRecipient = Recipient :
+MBIETransactionsPaymentRecapInvoiceRef = Invoice reference :
+MBIETransactionsPaymentRecapTransactionRef = Transaction reference :
+MBIETransactionsPaymentRecapName = Your name :
+MBIETransactionsPaymentRecapEmail = Your email address :
+MBIETransactionsPaymentRecapInvoiceAmount = Total invoice amount :
+MBIETransactionsPaymentRecapAlreadypaid = Already paid amount :
+MBIETransactionsPaymentRecapAdvance = Asked advance :
+MBIETransactionsPaymentRecapPaymentAmount = Total payment amount :
+MBIETransactionsPaymentLink = Payment link
+MBIETransactionsAcompte = Acompte (pourcentage)
+MBIETransactionsTrustImage = Trust image
+MBIETransactionsAdvanceAmountTTC = Advance amount
+MBIETransactionsMailTitlePaidInvoice = Paid invoice __REF__
+MBIETransactionsMailTitlePaymentLink = Payment link for the invoice __REF__
+MBIETransactionsPaymentPageContinue = Continue
+MBIETransactionsPaymentPageDeadline = Date of payment
+MBIETransactionsPaymentMultiple = Payment in x times
+
+#
+# Pages de paiement Standard
+#
+MBIETransactionsDoPayment = Payer par Carte
+MBIETransactionsDoPaymentAcompte = Acompte %s par Carte
+MBIETransactionsDoPaymentMultiple = Solde par Carte en %s fois

+ 116 - 0
langs/fr_FR/mbietransactions.lang

@@ -0,0 +1,116 @@
+# Copyright (C) 2020      	MB Informatique      	<info@mb-informatique.fr>
+# Copyright (C) 2022        Mathieu Moulin          <contact@iprospective.fr>
+#
+# 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 3 of the License, 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 program.  If not, see <https://www.gnu.org/licenses/>.
+
+#
+# Générique
+#
+# Module label 'ModuleMBIETransactionsName'
+ModuleMBIETransactionsName = Règlements ETransactions
+# Module description 'ModuleMBIETransactionsDesc'
+ModuleMBIETransactionsDesc = Module de paiement en ligne avec la solution de paiement <a href="https://www.ca-moncommerce.com/encaisser-sur-internet-avec-e-transactions/" target="_blank">ETransactions</a>
+
+#
+# Page d'administration
+#
+MBIETransactionsSetup = Configuration du module MBI ETransactions
+Settings = Réglages
+MBIETransactionsSetupPage = Page de configuration du module MBI ETransactions
+
+MBIETRANSACTIONS_TEST = Mode Test
+MBIETRANSACTIONS_TEST_RANK = Numéro de rang en mode Test
+MBIETRANSACTIONS_TEST_ID = Identifiant E-Transactions/Paybox en mode Test
+MBIETRANSACTIONS_TEST_SHOP_ID = Numéro de site en mode Test
+MBIETRANSACTIONS_TEST_KEY = Clé publique en mode Test
+MBIETRANSACTIONS_RANK = Numéro de rang
+MBIETRANSACTIONS_ID = Identifiant E-Transactions/Paybox
+MBIETRANSACTIONS_SHOP_ID = Numéro de site
+MBIETRANSACTIONS_KEY = Clé publique
+
+MBIETRANSACTIONS_DELIVERY_RECEIPT_EMAIL = Accusé de réception
+MBIETRANSACTIONS_CC_EMAILS = Adresses en copie des emails
+MBIETRANSACTIONS_CC_EMAILSTooltip = Séparées par une virgule
+MBIETRANSACTIONS_NOTIFICATION_FROM_EMAIL = Email expéditeur des notifications
+MBIETRANSACTIONS_NOTIFICATION_EMAIL = Email de réception des notifications
+MBIETRANSACTIONS_WEBSITE_CONTACT_URL = URL de contact sur le site web
+MBIETRANSACTIONS_BANK_ACCOUNT = Compte bancaire à créditer
+MBIETRANSACTIONS_TEMPLATE_PAYMENT_MAIL = Modèle du mail de paiement
+MBIETRANSACTIONS_TEMPLATE_PAYMENT_MAIL_DEFAULT = Bonjour __THIRDPARTY_NAME__,<br>vous pouvez cliquer sur le lien sécurisé ci-dessous pour effectuer le règlement de votre facture __REF__ à destination de SOCIETE via notre interface de paiement bancaire.<br>{URL}<br>Image de sécurité : Vous pouvez faire confiance à ce mail si votre numéro de téléphone apparait ci-dessous.<br>{IMG}<br>Cordialement, SOCIETE
+MBIETRANSACTIONS_TEMPLATE_PAYMENT_MAILTooltip = Modèle du mail envoyé après avoir envoyé la facture. Les variables {URL} (Lien de paiement) et {IMG} (Image de confiance avec le numéro de téléphone du client) peuvent être utilisées en plus des autres variables de substitution
+MBIETRANSACTIONS_TEMPLATE_PAID_INVOICE_MAIL = Modèle du mail de la facture acquitée
+MBIETRANSACTIONS_TEMPLATE_PAID_INVOICE_MAIL_DEFAULT = Bonjour __THIRDPARTY_NAME__, <br>nous vous remercions pour votre paiement et vous indiquons qu\'il ne reste plus rien à payer sur la facture __REF__.
+MBIETRANSACTIONS_TEMPLATE_PAID_INVOICE_MAILTooltip = Modèle du mail envoyé quand la facture est payée
+MBIETRANSACTIONS_SUBJECT_PAYMENT_MAIL = Sujet du mail de paiement
+MBIETRANSACTIONS_SUBJECT_PAID_INVOICE_MAIL = Sujet du mail avec facture acquitée
+
+#
+# Page À propos
+#
+About = À propos
+MBIETransactionsAbout = À propos de MBI ETransactions
+MBIETransactionsAboutPage = Page à propos de MBI ETransactions
+
+#
+# Hooks
+#
+MBIETransactionsPaymentButton = Paiement Etransactions
+
+#
+# Pages de paiement
+#
+MBIETransactionsPaymentPageTitle = Formulaire de paiement
+MBIETransactionsPaymentPageH1 = Service de paiement en ligne sécurisé
+MBIETransactionsPaymentAccepted = Le paiement a été accepté.
+MBIETransactionsPaymentAccepted2 = vous en remercie.
+MBIETransactionsPaymentAccepted3 = Un email de confirmation vous a été envoyé, merci de le conserver précieusement.
+MBIETransactionsPaymentCanceled = Le paiement a été annulé. Vous pouvez à tout moment cliquer de nouveau sur lien de règlement contenu dans l'email pour accéder au règlement de votre facture.
+MBIETransactionsPaymentRefused = Nous sommes désolés mais le paiement a été refusé. Nous vous invitons à réitérer le processus de règlement à partir du lien contenu dans l'email de règlement.
+MBIETransactionsPaymentRefused2 = Si le problème persiste, merci de nous contacter à l'adresse email
+MBIETransactionsPaymentRefused3 = en nous indiquant la référence de la facture.
+MBIETransactionsErrorConfig = Nous sommes désolés mais il y a un problème dans la configuration du service de paiement, merci de nous contacter à l'adresse email
+MBIETransactionsErrorConfigAlreadyPaid = Le paiement a été accepté. Nous vous en remercions. Un email de confirmation vous a été envoyé, merci de le conserver précieusement.
+MBIETransactionsPaymentRecapTitle = Cet écran vous permet de réaliser votre paiement en ligne à destination de
+MBIETransactionsPaymentRecapVerify = Merci de vérifier que ces informations sont correctes puis cliquer sur le bouton 'Continuer' pour être connecté sur le serveur sécurisé de paiement bancaire.
+MBIETransactionsPaymentRecapVerify2 = En cas d'erreur, vous pouvez envoyer un email à l'adresse
+MBIETransactionsPaymentRecapVerify3 = en spécifiant la référence de votre facture.
+MBIETransactionsPaymentRecapInfos = Voici les informations sur le paiement à réaliser :
+MBIETransactionsPaymentRecapRecipient = Bénéficiaire :
+MBIETransactionsPaymentRecapInvoiceRef = Référence facture :
+MBIETransactionsPaymentRecapTransactionRef = Référence de la transaction :
+MBIETransactionsPaymentRecapName = Votre nom :
+MBIETransactionsPaymentRecapEmail = Votre adresse email :
+MBIETransactionsPaymentRecapInvoiceAmount = Montant total de la facture :
+MBIETransactionsPaymentRecapAlreadypaid = Somme déjà perçue :
+MBIETransactionsPaymentRecapAdvance = Acompte demandé pour valider la commande :
+MBIETransactionsPaymentRecapPaymentAmount = Montant total du règlement :
+MBIETransactionsPaymentLink = Lien de paiement
+MBIETransactionsAcompte = Acompte (pourcentage)
+MBIETransactionsAcompteVal = Acompte (valeur)
+MBIETransactionsTrustImage = Image de confiance
+MBIETransactionsAdvanceAmountTTC = Montant de l'acompte TTC
+MBIETransactionsMailTitlePaidInvoice = Facture __REF__ acquittée
+MBIETransactionsMailTitlePaymentLink = Lien pour le règlement de la facture __REF__
+MBIETransactionsPaymentPageContinue = Continuer
+MBIETransactionsPaymentPageDeadline = Échéance
+MBIETransactionsPaymentMultiple = Paiement en x fois
+
+#
+# Pages de paiement Standard
+#
+MBIETransactionsDoPayment = Payer par Carte
+MBIETransactionsDoPaymentAcompte = Acompte %s par Carte
+MBIETransactionsDoPaymentMultiple = Payer en %s fois par Carte
+MBIETransactionsDoPaymentTransfer = Payer par virement bancaire
+MBIETransactionsDoPaymentCheque = Payer par chèque

+ 57 - 0
lib/create_link.lib.php

@@ -0,0 +1,57 @@
+<?php
+/**
+ * Copyright (C) 2020       MB Informatique         <info@mb-informatique.fr>
+ * Copyright (C) 2022       Mathieu Moulin          <contact@iprospective.fr>
+ */
+
+// Usual functions
+
+//dol_include_once('/mmipayments/class/mmi_payments.class.php');
+dol_include_once('/mbietransactions/class/mmi_etransactions.class.php');
+
+// @depreacated
+
+function mmi_etransactions_active($objecttype=NULL)
+{
+	return mmi_etransactions::active($objecttype);
+}
+
+function mmi_etransactions_paymentlink($objecttype, $id, $amount=NULL, $multiple=NULL, $autosubmit=false)
+{
+	return mmi_etransactions::paymentlink($objecttype, $id, $amount, $multiple, $autosubmit);
+}
+
+function mmi_etransactions_query($hash)
+{
+	return mmi_etransactions::query($hash);
+}
+
+function mmi_etransactions_info($hash)
+{
+	return mmi_etransactions::query($hash);
+}
+
+function mmi_etransactions_trans_query($hash, $trans, $autorisation)
+{
+	return mmi_etransactions::trans_query($hash, $trans, $autorisation);
+}
+
+function mmi_etransactions_trans_info($hash, $trans, $autorisation)
+{
+	return mmi_etransactions::trans_query($hash, $trans, $autorisation);
+}
+
+function mmi_etransactions_retrieve($hash)
+{
+	return mmi_etransactions::retrieve($hash);
+}
+
+function mmi_etransactions_loadobject($objecttype, $id)
+{
+	return mmi_payments::loadobject($objecttype, $id);
+}
+
+function mmi_etransactions_createhash()
+{
+	return mmi_etransactions::createhash();
+}

+ 38 - 0
lib/mbietransactions.lib.php

@@ -0,0 +1,38 @@
+<?php
+
+// Copyright (C) 2020      MB Informatique      <info@mb-informatique.fr>
+
+/**
+ * \file    mbietransactions/lib/mbietransactions.lib.php
+ * \ingroup mbietransactions
+ * \brief   Library files with common functions for MBIETransactions
+ */
+
+/**
+ * Prepare admin pages header
+ *
+ * @return array
+ */
+function mbietransactionsAdminPrepareHead()
+{
+	global $langs, $conf;
+
+	$langs->load("mbietransactions@mbietransactions");
+
+	$h = 0;
+	$head = array();
+
+	$head[$h][0] = dol_buildpath("/mbietransactions/admin/setup.php", 1);
+	$head[$h][1] = $langs->trans("Settings");
+	$head[$h][2] = 'settings';
+	$h++;
+
+	$head[$h][0] = dol_buildpath("/mbietransactions/admin/about.php", 1);
+	$head[$h][1] = $langs->trans("About");
+	$head[$h][2] = 'about';
+	$h++;
+
+	complete_head_from_modules($conf, $langs, null, $head, $h, 'mbietransactions');
+
+	return $head;
+}

+ 38 - 0
main_load.inc.php

@@ -0,0 +1,38 @@
+<?php
+
+// Load Dolibarr environment
+$res = 0;
+// Try main.inc.php into web root known defined into CONTEXT_DOCUMENT_ROOT (not always defined)
+if (!$res && !empty($_SERVER["CONTEXT_DOCUMENT_ROOT"])) {
+	$res = @include $_SERVER["CONTEXT_DOCUMENT_ROOT"]."/main.inc.php";
+}
+// Try main.inc.php into web root detected using web root calculated from SCRIPT_FILENAME
+$tmp = empty($_SERVER['SCRIPT_FILENAME']) ? '' : $_SERVER['SCRIPT_FILENAME']; $tmp2 = realpath(__FILE__); $i = strlen($tmp) - 1; $j = strlen($tmp2) - 1;
+while ($i > 0 && $j > 0 && isset($tmp[$i]) && isset($tmp2[$j]) && $tmp[$i] == $tmp2[$j]) {
+	$i--; $j--;
+}
+if (!$res && $i > 0 && file_exists(substr($tmp, 0, ($i + 1))."/main.inc.php")) {
+	$res = @include substr($tmp, 0, ($i + 1))."/main.inc.php";
+}
+if (!$res && $i > 0 && file_exists(dirname(substr($tmp, 0, ($i + 1)))."/main.inc.php")) {
+	$res = @include dirname(substr($tmp, 0, ($i + 1)))."/main.inc.php";
+}
+// Try main.inc.php using relative path
+if (!$res && file_exists("../main.inc.php")) {
+	$res = @include "../main.inc.php";
+}
+if (!$res && file_exists("../../main.inc.php")) {
+	$res = @include "../../main.inc.php";
+}
+if (!$res && file_exists("../../../main.inc.php")) {
+	$res = @include "../../../main.inc.php";
+}
+if (!$res) {
+	die("Include of main fails");
+}
+
+// Useful things
+$moduleclassname = 'mod'.$modulename;
+$moduledir = strtolower($modulename);
+$modulecontext = $moduledir."@".$moduledir;
+$moduleprefix = strtoupper($modulename);

+ 3 - 0
modulebuilder.txt

@@ -0,0 +1,3 @@
+# DO NOT DELETE THIS FILE MANUALLY
+# File to flag module built using official module template.
+# When this file is present into a module directory, you can edit it with the module builder tool. Use ModuleBuilder if you want to delete module. 

+ 52 - 0
payment.css

@@ -0,0 +1,52 @@
+div.buttonpayment {
+    min-height: 60px;
+    height: auto;
+    background-color: transparent;
+    border: 2px solid #068d95;
+    color: black;
+    padding: 0;
+    max-width: 367px;
+    margin-left: 3px;
+}
+div.buttonpayment input {
+    background-color: #068d95;
+    margin: 0 -0 10px 0;
+    padding: 5px;
+    width: 100%;
+}
+div.buttonpayment input:hover {
+    margin: 0 -0 10px 0;
+}
+
+div.buttonpayment .fa {
+    background-color: #068d95;
+}
+
+div.buttonpayment .buttonpaymentsmall img {
+    height: 31px;
+    padding: 0 8px 14px 8px;
+}
+
+div.buttonpayment .buttonpaymentsmall img.img_paypal {
+    height: 45px;
+    padding-bottom: 0;
+}
+
+div.buttonpayment .pay_infos {
+    padding: 0 10px 5px 10px;
+}
+
+div.buttonpayment .small {
+    font-size: 0.9em;
+    text-decoration: underline;
+}
+
+div.voile {
+    opacity: 0.75;
+    position: absolute;
+    margin-top: 0px;
+    left:0;
+    right:0;
+    height:1300px;
+    background-color: white;
+}

+ 331 - 0
payment.php

@@ -0,0 +1,331 @@
+<?php
+/**
+ * Copyright (C) 2020       MB Informatique         <info@mb-informatique.fr>
+ * Copyright (C) 2022       Mathieu Moulin          <contact@iprospective.fr>
+ */
+
+if (!defined('NOLOGIN')) define("NOLOGIN", 1); // This means this output page does not require to be logged.
+if (!defined('NOCSRFCHECK')) define("NOCSRFCHECK", 1); // We accept to go on this page from external web site.
+
+global $db, $conf, $langs;
+
+$confError = false;
+
+try {
+	if (!file_exists('../../main.inc.php'))
+		throw new Exception ('Does not exist');
+	else
+		require '../../main.inc.php';
+		$path = "/custom";
+}
+catch(Exception $e) {
+	require '../main.inc.php';
+	$path = "";
+}
+
+//require_once DOL_DOCUMENT_ROOT.'/core/lib/functions.lib.php';
+dol_include_once('/mbietransactions/lib/create_link.lib.php');
+
+$langs->loadLangs(array("mbietransactions@mbietransactions"));
+
+$hash = $_GET['hashp'];
+$autosubmit = isset($_GET['autosubmit']);
+
+if ($obj=mmi_etransactions::info($hash)) {
+	$objecttype = $obj->objecttype;
+	$id = $obj->fk_object;
+} else {
+	$confError = true;
+}
+//var_dump($obj);
+
+if (empty($objecttype))
+	die('Unknown Hash');
+//var_dump($objecttype); var_dump($id); die();
+
+if (!mmi_etransactions::active($objecttype))
+	$confError = true;
+
+if (!($object = mmi_payments::loadobject($objecttype, $id)))
+	die('Unknown Payment Object');
+
+$totalttc = $object->total_ttc; // TOTAL TTC
+if ($objecttype=='Facture') {
+	$dejaregle = $object->getSommePaiement(($conf->multicurrency->enabled && $object->multicurrency_tx != 1) ? 1 : 0); // DEJA REGLE
+	$resteapayer = ($totalttc - $dejaregle - $object->getSumCreditNotesUsed() - $object->getSumDepositsUsed()); // RESTE A PAYER
+}
+else {
+	$dejaregle = mmi_payments::total_regle($objecttype, $object->id);;
+	$resteapayer = ($totalttc - $dejaregle);
+}
+$extrafields2 = $object->array_options;
+
+// Multiple : total ou solde
+if ($obj->multiple) {
+	$resteapayer = price2num($resteapayer);
+	$extrafields2['options_mbi_payment_multiple'] = $obj->multiple;
+}
+// Acompte : d'un coup
+elseif ($obj->amount && empty($dejaregle)) {
+	$resteapayer = price2num($obj->amount);
+	$extrafields2['options_mbi_payment_deposit'] = $obj->amount;
+}
+// Montant à la main
+elseif ($obj->amount) {
+	$resteapayer = price2num($obj->amount);
+}
+
+if ($resteapayer == 0) {
+	$confError = true;
+}
+
+// Grosse parenthèse
+if (!$confError) {
+	// Mode test
+	if ($conf->global->MBIETRANSACTIONS_TEST) {
+		$pbx_site = $conf->global->MBIETRANSACTIONS_TEST_SHOP_ID;
+		$pbx_rang = $conf->global->MBIETRANSACTIONS_TEST_RANK;
+		$pbx_identifiant = $conf->global->MBIETRANSACTIONS_TEST_ID;
+		$key = $conf->global->MBIETRANSACTIONS_TEST_KEY;
+		$pbx_porteur = $conf->global->MAIN_INFO_SOCIETE_MAIL;
+		$serveurs = array('preprod-tpeweb.e-transactions.fr');
+	}
+	// Mode prod
+	else {
+		$pbx_site = $conf->global->MBIETRANSACTIONS_SHOP_ID;
+		$pbx_rang = $conf->global->MBIETRANSACTIONS_RANK;
+		$pbx_identifiant = $conf->global->MBIETRANSACTIONS_ID;
+		$key = $conf->global->MBIETRANSACTIONS_KEY;
+		$pbx_porteur = $object->thirdparty->email;
+		$serveurs = array('tpeweb.e-transactions.fr', 'tpeweb1.e-transactions.fr');
+	}
+	
+	$pbx_total = $resteapayer * 100;
+	//var_dump($object); die();
+	$usercode = '';
+
+	$contacts = $object->liste_contact(-1, 'internal');
+	foreach($contacts as $contact) {
+		//var_dump($contact);
+		// Contact suivi commande
+		if (in_array($contact['fk_c_type_contact'], [91, 31, 50, 140, 70])) {
+			$contactuser = new User($db);
+			$contactuser->fetch($contact['id']);
+			//var_dump($user); die();
+			$usercode = $contactuser->accountancy_code;
+		}
+	}
+	if (empty($usercode) && $object->thirdparty) {
+		$contactusers = $object->thirdparty->getSalesRepresentatives($user);
+		foreach($contactusers as $contactuser2) {
+			$contactuser = new User($db);
+			$contactuser->fetch($contactuser2['id']);
+			//var_dump($extrafields); die();
+			//var_dump($user); die();
+			$usercode = $contactuser->accountancy_code;
+			break;
+		}
+	}
+	$pbx_cmd = $object->ref.($object->thirdparty ?' - '.$object->thirdparty->name :'').(!empty($usercode) ?' - '.$usercode :'').' - '.$hash;
+	//var_dump($pbx_cmd); die();
+	
+	if ($extrafields2['options_mbi_payment_deposit'] > 0 && $extrafields2['options_mbi_payment_deposit'] > $dejaregle) {
+		$pbx_total = ($extrafields2['options_mbi_payment_deposit'] - $dejaregle) * 100;
+	}
+	$pbx_total = str_replace(",", "", $pbx_total);
+	$pbx_total = str_replace(".", "", $pbx_total);
+
+	if ($extrafields2['options_mbi_payment_multiple'] == "2" && empty($extrafields2['options_mbi_payment_deposit'])) {
+		$total = $resteapayer * 100;
+		$pbx_total = floor($total / 2);
+		$pbx_2mont1 = $total - $pbx_total;
+		$pbx_date1 = date('d/m/Y',strtotime('+1 month'));
+	} else if ($extrafields2['options_mbi_payment_multiple'] == "3" && empty($extrafields2['options_mbi_payment_deposit'])) {
+		$total = $resteapayer * 100;
+		$pbx_total = floor($total / 3);
+		$pbx_2mont1 = $pbx_total;
+		$pbx_2mont2 = $total - ($pbx_total + $pbx_2mont1);
+		$pbx_date1 = date('d/m/Y',strtotime('+1 month'));
+		$pbx_date2 = date('d/m/Y',strtotime('+2 month'));
+	}
+
+	$pbx_effectue = dol_buildpath($path . '/mbietransactions/accepted.php', 2);
+	$pbx_annule = dol_buildpath($path . '/mbietransactions/canceled.php', 2);
+	$pbx_refuse = dol_buildpath($path . '/mbietransactions/refused.php', 2);
+	$pbx_repondre_a = str_replace('http:', 'https:', dol_buildpath($path . '/mbietransactions/retour.php', 2));
+	$pbx_retour = 'Mt:M;Ref:R;Auto:A;Erreur:E;Trans:T';
+
+
+// --------------- TESTS DE DISPONIBILITE DES SERVEURS ---------------
+
+	$serveurOK = "";
+	foreach ($serveurs as $serveur) {
+		$doc = new DOMDocument();
+		$doc->loadHTMLFile('https://' . $serveur . '/load.html');
+		$server_status = "";
+		$element = $doc->getElementById('server_status');
+		if ($element) {
+			$server_status = $element->textContent;
+		}
+		if ($server_status == "OK") {
+			$serveurOK = $serveur;
+			break;
+		}
+	}
+
+	if (!$serveurOK) {
+		die("Erreur : Aucun serveur fonctionnel n'a été trouvé");
+	}
+
+	$serveurOK = 'https://' . $serveurOK . '/cgi/MYchoix_pagepaiement.cgi';
+
+// --------------- TRAITEMENT DES VARIABLES ---------------
+
+	$dateTime = date("c");
+
+	$msg = "PBX_SITE=" . $pbx_site .
+		"&PBX_RANG=" . $pbx_rang .
+		"&PBX_IDENTIFIANT=" . $pbx_identifiant .
+		"&PBX_TOTAL=" . $pbx_total .
+		"&PBX_DEVISE=978" .
+		"&PBX_CMD=" . $pbx_cmd .
+		"&PBX_PORTEUR=" . $pbx_porteur .
+		"&PBX_REPONDRE_A=" . $pbx_repondre_a .
+		"&PBX_RETOUR=" . $pbx_retour .
+		"&PBX_EFFECTUE=" . $pbx_effectue .
+		"&PBX_ANNULE=" . $pbx_annule .
+		"&PBX_REFUSE=" . $pbx_refuse .
+		"&PBX_HASH=SHA512" .
+		"&PBX_TIME=" . $dateTime;
+
+	if ($extrafields2['options_mbi_payment_multiple'] == "2" && empty($extrafields2['options_mbi_payment_deposit'])) {
+		$msg .= "&PBX_2MONT1=" . $pbx_2mont1;
+		$msg .= "&PBX_DATE1=" . $pbx_date1;
+	} else if ($extrafields2['options_mbi_payment_multiple'] == "3" && empty($extrafields2['options_mbi_payment_deposit'])) {
+		$msg .= "&PBX_2MONT1=" . $pbx_2mont1;
+		$msg .= "&PBX_DATE1=" . $pbx_date1;
+		$msg .= "&PBX_2MONT2=" . $pbx_2mont2;
+		$msg .= "&PBX_DATE2=" . $pbx_date2;
+	}
+
+	$binKey = pack("H*", $key);
+	$hmac = strtoupper(hash_hmac('sha512', $msg, $binKey));
+
+	$form = "<form id='payment_form' method='POST' action='" . $serveurOK . "'>"
+	."<input type='hidden' name='PBX_SITE' value='" . $pbx_site . "'>"
+	."<input type='hidden' name='PBX_RANG' value='" . $pbx_rang . "'>"
+	."<input type='hidden' name='PBX_IDENTIFIANT' value='" . $pbx_identifiant . "'>"
+	."<input type='hidden' name='PBX_TOTAL' value='" . $pbx_total . "'>"
+	."<input type='hidden' name='PBX_DEVISE' value='978'>"
+	."<input type='hidden' name='PBX_CMD' value='" . $pbx_cmd . "'>"
+	."<input type='hidden' name='PBX_PORTEUR' value='" . $pbx_porteur . "'>"
+	."<input type='hidden' name='PBX_REPONDRE_A' value='" . $pbx_repondre_a . "'>"
+	."<input type='hidden' name='PBX_RETOUR' value='" . $pbx_retour . "'>"
+	."<input type='hidden' name='PBX_EFFECTUE' value='" . $pbx_effectue . "'>"
+	."<input type='hidden' name='PBX_ANNULE' value='" . $pbx_annule . "'>"
+	."<input type='hidden' name='PBX_REFUSE' value='" . $pbx_refuse . "'>"
+	."<input type='hidden' name='PBX_HASH' value='SHA512'>"
+	."<input type='hidden' name='PBX_TIME' value='" . $dateTime . "'>";
+	if ($extrafields2['options_mbi_payment_multiple'] == "2" && empty($extrafields2['options_mbi_payment_deposit'])) {
+		$form .= "<input type='hidden' name='PBX_2MONT1' value='" . $pbx_2mont1 . "'>";
+		$form .= "<input type='hidden' name='PBX_DATE1' value='" . $pbx_date1 . "'>";
+	} else if ($extrafields2['options_mbi_payment_multiple'] == "3" && empty($extrafields2['options_mbi_payment_deposit'])) {
+		$form .= "<input type='hidden' name='PBX_2MONT1' value='" . $pbx_2mont1 . "'>";
+		$form .= "<input type='hidden' name='PBX_DATE1' value='" . $pbx_date1 . "'>";
+		$form .= "<input type='hidden' name='PBX_2MONT2' value='" . $pbx_2mont2 . "'>";
+		$form .= "<input type='hidden' name='PBX_DATE2' value='" . $pbx_date2 . "'>";
+	}
+	$form .= "<input type='hidden' name='PBX_HMAC' value='" . $hmac . "'>";
+	$form .= "<input class='button' type='submit' value='" . $langs->trans("MBIETransactionsPaymentPageContinue") . "'>";
+	$form .= "</form>";
+	
+	// REDIRECTION DIRECTE
+
+	if ($autosubmit) {
+		echo $form;
+		echo '<script type="text/javascript">document.getElementById(\'payment_form\').submit();</script>';
+		die();
+	}
+	
+	// AFFICHAGE COMPLET
+
+	echo "<head><meta name='robots' content='noindex,nofollow'><title>" . $langs->trans("MBIETransactionsPaymentPageTitle") . "</title>";
+	echo "<link rel='stylesheet' type='text/css' href='" . DOL_URL_ROOT . $conf->css . "?lang=" . $langs->defaultlang . "'>";
+	echo "<link rel='stylesheet' type='text/css' href='" . DOL_URL_ROOT . $path . "/mbietransactions/style.css'></head>";
+	echo "<div id='logo'>";
+	if (!empty($mysoc->logo)) {
+		echo "<img width='150px;' id='paymentlogo' title='" . $conf->global->MAIN_INFO_SOCIETE_NOM . "' src='" . DOL_URL_ROOT . "/viewimage.php?modulepart=mycompany&amp;file=" . urlencode('logos/' . $mysoc->logo) . "'>";
+	}
+	echo "</div>";
+
+	echo "<div id='payment-content'>";
+	echo "<h1>" . $langs->trans("MBIETransactionsPaymentPageH1") . "</h1><br />";
+	echo "<p style='font-size: 1.2em;'>" . $langs->trans("MBIETransactionsPaymentRecapTitle") . " <strong>" . $conf->global->MAIN_INFO_SOCIETE_NOM . "</strong></p>";
+	echo "<p style='font-size: 1.2em;'>" . $langs->trans("MBIETransactionsPaymentRecapVerify") . " <br />" . $langs->trans("MBIETransactionsPaymentRecapVerify2") . " <strong>" . $conf->global->MAIN_INFO_SOCIETE_MAIL . "</strong> " . $langs->trans("MBIETransactionsPaymentRecapVerify3") . "</p>";
+	echo "<table id='payment-table' style='font-size: 1.2em;'>";
+	echo "<tr class='liste_total'><td colspan='2'>" . $langs->trans("MBIETransactionsPaymentRecapInfos") . "</td></tr>";
+	echo "<tr><td class='payment-row-left'>" . $langs->trans("MBIETransactionsPaymentRecapRecipient") . "</td><td class='payment-row-right'><strong>" . $conf->global->MAIN_INFO_SOCIETE_NOM . "</strong></td></tr>";
+	echo "<tr><td class='payment-row-left'>" . $langs->trans("MBIETransactionsPaymentRecapInvoiceRef") . "</td><td class='payment-row-right'><strong>" . $object->ref . "</strong></td></tr>";
+	echo "<tr><td class='payment-row-left'>" . $langs->trans("MBIETransactionsPaymentRecapTransactionRef") . "</td><td class='payment-row-right'><strong>" . $pbx_cmd . "</strong></td></tr>";
+	echo "<tr><td class='payment-row-left'>" . $langs->trans("MBIETransactionsPaymentRecapName") . "</td><td class='payment-row-right'><strong>" . $object->thirdparty->name . "</strong></td></tr>";
+	echo "<tr><td class='payment-row-left'>" . $langs->trans("MBIETransactionsPaymentRecapEmail") . "</td><td class='payment-row-right'><strong>" . $object->thirdparty->email . "</strong></td></tr>";
+	echo "<tr class='liste_total'><td colspan'2'>&nbsp;</td></tr>";
+	echo "<tr><td class='payment-row-left'>" . $langs->trans("MBIETransactionsPaymentRecapInvoiceAmount") . "</td><td class='payment-row-right'><strong>" . price($totalttc) . " € TTC</strong></td></tr>";
+	echo "<tr><td class='payment-row-left'>" . $langs->trans("MBIETransactionsPaymentRecapAlreadypaid") . "</td><td class='payment-row-right'><strong>" . price($dejaregle) . " € TTC</strong></td></tr>";
+	// Acompte paramétré
+	if (!empty($extrafields2['options_mbi_payment_deposit']) && empty($dejaregle)) {
+		echo "<tr><td class='payment-row-left'><strong>" . $langs->trans("MBIETransactionsPaymentRecapAdvance") . "</strong></td><td class='payment-row-right'><strong>" . price($pbx_total / 100) . " € TTC</strong></td></tr>";
+	} else {
+		echo "<tr><td class='payment-row-left'><strong>" . $langs->trans("MBIETransactionsPaymentRecapPaymentAmount") . "</strong></td><td class='payment-row-right'><strong>" . price($pbx_total / 100) . " € TTC</strong></td></tr>";
+	}
+	// Paiement en plusieurs fois
+	if ($extrafields2['options_mbi_payment_multiple'] == "2" && empty($extrafields2['options_mbi_payment_deposit'])) {
+		echo "<tr><td>" . $langs->trans("MBIETransactionsPaymentPageDeadline") . " : " . price($pbx_2mont1 / 100) . " € TTC - " . $pbx_date1 . "</td></tr>";
+	} else if ($extrafields2['options_mbi_payment_multiple'] == "3" && empty($extrafields2['options_mbi_payment_deposit'])) {
+		echo "<tr><td>" . $langs->trans("MBIETransactionsPaymentPageDeadline") . " : " . price($pbx_2mont1 / 100) . " € TTC - " . $pbx_date1 . "</td></tr>";
+		echo "<tr><td>" . $langs->trans("MBIETransactionsPaymentPageDeadline") . " : " . price($pbx_2mont2 / 100) . " € TTC - " . $pbx_date2 . "</td></tr>";
+	}
+
+	echo "<tr class='liste_total'><td colspan='2' class='payment-button'>".$form."</td></tr></table></div><br><br>";
+
+	echo "<div><img style='width:250px' src='" . DOL_URL_ROOT . $path . "/mbietransactions/img/ca-e-transactions-cb-visa-mastercard.jpg'>";
+	echo "<p>" . $conf->global->MAIN_INFO_SOCIETE_NOM . " © " . date('Y') . "<br><small>";
+	if ($conf->global->MAIN_INFO_SIRET) {
+		echo "SIRET: " . $conf->global->MAIN_INFO_SIRET;
+	}
+	echo "<br>" . $conf->global->MAIN_INFO_SOCIETE_ADDRESS . " " . $conf->global->MAIN_INFO_SOCIETE_ZIP . " " . $conf->global->MAIN_INFO_SOCIETE_TOWN . " - " . $conf->global->MAIN_INFO_SOCIETE_TEL . "</small></p>";
+	echo "</div>";
+
+}
+// ERREUR de configuration
+else {
+
+	echo "<head><meta name='robots' content='noindex,nofollow'><title>" . $langs->trans("MBIETransactionsPaymentPageTitle") . "</title>";
+	echo "<link rel='stylesheet' type='text/css' href='" .  DOL_URL_ROOT . $conf->css . "?lang=" . $langs->defaultlang . "'>";
+	echo "<link rel='stylesheet' type='text/css' href='" . DOL_URL_ROOT . $path . "/mbietransactions/style.css'></head>";
+	echo "<div id='logo'>";
+	if (!empty($mysoc->logo)) {
+		echo "<img width='150px;' id='paymentlogo' title='" . $conf->global->MAIN_INFO_SOCIETE_NOM . "' src='" . DOL_URL_ROOT . "/viewimage.php?modulepart=mycompany&amp;file=" . urlencode('logos/'.$mysoc->logo) ."'>";
+	}
+	echo "</div>";
+
+	if ($resteapayer == 0) {
+		echo "<div id='payment-content'>
+	<h1 style='font-size: 1.6em;'>" . $langs->trans("MBIETransactionsPaymentPageH1") . "</h1>
+	<p style='font-size: 1.2em;'>" . $langs->trans("MBIETransactionsErrorConfigAlreadyPaid") . "</p>
+	</div>";
+	} else {
+		echo "<div id='payment-content'>
+	<h1 style='font-size: 1.6em;'>" . $langs->trans("MBIETransactionsPaymentPageH1") . "</h1>
+	<p style='font-size: 1.2em;'>" . $langs->trans("MBIETransactionsErrorConfig") . " <strong>" . $conf->global->MAIN_INFO_SOCIETE_MAIL . "</strong></p>
+	</div>";
+	}
+	?>
+	<br /><br />
+	<div>
+		<img style="width:250px" src="<?php echo DOL_URL_ROOT . $path . "/mbietransactions/img/ca-e-transactions-cb-visa-mastercard.jpg"; ?>" />
+		<p><?php echo $conf->global->MAIN_INFO_SOCIETE_NOM; ?> © <?php echo date('Y') ?><br><small><?php if ($conf->global->MAIN_INFO_SIRET) { echo "SIRET: " . $conf->global->MAIN_INFO_SIRET; } ?><br><?php echo $conf->global->MAIN_INFO_SOCIETE_ADDRESS; ?> <?php echo $conf->global->MAIN_INFO_SOCIETE_ZIP; ?> <?php echo $conf->global->MAIN_INFO_SOCIETE_TOWN; ?> - <?php echo $conf->global->MAIN_INFO_SOCIETE_TEL; ?></small></p>
+	</div>
+
+	<?php
+}

+ 45 - 0
refused.php

@@ -0,0 +1,45 @@
+<?php
+
+// Copyright (C) 2020      MB Informatique      <info@mb-informatique.fr>
+
+if (!defined('NOLOGIN')) define("NOLOGIN", 1); // This means this output page does not require to be logged.
+if (!defined('NOCSRFCHECK')) define("NOCSRFCHECK", 1); // We accept to go on this page from external web site.
+
+global $db, $conf, $langs;
+
+try {
+	if (!file_exists('../../main.inc.php'))
+		throw new Exception ('Does not exist');
+	else
+		require '../../main.inc.php';
+	$path = "/custom";
+}
+catch(Exception $e) {
+	require '../main.inc.php';
+	$path = "";
+}
+
+$langs->loadLangs(array("mbietransactions@mbietransactions"));
+
+echo "<head><meta name='robots' content='noindex,nofollow'><title>" . $langs->trans("MBIETransactionsPaymentPageTitle") . "</title>";
+echo "<link rel='stylesheet' type='text/css' href='" .  DOL_URL_ROOT . $conf->css . "?lang=" . $langs->defaultlang . "'>";
+echo "<link rel='stylesheet' type='text/css' href='" . DOL_URL_ROOT . $path . "/mbietransactions/style.css'></head>";
+echo "<div id='logo'>";
+if (!empty($mysoc->logo)) {
+	echo "<img width='150px;' id='paymentlogo' title='" . $conf->global->MAIN_INFO_SOCIETE_NOM . "' src='" . DOL_URL_ROOT . "/viewimage.php?modulepart=mycompany&amp;file=" . urlencode('logos/'.$mysoc->logo) ."'>";
+}
+echo "</div>";
+
+echo "<div id='payment-content'>
+<h1 style='font-size: 1.6em;'>" . $langs->trans("MBIETransactionsPaymentPageH1") . "</h1>
+<p style='font-size: 1.2em;'>" . $langs->trans("MBIETransactionsPaymentRefused") . "</p>
+<p style='font-size: 1.2em;'>" . $langs->trans("MBIETransactionsPaymentRefused2") . " <strong>" . $conf->global->MAIN_INFO_SOCIETE_MAIL . "</strong> " . $langs->trans("MBIETransactionsPaymentRefused3") . "</p>
+</div>";
+
+?>
+
+<br><br>
+<div>
+	<img style="width:250px" src="<?php echo DOL_URL_ROOT . $path . "/mbietransactions/img/ca-e-transactions-cb-visa-mastercard.jpg"; ?>" />
+	<p><?php echo $conf->global->MAIN_INFO_SOCIETE_NOM; ?> © <?php echo date('Y') ?><br><small><?php if ($conf->global->MAIN_INFO_SIRET) { echo "SIRET: " . $conf->global->MAIN_INFO_SIRET; } ?><br><?php echo $conf->global->MAIN_INFO_SOCIETE_ADDRESS; ?> <?php echo $conf->global->MAIN_INFO_SOCIETE_ZIP; ?> <?php echo $conf->global->MAIN_INFO_SOCIETE_TOWN; ?> - <?php echo $conf->global->MAIN_INFO_SOCIETE_TEL; ?></small></p>
+</div>

+ 222 - 0
retour.php

@@ -0,0 +1,222 @@
+<?php
+/**
+ * Copyright (C) 2020       MB Informatique         <info@mb-informatique.fr>
+ * Copyright (C) 2022       Mathieu Moulin          <contact@iprospective.fr>
+ */
+
+if (!defined('NOLOGIN')) define("NOLOGIN", 1); // This means this output page does not require to be logged.
+if (!defined('NOCSRFCHECK')) define("NOCSRFCHECK", 1); // We accept to go on this page from external web site.
+
+global $db, $conf, $mysoc;
+
+try {
+	if (!file_exists('../../main.inc.php'))
+		throw new Exception ('Does not exist');
+	else
+		require '../../main.inc.php';
+	$path = "/custom";
+}
+catch(Exception $e) {
+	require '../main.inc.php';
+	$path = "";
+}
+
+//var_dump($mysoc->email); die();
+
+require_once DOL_DOCUMENT_ROOT . '/custom/mmipayments/class/mmi_payments.class.php';
+dol_include_once('/mbietransactions/lib/create_link.lib.php');
+
+$error = GETPOST('Erreur');
+$autorisation = urldecode(GETPOST('Auto'));
+$trans = urldecode(GETPOST('Trans'));
+$mt = GETPOST('Mt');
+$hash = GETPOST('Ref');
+
+$email_info = 'Réf/Hash: '.$hash."\r\n"
+	.'Trans: '.$trans."\r\n"
+	.'Mt: '.$mt.' -> '.price(round($mt/100, 2), '', $langs, 0, - 1, - 1, $conf->currency)."\r\n"
+	.'Autorisation: '.$autorisation."\r\n"
+	.'Error Code: '.$error.($error=='00000' ?' -> OK' :'')."\r\n"
+	.($error!='00000' ?'Error : '.mmi_etransactions::error($error)."\r\n" :'');
+
+//var_dump($hash);
+// On récupère que le "vrai" hash
+$ehash = explode(' ', $hash);
+if (count($ehash)>0) {
+	if (strlen($ehash[count($ehash)-1])==32)
+		$hash = $ehash[count($ehash)-1];
+	elseif (strlen($ehash[0])==32)
+		$hash = $ehash[0];
+}
+//var_dump($hash);
+
+$obj = mmi_etransactions::info($hash);
+
+$mail_to = [];
+if ($conf->global->MBIETRANSACTIONS_NOTIFICATION_EMAIL)
+	$mail_to[] = $conf->global->MBIETRANSACTIONS_NOTIFICATION_EMAIL;
+
+
+//var_dump(DOL_MAIN_URL_ROOT);
+//var_dump($success);
+
+// Introuvable
+if (empty($obj)) {
+	if ($conf->global->MBIETRANSACTIONS_NOTIFICATION_EMAIL) {
+		mmi_etransactions::notification_email(NULL, 'Etransactions : transaction introuvable', $email_info);
+	}
+	die('Introuvable');
+}
+$objecttype = $obj->objecttype;
+$id = $obj->fk_object;
+$email_info .= ($obj->mutiple ?'Plusieurs fois: '.$obj->mutiple."\r\n".'Montant total: '.$obj->amount."\r\n" :'');
+
+// Mal enregistré
+if (empty($objecttype) || empty($id)) {
+	if ($conf->global->MBIETRANSACTIONS_NOTIFICATION_EMAIL) {
+		mmi_etransactions::notification_email(NULL, 'Etransactions : Requête mal enregistrée', $email_info);
+	}
+	die('Mal enregistré');
+}
+$object = mmi_etransactions_loadobject($objecttype, $id);
+//var_dump($hash.' - '.$object->ref.($object->thirdparty ?' - '.$object->thirdparty->name :'')); die();
+
+// Pas d'objet référent
+if (empty($object)) {
+	if ($conf->global->MBIETRANSACTIONS_NOTIFICATION_EMAIL) {
+		mmi_etransactions::notification_email(NULL, 'Etransactions : Transaction avec objet référent manquant', $email_info);
+	}
+	die('Objet référent manquant');
+}
+$ref = (!empty($object->ref) ?'Ref '.$object->ref :'Id '.$object->id);
+$email_info .= "\r\n".$objecttype.' '.$ref."\r\n";
+
+$client = $object->thirdparty;
+//var_dump($client);
+$email_info .= "\r\n".'Client Réf: '.$client->code_client."\r\n"
+	.'Client: '.$client->name."\r\n";
+
+if (!$trans) {
+	if ($conf->global->MBIETRANSACTIONS_NOTIFICATION_EMAIL) {
+		mmi_etransactions::notification_email(NULL, 'Etransactions : transaction sans numéro', $email_info);
+	}
+	die('Numéro de transaction invalide');
+}
+$obj_trans = mmi_etransactions::trans_info($hash, $trans, $autorisation);
+//var_dump($obj, $obj_trans); die();
+
+// Transaction déjà validée
+if ($obj_trans) {
+	if ($conf->global->MBIETRANSACTIONS_NOTIFICATION_EMAIL) {
+		mmi_etransactions::notification_email(NULL, 'Etransactions : transaction déjà validée', $email_info);
+	}
+	die('Déjà validé');
+}
+
+// OK
+if ($objecttype=='Propal')
+	$object_url = 'https://'.$_SERVER['HTTP_HOST'].'/comm/propal/card.php?id='.$id;
+elseif ($objecttype=='Commande')
+	$object_url = 'https://'.$_SERVER['HTTP_HOST'].'/commande/card.php?id='.$id;
+elseif ($objecttype=='Facture')
+	$object_url = 'https://'.$_SERVER['HTTP_HOST'].'/compta/facture/card.php?id='.$id;
+	
+$accountid = $conf->global->MBIETRANSACTIONS_BANK_ACCOUNT;
+//var_dump($accountid); die();
+$amount = $mt / 100;
+
+$resql2 = $db->query("SELECT *
+	FROM " . MAIN_DB_PREFIX . "c_paiement
+	WHERE code = 'CBI' AND entity = " . $conf->entity);
+if ($resql2) {
+	$obj2 = $db->fetch_object($resql2);
+	if ($obj2) {
+		$paiement_mode = $obj2->id;
+	}
+}
+
+// Insert MBE Return
+
+$sql = "INSERT INTO `".MAIN_DB_PREFIX."mbi_etransactions_return`
+	(`fk_mbi_etransactions`, `mt`, `auto`, `erreur`, `trans`)
+	VALUES
+	(".$obj->rowid.", ".(is_numeric($mt) ?"'".$mt."'" :'NULL').", '".$autorisation."', '".$error."', '".$trans."')";
+//echo $sql;
+$q = $db->query($sql); //  AND `return_tms` IS NULL ?
+$return_id = $db->last_insert_id(MAIN_DB_PREFIX.'mbi_etransactions_return');
+//var_dump($db); die();
+//var_dump($q);
+//var_dump($return_id); die();
+
+// Récupération liste contacts
+//var_dump($object);
+$contacts = $object->liste_contact(-1, 'internal');
+$contacts_ok = false;
+foreach($contacts as $contact) {
+	$contacts_ok = true;
+	if (!empty($contact->email) && !in_array($contact->email, $mail_to))
+		$mail_to[] = $contact->email;
+}
+$contacts = $client->getSalesRepresentatives($user);
+foreach($contacts as $contact) {
+	$contacts_ok = true;
+	if (!empty($contact['email']) && !in_array($contact['email'], $mail_to))
+		$mail_to[] = $contact['email'];
+}
+
+// Foireux
+if ($error !== '00000' || empty($autorisation) || empty($trans)) {
+	if (!empty($mail_to)) {
+		$ref = (!empty($object->ref) ?'Ref '.$object->ref :'Id '.$object->id);
+		mmi_etransactions::notification_email(implode(',', $mail_to), 'Etransactions : Erreur retour paiement '.$objecttype.' '.$ref, $email_info);
+	}
+}
+// Insert Paiement OK
+else {
+	$user = new User($db);
+	$user->fetch(1); // Admin @todo créer user spécifique pour trucs auto ?
+
+	$nb = mmi_etransactions::trans_query_nb($hash, $trans);
+	if ($nb>1)
+		$email_info .= "\r\n".'Echéance n°: '.$nb."\r\n";
+		
+	if (!empty($mail_to)) {
+		mmi_etransactions::notification_email(implode(',', $mail_to),
+			'Etransactions : Retour paiement '.$objecttype.' '.$ref.($nb>1 ?' - Echéance n°'.$nb :''),
+			"Rendez-vous dans le Backoffice :\r\n- ".$object_url."\r\n"
+			."\r\n".$email_info);
+	}
+
+	// Modification statut
+	if($objecttype == 'Propal') {
+		//var_dump($user, $object::STATUS_SIGNED);
+		if (! in_array($object->statut, [2, 4])) // $object::STATUS_SIGNED OR $object::STATUS_BILLED
+			$r = $object->closeProposal($user, $object::STATUS_SIGNED, 'Suite paiement Etransactions');
+		//var_dump($r);
+	}
+
+	$infos = [
+		//'date' => dol_now(), // automatique
+		'amount' => $amount,
+		'mode' => $paiement_mode,
+		'num' => $trans,
+		'note' => 'Etransactions Trans '.$trans.' pour '.$objecttype.' '.$ref,
+		'accountid' => $accountid,
+		//'chqemetteur' => '', // pas obligatoire
+		//'chqbank' => '', // pas obligatoire
+		'module_oid' => $return_id,
+	];
+	$paiement_id = mmi_payments::add($objecttype, $id, $infos);
+
+	if ($paiement_id) {
+		// Pour faciliter les liaisons dans l'autre sens
+		// Ne sert plus à rien en fait car on peux join dans l'autre sens7
+		// @depreacated Obsolète
+		$sql = "UPDATE `".MAIN_DB_PREFIX."mbi_etransactions_return`
+			SET fk_paiement=".$paiement_id."
+			WHERE rowid=".$return_id;
+		//echo $sql;
+		$q = $db->query($sql); // AND `return_tms` IS NULL ?
+	}
+}
+

+ 19 - 0
sql/llx_mbi_etransactions_hash.sql

@@ -0,0 +1,19 @@
+CREATE TABLE IF NOT EXISTS `llx_mbi_etransactions_hash` (
+  `rowid` int(11) NOT NULL,
+  `objecttype` enum('Facture','Commande','Propal','Client') NOT NULL,
+  `fk_object` int(11) NOT NULL,
+  `amount` decimal(10,2) DEFAULT NULL,
+  `multiple` tinyint(3) UNSIGNED DEFAULT NULL,
+  `tag` varchar(32) DEFAULT NULL,
+  `hash` varchar(255) NOT NULL,
+  `tms` timestamp NOT NULL DEFAULT current_timestamp(),
+  `info` varchar(255) NOT NULL
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+ALTER TABLE `llx_mbi_etransactions_hash`
+  ADD PRIMARY KEY (`rowid`),
+  ADD KEY `objecttype` (`objecttype`,`fk_object`),
+  ADD KEY `hash` (`hash`);
+
+ALTER TABLE `llx_mbi_etransactions_hash`
+  MODIFY `rowid` int(11) NOT NULL AUTO_INCREMENT;

+ 22 - 0
sql/llx_mbi_etransactions_return.sql

@@ -0,0 +1,22 @@
+CREATE TABLE IF NOT EXISTS `llx_mbi_etransactions_return` (
+  `rowid` int(11) NOT NULL,
+  `fk_mbi_etransactions` int(11) NOT NULL,
+  `tms` timestamp NOT NULL DEFAULT current_timestamp(),
+  `mt` int(11) DEFAULT NULL,
+  `auto` varchar(8) DEFAULT NULL,
+  `erreur` varchar(8) DEFAULT NULL,
+  `trans` varchar(16) DEFAULT NULL,
+  `fk_paiement` int(11) DEFAULT NULL
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+ALTER TABLE `llx_mbi_etransactions_return`
+  ADD PRIMARY KEY (`rowid`),
+  ADD KEY `fk_paiement` (`fk_paiement`),
+  ADD KEY `fk_mbi_etransactions` (`fk_mbi_etransactions`);
+
+ALTER TABLE `llx_mbi_etransactions_return`
+  ADD FOREIGN KEY (`fk_mbi_etransactions`) REFERENCES `llx_mbi_etransactions_hash`(`rowid`),
+  ADD FOREIGN KEY (`fk_paiement`) REFERENCES `llx_paiement`(`rowid`);
+
+ALTER TABLE `llx_mbi_etransactions_return`
+  MODIFY `rowid` int(11) NOT NULL AUTO_INCREMENT;

+ 24 - 0
sql/llx_paiement_extrafields.sql

@@ -0,0 +1,24 @@
+CREATE TABLE `llx_paiement_extrafields` (
+  `rowid` int(11) NOT NULL,
+  `tms` timestamp NOT NULL DEFAULT current_timestamp() ON UPDATE current_timestamp(),
+  `fk_object` int(11) NOT NULL,
+  `import_key` varchar(14) DEFAULT NULL,
+  `fk_module` int(11) DEFAULT NULL,
+  `fk_module_oid` int(11) DEFAULT NULL
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+ALTER TABLE `llx_paiement_extrafields`
+  ADD PRIMARY KEY (`rowid`),
+  ADD UNIQUE KEY `fk_object` (`fk_object`),
+  ADD KEY `fk_module` (`fk_module`,`fk_module_oid`);
+
+ALTER TABLE `llx_paiement_extrafields`
+  MODIFY `rowid` int(11) NOT NULL AUTO_INCREMENT;
+
+ALTER TABLE `llx_paiement_extrafields`
+  DROP FOREIGN KEY `llx_paiement_object_ibfk_1`;
+ALTER TABLE `llx_paiement_extrafields`
+  ADD CONSTRAINT `llx_paiement_object_ibfk_1`
+  FOREIGN KEY (`fk_object`)
+  REFERENCES `llx_paiement`(`rowid`)
+  ON DELETE CASCADE ON UPDATE CASCADE;

+ 28 - 0
sql/llx_paiement_object.sql

@@ -0,0 +1,28 @@
+CREATE TABLE IF NOT EXISTS `llx_paiement_object` (
+  `rowid` int(11) NOT NULL,
+  `fk_paiement` int(11) DEFAULT NULL,
+  `objecttype` enum('Commande','Propal','Client') NOT NULL,
+  `fk_object` int(11) DEFAULT NULL,
+  `amount` double(24,8) DEFAULT 0.00000000,
+  `multicurrency_code` varchar(255) DEFAULT NULL,
+  `multicurrency_tx` double(24,8) DEFAULT 1.00000000,
+  `multicurrency_amount` double(24,8) DEFAULT 0.00000000
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
+
+ALTER TABLE `llx_paiement_object`
+  ADD PRIMARY KEY (`rowid`),
+  ADD UNIQUE KEY `uk_paiement_facture` (`fk_paiement`,`objecttype`,`fk_object`) USING BTREE,
+  ADD KEY `idx_paiement_facture_fk_paiement` (`fk_paiement`),
+  ADD KEY `idx_paiement_facture_fk_facture` (`objecttype`,`fk_object`) USING BTREE;
+
+ALTER TABLE `llx_paiement_object`
+  DROP FOREIGN KEY `llx_paiement_object_ibfk_1`;
+ALTER TABLE `llx_paiement_object`
+  ADD CONSTRAINT `llx_paiement_object_ibfk_1`
+  FOREIGN KEY (`fk_paiement`)
+  REFERENCES `llx_paiement`(`rowid`)
+  ON DELETE CASCADE ON UPDATE CASCADE;
+
+ALTER TABLE `llx_paiement_object`
+  MODIFY `rowid` int(11) NOT NULL AUTO_INCREMENT;
+

+ 89 - 0
style.css

@@ -0,0 +1,89 @@
+body {
+	width : 80%;
+	margin: auto;
+	text-align : center;
+}
+
+h1 {
+	margin-top: 0;
+	background:#888;
+	height: 29px;
+	text-shadow: 1px 1px 1px #444;
+	-moz-box-shadow: inset 1px 1px 0px 0px #888;
+	-webkit-box-shadow: inset 1px 1px 0px 0px #888;
+	box-shadow: inset 1px 1px 0px 0px #888;
+	color: #EEE;
+	font-weight: bold;
+	height: 35px;
+	line-height: 35px;
+	padding: 0 25px;
+	border-width: 0 0 1px 0;
+	border-style: solid;
+	border-color: #CCC;
+	font-size: 1.2em;
+	border-radius: 5px;
+	-webkit-border-radius: 5px;
+	-moz-border-radius: 5px;
+}
+
+tr.liste_total td {
+	color: #000;
+	font-weight:bold;
+}
+
+.button {
+	color: #000;
+	font-weight:bold;
+	font-size:0.86em;
+	margin: 10px 0 10px 0;
+}
+
+#logo{
+	width : 100%;
+	margin : 30px 0px 30px 0px;
+}
+
+#payment-content{
+	width : 100%;
+	text-align : left;
+	-webkit-border-radius: 6px;
+	-moz-border-radius: 6px;
+	border-radius: 6px;
+	border-style: solid;
+	border-width: 1px;
+	border-color: #CCC;
+	background: #F5F5F5;
+	border-bottom: 1px solid #CCC;
+	margin: 0;
+	padding: 10px 10px;
+	font-size:0.86em;
+}
+
+#payment-table{
+	width : 100%;
+	text-align : left;
+	border : 1px solid #ccc;
+}
+
+#payment-table tr{
+	width : 100%;
+}
+
+.liste_total{
+	text-align : left;
+}
+
+.payment-row-left{
+	width : 40%;
+	text-align : left;
+
+}
+
+.payment-row-right{
+	width : 60%;
+	text-align : right;
+}
+
+.payment-button{
+	text-align : right;
+}