2023-02-12 23:13:04 +01:00
package model
2023-06-21 22:31:36 +02:00
import (
2023-06-21 23:22:27 +02:00
"github.com/h44z/wg-portal/internal"
2023-06-21 22:31:36 +02:00
"github.com/h44z/wg-portal/internal/domain"
"time"
)
2023-02-12 23:13:04 +01:00
2023-07-18 16:05:06 +02:00
const ExpiryDateTimeLayout = "\"2006-01-02\""
type ExpiryDate struct {
* time . Time
}
// UnmarshalJSON will unmarshal using 2006-01-02 layout
func ( d * ExpiryDate ) UnmarshalJSON ( b [ ] byte ) error {
2023-07-21 15:13:00 +02:00
if len ( b ) == 0 || string ( b ) == "null" || string ( b ) == "\"\"" {
2023-07-18 16:05:06 +02:00
return nil
}
parsed , err := time . Parse ( ExpiryDateTimeLayout , string ( b ) )
if err != nil {
return err
}
if ! parsed . IsZero ( ) {
d . Time = & parsed
}
return nil
}
// MarshalJSON will marshal using 2006-01-02 layout
func ( d * ExpiryDate ) MarshalJSON ( ) ( [ ] byte , error ) {
if d == nil || d . Time == nil {
return [ ] byte ( "null" ) , nil
}
s := d . Format ( ExpiryDateTimeLayout )
return [ ] byte ( s ) , nil
}
2023-02-12 23:13:04 +01:00
type Peer struct {
2023-06-21 23:22:27 +02:00
Identifier string ` json:"Identifier" example:"super_nice_peer" ` // peer unique identifier
DisplayName string ` json:"DisplayName" ` // a nice display name/ description for the peer
UserIdentifier string ` json:"UserIdentifier" ` // the owner
InterfaceIdentifier string ` json:"InterfaceIdentifier" ` // the interface id
Disabled bool ` json:"Disabled" ` // flag that specifies if the peer is enabled (up) or not (down)
DisabledReason string ` json:"DisabledReason" ` // the reason why the peer has been disabled
2023-07-18 16:05:06 +02:00
ExpiresAt ExpiryDate ` json:"ExpiresAt,omitempty" ` // expiry dates for peers
2023-06-23 19:24:59 +02:00
Notes string ` json:"Notes" ` // a note field for peers
2023-02-12 23:13:04 +01:00
2023-06-21 23:22:27 +02:00
Endpoint StringConfigOption ` json:"Endpoint" ` // the endpoint address
2023-06-23 19:24:59 +02:00
EndpointPublicKey StringConfigOption ` json:"EndpointPublicKey" ` // the endpoint public key
2023-06-21 23:22:27 +02:00
AllowedIPs StringSliceConfigOption ` json:"AllowedIPs" ` // all allowed ip subnets, comma seperated
ExtraAllowedIPs [ ] string ` json:"ExtraAllowedIPs" ` // all allowed ip subnets on the server side, comma seperated
PresharedKey string ` json:"PresharedKey" ` // the pre-shared Key of the peer
PersistentKeepalive IntConfigOption ` json:"PersistentKeepalive" ` // the persistent keep-alive interval
2023-02-12 23:13:04 +01:00
PrivateKey string ` json:"PrivateKey" example:"abcdef==" ` // private Key of the server peer
PublicKey string ` json:"PublicKey" example:"abcdef==" ` // public Key of the server peer
Mode string // the peer interface type (server, client, any)
2023-06-21 23:22:27 +02:00
Addresses [ ] string ` json:"Addresses" ` // the interface ip addresses
CheckAliveAddress string ` json:"CheckAliveAddress" ` // optional ip address or DNS name that is used for ping checks
Dns StringSliceConfigOption ` json:"Dns" ` // the dns server that should be set if the interface is up, comma separated
DnsSearch StringSliceConfigOption ` json:"DnsSearch" ` // the dns search option string that should be set if the interface is up, will be appended to DnsStr
Mtu IntConfigOption ` json:"Mtu" ` // the device MTU
FirewallMark Int32ConfigOption ` json:"FirewallMark" ` // a firewall mark
RoutingTable StringConfigOption ` json:"RoutingTable" ` // the routing table
2023-02-12 23:13:04 +01:00
2023-06-21 23:22:27 +02:00
PreUp StringConfigOption ` json:"PreUp" ` // action that is executed before the device is up
PostUp StringConfigOption ` json:"PostUp" ` // action that is executed after the device is up
PreDown StringConfigOption ` json:"PreDown" ` // action that is executed before the device is down
PostDown StringConfigOption ` json:"PostDown" ` // action that is executed after the device is down
2023-02-12 23:13:04 +01:00
}
func NewPeer ( src * domain . Peer ) * Peer {
return & Peer {
Identifier : string ( src . Identifier ) ,
DisplayName : src . DisplayName ,
UserIdentifier : string ( src . UserIdentifier ) ,
InterfaceIdentifier : string ( src . InterfaceIdentifier ) ,
Disabled : src . IsDisabled ( ) ,
DisabledReason : src . DisabledReason ,
2023-07-18 16:05:06 +02:00
ExpiresAt : ExpiryDate { src . ExpiresAt } ,
2023-06-21 23:22:27 +02:00
Notes : src . Notes ,
Endpoint : StringConfigOptionFromDomain ( src . Endpoint ) ,
2023-06-23 19:24:59 +02:00
EndpointPublicKey : StringConfigOptionFromDomain ( src . EndpointPublicKey ) ,
2023-06-21 23:22:27 +02:00
AllowedIPs : StringSliceConfigOptionFromDomain ( src . AllowedIPsStr ) ,
ExtraAllowedIPs : internal . SliceString ( src . ExtraAllowedIPsStr ) ,
2023-02-12 23:13:04 +01:00
PresharedKey : string ( src . PresharedKey ) ,
2023-06-21 23:22:27 +02:00
PersistentKeepalive : IntConfigOptionFromDomain ( src . PersistentKeepalive ) ,
2023-02-12 23:13:04 +01:00
PrivateKey : src . Interface . PrivateKey ,
PublicKey : src . Interface . PublicKey ,
Mode : string ( src . Interface . Type ) ,
Addresses : domain . CidrsToStringSlice ( src . Interface . Addresses ) ,
2023-06-21 23:22:27 +02:00
CheckAliveAddress : src . Interface . CheckAliveAddress ,
Dns : StringSliceConfigOptionFromDomain ( src . Interface . DnsStr ) ,
DnsSearch : StringSliceConfigOptionFromDomain ( src . Interface . DnsSearchStr ) ,
Mtu : IntConfigOptionFromDomain ( src . Interface . Mtu ) ,
FirewallMark : Int32ConfigOptionFromDomain ( src . Interface . FirewallMark ) ,
RoutingTable : StringConfigOptionFromDomain ( src . Interface . RoutingTable ) ,
PreUp : StringConfigOptionFromDomain ( src . Interface . PreUp ) ,
PostUp : StringConfigOptionFromDomain ( src . Interface . PostUp ) ,
PreDown : StringConfigOptionFromDomain ( src . Interface . PreDown ) ,
PostDown : StringConfigOptionFromDomain ( src . Interface . PostDown ) ,
2023-02-12 23:13:04 +01:00
}
}
func NewPeers ( src [ ] domain . Peer ) [ ] Peer {
results := make ( [ ] Peer , len ( src ) )
for i := range src {
results [ i ] = * NewPeer ( & src [ i ] )
}
return results
}
2023-06-21 22:31:36 +02:00
func NewDomainPeer ( src * Peer ) * domain . Peer {
now := time . Now ( )
2023-06-21 23:22:27 +02:00
cidrs , _ := domain . CidrsFromArray ( src . Addresses )
2023-06-21 22:31:36 +02:00
res := & domain . Peer {
BaseModel : domain . BaseModel { } ,
2023-06-21 23:22:27 +02:00
Endpoint : StringConfigOptionToDomain ( src . Endpoint ) ,
2023-06-23 19:24:59 +02:00
EndpointPublicKey : StringConfigOptionToDomain ( src . EndpointPublicKey ) ,
2023-06-21 23:22:27 +02:00
AllowedIPsStr : StringSliceConfigOptionToDomain ( src . AllowedIPs ) ,
ExtraAllowedIPsStr : internal . SliceToString ( src . ExtraAllowedIPs ) ,
PresharedKey : domain . PreSharedKey ( src . PresharedKey ) ,
PersistentKeepalive : IntConfigOptionToDomain ( src . PersistentKeepalive ) ,
DisplayName : src . DisplayName ,
Identifier : domain . PeerIdentifier ( src . Identifier ) ,
UserIdentifier : domain . UserIdentifier ( src . UserIdentifier ) ,
InterfaceIdentifier : domain . InterfaceIdentifier ( src . InterfaceIdentifier ) ,
Disabled : nil , // set below
DisabledReason : src . DisabledReason ,
2023-07-18 16:05:06 +02:00
ExpiresAt : src . ExpiresAt . Time ,
2023-06-21 23:22:27 +02:00
Notes : src . Notes ,
Interface : domain . PeerInterfaceConfig {
KeyPair : domain . KeyPair {
PrivateKey : src . PrivateKey ,
PublicKey : src . PublicKey ,
} ,
Type : domain . InterfaceType ( src . Mode ) ,
Addresses : cidrs ,
CheckAliveAddress : src . CheckAliveAddress ,
DnsStr : StringSliceConfigOptionToDomain ( src . Dns ) ,
DnsSearchStr : StringSliceConfigOptionToDomain ( src . DnsSearch ) ,
Mtu : IntConfigOptionToDomain ( src . Mtu ) ,
FirewallMark : Int32ConfigOptionToDomain ( src . FirewallMark ) ,
RoutingTable : StringConfigOptionToDomain ( src . RoutingTable ) ,
PreUp : StringConfigOptionToDomain ( src . PreUp ) ,
PostUp : StringConfigOptionToDomain ( src . PostUp ) ,
PreDown : StringConfigOptionToDomain ( src . PreDown ) ,
PostDown : StringConfigOptionToDomain ( src . PostDown ) ,
} ,
2023-06-21 22:31:36 +02:00
}
if src . Disabled {
res . Disabled = & now
}
return res
}
2023-07-07 15:36:07 +02:00
type MultiPeerRequest struct {
Identifiers [ ] string ` json:"Identifiers" `
Suffix string ` json:"Suffix" `
}
func NewDomainPeerCreationRequest ( src * MultiPeerRequest ) * domain . PeerCreationRequest {
return & domain . PeerCreationRequest {
2023-07-24 21:00:45 +02:00
UserIdentifiers : src . Identifiers ,
Suffix : src . Suffix ,
2023-07-07 15:36:07 +02:00
}
}
2023-07-07 21:24:02 +02:00
type PeerMailRequest struct {
Identifiers [ ] string ` json:"Identifiers" `
LinkOnly bool ` json:"LinkOnly" `
}
2023-07-18 16:05:06 +02:00
type PeerStats struct {
Enabled bool ` json:"Enabled" example:"true" ` // peer stats tracking enabled
Stats map [ string ] PeerStatData ` json:"Stats" ` // stats, map key = Peer identifier
}
func NewPeerStats ( enabled bool , src [ ] domain . PeerStatus ) * PeerStats {
stats := make ( map [ string ] PeerStatData , len ( src ) )
for _ , srcStat := range src {
stats [ string ( srcStat . PeerId ) ] = PeerStatData {
IsConnected : srcStat . IsConnected ( ) ,
IsPingable : srcStat . IsPingable ,
LastPing : srcStat . LastPing ,
BytesReceived : srcStat . BytesReceived ,
BytesTransmitted : srcStat . BytesTransmitted ,
LastHandshake : srcStat . LastHandshake ,
EndpointAddress : srcStat . Endpoint ,
LastSessionStart : srcStat . LastSessionStart ,
}
}
return & PeerStats {
Enabled : enabled ,
Stats : stats ,
}
}
type PeerStatData struct {
IsConnected bool ` json:"IsConnected" `
IsPingable bool ` json:"IsPingable" `
LastPing * time . Time ` json:"LastPing" `
BytesReceived uint64 ` json:"BytesReceived" `
BytesTransmitted uint64 ` json:"BytesTransmitted" `
LastHandshake * time . Time ` json:"LastHandshake" `
EndpointAddress string ` json:"EndpointAddress" `
LastSessionStart * time . Time ` json:"LastSessionStart" `
}