Jak wysyłać SMS-y przez SMPP API przy użyciu Javy

Short Message Peer-to-Peer (SMPP) API to potężny protokół telekomunikacyjny zaprojektowany do wymiany wiadomości SMS między centrami wiadomości SMS (SMSC) a zewnętrznymi jednostkami obsługującymi wiadomości SMS (ESME). Wykorzystując Javę i SMPP API, programiści mogą tworzyć solidne aplikacje do efektywnego wysyłania i odbierania wiadomości SMS. Ten kompleksowy przewodnik przeprowadzi Cię przez proces implementacji SMPP API w Javie w celu połączenia z bramką SMS Ozeki, zawierając praktyczne przykłady kodu dotyczące zarządzania połączeniami, wysyłania wiadomości i obsługi raportów dostarczenia.

Dlaczego warto używać Javy i SMPP API do wysyłania SMS-ów?

Java to wszechstronny, niezależny od platformy język programowania, powszechnie używany do tworzenia aplikacji klasy enterprise. W połączeniu z SMPP API, Java umożliwia programistom tworzenie skalowalnych rozwiązań SMS, które bezproblemowo integrują się z bramkami SMS, takimi jak Ozeki. Protokół SMPP jest idealny dla aplikacji SMS o wysokiej przepustowości ze względu na swoją niezawodność, obsługę masowego wysyłania wiadomości i możliwości śledzenia dostarczenia. W tym przewodniku używana jest biblioteka jSMPP, czysta implementacja protokołu SMPP w Javie, aby uprościć rozwój.

Konfiguracja klienta SMPP API w Javie do wysyłania wiadomości SMS

Aby rozpocząć wysyłanie wiadomości SMS przy użyciu SMPP API w Javie, należy utworzyć konto użytkownika SMPP na serwerze SMPP bramki SMS Ozeki i skonfigurować aplikację Java do połączenia z jego serwerem SMPP. Biblioteka jSMPP jest popularnym wyborem wśród programistów Java ze względu na kompleksowe wsparcie dla funkcji protokołu SMPP. Poniżej przedstawiamy kroki konfiguracji projektu Java.

Krok 1: Dodanie zależności jSMPP

Aby użyć biblioteki jSMPP w projekcie Java, dodaj następującą zależność Maven do pliku pom.xml:

<dependency>
    <groupId>org.jsmpp</groupId>
    <artifactId>jsmpp</artifactId>
    <version>2.3.10</version>
</dependency>

Ta zależność zapewnia wszystkie niezbędne klasy do implementacji SMPP API w Javie, w tym zarządzanie sesją, kodowanie wiadomości i obsługę potwierdzeń dostarczenia.

Krok 2: Podstawowy przykład połączenia SMPP

Połączenie z serwerem SMPP wymaga nawiązania sesji i powiązania jej z bramką SMS Ozeki. Poniższy kod Java demonstruje, jak utworzyć prostego klienta SMPP przy użyciu biblioteki jSMPP:

import org.jsmpp.*;
import org.jsmpp.bean.*;
import org.jsmpp.session.*;

public class SimpleSMPPClient {
    public static void main(String[] args) {
        SMPPSession session = new SMPPSession();
        try {
            // Połącz i powiąż z bramką SMS Ozeki
            session.connectAndBind(
                "your.ozeki.server", 
                2775, 
                new BindParameter(
                    BindType.BIND_TX, 
                    "your_username", 
                    "your_password", 
                    "cp", 
                    TypeOfNumber.ALPHANUMERIC, 
                    NumberingPlanIndicator.UNKNOWN, 
                    null)
            );
            
            System.out.println("Pomyślnie połączono z serwerem SMPP");
            
            // Tutaj dodaj kod wysyłania wiadomości
            
        } catch (Exception e) {
            System.err.println("Nie udało się połączyć i powiązać z serwerem SMPP: " + e.getMessage());
        } finally {
            session.unbindAndClose();
        }
    }
}

W tym przykładzie zastąp your.ozeki.server, your_username i your_password rzeczywistymi danymi dostarczonymi przez administratora bramki SMS Ozeki. BindType.BIND_TX wskazuje na powiązanie nadawcy, odpowiednie do wysyłania wiadomości SMS.

