basic bot: set unix fileformat, add KBI handling to cancel order submission
parent
63a6c6efde
commit
5690595064
|
@ -1,143 +1,146 @@
|
||||||
import tractor
|
import tractor
|
||||||
import trio
|
import trio
|
||||||
from uuid import uuid4
|
from uuid import uuid4
|
||||||
|
|
||||||
from piker.clearing import (
|
from piker.clearing import (
|
||||||
open_ems,
|
open_ems,
|
||||||
OrderClient,
|
OrderClient,
|
||||||
)
|
)
|
||||||
|
|
||||||
# TODO: we should probably expose these top level in this subsys?
|
# TODO: we should probably expose these top level in this subsys?
|
||||||
from piker.clearing._messages import (
|
from piker.clearing._messages import (
|
||||||
Order,
|
Order,
|
||||||
Status,
|
Status,
|
||||||
BrokerdPosition,
|
BrokerdPosition,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
async def wait_for_order_status(
|
async def wait_for_order_status(
|
||||||
trades_stream: tractor.MsgStream,
|
trades_stream: tractor.MsgStream,
|
||||||
oid: str,
|
oid: str,
|
||||||
expect_status: str,
|
expect_status: str,
|
||||||
|
|
||||||
) -> tuple[
|
) -> tuple[
|
||||||
list[Status],
|
list[Status],
|
||||||
list[BrokerdPosition],
|
list[BrokerdPosition],
|
||||||
]:
|
]:
|
||||||
'''
|
'''
|
||||||
Wait for a specific order status for a given dialog, return msg flow
|
Wait for a specific order status for a given dialog, return msg flow
|
||||||
up to that msg and any position update msgs in a tuple.
|
up to that msg and any position update msgs in a tuple.
|
||||||
|
|
||||||
'''
|
'''
|
||||||
# Wait for position message before moving on to verify flow(s)
|
# Wait for position message before moving on to verify flow(s)
|
||||||
# for the multi-order position entry/exit.
|
# for the multi-order position entry/exit.
|
||||||
status_msgs: list[Status] = []
|
status_msgs: list[Status] = []
|
||||||
pp_msgs: list[BrokerdPosition] = []
|
pp_msgs: list[BrokerdPosition] = []
|
||||||
|
|
||||||
async for msg in trades_stream:
|
async for msg in trades_stream:
|
||||||
match msg:
|
match msg:
|
||||||
case {'name': 'position'}:
|
case {'name': 'position'}:
|
||||||
ppmsg = BrokerdPosition(**msg)
|
ppmsg = BrokerdPosition(**msg)
|
||||||
pp_msgs.append(ppmsg)
|
pp_msgs.append(ppmsg)
|
||||||
|
|
||||||
case {
|
case {
|
||||||
'name': 'status',
|
'name': 'status',
|
||||||
}:
|
}:
|
||||||
msg = Status(**msg)
|
msg = Status(**msg)
|
||||||
status_msgs.append(msg)
|
status_msgs.append(msg)
|
||||||
|
|
||||||
# if we get the status we expect then return all
|
# if we get the status we expect then return all
|
||||||
# collected msgs from the brokerd dialog up to the
|
# collected msgs from the brokerd dialog up to the
|
||||||
# exected msg B)
|
# exected msg B)
|
||||||
if (
|
if (
|
||||||
msg.resp == expect_status
|
msg.resp == expect_status
|
||||||
and msg.oid == oid
|
and msg.oid == oid
|
||||||
):
|
):
|
||||||
return status_msgs, pp_msgs
|
return status_msgs, pp_msgs
|
||||||
|
|
||||||
|
|
||||||
async def bot_main():
|
async def bot_main():
|
||||||
'''
|
'''
|
||||||
Boot the piker runtime, open an ems connection, submit
|
Boot the piker runtime, open an ems connection, submit
|
||||||
and process orders statuses in real-time.
|
and process orders statuses in real-time.
|
||||||
|
|
||||||
'''
|
'''
|
||||||
from piker.service import maybe_open_pikerd
|
from piker.service import maybe_open_pikerd
|
||||||
|
|
||||||
port: int = 6666 # non-default pikerd addr
|
port: int = 6666 # non-default pikerd addr
|
||||||
ll: str = 'info'
|
ll: str = 'info'
|
||||||
reg_addr: tuple[str, int] = ('127.0.0.1', port)
|
reg_addr: tuple[str, int] = ('127.0.0.1', port)
|
||||||
|
|
||||||
# open an order ctl client
|
# open an order ctl client
|
||||||
client: OrderClient
|
client: OrderClient
|
||||||
trades_stream: tractor.MsgStream
|
trades_stream: tractor.MsgStream
|
||||||
accounts: list[str]
|
accounts: list[str]
|
||||||
|
|
||||||
fqme: str = 'btcusdt.usdtm.perp.binance'
|
fqme: str = 'btcusdt.usdtm.perp.binance'
|
||||||
|
|
||||||
async with (
|
async with (
|
||||||
|
|
||||||
# init and sync actor-service runtime
|
# init and sync actor-service runtime
|
||||||
maybe_open_pikerd(
|
maybe_open_pikerd(
|
||||||
registry_addr=reg_addr,
|
# registry_addr=reg_addr,
|
||||||
loglevel=ll,
|
loglevel=ll,
|
||||||
debug_mode=False,
|
debug_mode=False,
|
||||||
|
|
||||||
),
|
),
|
||||||
tractor.wait_for_actor(
|
tractor.wait_for_actor(
|
||||||
'pikerd',
|
'pikerd',
|
||||||
arbiter_sockaddr=reg_addr,
|
# arbiter_sockaddr=reg_addr,
|
||||||
),
|
),
|
||||||
|
|
||||||
open_ems(
|
open_ems(
|
||||||
fqme,
|
fqme,
|
||||||
mode='paper', # {'live', 'paper'}
|
mode='paper', # {'live', 'paper'}
|
||||||
loglevel=ll,
|
loglevel=ll,
|
||||||
|
|
||||||
) as (
|
) as (
|
||||||
client, # OrderClient
|
client, # OrderClient
|
||||||
trades_stream, # tractor.MsgStream startup_pps,
|
trades_stream, # tractor.MsgStream startup_pps,
|
||||||
_, # positions
|
_, # positions
|
||||||
accounts,
|
accounts,
|
||||||
_, # dialogs
|
_, # dialogs
|
||||||
)
|
)
|
||||||
):
|
):
|
||||||
print(f'Loaded binance accounts: {accounts}')
|
print(f'Loaded binance accounts: {accounts}')
|
||||||
|
|
||||||
price: float = 10e3 # non-clearable
|
price: float = 30e3 # non-clearable
|
||||||
size: float = 0.01
|
size: float = 0.01
|
||||||
oid: str = str(uuid4())
|
oid: str = str(uuid4())
|
||||||
|
|
||||||
order = Order(
|
order = Order(
|
||||||
exec_mode='live', # {'dark', 'live', 'alert'}
|
exec_mode='live', # {'dark', 'live', 'alert'}
|
||||||
action='buy', # TODO: remove this from our schema?
|
action='buy', # TODO: remove this from our schema?
|
||||||
oid=oid,
|
oid=oid,
|
||||||
account='paper', # use binance.usdtm for binance futes
|
account='paper', # use binance.usdtm for binance futes
|
||||||
size=size,
|
size=size,
|
||||||
symbol=fqme,
|
symbol=fqme,
|
||||||
price=price,
|
price=price,
|
||||||
brokers=['binance'],
|
brokers=['binance'],
|
||||||
)
|
)
|
||||||
await client.send(order)
|
await client.send(order)
|
||||||
|
|
||||||
msgs, pps = await wait_for_order_status(
|
msgs, pps = await wait_for_order_status(
|
||||||
trades_stream,
|
trades_stream,
|
||||||
oid,
|
oid,
|
||||||
'open'
|
'open'
|
||||||
)
|
)
|
||||||
|
|
||||||
assert not pps
|
assert not pps
|
||||||
assert msgs[-1].oid == oid
|
assert msgs[-1].oid == oid
|
||||||
|
|
||||||
# cancel the open order
|
try:
|
||||||
await client.cancel(oid)
|
# wait for ctl-c from user..
|
||||||
msgs, pps = await wait_for_order_status(
|
await trio.sleep_forever()
|
||||||
trades_stream,
|
except KeyboardInterrupt:
|
||||||
oid,
|
# cancel the open order
|
||||||
'canceled'
|
await client.cancel(oid)
|
||||||
)
|
msgs, pps = await wait_for_order_status(
|
||||||
|
trades_stream,
|
||||||
|
oid,
|
||||||
|
'canceled'
|
||||||
if __name__ == '__main__':
|
)
|
||||||
trio.run(bot_main)
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
trio.run(bot_main)
|
||||||
|
|
Loading…
Reference in New Issue