Split + Join

This commit is contained in:
Juan Batiz-Benet 2014-11-05 02:20:27 -08:00
parent 5b8fc748ca
commit 9d04132166
4 changed files with 54 additions and 43 deletions

View File

@ -39,10 +39,4 @@ type Multiaddr interface {
// /ip4/1.2.3.4/tcp/80 decapsulate /ip4/1.2.3.4 = /tcp/80
//
Decapsulate(Multiaddr) Multiaddr
// Split returns the sub-address portions of this multiaddr.
//
// m, _ := NewMultiaddr("/ip4/1.2.3.4/tcp/1234")
// m.Split() -> [/ip4/1.2.3.4, /tcp/1234]
Split() []Multiaddr
}

View File

@ -108,37 +108,3 @@ func (m *multiaddr) Decapsulate(o Multiaddr) Multiaddr {
}
return ma
}
// Split returns the sub-address portions of this multiaddr.
func (m *multiaddr) Split() []Multiaddr {
split, err := bytesSplit(m.bytes)
if err != nil {
panic(fmt.Errorf("invalid multiaddr %s", m.String()))
}
addrs := make([]Multiaddr, len(split))
for i, addr := range split {
c := make([]byte, len(addr))
copy(c, addr)
addrs[i] = &multiaddr{bytes: c}
}
return addrs
}
// Cast re-casts a byte slice as a multiaddr. will panic if it fails to parse.
func Cast(b []byte) Multiaddr {
_, err := bytesToString(b)
if err != nil {
panic(fmt.Errorf("multiaddr failed to parse: %s", err))
}
return &multiaddr{bytes: b}
}
// StringCast like Cast, but parses a string. Will also panic if it fails to parse.
func StringCast(s string) Multiaddr {
m, err := NewMultiaddr(s)
if err != nil {
panic(fmt.Errorf("multiaddr failed to parse: %s", err))
}
return m
}

View File

@ -91,7 +91,7 @@ func TestBytesToString(t *testing.T) {
testString("/ip4/127.0.0.1/udp/1234", "047f0000011104d2")
}
func TestBytesSplit(t *testing.T) {
func TestBytesSplitAndJoin(t *testing.T) {
testString := func(s string, res []string) {
m, err := NewMultiaddr(s)
@ -99,7 +99,7 @@ func TestBytesSplit(t *testing.T) {
t.Error("failed to convert", s)
}
split := m.Split()
split := Split(m)
if len(split) != len(res) {
t.Error("not enough split components", split)
return
@ -111,6 +111,11 @@ func TestBytesSplit(t *testing.T) {
}
}
joined := Join(split...)
if !m.Equal(joined) {
t.Errorf("joined components failed: %s != %s", m, joined)
}
// modifying underlying bytes is fine.
m2 := m.(*multiaddr)
for i := range m2.bytes {
@ -122,7 +127,6 @@ func TestBytesSplit(t *testing.T) {
t.Errorf("split component failed: %s != %s", a, res[i])
}
}
}
testString("/ip4/1.2.3.4/udp/1234", []string{"/ip4/1.2.3.4", "/udp/1234"})

47
util.go Normal file
View File

@ -0,0 +1,47 @@
package multiaddr
import (
"bytes"
"fmt"
)
// Split returns the sub-address portions of a multiaddr.
func Split(m Multiaddr) []Multiaddr {
split, err := bytesSplit(m.Bytes())
if err != nil {
panic(fmt.Errorf("invalid multiaddr %s", m.String()))
}
addrs := make([]Multiaddr, len(split))
for i, addr := range split {
addrs[i] = &multiaddr{bytes: addr}
}
return addrs
}
// Join returns a combination of addresses.
func Join(ms ...Multiaddr) Multiaddr {
var b bytes.Buffer
for _, m := range ms {
b.Write(m.Bytes())
}
return &multiaddr{bytes: b.Bytes()}
}
// Cast re-casts a byte slice as a multiaddr. will panic if it fails to parse.
func Cast(b []byte) Multiaddr {
_, err := bytesToString(b)
if err != nil {
panic(fmt.Errorf("multiaddr failed to parse: %s", err))
}
return &multiaddr{bytes: b}
}
// StringCast like Cast, but parses a string. Will also panic if it fails to parse.
func StringCast(s string) Multiaddr {
m, err := NewMultiaddr(s)
if err != nil {
panic(fmt.Errorf("multiaddr failed to parse: %s", err))
}
return m
}