Zarządzanie połączeniami SMPP API w Javie dla niezawodnego dostarczania SMS-ów

Niezawodne dostarczanie SMS-ów wymaga utrzymania aktywnego połączenia SMPP. Protokół SMPP używa wiadomości keep-alive (PDU enquire_link) do zapewnienia, że połączenie pozostaje aktywne. Poniżej znajduje się przykład konfiguracji ustawień keep-alive i monitorowania zmian stanu sesji w Javie:

session.setEnquireLinkTimer(30000); // Wysyłaj keep-alive co 30 sekund
session.setTransactionTimer(10000); // Ustaw limit czasu transakcji na 10 sekund

// Dodaj nasłuchiwacz stanu sesji do monitorowania
session.addSessionStateListener(new SessionStateListener() {
    @Override
    public void onStateChange(SessionState newState, SessionState oldState, Session source) {
        System.out.println("Stan sesji SMPP zmienił się z " + oldState + " na " + newState);
    }
});

Te ustawienia zapewniają stabilność połączenia, a nasłuchiwacz stanu sesji pomaga monitorować zmiany, takie jak rozłączenia, dla solidnej obsługi błędów.

Wysyłanie SMS-ów za pomocą Java przez interfejs SMPP

Po nawiązaniu połączenia możesz wysyłać wiadomości SMS za pomocą PDU submit_sm. Poniższa metoda w języku Java demonstruje, jak wysłać SMS przy użyciu interfejsu SMPP w Javie:

public static void sendSMS(SMPPSession session, String sender, String recipient, String message) throws Exception {
    try {
        String messageId = session.submitShortMessage(
            "CMT", // Typ usługi
            TypeOfNumber.ALPHANUMERIC, // Źródłowy TON
            NumberingPlanIndicator.UNKNOWN, // Źródłowy NPI
            sender, // Adres nadawcy
            TypeOfNumber.INTERNATIONAL, // Docelowy TON
            NumberingPlanIndicator.ISDN, // Docelowy NPI
            recipient, // Adres odbiorcy
            new ESMClass(), // Klasa ESM
            (byte)0, // ID protokołu
            (byte)1, // Flaga priorytetu
            null, // Czas dostarczenia
            null, // Okres ważności
            new RegisteredDelivery(SMSCDeliveryReceipt.SUCCESS_FAILURE), // Potwierdzenie dostarczenia
            (byte)0, // Flaga zastąpienia, jeśli obecna
            new GeneralDataCoding(Alphabet.ALPHA_DEFAULT), // Kodowanie danych
            (byte)0, // Domyślne ID wiadomości
            message.getBytes() // Treść wiadomości
        );
        
        System.out.println("SMS wysłany z ID wiadomości: " + messageId);
    } catch (PDUException e) {
        System.err.println("Nieprawidłowy parametr PDU: " + e.getMessage());
        throw e;
    } catch (ResponseTimeoutException e) {
        System.err.println("Przekroczony czas odpowiedzi: " + e.getMessage());
        throw e;
    } catch (InvalidResponseException e) {
        System.err.println("Nieprawidłowa odpowiedź: " + e.getMessage());
        throw e;
    } catch (NegativeResponseException e) {
        System.err.println("Otrzymano negatywną odpowiedź: " + e.getMessage());
        throw e;
    } catch (Exception e) {
        System.err.println("Nie udało się wysłać SMS-a: " + e.getMessage());
        throw e;
    }
}

Ta metoda wysyła SMS-a z włączonym śledzeniem potwierdzenia dostarczenia. Parametr RegisteredDelivery zapewnia otrzymywanie powiadomień o statusie dostarczenia wiadomości.

Obsługa raportów dostarczenia SMS-ów za pomocą Java i interfejsu SMPP

Aby śledzić, czy SMS został pomyślnie dostarczony, możesz powiązać sesję SMPP jako transceiver (BindType.BIND_TRX) i zaimplementować odbiornik wiadomości. Poniżej znajduje się przykład obsługi raportów dostarczenia w Javie:

