2020-07-01 12:04:09 +00:00
package push_notification_server
2020-06-30 08:30:58 +00:00
import (
2020-07-01 10:09:40 +00:00
"crypto/ecdsa"
2020-06-30 08:30:58 +00:00
"database/sql"
2020-07-01 10:09:40 +00:00
2020-07-01 12:04:09 +00:00
"github.com/golang/protobuf/proto"
"github.com/status-im/status-go/eth-node/crypto"
2020-07-01 10:09:40 +00:00
"github.com/status-im/status-go/protocol/protobuf"
2020-06-30 08:30:58 +00:00
)
2020-07-01 10:09:40 +00:00
type Persistence interface {
2020-07-02 08:08:19 +00:00
// GetPushNotificationRegistration retrieve a push notification registration from storage given a public key and installation id
GetPushNotificationRegistration ( publicKey * ecdsa . PublicKey , installationID string ) ( * protobuf . PushNotificationRegistration , error )
// DeletePushNotificationRegistration deletes a push notification registration from storage given a public key and installation id
DeletePushNotificationRegistration ( publicKey * ecdsa . PublicKey , installationID string ) error
// SavePushNotificationRegistration saves a push notification option to the db
SavePushNotificationRegistration ( publicKey * ecdsa . PublicKey , registration * protobuf . PushNotificationRegistration ) error
2020-07-01 10:09:40 +00:00
}
type SQLitePersistence struct {
2020-06-30 08:30:58 +00:00
db * sql . DB
}
2020-07-01 10:09:40 +00:00
func NewSQLitePersistence ( db * sql . DB ) Persistence {
return & SQLitePersistence { db : db }
}
2020-07-02 08:08:19 +00:00
func ( p * SQLitePersistence ) GetPushNotificationRegistration ( publicKey * ecdsa . PublicKey , installationID string ) ( * protobuf . PushNotificationRegistration , error ) {
var marshaledRegistration [ ] byte
2020-07-02 10:49:04 +00:00
err := p . db . QueryRow ( ` SELECT registration FROM push_notification_server_registrations WHERE public_key = ? AND installation_id = ? ` , p . hashPublicKey ( publicKey ) , installationID ) . Scan ( & marshaledRegistration )
2020-07-01 12:04:09 +00:00
if err == sql . ErrNoRows {
return nil , nil
} else if err != nil {
return nil , err
}
2020-07-02 08:08:19 +00:00
registration := & protobuf . PushNotificationRegistration { }
2020-07-01 12:04:09 +00:00
2020-07-02 08:08:19 +00:00
if err := proto . Unmarshal ( marshaledRegistration , registration ) ; err != nil {
2020-07-01 12:04:09 +00:00
return nil , err
}
2020-07-02 08:08:19 +00:00
return registration , nil
2020-07-01 12:04:09 +00:00
}
2020-07-02 08:08:19 +00:00
func ( p * SQLitePersistence ) SavePushNotificationRegistration ( publicKey * ecdsa . PublicKey , registration * protobuf . PushNotificationRegistration ) error {
marshaledRegistration , err := proto . Marshal ( registration )
2020-07-01 12:04:09 +00:00
if err != nil {
return err
}
2020-07-02 10:49:04 +00:00
_ , err = p . db . Exec ( ` INSERT INTO push_notification_server_registrations (public_key, installation_id, version, registration) VALUES (?, ?, ?, ?) ` , p . hashPublicKey ( publicKey ) , registration . InstallationId , registration . Version , marshaledRegistration )
2020-07-01 12:04:09 +00:00
return err
}
2020-07-02 08:08:19 +00:00
func ( p * SQLitePersistence ) DeletePushNotificationRegistration ( publicKey * ecdsa . PublicKey , installationID string ) error {
2020-07-02 10:49:04 +00:00
_ , err := p . db . Exec ( ` DELETE FROM push_notification_server_registrations WHERE public_key = ? AND installation_id = ? ` , p . hashPublicKey ( publicKey ) , installationID )
2020-07-01 12:04:09 +00:00
return err
2020-06-30 08:30:58 +00:00
}
2020-07-02 10:49:04 +00:00
func ( p * SQLitePersistence ) hashPublicKey ( pk * ecdsa . PublicKey ) [ ] byte {
return shake256 ( crypto . CompressPubkey ( pk ) )
}