1. Wstęp
  2. Biblioteki dla webmasterów
  3. Płatności talerzykowe
  4. Jak podpiąć płatności talerzykowe (Node.js)?

Jak podpiąć płatności talerzykowe (Node.js)?

Obsługa płatności talerzykowych po stronie serwera

Obsługę płatności talerzykowych należy rozpocząć od zainstalowania frameworku Sails.js (instrukcja), utworzenia aplikacji Sails.js i zainstalowaniu w niej modułu Node.js – billon: sudo npm install billon --save Po zainstalowaniu modułu obsługującego płatność w wygenerowanej przez „Sails.js” strukturze plików należy utworzyć w katalogu „/api/services/” plik (usługę) o nazwie np. „plates.js”:

var billon = require("billon");
var myShop = new billon.Payment();
var alpha = 10; // cena za najtańszy artykuł, np. 1 gr (liczba dziesiątych części grosza)
var beta = 100; // cena za drugi artykuł, np. 10 gr
var gamma = 200; // cena za trzeci artykuł, np. 20 gr
var delta = 500; // cena za czwarty artykuł, np. 50 gr
var epsilon = 1000; // cena za najdroższy artykuł, np. 1 zł
myShop.user(function (requestData, cb)
{
   cb(requestData.user);
}).products(function (requestData, cb)
{
   cb(requestData.itemsId);
}).product(function (requestData, itemId, cb)
{
   switch (itemId)
   { // lista artykułów - produktów, ustawianie artykułu według typu talerzyka jest niezalecane w przypadku taryf składających się z mniejszej liczby talerzyków
      case 1:
          cb(alpha);
       break;
       case 2:
          cb(beta);
       break;
       case 3:
          cb(gamma);
       break;
       case 4:
          cb(delta);
       break;
       case 5:
          cb(epsilon);
       break;
   }
}).productBillon(function (requestData, item, cb) 
{ // wywołanie metody niewymagane, jeśli dla wszystkich produktów określono parametr "quantity"
   cb(item);
}).paymentTitle(function (requestData, items, delivery, cb) 
{
   return cb("Tytuł płatności");
}).plates(function(requestData, cb)
{ // ustawienie cen, brak argumentu lub liczba 0 usuwa talerzyk z taryfy
   cb(alpha, beta, gamma, delta, epsilon);
}).cNode(function (requestData, items, delivery, cb)
{
cb("eyJhkGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJ1c3VyIjp7ImlkIjoyNSwic2FsdCI6IjEyZWVkMzQwLTM2NGUtMThNjgyN1hNDM5zA1MiOjEh0OTCJpYXQiDk0NjF9Q1M.zeWXG7Nyr3PFVhb4HRgLi5rh8fLZx41VHySHWUStIzc"); // API key użytkownika serwisu "billon.me"
    /*cb({
       name: "billonpayments4", // nazwa użytkownika węzła Corporate Node
       address: "http://213.189.38.34:20891" // adres i port węzła Corporate Node
    });*/ // komunikacja bezpośrednio z węzłem Corporate Node
}).currency(function(requestData, cb)
{ // kod ISO 4217 waluty, metoda niewymagana, domyślnie "PLN"
   cb('PLN');
}).maxTotalAmount(function(requestData, cb)
{ // maksymalna suma płatności w serii wyrażona w dziesiątych częściach grosza, metoda niewymagana
   cb(10000);
}).duration(function(requestData, cb)
{ // czas trwania serii płatności w sekundach, metoda wymagana, aby seria miała nie zerową długość czasu trwania
   cb(3600);
}).maxPaymentsInSeries(function(requestData, cb)
{ // maksymalna liczba płatności w serii, metoda niewymagana
   cb(10);
}).platePayment(function(requestData, cb)
{ // ustawienie identyfikatora serii i rodzaju talerzyka
   cb(requestData.seriesId, requestData.type);
}).merchantBrandName(function(requestData, cb)
{ // ustawienie brandu, metoda niewymagana, domyślnie domena strony, na której wykonywane są płatności
   cb('Nazwa brandu');
}).onReceivedPlatePaymentSeriesStatus(function (response)
{ // zdarzenie odpowiedzi węzła Corporate Node w tracie operacji akceptacji serii, metoda niewymagana
   console.log(response);
   if (response.status == 'SERIES_ACCEPTED' || response.status == 'TRANSFERRING' || response.status == 'TRANSFERING')
   {
      console.log('Seria płatności zakceptowana');
   }
}).onAcceptedPlatePaymentSeries(function (paymentData)
{ // zdarzenie zaakceptowanej serii płatności, metoda niewymagana
   console.log(paymentData);
}).onFinishedPayment(function (items, delivery_option, document, requestData)
{ // zdarzenie ukończonej płatności, metoda niewymagana
   console.log(document);
   console.log(requestData);
   if (requestData.itemsId.constructor === Array)
   {
      for (var i = 0; i < requestData.itemsId; ++i)
      { // tutaj można wykonać operację po pomyślnie dokonanym zakupie artykułu - produktu
         console.log(requestData.itemsId[i]);
      }
   }
}).onRequestSend(function (requestName, parameters, requestResponse, error)
{ // zdarzenie wysłania operacji SOAP, metoda niewymagana
   console.log('Wiadomość SOAP: ', requestName);
   console.log('Parametry wiadomości: ', parameters);
   console.log('Odpowiedź węzła Corporate Node: ', requestResponse);
   console.log('Błąd przy wysyłaniu: ', error);
});
module.exports = myShop;