// Powiązanie jako transceiver do wysyłania i odbierania wiadomości
BindParameter bindParam = new BindParameter(
    BindType.BIND_TRX,
    "twoja_nazwa_użytkownika",
    "twoje_hasło",
    "cp",
    TypeOfNumber.ALPHANUMERIC,
    NumberingPlanIndicator.UNKNOWN,
    null
);

// Ustawienie odbiornika wiadomości dla raportów dostarczenia
session.setMessageReceiverListener(new MessageReceiverListener() {
    @Override
    public void onAcceptDeliverSm(DeliverSm deliverSm) {
        if (MessageType.SMSC_DEL_RECEIPT.containedIn(deliverSm.getEsmClass())) {
            DeliveryReceipt delReceipt = deliverSm.getShortMessageAsDeliveryReceipt();
            System.out.println(String.format(
                "Otrzymano raport dostarczenia dla wiadomości %s: %s",
                delReceipt.getId(),
                delReceipt.getFinalStatus()
            ));
        }
        
        // Odpowiedź na raport dostarczenia
        try {
            byte[] messageId = new byte[]{1};
            session.deliverSmResponse(0, messageId, deliverSm);
        } catch (PDUException e) {
            System.err.println("Nie udało się odpowiedzieć na deliver_sm: " + e.getMessage());
        }
    }
});

Ten kod przetwarza raporty dostarczenia, umożliwiając śledzenie sukcesu lub porażki każdego SMS-a wysłanego przez interfejs SMPP w Javie.

Kompletny klient Java SMPP do wysyłania SMS-ów przez interfejs SMPP

Poniżej znajduje się kompletna klasa Java, która integruje zarządzanie połączeniami, wysyłanie wiadomości oraz obsługę raportów doręczeń. Ta implementacja jest gotowa do użycia w środowisku produkcyjnym, z odpowiednią obsługą błędów i zarządzaniem zasobami:

import org.jsmpp.*;
import org.jsmpp.bean.*;
import org.jsmpp.session.*;
import org.jsmpp.util.*;

public class SMPPClient implements AutoCloseable {
    private SMPPSession session;
    private String host;
    private int port;
    private String username;
    private String password;
    
    public SMPPClient(String host, int port, String username, String password) {
        this.host = host;
        this.port = port;
        this.username = username;
        this.password = password;
        this.session = new SMPPSession();
    }
    
    public void connect() throws Exception {
        try {
            BindParameter bindParam = new BindParameter(
                BindType.BIND_TRX,
                username,
                password,
                "cp",
                TypeOfNumber.ALPHANUMERIC,
                NumberingPlanIndicator.UNKNOWN,
                null
            );
            
            session.connectAndBind(host, port, bindParam);
            
            // Konfiguracja ustawień sesji
            session.setEnquireLinkTimer(30000);
            session.setTransactionTimer(10000);
            
            // Ustawienie odbiorcy raportów doręczeń
            session.setMessageReceiverListener(new DeliveryReceiptListener());
            
            System.out.println("Pomyślnie połączono z serwerem SMPP");
        } catch (Exception e) {
            System.err.println("Nie udało się połączyć z serwerem SMPP: " + e.getMessage());
            throw e;
        }
    }
    
    public String sendSMS(String sender, String recipient, String message) throws Exception {
        try {
            return session.submitShortMessage(
                "CMT",
                TypeOfNumber.ALPHANUMERIC,
                NumberingPlanIndicator.UNKNOWN,
                sender,
                TypeOfNumber.INTERNATIONAL,
                NumberingPlanIndicator.ISDN,
                recipient,
                new ESMClass(),
                (byte)0,
                (byte)1,
                null,
                null,
                new RegisteredDelivery(SMSCDeliveryReceipt.SUCCESS_FAILURE),
                (byte)0,
                new GeneralDataCoding(Alphabet.ALPHA_DEFAULT),
                (byte)0,
                message.getBytes()
            );
        } catch (Exception e) {
            System.err.println("Nie udało się wysłać SMS-a: " + e.getMessage());
            throw e;
        }
    }
    
