mirror of
https://github.com/freqtrade/freqtrade.git
synced 2024-11-10 10:21:59 +00:00
Compare commits
8 Commits
3e10b520f0
...
a06bb56794
Author | SHA1 | Date | |
---|---|---|---|
|
a06bb56794 | ||
|
f50a633f87 | ||
|
ad295946c0 | ||
|
705d1e4cc0 | ||
|
5b3f348bbb | ||
|
aa81c75bef | ||
|
6b889814ad | ||
|
1ade11f00b |
|
@ -130,20 +130,20 @@ Most properties here can be None as they are dependent on the exchange response.
|
||||||
|
|
||||||
| Attribute | DataType | Description |
|
| Attribute | DataType | Description |
|
||||||
|------------|-------------|-------------|
|
|------------|-------------|-------------|
|
||||||
`trade` | Trade | Trade object this order is attached to
|
| `trade` | Trade | Trade object this order is attached to |
|
||||||
`ft_pair` | string | Pair this order is for
|
| `ft_pair` | string | Pair this order is for |
|
||||||
`ft_is_open` | boolean | is the order filled?
|
| `ft_is_open` | boolean | is the order filled? |
|
||||||
`order_type` | string | Order type as defined on the exchange - usually market, limit or stoploss
|
| `order_type` | string | Order type as defined on the exchange - usually market, limit or stoploss |
|
||||||
`status` | string | Status as defined by ccxt. Usually open, closed, expired or canceled
|
| `status` | string | Status as defined by ccxt. Usually open, closed, expired or canceled |
|
||||||
`side` | string | Buy or Sell
|
| `side` | string | Buy or Sell |
|
||||||
`price` | float | Price the order was placed at
|
| `price` | float | Price the order was placed at |
|
||||||
`average` | float | Average price the order filled at
|
| `average` | float | Average price the order filled at |
|
||||||
`amount` | float | Amount in base currency
|
| `amount` | float | Amount in base currency |
|
||||||
`filled` | float | Filled amount (in base currency)
|
| `filled` | float | Filled amount (in base currency) |
|
||||||
`remaining` | float | Remaining amount
|
| `remaining` | float | Remaining amount |
|
||||||
`cost` | float | Cost of the order - usually average * filled (*Exchange dependent on futures, may contain the cost with or without leverage and may be in contracts.*)
|
| `cost` | float | Cost of the order - usually average * filled (*Exchange dependent on futures, may contain the cost with or without leverage and may be in contracts.*) |
|
||||||
`stake_amount` | float | Stake amount used for this order. *Added in 2023.7.*
|
| `stake_amount` | float | Stake amount used for this order. *Added in 2023.7.* |
|
||||||
`order_date` | datetime | Order creation date **use `order_date_utc` instead**
|
| `order_date` | datetime | Order creation date **use `order_date_utc` instead** |
|
||||||
`order_date_utc` | datetime | Order creation date (in UTC)
|
| `order_date_utc` | datetime | Order creation date (in UTC) |
|
||||||
`order_fill_date` | datetime | Order fill date **use `order_fill_utc` instead**
|
| `order_fill_date` | datetime | Order fill date **use `order_fill_utc` instead** |
|
||||||
`order_fill_date_utc` | datetime | Order fill date
|
| `order_fill_date_utc` | datetime | Order fill date |
|
||||||
|
|
|
@ -47,19 +47,20 @@ class BaseEnvironment(gym.Env):
|
||||||
|
|
||||||
def __init__(
|
def __init__(
|
||||||
self,
|
self,
|
||||||
df: DataFrame = DataFrame(),
|
*,
|
||||||
prices: DataFrame = DataFrame(),
|
df: DataFrame,
|
||||||
reward_kwargs: dict = {},
|
prices: DataFrame,
|
||||||
|
reward_kwargs: dict,
|
||||||
window_size=10,
|
window_size=10,
|
||||||
starting_point=True,
|
starting_point=True,
|
||||||
id: str = "baseenv-1", # noqa: A002
|
id: str = "baseenv-1", # noqa: A002
|
||||||
seed: int = 1,
|
seed: int = 1,
|
||||||
config: dict = {},
|
config: dict,
|
||||||
live: bool = False,
|
live: bool = False,
|
||||||
fee: float = 0.0015,
|
fee: float = 0.0015,
|
||||||
can_short: bool = False,
|
can_short: bool = False,
|
||||||
pair: str = "",
|
pair: str = "",
|
||||||
df_raw: DataFrame = DataFrame(),
|
df_raw: DataFrame,
|
||||||
):
|
):
|
||||||
"""
|
"""
|
||||||
Initializes the training/eval environment.
|
Initializes the training/eval environment.
|
||||||
|
|
|
@ -488,7 +488,7 @@ def make_env(
|
||||||
seed: int,
|
seed: int,
|
||||||
train_df: DataFrame,
|
train_df: DataFrame,
|
||||||
price: DataFrame,
|
price: DataFrame,
|
||||||
env_info: Dict[str, Any] = {},
|
env_info: Dict[str, Any],
|
||||||
) -> Callable:
|
) -> Callable:
|
||||||
"""
|
"""
|
||||||
Utility function for multiprocessed env.
|
Utility function for multiprocessed env.
|
||||||
|
|
|
@ -214,7 +214,7 @@ class FreqaiDataKitchen:
|
||||||
self,
|
self,
|
||||||
unfiltered_df: DataFrame,
|
unfiltered_df: DataFrame,
|
||||||
training_feature_list: List,
|
training_feature_list: List,
|
||||||
label_list: List = list(),
|
label_list: Optional[List] = None,
|
||||||
training_filter: bool = True,
|
training_filter: bool = True,
|
||||||
) -> Tuple[DataFrame, DataFrame]:
|
) -> Tuple[DataFrame, DataFrame]:
|
||||||
"""
|
"""
|
||||||
|
@ -244,7 +244,7 @@ class FreqaiDataKitchen:
|
||||||
# we don't care about total row number (total no. datapoints) in training, we only care
|
# we don't care about total row number (total no. datapoints) in training, we only care
|
||||||
# about removing any row with NaNs
|
# about removing any row with NaNs
|
||||||
# if labels has multiple columns (user wants to train multiple modelEs), we detect here
|
# if labels has multiple columns (user wants to train multiple modelEs), we detect here
|
||||||
labels = unfiltered_df.filter(label_list, axis=1)
|
labels = unfiltered_df.filter(label_list or [], axis=1)
|
||||||
drop_index_labels = pd.isnull(labels).any(axis=1)
|
drop_index_labels = pd.isnull(labels).any(axis=1)
|
||||||
drop_index_labels = (
|
drop_index_labels = (
|
||||||
drop_index_labels.replace(True, 1).replace(False, 0).infer_objects(copy=False)
|
drop_index_labels.replace(True, 1).replace(False, 0).infer_objects(copy=False)
|
||||||
|
@ -654,8 +654,8 @@ class FreqaiDataKitchen:
|
||||||
pair: str,
|
pair: str,
|
||||||
tf: str,
|
tf: str,
|
||||||
strategy: IStrategy,
|
strategy: IStrategy,
|
||||||
corr_dataframes: dict = {},
|
corr_dataframes: dict,
|
||||||
base_dataframes: dict = {},
|
base_dataframes: dict,
|
||||||
is_corr_pairs: bool = False,
|
is_corr_pairs: bool = False,
|
||||||
) -> DataFrame:
|
) -> DataFrame:
|
||||||
"""
|
"""
|
||||||
|
@ -776,7 +776,7 @@ class FreqaiDataKitchen:
|
||||||
corr_dataframes: dict = {},
|
corr_dataframes: dict = {},
|
||||||
base_dataframes: dict = {},
|
base_dataframes: dict = {},
|
||||||
pair: str = "",
|
pair: str = "",
|
||||||
prediction_dataframe: DataFrame = pd.DataFrame(),
|
prediction_dataframe: Optional[DataFrame] = None,
|
||||||
do_corr_pairs: bool = True,
|
do_corr_pairs: bool = True,
|
||||||
) -> DataFrame:
|
) -> DataFrame:
|
||||||
"""
|
"""
|
||||||
|
@ -822,7 +822,7 @@ class FreqaiDataKitchen:
|
||||||
if tf not in corr_dataframes[p]:
|
if tf not in corr_dataframes[p]:
|
||||||
corr_dataframes[p][tf] = pd.DataFrame()
|
corr_dataframes[p][tf] = pd.DataFrame()
|
||||||
|
|
||||||
if not prediction_dataframe.empty:
|
if prediction_dataframe is not None and not prediction_dataframe.empty:
|
||||||
dataframe = prediction_dataframe.copy()
|
dataframe = prediction_dataframe.copy()
|
||||||
base_dataframes[self.config["timeframe"]] = dataframe.copy()
|
base_dataframes[self.config["timeframe"]] = dataframe.copy()
|
||||||
else:
|
else:
|
||||||
|
|
|
@ -25,7 +25,7 @@ class PyTorchModelTrainer(PyTorchTrainerInterface):
|
||||||
criterion: nn.Module,
|
criterion: nn.Module,
|
||||||
device: str,
|
device: str,
|
||||||
data_convertor: PyTorchDataConvertor,
|
data_convertor: PyTorchDataConvertor,
|
||||||
model_meta_data: Dict[str, Any] = {},
|
model_meta_data: Optional[Dict[str, Any]] = None,
|
||||||
window_size: int = 1,
|
window_size: int = 1,
|
||||||
tb_logger: Any = None,
|
tb_logger: Any = None,
|
||||||
**kwargs,
|
**kwargs,
|
||||||
|
@ -45,6 +45,8 @@ class PyTorchModelTrainer(PyTorchTrainerInterface):
|
||||||
:param n_epochs: The maximum number batches to use for evaluation.
|
:param n_epochs: The maximum number batches to use for evaluation.
|
||||||
:param batch_size: The size of the batches to use during training.
|
:param batch_size: The size of the batches to use during training.
|
||||||
"""
|
"""
|
||||||
|
if model_meta_data is None:
|
||||||
|
model_meta_data = {}
|
||||||
self.model = model
|
self.model = model
|
||||||
self.optimizer = optimizer
|
self.optimizer = optimizer
|
||||||
self.criterion = criterion
|
self.criterion = criterion
|
||||||
|
|
|
@ -62,7 +62,7 @@ from freqtrade.rpc.rpc_types import (
|
||||||
)
|
)
|
||||||
from freqtrade.strategy.interface import IStrategy
|
from freqtrade.strategy.interface import IStrategy
|
||||||
from freqtrade.strategy.strategy_wrapper import strategy_safe_wrapper
|
from freqtrade.strategy.strategy_wrapper import strategy_safe_wrapper
|
||||||
from freqtrade.util import MeasureTime
|
from freqtrade.util import FtPrecise, MeasureTime
|
||||||
from freqtrade.util.migrations.binance_mig import migrate_binance_futures_names
|
from freqtrade.util.migrations.binance_mig import migrate_binance_futures_names
|
||||||
from freqtrade.wallets import Wallets
|
from freqtrade.wallets import Wallets
|
||||||
|
|
||||||
|
@ -784,7 +784,14 @@ class FreqtradeBot(LoggingMixin):
|
||||||
if stake_amount is not None and stake_amount < 0.0:
|
if stake_amount is not None and stake_amount < 0.0:
|
||||||
# We should decrease our position
|
# We should decrease our position
|
||||||
amount = self.exchange.amount_to_contract_precision(
|
amount = self.exchange.amount_to_contract_precision(
|
||||||
trade.pair, abs(float(stake_amount * trade.amount / trade.stake_amount))
|
trade.pair,
|
||||||
|
abs(
|
||||||
|
float(
|
||||||
|
FtPrecise(stake_amount)
|
||||||
|
* FtPrecise(trade.amount)
|
||||||
|
/ FtPrecise(trade.stake_amount)
|
||||||
|
)
|
||||||
|
),
|
||||||
)
|
)
|
||||||
|
|
||||||
if amount == 0.0:
|
if amount == 0.0:
|
||||||
|
|
|
@ -168,8 +168,6 @@ max-complexity = 12
|
||||||
[tool.ruff.lint.per-file-ignores]
|
[tool.ruff.lint.per-file-ignores]
|
||||||
"freqtrade/freqai/**/*.py" = [
|
"freqtrade/freqai/**/*.py" = [
|
||||||
"S311", # Standard pseudo-random generators are not suitable for cryptographic purposes
|
"S311", # Standard pseudo-random generators are not suitable for cryptographic purposes
|
||||||
"B006", # Bugbear - mutable default argument
|
|
||||||
"B008", # bugbear - Do not perform function calls in argument defaults
|
|
||||||
]
|
]
|
||||||
"tests/**/*.py" = [
|
"tests/**/*.py" = [
|
||||||
"S101", # allow assert in tests
|
"S101", # allow assert in tests
|
||||||
|
|
|
@ -151,7 +151,9 @@ def test_get_pair_data_for_features_with_prealoaded_data(mocker, freqai_conf):
|
||||||
freqai.dd.load_all_pair_histories(timerange, freqai.dk)
|
freqai.dd.load_all_pair_histories(timerange, freqai.dk)
|
||||||
|
|
||||||
_, base_df = freqai.dd.get_base_and_corr_dataframes(timerange, "LTC/BTC", freqai.dk)
|
_, base_df = freqai.dd.get_base_and_corr_dataframes(timerange, "LTC/BTC", freqai.dk)
|
||||||
df = freqai.dk.get_pair_data_for_features("LTC/BTC", "5m", strategy, base_dataframes=base_df)
|
df = freqai.dk.get_pair_data_for_features(
|
||||||
|
"LTC/BTC", "5m", strategy, {}, base_dataframes=base_df
|
||||||
|
)
|
||||||
|
|
||||||
assert df is base_df["5m"]
|
assert df is base_df["5m"]
|
||||||
assert not df.empty
|
assert not df.empty
|
||||||
|
@ -171,7 +173,9 @@ def test_get_pair_data_for_features_without_preloaded_data(mocker, freqai_conf):
|
||||||
freqai.dd.load_all_pair_histories(timerange, freqai.dk)
|
freqai.dd.load_all_pair_histories(timerange, freqai.dk)
|
||||||
|
|
||||||
base_df = {"5m": pd.DataFrame()}
|
base_df = {"5m": pd.DataFrame()}
|
||||||
df = freqai.dk.get_pair_data_for_features("LTC/BTC", "5m", strategy, base_dataframes=base_df)
|
df = freqai.dk.get_pair_data_for_features(
|
||||||
|
"LTC/BTC", "5m", strategy, {}, base_dataframes=base_df
|
||||||
|
)
|
||||||
|
|
||||||
assert df is not base_df["5m"]
|
assert df is not base_df["5m"]
|
||||||
assert not df.empty
|
assert not df.empty
|
||||||
|
|
Loading…
Reference in New Issue
Block a user