refactor: fix merge.

This commit is contained in:
UpstreamData
2024-01-15 13:09:23 -07:00
parent f1501718a3
commit e45e51ce65
19 changed files with 373 additions and 279 deletions

View File

@@ -26,6 +26,7 @@ class BaseWebAPI(ABC):
self.ip = ip # ipaddress.ip_address(ip)
self.username = "root"
self.pwd = "root"
self.port = 80
def __new__(cls, *args, **kwargs):
if cls is BaseWebAPI:

View File

@@ -35,10 +35,12 @@ class AntminerModernWebAPI(BaseWebAPI):
allow_warning: bool = True,
**parameters: Union[str, int, bool],
) -> dict:
url = f"http://{self.ip}/cgi-bin/{command}.cgi"
url = f"http://{self.ip}:{self.port}/cgi-bin/{command}.cgi"
auth = httpx.DigestAuth(self.username, self.pwd)
try:
async with httpx.AsyncClient(transport=settings.transport()) as client:
async with httpx.AsyncClient(
transport=settings.transport(),
) as client:
if parameters:
data = await client.post(
url,
@@ -149,7 +151,7 @@ class AntminerOldWebAPI(BaseWebAPI):
allow_warning: bool = True,
**parameters: Union[str, int, bool],
) -> dict:
url = f"http://{self.ip}/cgi-bin/{command}.cgi"
url = f"http://{self.ip}:{self.port}/cgi-bin/{command}.cgi"
auth = httpx.DigestAuth(self.username, self.pwd)
try:
async with httpx.AsyncClient(transport=settings.transport()) as client:

View File

@@ -31,6 +31,7 @@ class BOSMinerWebAPI(BaseWebAPI):
ip, settings.get("default_bosminer_password", "root")
)
self._pwd = settings.get("default_bosminer_password", "root")
self._port = 80
super().__init__(ip)
@property
@@ -42,6 +43,15 @@ class BOSMinerWebAPI(BaseWebAPI):
self._pwd = other
self.luci.pwd = other
@property
def port(self):
return self._port
@port.setter
def port(self, other: str):
self._port = other
self.luci.port = other
async def send_command(
self,
command: Union[str, dict],
@@ -63,6 +73,7 @@ class BOSerWebAPI(BOSMinerWebAPI):
ip, settings.get("default_bosminer_password", "root")
)
self.grpc = BOSerGRPCAPI(ip, settings.get("default_bosminer_password", "root"))
self._port = 80
super().__init__(ip)
@property
@@ -76,6 +87,16 @@ class BOSerWebAPI(BOSMinerWebAPI):
self.gql.pwd = other
self.grpc.pwd = other
@property
def port(self):
return self._port
@port.setter
def port(self, other: str):
self._port = other
self.luci.port = other
self.gql.port = other
async def send_command(
self,
command: Union[str, dict],
@@ -84,14 +105,14 @@ class BOSerWebAPI(BOSMinerWebAPI):
**parameters: Union[str, int, bool],
) -> dict:
command_type = self.select_command_type(command)
if command_type is "gql":
if command_type == "gql":
return await self.gql.send_command(command)
elif command_type is "grpc":
elif command_type == "grpc":
try:
return await (getattr(self.grpc, command.replace("grpc_", "")))()
except AttributeError:
raise APIError(f"No gRPC command found for command: {command}")
elif command_type is "luci":
elif command_type == "luci":
return await self.luci.send_command(command)
@staticmethod

View File