    @Override
    public void close() {
        if (session != null) {
            session.unbindAndClose();
        }
    }
    
    private static class DeliveryReceiptListener implements MessageReceiverListener {
        @Override
        public void onAcceptDeliverSm(DeliverSm deliverSm) {
            if (MessageType.SMSC_DEL_RECEIPT.containedIn(deliverSm.getEsmClass())) {
                DeliveryReceipt delReceipt = deliverSm.getShortMessageAsDeliveryReceipt();
                System.out.println(String.format(
                    "Otrzymano raport doręczenia dla wiadomości %s: %s",
                    delReceipt.getId(),
                    delReceipt.getFinalStatus()
                ));
            }
        }
    }
    
    public static void main(String[] args) {
        try (SMPPClient client = new SMPPClient(
                "your.ozeki.server", 
                2775, 
                "your_username", 
                "your_password")) {
            
            client.connect();
            
            String messageId = client.sendSMS(
                "12345", 
                "+1234567890", 
                "Witaj z klienta SMPP w Javie!"
            );
            
            System.out.println("SMS wysłany z ID: " + messageId);
            
            // Utrzymanie działania aplikacji w celu odbierania raportów doręczeń
            System.out.println("Naciśnij Ctrl+C, aby wyjść...");
            Thread.sleep(Long.MAX_VALUE);
            
        } catch (Exception e) {
            System.err.println("Błąd w kliencie SMPP: " + e.getMessage());
        }
    }
}

Ta kompletna implementacja enkapsuluje funkcjonalność klienta SMPP w klasie wielokrotnego użytku, ułatwiając integrację z większymi aplikacjami Java. Interfejs AutoCloseable zapewnia prawidłowe czyszczenie zasobów.

Najlepsze praktyki przy tworzeniu klientów SMPP w Javie

Aby zapewnić, że Twój klient SMPP API w Javie jest solidny i skalowalny, postępuj zgodnie z tymi najlepszymi praktykami:

  • Pula połączeń: Używaj puli połączeń dla aplikacji wysyłających duże ilości SMS-ów, aby efektywnie zarządzać wieloma sesjami SMPP.
  • Obsługa wyjątków: Zaimplementuj kompleksową obsługę wyjątków, aby radzić sobie z problemami sieciowymi lub błędami serwera.
  • Pule wątków: Używaj pul wątków do przetwarzania wiadomości współbieżnie, aby poprawić wydajność.
  • Kolejkowanie wiadomości: Zaimplementuj mechanizm kolejkowania, aby zapewnić niezawodne dostarczanie wiadomości podczas zakłóceń sieciowych.
  • Monitorowanie połączenia: Monitoruj stan sesji SMPP i zaimplementuj logikę automatycznego ponownego łączenia dla niezawodności.
  • Kodowanie znaków: Obsługuj różne kodowania znaków (np. GSM 7-bit, UCS-2), aby wspierać międzynarodowe wiadomości SMS.

Podsumowanie

Implementacja interfejsu SMPP w Javie z bramką SMS Ozeki dostarcza potężne rozwiązanie do wysyłania i odbierania wiadomości SMS w Twoich aplikacjach. Biblioteka jSMPP upraszcza złożoności protokołu SMPP, pozwalając programistom skupić się na budowaniu solidnych funkcji związanych z wiadomościami. Ten przewodnik omówił podstawy konfiguracji klienta SMPP w Javie, zarządzania połączeniami, wysyłania wiadomości SMS i obsługi raportów doręczeń. Postępując zgodnie z podanymi przykładami i najlepszymi praktykami, możesz tworzyć skalowalne i niezawodne aplikacje SMS przy użyciu Javy i interfejsu SMPP.

W środowiskach produkcyjnych rozważ dodanie zaawansowanych funkcji, takich jak łączenie wiadomości dla długich SMS-ów, szczegółowe logowanie i monitorowanie wydajności. Protokół SMPP oferuje dodatkowe możliwości, tak jak zaplanowane wysyłanie wiadomości i ustawienia priorytetów, aby rozszerzyć funkcjonalność aplikacji w miarę ewolucji wymagań.

More information