Skip to content

Conversation

@matmerr
Copy link
Member

@matmerr matmerr commented Aug 26, 2020

Reason for Change:

Lay the groundwork for the monitor that will make calls to CNS and RequestController to adjust CNS pool size

Issue Fixed:

Requirements:

Notes:

@codecov
Copy link

codecov bot commented Aug 26, 2020

Codecov Report

Merging #663 into master will decrease coverage by 0.11%.
The diff coverage is 29.41%.

@@            Coverage Diff             @@
##           master     #663      +/-   ##
==========================================
- Coverage   42.06%   41.94%   -0.12%     
==========================================
  Files          71       72       +1     
  Lines       10271    10354      +83     
==========================================
+ Hits         4320     4343      +23     
- Misses       5474     5537      +63     
+ Partials      477      474       -3     

// APIClient interface to update cns state
type APIClient interface {
ReconcileNCState(*cns.CreateNetworkContainerRequest, map[string]cns.KubernetesPodInfo) error
ReconcileNCState(nc *cns.CreateNetworkContainerRequest, pods map[string]cns.KubernetesPodInfo, batchSize int64, requestThreshold, releaseThreshold float64) error
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we pass all these in some struct, (say ScalerUnits), You also need to initialize the Spec (at least the UpdatedCount) durining init.

type APIClient interface {
ReconcileNCState(*cns.CreateNetworkContainerRequest, map[string]cns.KubernetesPodInfo) error
ReconcileNCState(nc *cns.CreateNetworkContainerRequest, pods map[string]cns.KubernetesPodInfo, batchSize int64, requestThreshold, releaseThreshold float64) error
CreateOrUpdateNC(cns.CreateNetworkContainerRequest) error
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We need to pass at least scaler units in this createorUpdateNC call as well, as the scaler units can change at runtime. You can add that later in a a different PR too if you want

func (service *HTTPRestService) StartCNSIPAMPoolMonitor(cnsService *HTTPRestService, requestController requestcontroller.RequestController) {

// TODO, start pool monitor as well
service.poolMonitor = NewCNSIPAMPoolMonitor(cnsService, requestController)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we need to pass cnsService? Is cnsService different from service.

}
}

service.poolMonitor.UpdatePoolLimitsTransacted(int(batchSize), requestThreshold, releaseThreshold)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you define a ScalerUnit struct and pass that instead as separate parameters

@@ -0,0 +1,138 @@
package restserver
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Add // Copyright 2017 Microsoft. All rights reserved.
// MIT License

decreaseIPCount := len(pm.cns.PodIPConfigState) - pm.batchSize

// mark n number of IP's as pending
pendingIPAddresses, err := pm.cns.MarkIPsAsPendingTransacted(decreaseIPCount)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you expose a method in internalapi.go than calling a TransactedAPI directly? If this poolMonitor is outside the RestServer package, then we cant call Transacted APIs directl. Also it will help to expose the same as debug API from client.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

it should be pm.cns.MarkIPsAsPendingTransacted(pm.batchsize)

func (pm *CNSIPAMPoolMonitor) Start() error {

if pm.initialized {
availableIPConfigs := pm.cns.GetAvailableIPConfigs()
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

To be optmized later: We need a more optimized solution to find available IPs, then looping the range everytime. may be keep a counter.

func (pm *CNSIPAMPoolMonitor) checkForResize(freeIPConfigCount int) int {
switch {
// pod count is increasing
case freeIPConfigCount < pm.minimumFreeIps:
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You also need to account existing UpdatedCount, scenario we discussed in the meeting where SpecCount is already updated (so now freeIp = AvailableIPs + (If UpdatedSpecCount > TotalIPCount then (UpdatedSpec - TotalIpCount), else 0))

func (pm *CNSIPAMPoolMonitor) decreasePoolSize() error {

// TODO: Better handling here, negatives?
decreaseIPCount := len(pm.cns.PodIPConfigState) - pm.batchSize
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Also need to handle if there are some ips got allocated in the interim

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I dont think above logic is correct. say I have 40 Ips in PodIPConfigState, and available free ips is 20. Now 20 > 15 (maxFreeIps), decreaseIpCount = 40-10 = 30.

DecreaseIPCount is always 10. But you need to handle if some allocations happened in the interim.

}

func (pm *CNSIPAMPoolMonitor) increasePoolSize() error {
increaseIPCount := len(pm.cns.PodIPConfigState) + pm.batchSize
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You also need to cache this increaseCount to account for next calculation

return
}

func (service *HTTPRestService) StartCNSIPAMPoolMonitor(cnsService *HTTPRestService, requestController requestcontroller.RequestController) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shouldnt cnsService be HTTPService?

cns/api.go Outdated
SyncNodeStatus(string, string, string, json.RawMessage) (int, string)
GetAvailableIPConfigs() []IPConfigurationStatus
GetPodIPConfigState() map[string]IPConfigurationStatus
MarkIPsAsPendingTransacted(numberToMark int) (map[string]SecondaryIPConfig, error)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we remove Transacted? All the APIs exposed from this interface are expected to be transacted.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

sure

neaggarwMS
neaggarwMS previously approved these changes Aug 26, 2020
return make(map[string]cns.IPConfigurationStatus)
}

func (fake *HTTPServiceFake) MarkIPsAsPendingTransacted(numberToMark int) (map[string]cns.SecondaryIPConfig, error) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This needs to be updated too

@matmerr matmerr merged commit 66e9be1 into Azure:master Aug 27, 2020
@matmerr matmerr deleted the cnspoolmonitor branch August 27, 2020 06:20
neaggarwMS pushed a commit to neaggarwMS/azure-container-networking that referenced this pull request Nov 13, 2020
* init CNS IPAM pool monitor

* update tests

* scalar struct, separate package, cns interface

* addressing feedback
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants