1 changed files with 89 additions and 0 deletions
@ -0,0 +1,89 @@
@@ -0,0 +1,89 @@
|
||||
package simulation |
||||
|
||||
import ( |
||||
"math/rand" |
||||
) |
||||
|
||||
type CDNNode struct { |
||||
ID string |
||||
Label string |
||||
TTL int |
||||
GeoReplication string |
||||
CachingStrategy string |
||||
Compression string |
||||
HTTP2 string |
||||
CacheHitRate float64 // % of requests served from edge cache
|
||||
CurrentLoad int // optional: can track active queue length
|
||||
Queue []*Request // incoming request queue
|
||||
EdgeNodes map[string]*CDNNode // future expansion: simulate geographic edge clusters
|
||||
Alive bool |
||||
Targets []string |
||||
output []*Request // cache HIT responses
|
||||
missQueue []*Request // cache MISSes to forward
|
||||
} |
||||
|
||||
func (n *CDNNode) GetID() string { return n.ID } |
||||
func (n *CDNNode) Type() string { return "cdn" } |
||||
func (n *CDNNode) IsAlive() bool { return n.Alive } |
||||
func (n *CDNNode) QueueState() []*Request { return n.Queue } |
||||
|
||||
func (n *CDNNode) Tick(tick int) { |
||||
if len(n.Queue) == 0 { |
||||
return |
||||
} |
||||
|
||||
maxProcessPerTick := 10 |
||||
processCount := min(len(n.Queue), maxProcessPerTick) |
||||
|
||||
// Avoid slice leak by reusing a cleared slice
|
||||
queue := n.Queue |
||||
n.Queue = n.Queue[:0] |
||||
|
||||
for i := 0; i < processCount; i++ { |
||||
req := queue[i] |
||||
|
||||
// Simulate cache hit or miss
|
||||
hitRate := n.CacheHitRate |
||||
if hitRate == 0 { |
||||
hitRate = 0.8 // default if unset
|
||||
} |
||||
|
||||
if rand.Float64() < hitRate { |
||||
// Cache HIT
|
||||
req.LatencyMS += 5 |
||||
req.Path = append(req.Path, n.ID) |
||||
n.output = append(n.output, req) |
||||
} else { |
||||
// Cache MISS
|
||||
req.LatencyMS += 10 |
||||
req.Path = append(req.Path, n.ID+"(miss)") |
||||
n.missQueue = append(n.missQueue, req) |
||||
} |
||||
} |
||||
|
||||
// Optionally simulate cache expiration every 100 ticks
|
||||
if tick%100 == 0 { |
||||
// e.g., simulate reduced hit rate or TTL expiration
|
||||
} |
||||
} |
||||
|
||||
func (n *CDNNode) Receive(req *Request) { |
||||
if req == nil { |
||||
return |
||||
} |
||||
|
||||
geoLatency := rand.Intn(20) + 5 // 5–25ms routing delay
|
||||
req.LatencyMS += geoLatency |
||||
|
||||
n.Queue = append(n.Queue, req) |
||||
} |
||||
|
||||
func (n *CDNNode) Emit() []*Request { |
||||
out := append(n.output, n.missQueue...) |
||||
|
||||
// Clear for next tick
|
||||
n.output = n.output[:0] |
||||
n.missQueue = n.missQueue[:0] |
||||
|
||||
return out |
||||
} |
||||
Loading…
Reference in new issue