1+ import enoslib as en
12import logging
2- import time
33import os
44import tarfile
5+ import time
56from pathlib import Path
6- import enoslib as en
77from tqdm import tqdm
88
99en .init_logging (level = logging .INFO )
1010
1111# --- Experiment parameters ---
12- ACTOR_IMAGE = "collaborativestatemachines/cirrina-baselines-diningPhilosophers "
12+ ACTOR_IMAGE = "collaborativestatemachines/cirrina-baselines-diningphilosophers:unstable "
1313REDIS_IMAGE = "redis:8.2.4-alpine"
1414SIDECAR_IMAGE = "daprio/daprd:edge"
1515PLACEMENT_IMAGE = "daprio/placement:1.16.0"
1616COMPONENTS_PATH = "/tmp/dapr-components"
17- LOCAL_ROOT = Path ("./results" )
17+ LOCAL_ROOT = Path ("./results" )
1818TIME_BEFORE_FETCH = 60 * 20
19- NUM_RUNS = 5
19+ NUM_RUNS = 5
2020# -------------------------------------
2121
2222# Infrastructure Reservation
2323conf = (
24- en .G5kConf .from_settings (job_name = Path (__file__ ).name , walltime = "03:00:00" )
25- .add_machine (roles = ["arbitrator" ], cluster = "gros" , nodes = 1 )
26- .add_machine (roles = ["worker" ], cluster = "gros" , nodes = 6 )
24+ en .G5kConf .from_settings (job_name = Path (__file__ ).name , walltime = "03:00:00" )
25+ .add_machine (roles = ["arbitrator" ], cluster = "gros" , nodes = 1 )
26+ .add_machine (roles = ["worker" ], cluster = "gros" , nodes = 6 )
2727)
2828
2929provider = en .G5k (conf )
5656 value: ""
5757"""
5858
59- Path ("../ config/redis/components-grid5000/pubsub.yaml" ).write_text (pubsub_yaml )
59+ Path ("config/redis/components-grid5000/pubsub.yaml" ).write_text (pubsub_yaml )
6060
6161# Network emulation
6262netem = en .NetemHTB ()
6767netem .deploy ()
6868
6969for run_idx in range (1 , NUM_RUNS + 1 ):
70- run_label = f"run{ run_idx } "
71- print (f"\n >>> Starting { run_label } ..." )
72-
73- # Ensure a fresh metrics directory on every node and push component files
74- with en .actions (roles = roles ) as a :
75- a .file (path = "/tmp/metrics" , state = "absent" )
76- a .file (path = "/tmp/metrics" , state = "directory" , mode = "0777" )
77- a .file (path = COMPONENTS_PATH , state = "directory" )
78- a .copy (src = "../config/redis/components-grid5000/" , dest = COMPONENTS_PATH + "/" )
79-
80- # Deploy Containers on Arbitrator
81- with en .actions (roles = roles ["arbitrator" ]) as a :
82- a .docker_container (
83- name = "redis" , image = REDIS_IMAGE ,
84- network_mode = "host" , state = "started"
85- )
86- a .docker_container (
87- name = "placement" , image = PLACEMENT_IMAGE ,
88- network_mode = "host" , state = "started" ,
89- command = ["./placement" , "--port" , "50006" ]
90- )
91- a .docker_container (
92- name = "arbitrator-sidecar" , image = SIDECAR_IMAGE ,
93- network_mode = "host" , state = "started" ,
94- command = [
95- "./daprd" ,
96- "--app-id" , "arbitrator-sidecar" ,
97- "--app-port" , "3000" ,
98- "--resources-path" , "/components" ,
99- "--placement-host-address" , "localhost:50006" ,
100- "--metrics-port" , "9091" ,
101- ],
102- volumes = [f"{ COMPONENTS_PATH } :/components" ],
103- )
104- a .docker_container (
105- name = "arbitrator" , image = ACTOR_IMAGE ,
106- network_mode = "host" , state = "started" ,
107- volumes = ["/tmp/metrics:/metrics:rw" ],
108- env = {
109- "ROLE" : "arbitrator" ,
110- "NUMBER_OF_PHILOSOPHERS" : "6" ,
111- "DAPR_HTTP_ENDPOINT" : "http://localhost:3500" ,
112- "DAPR_GRPC_ENDPOINT" : "http://localhost:50001" ,
113- "METRICS_DIRECTORY" : "/metrics" ,
114- },
115- )
116-
117- # Deploy Containers on Workers
118- for i , host in enumerate (roles ["worker" ]):
119- with en .actions (pattern_hosts = host .address , roles = roles ) as a :
120- a .docker_container (
121- name = "redis" , image = REDIS_IMAGE ,
122- network_mode = "host" , state = "started"
123- )
124- a .docker_container (
125- name = "placement" , image = PLACEMENT_IMAGE ,
126- network_mode = "host" , state = "started" ,
127- command = ["./placement" , "--port" , "50006" ]
128- )
129- a .docker_container (
130- name = f"w{ i } -sidecar" , image = SIDECAR_IMAGE ,
131- network_mode = "host" , state = "started" ,
132- command = [
133- "./daprd" ,
134- "--app-id" , f"w{ i } -sidecar" ,
135- "--app-port" , "3000" ,
136- "--resources-path" , "/components" ,
137- "--placement-host-address" , "localhost:50006" ,
138- "--metrics-port" , "9091" ,
139- ],
140- volumes = [f"{ COMPONENTS_PATH } :/components" ],
141- )
142- a .docker_container (
143- name = f"w{ i } " , image = ACTOR_IMAGE ,
144- network_mode = "host" , state = "started" ,
145- volumes = ["/tmp/metrics:/metrics:rw" ],
146- env = {
147- "PHILOSOPHER_ID" : str (i ),
148- "DAPR_HTTP_ENDPOINT" : "http://localhost:3500" ,
149- "DAPR_GRPC_ENDPOINT" : "http://localhost:50001" ,
150- "METRICS_DIRECTORY" : "/metrics" ,
151- },
152- )
153-
154- # Wait for data collection
155- print (f"--- { run_label } : Collecting data for { TIME_BEFORE_FETCH } s ---" )
156- for _ in tqdm (range (TIME_BEFORE_FETCH ), desc = run_label , unit = "s" , mininterval = 60 ):
157- time .sleep (1 )
158-
159- # Fetch and Organize Results locally into run1, run2, etc.
160- run_dest = LOCAL_ROOT / run_label
161- run_dest .mkdir (parents = True , exist_ok = True )
162-
163- with en .actions (roles = roles ) as a :
164- a .archive (path = "/tmp/metrics" , dest = "/tmp/metrics.tar.gz" , format = "gz" )
165- a .fetch (src = "/tmp/metrics.tar.gz" , dest = str (run_dest ), flat = False )
166-
167- # Local extraction
168- print (f"--- { run_label } : Extracting results ---" )
169- for host in en .get_hosts (roles ):
170- host_dir = run_dest / host .address
171- tar_path = host_dir / "tmp" / "metrics.tar.gz"
172-
173- if tar_path .exists ():
174- with tarfile .open (tar_path , "r:gz" ) as tar :
175- tar .extractall (path = host_dir )
176-
177- tar_path .unlink ()
178- try :
179- (host_dir / "tmp" ).rmdir ()
180- except OSError :
181- pass
182- # Clean up all containers for next run
183- with en .actions (roles = roles ) as a :
184- a .shell ("docker rm -f $(docker ps -aq) || true" )
70+ run_label = f"run{ run_idx } "
71+ print (f"\n >>> Starting { run_label } ..." )
72+
73+ # Ensure a fresh metrics directory on every node and push component files
74+ with en .actions (roles = roles ) as a :
75+ a .file (path = "/tmp/metrics" , state = "absent" )
76+ a .file (path = "/tmp/metrics" , state = "directory" , mode = "0777" )
77+ a .file (path = COMPONENTS_PATH , state = "directory" )
78+ a .copy (src = "config/redis/components-grid5000/" ,
79+ dest = COMPONENTS_PATH + "/" )
80+
81+ # Deploy Containers on Arbitrator
82+ with en .actions (roles = roles ["arbitrator" ]) as a :
83+ a .docker_container (
84+ name = "redis" , image = REDIS_IMAGE ,
85+ network_mode = "host" , state = "started"
86+ )
87+ a .docker_container (
88+ name = "placement" , image = PLACEMENT_IMAGE ,
89+ network_mode = "host" , state = "started" ,
90+ command = ["./placement" , "--port" , "50006" ]
91+ )
92+ a .docker_container (
93+ name = "arbitrator-sidecar" , image = SIDECAR_IMAGE ,
94+ network_mode = "host" , state = "started" ,
95+ command = [
96+ "./daprd" ,
97+ "--app-id" , "arbitrator-sidecar" ,
98+ "--app-port" , "3000" ,
99+ "--resources-path" , "/components" ,
100+ "--placement-host-address" , "localhost:50006" ,
101+ "--metrics-port" , "9091" ,
102+ ],
103+ volumes = [f"{ COMPONENTS_PATH } :/components" ],
104+ )
105+ a .docker_container (
106+ name = "arbitrator" , image = ACTOR_IMAGE ,
107+ network_mode = "host" , state = "started" ,
108+ volumes = ["/tmp/metrics:/metrics:rw" ],
109+ env = {
110+ "ROLE" : "arbitrator" ,
111+ "NUMBER_OF_PHILOSOPHERS" : "6" ,
112+ "DAPR_HTTP_ENDPOINT" : "http://localhost:3500" ,
113+ "DAPR_GRPC_ENDPOINT" : "http://localhost:50001" ,
114+ "METRICS_DIRECTORY" : "/metrics" ,
115+ },
116+ )
117+
118+ # Deploy Containers on Workers
119+ for i , host in enumerate (roles ["worker" ]):
120+ with en .actions (pattern_hosts = host .address , roles = roles ) as a :
121+ a .docker_container (
122+ name = "redis" , image = REDIS_IMAGE ,
123+ network_mode = "host" , state = "started"
124+ )
125+ a .docker_container (
126+ name = "placement" , image = PLACEMENT_IMAGE ,
127+ network_mode = "host" , state = "started" ,
128+ command = ["./placement" , "--port" , "50006" ]
129+ )
130+ a .docker_container (
131+ name = f"w{ i } -sidecar" , image = SIDECAR_IMAGE ,
132+ network_mode = "host" , state = "started" ,
133+ command = [
134+ "./daprd" ,
135+ "--app-id" , f"w{ i } -sidecar" ,
136+ "--app-port" , "3000" ,
137+ "--resources-path" , "/components" ,
138+ "--placement-host-address" , "localhost:50006" ,
139+ "--metrics-port" , "9091" ,
140+ ],
141+ volumes = [f"{ COMPONENTS_PATH } :/components" ],
142+ )
143+ a .docker_container (
144+ name = f"w{ i } " , image = ACTOR_IMAGE ,
145+ network_mode = "host" , state = "started" ,
146+ volumes = ["/tmp/metrics:/metrics:rw" ],
147+ env = {
148+ "PHILOSOPHER_ID" : str (i ),
149+ "DAPR_HTTP_ENDPOINT" : "http://localhost:3500" ,
150+ "DAPR_GRPC_ENDPOINT" : "http://localhost:50001" ,
151+ "METRICS_DIRECTORY" : "/metrics" ,
152+ },
153+ )
154+
155+ # Wait for data collection
156+ print (f"--- { run_label } : Collecting data for { TIME_BEFORE_FETCH } s ---" )
157+ for _ in tqdm (range (TIME_BEFORE_FETCH ), desc = run_label , unit = "s" ,
158+ mininterval = 60 ):
159+ time .sleep (1 )
160+
161+ # Fetch and Organize Results locally into run1, run2, etc.
162+ run_dest = LOCAL_ROOT / run_label
163+ run_dest .mkdir (parents = True , exist_ok = True )
164+
165+ with en .actions (roles = roles ) as a :
166+ a .archive (path = "/tmp/metrics" , dest = "/tmp/metrics.tar.gz" , format = "gz" )
167+ a .fetch (src = "/tmp/metrics.tar.gz" , dest = str (run_dest ), flat = False )
168+
169+ # Local extraction
170+ print (f"--- { run_label } : Extracting results ---" )
171+ for host in en .get_hosts (roles ):
172+ host_dir = run_dest / host .address
173+ tar_path = host_dir / "tmp" / "metrics.tar.gz"
174+
175+ if tar_path .exists ():
176+ with tarfile .open (tar_path , "r:gz" ) as tar :
177+ tar .extractall (path = host_dir )
178+
179+ tar_path .unlink ()
180+ try :
181+ (host_dir / "tmp" ).rmdir ()
182+ except OSError :
183+ pass
184+
185+ # Clean up all containers for next run
186+ with en .actions (roles = roles ) as a :
187+ a .shell ("docker rm -f $(docker ps -aq) || true" )
185188
186189print (f"\n --- SUCCESS: All { NUM_RUNS } runs finished. Data in { LOCAL_ROOT } ---" )
187- provider .destroy ()
190+ provider .destroy ()
0 commit comments