Kiedy już posiadamy skonfigurowany serwer i usługę Sails.js, trzeba utworzyć kontroler, aby mógł się on skomunikować z użytkownikiem strony WWW:

sails generate controller Plates

W katalogu „api/controllers” powstanie plik „PlatesController.js”, w którym należy obsłużyć komunikację do danego adresu i powiązać ją z usługą „plates.js”, którą wcześniej utworzyliśmy. Przykład pliku „PlatesController.js”:

module.exports = {
  list: function(req, res)
  { // metoda wysyłającą ustawioną listę cen, walutę, 
    // limit czasu trwania serii, maksymalną sumę płatności w serii i nazwę brandu
    plates.tariff(res);
  },
  initiate: function(req, res)
  { // metoda inicjująca start serii płatności
    plates.platePaymentSeriesStart(req, res);
  },
  pay: function(req, res)
  { // metoda inicjująca płatność
    plates.paymentInitiation(req, res);
  },
  status: function(req, res)
  { // metoda nasłuchująca
    plates.paymentStatus(req.body.taskId || req.query.taskId, function(response)
    {
      res.json(response);
    });
  }
};

Podpięcie płatności talerzykowych na stronach internetowych

W celu podpięcia płatności do strony internetowej należy skorzystać ze skryptów JavaScript Billon:

