Skip to content

Commit

Permalink
Add Node.Status.Address to GameServer.Status in CRD and SDK (#3299)
Browse files Browse the repository at this point in the history
* Add GameServer.Status.Addresses
* Add Status.addresses to SDK
* Delete test/sdk/restapi/alpha/swagger/model_alpha_empty.go, it is not generated
* Run make gen-install
* Run make gen-crd-client
* Run make gen-crd-api-reference-docs
* Run make gen-all-sdk-grpc
  • Loading branch information
zmerlynn authored Aug 1, 2023
1 parent a59c539 commit 4d1086f
Show file tree
Hide file tree
Showing 22 changed files with 2,010 additions and 689 deletions.
11 changes: 11 additions & 0 deletions install/helm/agones/templates/crds/_gameserverstatus.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,17 @@ status:
type: integer
address:
type: string
addresses:
type: array
title: Array of addresses at which the GameServer can be reached; copy of Node.Status.addresses
nullable: true
items:
type: object
properties:
address:
type: string
type:
type: string
nodeName:
type: string
reservedUntil:
Expand Down
11 changes: 11 additions & 0 deletions install/yaml/install.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -10600,6 +10600,17 @@ spec:
type: integer
address:
type: string
addresses:
type: array
title: Array of addresses at which the GameServer can be reached; copy of Node.Status.addresses
nullable: true
items:
type: object
properties:
address:
type: string
type:
type: string
nodeName:
type: string
reservedUntil:
Expand Down
13 changes: 8 additions & 5 deletions pkg/apis/agones/v1/gameserver.go
Original file line number Diff line number Diff line change
Expand Up @@ -280,11 +280,14 @@ type SdkServer struct {
// GameServerStatus is the status for a GameServer resource
type GameServerStatus struct {
// GameServerState is the current state of a GameServer, e.g. Creating, Starting, Ready, etc
State GameServerState `json:"state"`
Ports []GameServerStatusPort `json:"ports"`
Address string `json:"address"`
NodeName string `json:"nodeName"`
ReservedUntil *metav1.Time `json:"reservedUntil"`
State GameServerState `json:"state"`
Ports []GameServerStatusPort `json:"ports"`
Address string `json:"address"`
// Addresses is the array of addresses at which the GameServer can be reached; copy of Node.Status.addresses.
// +optional
Addresses []corev1.NodeAddress `json:"addresses"`
NodeName string `json:"nodeName"`
ReservedUntil *metav1.Time `json:"reservedUntil"`
// [Stage:Alpha]
// [FeatureFlag:PlayerTracking]
// +optional
Expand Down
6 changes: 6 additions & 0 deletions pkg/apis/agones/v1/zz_generated.deepcopy.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions pkg/gameservers/controller.go
Original file line number Diff line number Diff line change
Expand Up @@ -554,6 +554,7 @@ func (c *Controller) syncDevelopmentGameServer(ctx context.Context, gs *agonesv1

gsCopy.Status.Ports = ports
gsCopy.Status.Address = devIPAddress
gsCopy.Status.Addresses = []corev1.NodeAddress{{Address: devIPAddress, Type: "InternalIP"}}
gsCopy.Status.NodeName = devIPAddress
}

Expand Down
4 changes: 4 additions & 0 deletions pkg/gameservers/controller_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -120,6 +120,7 @@ func TestControllerSyncGameServer(t *testing.T) {
assert.Equal(t, expectedState, gs.Status.State)
if expectedState == agonesv1.GameServerStateScheduled {
assert.Equal(t, ipFixture, gs.Status.Address)
assert.Equal(t, []corev1.NodeAddress{{Address: ipFixture, Type: "ExternalIP"}}, gs.Status.Addresses)
assert.NotEmpty(t, gs.Status.Ports[0].Port)
}

Expand Down Expand Up @@ -208,6 +209,7 @@ func TestControllerSyncGameServerWithDevIP(t *testing.T) {

assert.Equal(t, expectedState, gs.Status.State)
assert.Equal(t, ipFixture, gs.Status.Address)
assert.Equal(t, []corev1.NodeAddress{{Address: ipFixture, Type: "InternalIP"}}, gs.Status.Addresses)
assert.NotEmpty(t, gs.Status.Ports[0].Port)

return true, gs, nil
Expand Down Expand Up @@ -986,6 +988,7 @@ func TestControllerSyncGameServerStartingState(t *testing.T) {
assert.True(t, gsUpdated)
assert.Equal(t, gs.Status.NodeName, node.ObjectMeta.Name)
assert.Equal(t, gs.Status.Address, ipFixture)
assert.Equal(t, []corev1.NodeAddress{{Address: ipFixture, Type: "ExternalIP"}}, gs.Status.Addresses)

agtesting.AssertEventContains(t, m.FakeRecorder.Events, "Address and port populated")
assert.NotEmpty(t, gs.Status.Ports)
Expand Down Expand Up @@ -1425,6 +1428,7 @@ func TestControllerSyncGameServerRequestReadyState(t *testing.T) {

assert.Equal(t, gs.Status.NodeName, nodeFixture.ObjectMeta.Name)
assert.Equal(t, gs.Status.Address, ipFixture)
assert.Equal(t, []corev1.NodeAddress{{Address: ipFixture, Type: "ExternalIP"}}, gs.Status.Addresses)

agtesting.AssertEventContains(t, m.FakeRecorder.Events, "Address and port populated")
agtesting.AssertEventContains(t, m.FakeRecorder.Events, "SDK.Ready() complete")
Expand Down
33 changes: 20 additions & 13 deletions pkg/gameservers/gameservers.go
Original file line number Diff line number Diff line change
Expand Up @@ -34,51 +34,58 @@ func isGameServerPod(pod *corev1.Pod) bool {
return false
}

// address returns the network address that the given Pod is run on.
// This will default to the ExternalDNS, but if the ExternalDNS is
// address returns the "primary" network address that the given Pod is run on,
// and a slice of all network addresses.
//
// The primary address will default to the ExternalDNS, but if the ExternalDNS is
// not set, it will fall back to the ExternalIP then InternalDNS then InternalIP,
// If externalDNS is false, skip ExternalDNS and InternalDNS.
// since we can have clusters that are private, and/or tools like minikube
// that only report an InternalIP.
func address(node *corev1.Node) (string, error) {

func address(node *corev1.Node) (string, []corev1.NodeAddress, error) {
addresses := make([]corev1.NodeAddress, 0, len(node.Status.Addresses))
for _, a := range node.Status.Addresses {
addresses = append(addresses, *a.DeepCopy())
}

for _, a := range addresses {
if a.Type == corev1.NodeExternalDNS {
return a.Address, nil
return a.Address, addresses, nil
}
}

for _, a := range node.Status.Addresses {
for _, a := range addresses {
if a.Type == corev1.NodeExternalIP && net.ParseIP(a.Address) != nil {
return a.Address, nil
return a.Address, addresses, nil
}
}

// There might not be a public DNS/IP, so fall back to the private DNS/IP
for _, a := range node.Status.Addresses {
for _, a := range addresses {
if a.Type == corev1.NodeInternalDNS {
return a.Address, nil
return a.Address, addresses, nil
}
}

for _, a := range node.Status.Addresses {
for _, a := range addresses {
if a.Type == corev1.NodeInternalIP && net.ParseIP(a.Address) != nil {
return a.Address, nil
return a.Address, addresses, nil
}
}

return "", errors.Errorf("Could not find an address for Node: %s", node.ObjectMeta.Name)
return "", nil, errors.Errorf("Could not find an address for Node: %s", node.ObjectMeta.Name)
}

// applyGameServerAddressAndPort gathers the address and port details from the node and pod
// and applies them to the GameServer that is passed in, and returns it.
func applyGameServerAddressAndPort(gs *agonesv1.GameServer, node *corev1.Node, pod *corev1.Pod, syncPodPortsToGameServer func(*agonesv1.GameServer, *corev1.Pod) error) (*agonesv1.GameServer, error) {
addr, err := address(node)
addr, addrs, err := address(node)
if err != nil {
return gs, errors.Wrapf(err, "error getting external address for GameServer %s", gs.ObjectMeta.Name)
}

gs.Status.Address = addr
gs.Status.Addresses = addrs
gs.Status.NodeName = pod.Spec.NodeName

if err := syncPodPortsToGameServer(gs, pod); err != nil {
Expand Down
3 changes: 2 additions & 1 deletion pkg/gameservers/gameservers_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -98,9 +98,10 @@ func TestAddress(t *testing.T) {
err := runtime.ParseFeatures(fixture.featureFlags)
assert.NoError(t, err)

addr, err := address(fixture.node)
addr, addrs, err := address(fixture.node)
require.NoError(t, err)
assert.Equal(t, fixture.expectedAddress, addr)
assert.Equal(t, fixture.node.Status.Addresses, addrs)
})
}
}
Expand Down
Loading

0 comments on commit 4d1086f

Please sign in to comment.