Spaces:
Running
Running
File size: 4,933 Bytes
a1561e0 5da763a 980944f a1561e0 980944f a1561e0 980944f a1561e0 55f36d8 a0f09fb 7438000 a1561e0 b5c6cc2 a1561e0 f6e5539 b5c6cc2 36e8169 f6e5539 36e8169 a1561e0 36e8169 ec76e7d 980944f 9c1bf5a 26c150c 980944f b92f011 10339b2 980944f c2d6726 3cc50ff 6b1d22f 3cc50ff 6b1d22f b5c6cc2 bbe95b6 e8c4b5e bbe95b6 ec76e7d 2d547d3 deab62a ec76e7d b5c6cc2 a1561e0 ec76e7d b735535 0c91655 9c1bf5a b735535 8efd70a b735535 8505461 2d547d3 be2b9eb bb6c41f ab64dd3 7f81767 6b1d22f 62f47df 8505461 2d547d3 b92f011 980944f 2d547d3 7a9f43d 2d547d3 7a9f43d 2d547d3 62f47df 8505461 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 |
import os
import streamlit as st
from dateutil import parser
import googleapiclient.discovery
from datetime import datetime, timedelta
from google.oauth2 import service_account
def auth():
with open("/tmp/token.json", "w") as token_f:
google_key = os.getenv("GOOGLE_KEY")
token_f.write(google_key)
credentials = service_account.Credentials.from_service_account_file('/tmp/token.json')
return credentials
def get_status(credentials, instance_name):
status = False
client = googleapiclient.discovery.build('compute', 'v1', credentials=credentials)
response = client.instances().list(project='nus-cisco-corp-lab-wp1', zone='asia-southeast1-c').execute()
for item in response['items']:
if item["name"] == instance_name:
try:
ip_address = item['networkInterfaces'][0]['accessConfigs'][0]['natIP']
except Exception as e:
ip_address = None
status = True if item["status"] == "RUNNING" else False
return status, ip_address
def get_time_remaining(last_start_timestamp, run_duration_seconds):
if run_duration_seconds == -1:
return -1
run_duration_seconds = int(run_duration_seconds)
last_start_dt = parser.isoparse(last_start_timestamp)
end_run_dt = last_start_dt + timedelta(seconds=run_duration_seconds)
now_dt = datetime.now(tz=last_start_dt.tzinfo)
delta = int((end_run_dt - now_dt).total_seconds() / 60)
return max(delta, 0)
def get_server(credentials, instance_name):
service = googleapiclient.discovery.build('compute', 'v1', credentials=credentials)
request = service.instances().get(project='nus-cisco-corp-lab-wp1', zone='asia-southeast1-c', instance=instance_name)
response = request.execute()
return response
def schedule_server(credentials, instance_name, running_time):
service = googleapiclient.discovery.build('compute', 'v1', credentials=credentials)
request = service.instances().setScheduling(project='nus-cisco-corp-lab-wp1', zone='asia-southeast1-c', instance=instance_name, body={"automaticRestart": False,"maxRunDuration": {"seconds": running_time*3600}})
response = request.execute()
return response
def activate_server(credentials, instance_name):
service = googleapiclient.discovery.build('compute', 'v1', credentials=credentials)
request = service.instances().start(project='nus-cisco-corp-lab-wp1', zone='asia-southeast1-c', instance=instance_name)
response = request.execute()
return response
def deactivate_server(credentials, instance_name):
service = googleapiclient.discovery.build('compute', 'v1', credentials=credentials)
request = service.instances().stop(project='nus-cisco-corp-lab-wp1',zone='asia-southeast1-c',instance=instance_name, discardLocalSsd=False)
response = request.execute()
return response
st.title("Lucky Reactor Panel")
instance_name = "lucky-reactor"
credentials = auth()
# Get instance info
instance_info = get_server(credentials, instance_name)
status = instance_info['status']
ip_address = instance_info['networkInterfaces'][0]['accessConfigs'][0]['natIP'] if status == 'RUNNING' else None
max_run_duration = instance_info['scheduling']['maxRunDuration']['seconds'] if 'maxRunDuration' in instance_info['scheduling'] else -1
last_start_timestamp = instance_info['lastStartTimestamp']
max_remaining_time = get_time_remaining(last_start_timestamp, max_run_duration)
# UI
st.image("cover.jpg", caption="Lucky Reactor is currently " + ("running ๐" if status == 'RUNNING' else "sleeping ๐ด") + ".")
if status == 'TERMINATED':
with st.form("activate_form"):
token = st.text_input("**Token** (The reactor costs USD $10 per hour to operate)")
running_time = st.select_slider("**Running Hours** (How many hours do you need the reactor)", options=[1,2,3,4,5,6])
submitted = st.form_submit_button("Ignite ๐")
if submitted and token == os.getenv("EASY_TOKEN"):
st.write("Lucky Reactor has been ignited. Please wait a few minutes (3~5) to preceed...")
schedule_response = schedule_server(credentials, instance_name, running_time)
activate_response = activate_server(credentials, instance_name)
elif status == 'RUNNING':
st.write(f"You can access Lucky Reactor via http://{ip_address}:7860")
st.write(f'The reactor can still run **{max_remaining_time}** minutes. You can terminate it in advance.')
with st.form("deactivate_form"):
token = st.text_input("Token")
terminated_btn = st.form_submit_button("Terminate ๐๏ธ")
if terminated_btn and token == os.getenv("EASY_TOKEN"):
st.write("Lucky Reactor has been terminated.")
deactivate_response = deactivate_server(credentials, instance_name)
else:
st.write(f"Server is [{status}]. Please wait...") |