github.com/status-im/status-go@v1.1.0/notifier/notifier.go (about)

     1  package notifier
     2  
     3  import (
     4  	"bytes"
     5  	"encoding/json"
     6  	"errors"
     7  	"io/ioutil"
     8  	"log"
     9  	"net/http"
    10  )
    11  
    12  const (
    13  	// IOS identifier for an iOS notification.
    14  	IOS = 1
    15  	// Android identifier for an android notification.
    16  	Android             = 2
    17  	failedPushErrorType = "failed-push"
    18  	pushEndpoint        = "/api/push"
    19  )
    20  
    21  // Notifier handles android and ios push notifications.
    22  type Notifier struct {
    23  	client *http.Client
    24  	url    string
    25  }
    26  
    27  // New notifier connected to the specified server.
    28  func New(url string) *Notifier {
    29  	client := &http.Client{}
    30  
    31  	return &Notifier{url: url, client: client}
    32  }
    33  
    34  // Notification details for gorush.
    35  type Notification struct {
    36  	Tokens   []string `json:"tokens"`
    37  	Platform float32  `json:"platform"`
    38  	Message  string   `json:"message"`
    39  }
    40  
    41  type request struct {
    42  	Notifications []*Notification `json:"notifications"`
    43  }
    44  
    45  // Response from gorush.
    46  type Response struct {
    47  	Logs []struct {
    48  		Type  string `json:"type"`
    49  		Error string `json:"error"`
    50  	} `json:"logs"`
    51  }
    52  
    53  // Send a push notification to given devices.
    54  func (n *Notifier) Send(notifications []*Notification) error {
    55  	url := n.url + pushEndpoint
    56  	r := request{Notifications: notifications}
    57  
    58  	body, err := json.Marshal(r)
    59  	if err != nil {
    60  		return err
    61  	}
    62  
    63  	res, err := n.doRequest(url, body)
    64  	if err != nil {
    65  		return err
    66  	}
    67  
    68  	if len(res.Logs) > 0 {
    69  		if res.Logs[0].Type == failedPushErrorType {
    70  			return errors.New(res.Logs[0].Error)
    71  		}
    72  	}
    73  
    74  	return err
    75  }
    76  
    77  func (n *Notifier) doRequest(url string, body []byte) (res Response, err error) {
    78  	req, err := http.NewRequest("POST", url, bytes.NewBuffer(body))
    79  	if err != nil {
    80  		return
    81  	}
    82  	req.Header.Set("Content-Type", "application/json")
    83  
    84  	resp, err := n.client.Do(req)
    85  	if err != nil {
    86  		return
    87  	}
    88  	defer func() {
    89  		if err := resp.Body.Close(); err != nil {
    90  			log.Println(err.Error())
    91  		}
    92  	}()
    93  
    94  	body, err = ioutil.ReadAll(resp.Body)
    95  	if err != nil {
    96  		return
    97  	}
    98  
    99  	return res, json.Unmarshal(body, &res)
   100  }