mirror of
https://github.com/renorris/openfsd
synced 2026-03-22 14:35:36 +08:00
240 lines
4.2 KiB
Go
240 lines
4.2 KiB
Go
package main
|
|
|
|
import (
|
|
"github.com/renorris/openfsd/protocol"
|
|
"github.com/stretchr/testify/assert"
|
|
"testing"
|
|
"time"
|
|
)
|
|
|
|
func TestPostOffice(t *testing.T) {
|
|
configurePostOffice()
|
|
|
|
c1 := FSDClient{
|
|
Conn: nil,
|
|
Reader: nil,
|
|
AuthVerify: nil,
|
|
AuthSelf: nil,
|
|
NetworkRating: protocol.NetworkRatingOBS,
|
|
Mailbox: make(chan string, 16),
|
|
}
|
|
|
|
c2 := FSDClient{
|
|
Conn: nil,
|
|
Reader: nil,
|
|
AuthVerify: nil,
|
|
AuthSelf: nil,
|
|
NetworkRating: protocol.NetworkRatingSUP,
|
|
Mailbox: make(chan string, 16),
|
|
}
|
|
|
|
// Test RegisterCallsign
|
|
|
|
// Register "1"
|
|
{
|
|
err := PO.RegisterCallsign("1", &c1)
|
|
assert.Nil(t, err)
|
|
}
|
|
|
|
// Register "1" twice
|
|
{
|
|
err := PO.RegisterCallsign("1", &c1)
|
|
assert.NotNil(t, err)
|
|
assert.ErrorIs(t, CallsignAlreadyRegisteredError, err)
|
|
}
|
|
|
|
// Register "2"
|
|
{
|
|
err := PO.RegisterCallsign("2", &c2)
|
|
assert.Nil(t, err)
|
|
}
|
|
|
|
// Register "2" twice
|
|
{
|
|
err := PO.RegisterCallsign("2", &c2)
|
|
assert.NotNil(t, err)
|
|
assert.ErrorIs(t, CallsignAlreadyRegisteredError, err)
|
|
}
|
|
|
|
// Test SendMail
|
|
{
|
|
m := Mail{
|
|
Type: MailTypeDirect,
|
|
Source: &c1,
|
|
Recipients: []string{"2"},
|
|
Packets: []string{"hello"},
|
|
}
|
|
|
|
PO.SendMail([]Mail{m})
|
|
|
|
assert.Empty(t, c1.Mailbox)
|
|
assert.NotEmpty(t, c2.Mailbox)
|
|
|
|
msg := <-c2.Mailbox
|
|
assert.Equal(t, "hello", msg)
|
|
|
|
assert.Empty(t, c1.Mailbox)
|
|
assert.Empty(t, c2.Mailbox)
|
|
}
|
|
|
|
{
|
|
m := Mail{
|
|
Type: MailTypeBroadcastAll,
|
|
Source: &c1,
|
|
Recipients: []string{"2"},
|
|
Packets: []string{"hello"},
|
|
}
|
|
|
|
PO.SendMail([]Mail{m})
|
|
|
|
assert.Empty(t, c1.Mailbox)
|
|
assert.NotEmpty(t, c2.Mailbox)
|
|
|
|
{
|
|
msg := <-c2.Mailbox
|
|
assert.Equal(t, "hello", msg)
|
|
}
|
|
}
|
|
|
|
// Test supervisor message
|
|
{
|
|
m := Mail{
|
|
Type: MailTypeBroadcastSupervisors,
|
|
Source: &c1,
|
|
Recipients: nil,
|
|
Packets: []string{"hello"},
|
|
}
|
|
|
|
PO.SendMail([]Mail{m})
|
|
assert.Empty(t, c1.Mailbox)
|
|
assert.NotEmpty(t, c2.Mailbox)
|
|
|
|
{
|
|
msg := <-c2.Mailbox
|
|
assert.Equal(t, "hello", msg)
|
|
}
|
|
}
|
|
|
|
// Test ranged broadcast mail
|
|
{
|
|
// c1 and c2 in range:
|
|
PO.SetLocation(&c1, 45.0, 45.0)
|
|
PO.SetLocation(&c2, 45.0, 45.0)
|
|
|
|
m := Mail{
|
|
Type: MailTypeBroadcastRanged,
|
|
Source: &c1,
|
|
Recipients: nil,
|
|
Packets: []string{"hello"},
|
|
}
|
|
|
|
PO.SendMail([]Mail{m})
|
|
|
|
// c2 should receive the broadcast
|
|
assert.Empty(t, c1.Mailbox)
|
|
assert.NotEmpty(t, c2.Mailbox)
|
|
|
|
{
|
|
msg := <-c2.Mailbox
|
|
assert.Equal(t, "hello", msg)
|
|
}
|
|
|
|
// Move c2 far away from c1
|
|
PO.SetLocation(&c2, -45.0, -45.0)
|
|
|
|
// Try again, nobody should get anything now
|
|
PO.SendMail([]Mail{m})
|
|
|
|
assert.Empty(t, c1.Mailbox)
|
|
assert.Empty(t, c2.Mailbox)
|
|
|
|
// Move back
|
|
PO.SetLocation(&c2, 45.0, 45.0)
|
|
|
|
// Should get the message again
|
|
PO.SendMail([]Mail{m})
|
|
assert.Empty(t, c1.Mailbox)
|
|
assert.NotEmpty(t, c2.Mailbox)
|
|
|
|
{
|
|
msg := <-c2.Mailbox
|
|
assert.Equal(t, "hello", msg)
|
|
}
|
|
|
|
// Move c2 to a "neighbor" geohash cell
|
|
PO.SetLocation(&c2, 45.7, 47.1)
|
|
|
|
// c1 geohash: v00
|
|
// c2 geohash: v01 (neighbor)
|
|
|
|
PO.SendMail([]Mail{m})
|
|
assert.Empty(t, c1.Mailbox)
|
|
assert.NotEmpty(t, c2.Mailbox)
|
|
|
|
{
|
|
msg := <-c2.Mailbox
|
|
assert.Equal(t, "hello", msg)
|
|
}
|
|
}
|
|
|
|
// Test DeregisterCallsign
|
|
|
|
// "3" is not registered
|
|
{
|
|
err := PO.DeregisterCallsign("3")
|
|
assert.NotNil(t, err)
|
|
assert.ErrorIs(t, CallsignNotRegisteredError, err)
|
|
}
|
|
|
|
// Unavailable client mailbox should not block SendMail
|
|
{
|
|
m := Mail{
|
|
Type: MailTypeDirect,
|
|
Source: &c1,
|
|
Recipients: []string{"2"},
|
|
Packets: []string{"hello"},
|
|
}
|
|
|
|
c2.Mailbox = nil
|
|
|
|
timer := time.NewTimer(100 * time.Millisecond)
|
|
done := make(chan interface{})
|
|
go func() {
|
|
PO.SendMail([]Mail{m})
|
|
close(done)
|
|
}()
|
|
|
|
select {
|
|
case <-timer.C:
|
|
assert.Fail(t, "SendMail timeout")
|
|
case <-done:
|
|
}
|
|
}
|
|
|
|
// Deregister "2"
|
|
{
|
|
err := PO.DeregisterCallsign("2")
|
|
assert.Nil(t, err)
|
|
}
|
|
|
|
// Deregister "2" twice
|
|
{
|
|
err := PO.DeregisterCallsign("2")
|
|
assert.NotNil(t, err)
|
|
assert.ErrorIs(t, CallsignNotRegisteredError, err)
|
|
}
|
|
|
|
// Deregister "1"
|
|
{
|
|
err := PO.DeregisterCallsign("1")
|
|
assert.Nil(t, err)
|
|
}
|
|
|
|
// Deregister "1" twice
|
|
{
|
|
err := PO.DeregisterCallsign("1")
|
|
assert.NotNil(t, err)
|
|
assert.ErrorIs(t, CallsignNotRegisteredError, err)
|
|
}
|
|
}
|