<div id="button-container-1"></div>
<script src="//cdn.billon.pro/js/billon.js"></script>
<script src="//cdn.billon.pro/js/billon-agent.js"></script>
<script src="//cdn.billon.pro/js/billon-object.js"></script>
<script src="//cdn.billon.pro/js/billon-user.js"></script>
<script src="//cdn.billon.pro/js/billon-plates.js"></script>
<script>
   billon.plates({
      connection: new billon.agent("http://billon.info:1401/plates"), // adres wskazujący na kontroler Sails.js obsługujący płatność (w tym przypadku PlatesController)
      lang: 'pl', // język "pl" lub "en", domyślnie "en"
      plateButtonAddress: "https://cdn.billon.pro/screen/plate-button/index.html", // w przypadku problemów z niepokazywaniem przycisków, w przypadku braku problemów pominąć
      plateDialogAddress: "https://cdn.billon.pro/screen/plate-dialog/index.html", // w przypadku problemów z niepokazywaniem okna dialogowego, w przypadku braku problemów pominąć
      skipAnotherUser: false, // opcjonalne - pominięcie kroku wyboru innego użytkownika niż wykryty, domyślnie krok nie jest pomijany
      disableButtonsTitle: false, // opcjonalne - domyślne niedodawanie tytułu (etykiety) z ceną do przycisków, domyślnie tytuły są ustawiane
      tariff: {
         address: 'list', // nazwa parametru kontrolera, gdzie wywoływana jest metoda "tariff"
         displayedCurrency: '', // wyświetlana waluta, 
                                   // domyślnie kwoty są sformatowana według kodu ISO 4217 waluty ustawionej za pomocą serwerowego modułu Node.js 'billon' i ustawień regionalnych użytkownika, 
                                   // jeśli nie ustawiono parametru "displayedCurrencyBefore" i gdy są wyższe lub równe 1 lub nie ustawiono parametru, 
                                   // przy ustawionym parametrze "displayCurrencyBefore" jako symbol waluty używany jest kod ISO 4217 waluty ustawionej za pomocą modułu Node.js 'billon'
         displayCurrencyBefore: false, // czy wyświetlać walutę przed liczbą, 
                                    // domyślnie symbol z parametru "displayedCurrency" doklejany jest na końcu liczby
         centSign: ' gr', // symbol waluty dla setnej części podstawowej jednostki pieniężnej wyświetlany dla cen o wartości poniżej tej jednostki, 
                    // domyślnie stosowany jest symbol, jak dla wyższych cen
         displayCentSignBefore: false // czy wyświetlać symbol waluty ustawiony w parametrze "centSign" przed liczbą, domyślnie ten symbol doklejany jest na końcu liczby
      },
      series: {
         request: {
            address: 'initiate', // nazwa parametru kontrolera, gdzie wywoływana jest metoda "platePaymentSeriesStart"
            data: function (user) 
            {
              return {
                user: user
              };
            }
         },
         listenResponse: function (response, user)
         {
            if (response.status == "SERIES_ACCEPTED" || response.status == "TRANSFERRING" || response.status == "TRANSFERING")
            { // zapis identyfikatora serii i nazwy użytkownika Billon, w tym przypadku w Local Storage
               localStorage.setItem("seriesId", response.taskId);
	       localStorage.setItem("user", JSON.stringify(user));
            }
         }
      },
      paymentRequest: {
         address: 'pay', // nazwa parametru kontrolera, gdzie wywoływana jest metoda "paymentInitiation"
         data: function()
         { // odczyt zapisanego wcześniej identyfikatora serii i nazwy użytkownika Billon, w tym przypadku z Local Storage
            try
            {
               return {
                  seriesId: localStorage.getItem("seriesId"),
                  user: JSON.parse(localStorage.getItem("user"))
               };
            }
            catch (e)
            {
               return {};
            }
         }
      },
      listen: {
         address: "status", // nazwa parametru kontrolera, gdzie wywoływana jest metoda "paymentStatus"
         data: function (requestResponse) 
         {
           return {
             taskId: requestResponse.taskId
           };
         }
      },
      buttons: [ // tablica przycisków
      {
         place: document.getElementById('button-container-1'), // element HTML, w którym ma być umieszczony przycisk
         type: 'alpha', // można podać 0 zamiast 'alpha' - typ przycisku
         disableTitle: false, // opcjonalne - nieustawianie tytułu przycisku z ceną,
                              // domyślnie brana pod uwagę jest globalna opcja "DisableButtonsTitle"
         requestData: function(type)
         {
            return {
               type: type,
               itemsId: [1] // tablica identyfikatorów produktów
            }
         },
         listenResponse: function(response)
         { // metoda opcjonalna
            switch (response.status)
            {
               case "FINISHED_OK":
                  // zdarzenie pomyślnej zapłaty przyciskiem
                  break;
               case "FINISHED_ERR_USER_REJECTED": // brak możliwości płatności w ramach zapamiętanej serii
                  localStorage.setItem("seriesId", null);
		  localStorage.setItem("user", JSON.stringify(null));
            }
         }
      },
      {
         place: document.getElementById('button-container-2'),
         type: 'beta',
         requestData: function(type)
         {
            return {
               type: type,
               itemsId: [2]
            }
         },
         listenResponse: function(response)
         {
            switch (response.status)
            {
               case "FINISHED_OK":
                  // zdarzenie pomyślnej zapłaty przyciskiem
                  break;
               case "FINISHED_ERR_USER_REJECTED": // brak możliwości płatności w ramach zapamiętanej serii
                  localStorage.setItem("seriesId", null);
		  localStorage.setItem("user", JSON.stringify(null));
            }
         }
      },
      {
         place: document.getElementById('button-container-3'),
         type: 'gamma',
         requestData: function(type)
         {
            return {
               type: type,
               itemsId: [3]
            }
         },
         listenResponse: function(response)
         {
            switch (response.status)
            {
               case "FINISHED_OK":
                  // zdarzenie pomyślnej zapłaty przyciskiem
                  break;
               case "FINISHED_ERR_USER_REJECTED": // brak możliwości płatności w ramach zapamiętanej serii
                  localStorage.setItem("seriesId", null);
		  localStorage.setItem("user", JSON.stringify(null));
            }
         }
      },
      {
         place: document.getElementById('button-container-4'),
         type: 'delta',
         requestData: function(type)
         {
            return {
               type: type,
               itemsId: [4]
            }
         },
         listenResponse: function(response)
         {
            switch (response.status)
            {
               case "FINISHED_OK":
                  // zdarzenie pomyślnej zapłaty przyciskiem
                  break;
               case "FINISHED_ERR_USER_REJECTED": // brak możliwości płatności w ramach zapamiętanej serii
                  localStorage.setItem("seriesId", null);
		  localStorage.setItem("user", JSON.stringify(null));
            }
         }
      },
      {
         place: document.getElementById('button-container-5'),
         type: 'epsilon',
         requestData: function(type)
         {
            return {
               type: type,
               itemsId: [5]
            }
         },
         listenResponse: function(response)
         {
            switch (response.status)
            {
               case "FINISHED_OK":
                  // zdarzenie pomyślnej zapłaty przyciskiem
                  break;
               case "FINISHED_ERR_USER_REJECTED": // brak możliwości płatności w ramach zapamiętanej serii
                  localStorage.setItem("seriesId", null);
		  localStorage.setItem("user", JSON.stringify(null));
            }
         }
      }]
   });
</script>
Czy ten artykuł jest dla Ciebie pomocny? Tak Nie

Jak możemy pomóc?