// Post injects a message into the whisper network for distribution. func (self *Whisper) Post(payload string, to, from string, topics []string, priority, ttl uint32) error { // Decode the topic strings topicsDecoded := make([][]byte, len(topics)) for i, topic := range topics { topicsDecoded[i] = common.FromHex(topic) } // Construct the whisper message and transmission options message := whisper.NewMessage(common.FromHex(payload)) options := whisper.Options{ To: crypto.ToECDSAPub(common.FromHex(to)), TTL: time.Duration(ttl) * time.Second, Topics: whisper.NewTopics(topicsDecoded...), } if len(from) != 0 { if key := self.Whisper.GetIdentity(crypto.ToECDSAPub(common.FromHex(from))); key != nil { options.From = key } else { return fmt.Errorf("unknown identity to send from: %s", from) } } // Wrap and send the message pow := time.Duration(priority) * time.Millisecond envelope, err := message.Wrap(pow, options) if err != nil { return err } if err := self.Whisper.Send(envelope); err != nil { return err } return nil }
// Watch installs a new message handler to run in case a matching packet arrives // from the whisper network. func (self *Whisper) Watch(to, from string, topics [][]string, fn func(WhisperMessage)) int { // Decode the topic strings topicsDecoded := make([][][]byte, len(topics)) for i, condition := range topics { topicsDecoded[i] = make([][]byte, len(condition)) for j, topic := range condition { topicsDecoded[i][j] = common.FromHex(topic) } } // Assemble and inject the filter into the whisper client filter := whisper.Filter{ To: crypto.ToECDSAPub(common.FromHex(to)), From: crypto.ToECDSAPub(common.FromHex(from)), Topics: whisper.NewFilterTopics(topicsDecoded...), } filter.Fn = func(message *whisper.Message) { fn(NewWhisperMessage(message)) } return self.Whisper.Watch(filter) }
// importPublicKey unmarshals 512 bit public keys. func importPublicKey(pubKey []byte) (*ecies.PublicKey, error) { var pubKey65 []byte switch len(pubKey) { case 64: // add 'uncompressed key' flag pubKey65 = append([]byte{0x04}, pubKey...) case 65: pubKey65 = pubKey default: return nil, fmt.Errorf("invalid public key length %v (expect 64/65)", len(pubKey)) } // TODO: fewer pointless conversions return ecies.ImportECDSAPublic(crypto.ToECDSAPub(pubKey65)), nil }
// HasIdentity checks if the the whisper node is configured with the private key // of the specified public pair. func (self *Whisper) HasIdentity(key string) bool { return self.Whisper.HasIdentity(crypto.ToECDSAPub(common.FromHex(key))) }