@@ -26,6 +26,7 @@ class BOSerGraphQLAPI:
self.ip = ip
self.username = "root"
self.pwd = pwd
self.port = 80
async def multicommand(self, *commands: dict) -> dict:
def merge(*d: dict):
@@ -60,7 +61,7 @@ class BOSerGraphQLAPI:
self,
command: dict,
) -> dict:
url = f"http://{self.ip}/graphql"
url = f"http://{self.ip}:{self.port}/graphql"
query = command
if command is None:
return {}
@@ -93,7 +94,7 @@ class BOSerGraphQLAPI:
return "{" + ",".join(data) + "}"
async def auth(self, client: httpx.AsyncClient) -> None:
url = f"http://{self.ip}/graphql"
url = f"http://{self.ip}:{self.port}/graphql"
await client.post(
url,
json={

View File

@@ -14,9 +14,11 @@
# limitations under the License. -
# ------------------------------------------------------------------------------
import asyncio
import logging
from datetime import timedelta
from betterproto import Message
from grpclib import GRPCError, Status
from grpclib.client import Channel
from pyasic.errors import APIError
@@ -44,6 +46,7 @@ class BOSerGRPCAPI:
self.ip = ip
self.username = "root"
self.pwd = pwd
self.port = 50051
self._auth = None
self._auth_time = datetime.now()
@@ -90,13 +93,23 @@ class BOSerGRPCAPI:
metadata = []
if auth:
metadata.append(("authorization", await self.auth()))
async with Channel(self.ip, 50051) as c:
endpoint = getattr(BOSMinerGRPCStub(c), command)
if endpoint is None:
if not ignore_errors:
raise APIError(f"Command not found - {endpoint}")
return {}
return (await endpoint(message, metadata=metadata)).to_pydict()
try:
async with Channel(self.ip, self.port) as c:
endpoint = getattr(BOSMinerGRPCStub(c), command)
if endpoint is None:
if not ignore_errors:
raise APIError(f"Command not found - {endpoint}")
return {}
try:
return (await endpoint(message, metadata=metadata)).to_pydict()
except GRPCError as e:
if e.status == Status.UNAUTHENTICATED:
await self._get_auth()
metadata = [("authorization", await self.auth())]
return (await endpoint(message, metadata=metadata)).to_pydict()
raise e
except GRPCError as e:
raise APIError(f"gRPC command failed - {endpoint}") from e
async def auth(self):
if self._auth is not None and self._auth_time - datetime.now() < timedelta(
@@ -107,7 +120,7 @@ class BOSerGRPCAPI:
return self._auth
async def _get_auth(self):
async with Channel(self.ip, 50051) as c:
async with Channel(self.ip, self.port) as c:
req = LoginRequest(username=self.username, password=self.pwd)
async with c.request(
"/braiins.bos.v1.AuthenticationService/Login",
@@ -152,7 +165,9 @@ class BOSerGRPCAPI:
)
async def get_locate_device_status(self):
return await self.send_command("get_locate_device_status")
return await self.send_command(
"get_locate_device_status", GetLocateDeviceStatusRequest()
)
async def set_password(self, password: str = None):
return await self.send_command(
@@ -281,16 +296,72 @@ class BOSerGRPCAPI:
async def set_dps(
self,
enable: bool,
power_step: int,
min_power_target: int,
enable_shutdown: bool = None,
shutdown_duration: int = None,
):
raise NotImplementedError
return await self.send_command("braiins.bos.v1.PerformanceService/SetDPS")
async def set_performance_mode(self):
raise NotImplementedError
return await self.send_command(
"braiins.bos.v1.PerformanceService/SetPerformanceMode"
"set_dps",
message=SetDpsRequest(
enable=enable,
enable_shutdown=enable_shutdown,
shutdown_duration=shutdown_duration,
target=DpsTarget(
power_target=DpsPowerTarget(
power_step=Power(power_step),
min_power_target=Power(min_power_target),
)
),
),
)
async def set_performance_mode(
self,
wattage_target: int = None,
hashrate_target: int = None,
save_action: SaveAction = SaveAction.SAVE_ACTION_SAVE_AND_APPLY,
):
if wattage_target is not None and hashrate_target is not None:
logging.error(
"Cannot use both wattage_target and hashrate_target, using wattage_target."
)
elif wattage_target is None and hashrate_target is None:
raise APIError(
"No target supplied, please supply either wattage_target or hashrate_target."
)
if wattage_target is not None:
return await self.send_command(
"set_performance_mode",
message=SetPerformanceModeRequest(
save_action=save_action,
mode=PerformanceMode(
tuner_mode=TunerPerformanceMode(
power_target=PowerTargetMode(
power_target=Power(watt=wattage_target)
)
)
),
),
)
if hashrate_target is not None:
return await self.send_command(
"set_performance_mode",
message=SetPerformanceModeRequest(
save_action=save_action,
mode=PerformanceMode(
tuner_mode=TunerPerformanceMode(
hashrate_target=HashrateTargetMode(
hashrate_target=TeraHashrate(
terahash_per_second=hashrate_target
)
)
)
),
),
)
async def get_active_performance_mode(self):
return await self.send_command(
"get_active_performance_mode", GetPerformanceModeRequest()

View File

@@ -26,6 +26,7 @@ class BOSMinerLuCIAPI:
self.ip = ip
self.username = "root"
self.pwd = pwd
self.port = 80
async def multicommand(self, *commands: str) -> dict:
data = {}
@@ -38,7 +39,7 @@ class BOSMinerLuCIAPI:
async with httpx.AsyncClient(transport=settings.transport()) as client:
await self.auth(client)
data = await client.get(
f"http://{self.ip}/cgi-bin/luci/{path}",
f"http://{self.ip}:{self.port}/cgi-bin/luci/{path}",
headers={"User-Agent": "BTC Tools v0.1"},
)
if data.status_code == 200:
@@ -55,7 +56,7 @@ class BOSMinerLuCIAPI:
async def auth(self, session: httpx.AsyncClient):
login = {"luci_username": self.username, "luci_password": self.pwd}
url = f"http://{self.ip}/cgi-bin/luci"
url = f"http://{self.ip}:{self.port}/cgi-bin/luci"
headers = {
"User-Agent": "BTC Tools v0.1", # only seems to respond if this user-agent is set
"Content-Type": "application/x-www-form-urlencoded",

View File

@@ -29,6 +29,7 @@ class ePICWebAPI(BaseWebAPI):
self.username = "root"
self.pwd = settings.get("default_epic_password", "letmein")
self.token = None
self.port = 4028
async def send_command(
self,
@@ -50,13 +51,13 @@ class ePICWebAPI(BaseWebAPI):
"password": self.pwd,
}
response = await client.post(
f"http://{self.ip}:4028/{command}",
f"http://{self.ip}:{self.port}/{command}",
timeout=5,
json=epic_param,
)
else:
response = await client.get(
f"http://{self.ip}:4028/{command}",
f"http://{self.ip}:{self.port}/{command}",
timeout=5,
)
if not response.status_code == 200:

View File

@@ -33,10 +33,10 @@ class GoldshellWebAPI(BaseWebAPI):
async def auth(self):
async with httpx.AsyncClient(transport=settings.transport()) as client:
try:
await client.get(f"http://{self.ip}/user/logout")
await client.get(f"http://{self.ip}:{self.port}/user/logout")
auth = (
await client.get(
f"http://{self.ip}/user/login?username={self.username}&password={self.pwd}&cipher=false"
f"http://{self.ip}:{self.port}/user/login?username={self.username}&password={self.pwd}&cipher=false"
)
).json()
except httpx.HTTPError:
@@ -46,7 +46,7 @@ class GoldshellWebAPI(BaseWebAPI):
try:
auth = (
await client.get(
f"http://{self.ip}/user/login?username=admin&password=bbad7537f4c8b6ea31eea0b3d760e257&cipher=true"
f"http://{self.ip}:{self.port}/user/login?username=admin&password=bbad7537f4c8b6ea31eea0b3d760e257&cipher=true"
)
).json()
except (httpx.HTTPError, json.JSONDecodeError):
@@ -76,14 +76,14 @@ class GoldshellWebAPI(BaseWebAPI):
try:
if parameters:
response = await client.put(
f"http://{self.ip}/mcb/{command}",
f"http://{self.ip}:{self.port}/mcb/{command}",
headers={"Authorization": "Bearer " + self.jwt},
timeout=settings.get("api_function_timeout", 5),
json=parameters,
)
else:
response = await client.get(
f"http://{self.ip}/mcb/{command}",
f"http://{self.ip}:{self.port}/mcb/{command}",
headers={"Authorization": "Bearer " + self.jwt},
timeout=settings.get("api_function_timeout", 5),
)
@@ -106,7 +106,7 @@ class GoldshellWebAPI(BaseWebAPI):
for command in commands:
try:
response = await client.get(
f"http://{self.ip}/mcb/{command}",
f"http://{self.ip}:{self.port}/mcb/{command}",
headers={"Authorization": "Bearer " + self.jwt},
timeout=settings.get("api_function_timeout", 5),
)

View File

@@ -35,7 +35,7 @@ class InnosiliconWebAPI(BaseWebAPI):
async with httpx.AsyncClient(transport=settings.transport()) as client:
try:
auth = await client.post(
f"http://{self.ip}/api/auth",
f"http://{self.ip}:{self.port}/api/auth",
data={"username": self.username, "password": self.pwd},
)
except httpx.HTTPError:
@@ -58,7 +58,7 @@ class InnosiliconWebAPI(BaseWebAPI):
for i in range(settings.get("get_data_retries", 1)):
try:
response = await client.post(
f"http://{self.ip}/api/{command}",
f"http://{self.ip}:{self.port}/api/{command}",
headers={"Authorization": "Bearer " + self.jwt},
timeout=settings.get("api_function_timeout", 5),
json=parameters,
@@ -94,7 +94,7 @@ class InnosiliconWebAPI(BaseWebAPI):
for command in commands:
try:
response = await client.post(
f"http://{self.ip}/api/{command}",
f"http://{self.ip}:{self.port}/api/{command}",
headers={"Authorization": "Bearer " + self.jwt},
timeout=settings.get("api_function_timeout", 5),
)

View File

@@ -34,7 +34,7 @@ class VNishWebAPI(BaseWebAPI):
async with httpx.AsyncClient(transport=settings.transport()) as client:
try:
auth = await client.post(
f"http://{self.ip}/api/v1/unlock",
f"http://{self.ip}:{self.port}/api/v1/unlock",
json={"pw": self.pwd},
)
except httpx.HTTPError:
@@ -68,21 +68,21 @@ class VNishWebAPI(BaseWebAPI):
if parameters.get("post"):
parameters.pop("post")
response = await client.post(
f"http://{self.ip}/api/v1/{command}",
f"http://{self.ip}:{self.port}/api/v1/{command}",
headers={"Authorization": auth},
timeout=settings.get("api_function_timeout", 5),
json=parameters,
)
elif not parameters == {}:
response = await client.post(
f"http://{self.ip}/api/v1/{command}",
f"http://{self.ip}:{self.port}/api/v1/{command}",
headers={"Authorization": auth},
timeout=settings.get("api_function_timeout", 5),
json=parameters,
)
else:
response = await client.get(
f"http://{self.ip}/api/v1/{command}",
f"http://{self.ip}:{self.port}/api/v1/{command}",
headers={"Authorization": auth},
timeout=settings.get("api_function_timeout", 5),
)