You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Docker容器的Python脚本中用环境变量解析起止时间

用环境变量配置OLED显示时段的解决方案

问题背景

当前Python脚本运行在Docker容器中,原本硬编码了8:30至23:00的显示时段,希望通过Docker环境变量调整该时段(无需进入容器修改代码或挂载配置卷)。但尝试将8, 30, 0作为名为start的环境变量解析时遇到问题:直接使用字符串无法处理,转换为int时触发ValueError(invalid literal for int() with base 10: '8, 30, 0')。需要实现支持用户指定**时、分(秒可选)**的起止时间方案。

实现步骤

  • 导入os模块读取Docker环境变量
  • 编写时间解析函数,将环境变量的逗号分隔字符串转换为datetime.time对象,自动补全缺失的秒数为0
  • 保留原硬编码值作为默认值,确保未设置环境变量时脚本仍正常运行

修改后的完整代码

#!/usr/bin/env python3
# For Raspberry Pi Desktop Case with OLED Stats Display
# Base on Adafruit CircuitPython & SSD1306 Libraries
import os
import time
import board
import busio
import digitalio
import adafruit_ssd1306
import subprocess
import datetime
from time import sleep
from PIL import Image, ImageDraw, ImageFont

def time_in_range(start, end, current):
    # 判断当前时间是否在[start, end]区间内
    return start <= current <= end

def parse_time_env(env_str, default_hour, default_minute, default_second=0):
    """解析环境变量中的时间字符串,格式支持"时,分"或"时,分,秒",返回datetime.time对象"""
    if not env_str:
        return datetime.time(default_hour, default_minute, default_second)
    parts = list(map(int, env_str.strip().split(',')))
    hour = parts[0] if len(parts) >=1 else default_hour
    minute = parts[1] if len(parts) >=2 else default_minute
    second = parts[2] if len(parts) >=3 else default_second
    return datetime.time(hour, minute, second)

# Display Parameters
width = 128
height = 64

# Font size
font_sz = 16

# 从环境变量读取起止时间,未设置则用默认值
start = parse_time_env(os.getenv('START_TIME'), 8, 30, 0)
end = parse_time_env(os.getenv('END_TIME'), 23, 0, 0)
current = datetime.datetime.now().time()

# 初始化OLED显示屏
oled = adafruit_ssd1306.SSD1306_I2C(width, height, board.I2C(), addr=0x3C, reset=digitalio.DigitalInOut(board.D4))

# 清空显示屏
oled.fill(0)
oled.show()

# 创建用于绘制的空白图像(1位颜色)
image = Image.new('1', (oled.width, oled.height))

# 获取绘图对象
draw = ImageDraw.Draw(image)

# 导入自定义字体
font = ImageFont.truetype('PixelOperator.ttf', font_sz)
icon_font= ImageFont.truetype('lineawesome-webfont.ttf', font_sz)
while True:
    while (time_in_range(start, end, current)):
        current = datetime.datetime.now().time()
        draw.rectangle((0, 0, oled.width, oled.height), fill=0) # 绘制黑色填充框清空图像
        cmd = "ip addr | awk '/inet / { print $2 }' | sed -n '2{p;q}' | cut -d '/' -f1"
        IP = subprocess.check_output(cmd, shell = True )
        cmd = "vmstat 4 2|tail -1|awk '{print 100-$15}' | tr -d '\n'"
        CPU = subprocess.check_output(cmd, shell = True )
        cmd = "free -m | awk 'NR==2{printf $3}'| awk '{printf $1/1000}'"
        Memuse = subprocess.check_output(cmd, shell = True )
        cmd = "cat /proc/meminfo | head -n 1 | awk -v CONVFMT='%.0f' '{printf $2/1000000}'"
        MemTotal = subprocess.check_output(cmd, shell = True )
        cmd = "free -m | awk -v CONVFMT='%.1f' 'NR==2{printf $3*100/$2}'"
        Memuseper = subprocess.check_output(cmd, shell = True )
        cmd = "df -h | awk '$NF==\"/\"{printf \"%s\", $5}'"
        Disk = subprocess.check_output(cmd, shell = True )
        cmd = "uptime | awk '{print $3,$4}' | cut -f1 -d','"
        uptime = subprocess.check_output(cmd, shell = True )
        cmd = "cat /sys/class/thermal/thermal_zone*/temp | awk -v CONVFMT='%.1f' '{printf $1/1000}'"
        temp = subprocess.check_output(cmd, shell = True )

        # 绘制图标
        draw.text((1, 0), chr(61931), font=icon_font, fill=255)
        draw.text((1, 16), chr(62171), font=icon_font, fill=255)
        draw.text((111, 16), chr(62153), font=icon_font, fill=255)
        draw.text((1, 32), chr(62776), font=icon_font, fill=255)
        draw.text((1, 48), chr(63426), font=icon_font, fill=255)
        draw.text((111, 48), chr(62034), font=icon_font, fill=255)

        # 绘制系统状态文本
        draw.text((22, 0), str(IP,'utf-8'), font=font, fill=255)
        draw.text((22, 16), str(CPU,'utf-8') + "%", font=font, fill=255)
        draw.text((107, 16), str(temp,'utf-8') + "°C", font=font, fill=255, anchor="ra")
        draw.text((22, 32), str(Memuseper,'utf-8') + "%", font=font, fill=255)
        draw.text((125, 32), str(Memuse,'utf-8') + "/" + str(MemTotal,'utf-8') + "G", font=font, fill=255, anchor="ra")
        draw.text((22, 48), str(Disk,'utf-8'), font=font, fill=255)
        draw.text((107, 48), str(uptime,'utf-8'), font=font, fill=255, anchor="ra")

        # 显示图像
        oled.image(image)
        oled.show()
        time.sleep(0)
    else:
        oled.fill(0)
        oled.show()
        sleep(60)
        current = datetime.datetime.now().time()

使用说明

运行Docker容器时,通过-e参数传递环境变量即可调整显示时段:

  • 指定开始时间(仅时分):docker run -e *START_TIME*="9,0" ...
  • 指定结束时间(包含秒):docker run -e *END_TIME*="22,30,0" ...
  • 同时指定起止时间:docker run -e *START_TIME*="7,45" -e *END_TIME*="23,15" ...

如果不传递环境变量,脚本会默认使用原有的8:30至23:00时段。

内容的提问来源于stack exchange,提问作者Macley

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.18 03:35:32