Comments (16)
Chatting with @dzlier-gcp right now. We're going to look at doing this in a phased approach.
To start - do it a little more open than ideal, but gets us moving forward:
- The
controller
has access to basically do all the things to GameServers and Pods (get, update, delete, list). It may also need read access to CRDs, as it waits for the GameServer CRD to move to established state before doing any work. This may not be necessary long term. - The
sidecar
only has access to get and update the GameServer (it has no reason to list)
Second phase would be that, depending on how that goes, (and how fast subresources comes out), we remove access to update
on the GameServer
for the sidecar, and we create a separate CRD (GameServerState
?) that the sidecar can create with the name of the GameServer and the update state required. The controller will look out for the creation of this CRD, which would be used to communicate to the that a state change has been requested - which would also limit the amount of damage a comprimised gameserver could potentially do as well to a much smaller surface area.
@dzlier-gcp did I miss anything?
from agones.
We should set the make minikube-test-cluster
to enable RBAC when we have this implementation as well:
https://github.com/kubernetes/minikube/blob/master/docs/configuring_kubernetes.md#examples
from agones.
RBAC in essence is much like IAM in that it defines Roles and RoleBindings, which describe what actions can be taken on what resources, and who can take those actions, respectively. There are also ClusterRoles and ClusterRoleBindings, which apply across and entire cluster instead of being limited to a specific namespace.
Given that, in thinking about what kind of default Roles and RoleBindings we should provide, and which we should instruct users to implement.
I think a good place to start would be to define read-only and admin Roles and ClusterRoles to GameServers & GameServer pods. We can develop more Roles/ClusterRoles based on common use cases moving forward.
from agones.
(Assuming I get RBAC right)
I feel like we would need 2 Roles
- For the controller - who would likely need
- read: CustomResourceDefinitions
- read/write GameServers, Pods
- For the sidecar for the GameServer Pod
- read/write on the GameServers
I'm not sure how you apply RBAC roles to running containers however.
Does that seem right to you?
from agones.
What is the flow of information between kube api and the game server pod (sidecar)?
We should probably aim for least privilege. We don't want a compromised game server to be able to fetch information of all other game servers.
Kubernetes RBAC is resource oriented, meaning that a service account with read access to the game server resource is able to list/get all of them. So if sidecar has a service account token to read all that data, then the game binary can send RPC commands to retrieve that as well.
If sidecar only need to read some data about the current game instance, then a config map mounted to sidecar pod might be a better solution.
from agones.
from agones.
So the sidecar needs to read the information of the GameServer it's with, and update it's Status.State
as well (need to read to do the update) - basically the state of the GameServer (through master) is the communication mechanism between the controller and the sidecar.
I take it there is no way to limit access to the specific GameServer, but is there a way to only enable access to the Kubernetes API from the sidecar, and not the GameServer container?
from agones.
from agones.
AFAIK the service accounts are defined at pod level only. The same service account token will be distributed to all pod containers on their filesystem in /var/run/secrets/kubernetes.io/serviceaccount/
.
Do we actually need to use a "push" model to update the game server pod metadata?
It seems that traditionally, when we compare with other Kubernetes CRD controllers, it's the other way around.
For instance, etcd-operator will loop through all running etcd clusters defined and poll each of the individual cluster member, then update the cluster member list and phase accordingly.
Following that approach would mean that only control plane components, like agon controller, need to have special service accounts with read/write to the CRD.
The sidecar could expose some "/health" endpoint and the controller would periodically fetch this to get current state. Something akin to the prometheus /metrics endpoint pulls during scaping.
We could probably even do a spec.automountServiceAccountToken = false
to prevent all interaction with the kube api at all from the game server pods.
from agones.
Example of the etcd-operator run loop that runs in a separate goroutine for each cluster resource:
from agones.
@alexandrem there is a centralised controller - you can see it here:
https://github.com/googleprivate/agon/tree/master/gameservers/controller
This controls Pods allocation and the majority of the life cycle of the GameServer.
However, we needed a way to do simple communicating from the sidecar back to the controller because of the SDK. So the sidecar does this by updating the Status.State
value on the GameServer. To be 100% clear - the sidecar does not do anything to do with allocating pods or managing the life cycle of the GameServer. You can see the code here:
https://github.com/googleprivate/agon/tree/master/gameservers/sidecar
Doing the communication this way is nice, because we don't have to build and test our own scaling mechanism for communication from sidecar <--> controller - there is a already a lot of battle tested work on scaling up the K8s master as the size of your cluster and the workload increases.
That being said - @dzlier-gcp and I are discussing if it's possible for the controller to dynamically create a role for each GameServer so each Pod can only access and edit the information of the GameServer that it belongs to, because we don't want to have a GameServer to be able to access all information about all GameServers - or edit their information.
from agones.
Did you give any thought to built-in objects? Does the controller or sidecar need access to Secrets or ConfigMaps? Pods?
from agones.
@ianlewis Neither the sidecar or the controller needs to directly create Secrets or ConfigMaps. The controller definitely needs access to Pods (see my comment above), but outside of that, I don't think there are other built in objects that will require direct access to.
I currently don't see any reason why this would change would going forward, but if it shows up, we can cross that bridge when we come to it.
from agones.
@dzlier-gcp Just a heads up, I just did a big refactor, so you may want to delete the old branch and start anew, just to avoid merge conflicts.
from agones.
from agones.
Woo!
from agones.
Related Issues (20)
- Some info logs logged from sidecar when sdkServer.logLevel set to Error
- Custom gameserver configuration not working on containerized local SDK HOT 4
- [FeatureRequest]: GameServer can run on aws fargate? HOT 2
- NewSDK configurable 'host' HOT 4
- Document Allocation batching
- JSON Patch in GameServer Controller is Lossy on Int64 HOT 1
- runtime.boundsError from watchGameServer HOT 9
- Agones SDK for Unity Client Server example HOT 9
- SDK Server: Adopt Sidecar Containers HOT 1
- Rust CountsAndLists SDK implementation and conformance tests
- Node.js CountsAndLists SDK implementation and conformance tests HOT 3
- C++ CountsAndLists SDK implementation and conformance tests
- Unity CountsAndLists SDK implementation
- Unreal CountsAndLists SDK implementation
- Counters and Lists: Default Grafana dashboards
- Unreal implementation and conformance tests HOT 1
- Docs: Enhance "Scheduling and Autoscaling" with details on Counts and Lists
- Docs | Integration Patterns: Update Allocating based on GameServer Player Capacity to use Lists
- Docs | Integration Patterns: Update High Density GameServers to use a Counter
- Docs: Do you want a migration guide from Player Tracking to Lists?
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from agones.