Initial commit setup with docker

This commit is contained in:
Mike
2023-07-13 16:53:03 +02:00
commit 427079a687
9 changed files with 550 additions and 0 deletions
+1
View File
@@ -0,0 +1 @@
.vscode
Executable
+84
View File
@@ -0,0 +1,84 @@
# Trading Bot
[![License](https://img.shields.io/badge/license-MIT-blue.svg)](LICENSE)
A trading bot built using Python and TensorFlow to automate trading strategies.
## Table of Contents
- [Introduction](#introduction)
- [Features](#features)
- [Installation](#installation)
- [Usage](#usage)
- [Configuration](#configuration)
- [Contributing](#contributing)
- [License](#license)
## Introduction
The trading bot is designed to automate trading strategies using historical data, technical indicators, and machine learning. It connects to the MetaTrader 5 platform, retrieves historical data, calculates indicators, generates trade signals, executes trades, and updates a neural network model based on trade outcomes.
## Features
- Retrieval of historical data from MetaTrader 5
- Calculation of technical indicators (RSI, MACD, etc.)
- Detection of double tops and bottoms patterns
- Generation of trade signals based on indicators, patterns, and trend direction
- Execution of trades with risk management
- Update of a TensorFlow neural network model based on trade outcomes
- Visualization of data and trade signals
## Installation
1. Clone the repository:
```shell
git clone https://github.com/your-username/trading-bot.git
```
1. Install Docker and Docker Compose on your system.
1. Build the Docker image and start the container:
```shell
cd trading-bot
docker-compose up -d --build
```
## Usage
1. Ensure that the Docker container is running.
1. Access the running container:
```shell
docker exec -it trading-bot_app_1 bash
```
1. Inside the container, run the trading bot:
```shell
python main.py
```
1. The trading bot will start executing the trading strategies based on the predefined logic.
1. Monitor the bot's output and visualizations.
1. To stop the bot, use `Ctrl + C` in the terminal.
## Configuration
The trading bot can be customized and configured by modifying the following files:
- `main.py`: Contains the main logic for running the trading bot.
- `config.py`: Defines the configuration parameters such as symbol, timeframe, lot size, stop loss, take profit, etc.
- `indicators.py`: Defines additional technical indicators and patterns to be used.
- `preprocess.py`: Handles data preprocessing and feature engineering.
- `model.py`: Defines the structure and training of the neural network model.
- `docker-compose.yml`: Configures the Docker container for running the trading bot.
## Contributing
Contributions are welcome! If you encounter any issues or have suggestions for improvements, please feel free to submit a pull request or create an issue in the repository.
## License
This project is licensed under the [MIT Licence](https://opensource.org/license/mit/).
Binary file not shown.
+351
View File
@@ -0,0 +1,351 @@
import time
import pandas as pd
import numpy as np
from sklearn.preprocessing import MinMaxScaler
import talib
import matplotlib.pyplot as plt
import MetaTrader5 as mt5
from keras.models import Sequential
from keras.layers import Dense, Dropout
from keras.optimizers import Adam
import socket
def start_mt5(username, password, server, path):
# Ensure that all variables are the correct type
uname = int(username) # Username must be an int
pword = str(password) # Password must be a string
trading_server = str(server) # Server must be a string
filepath = str(path) # Filepath must be a string
# Connect to MetaTrader 5
if mt5.initialize(login=uname, password=pword, server=trading_server, path=filepath):
# Login to MT5
if mt5.login(login=uname, password=pword, server=trading_server):
return True
else:
print("Login Fail")
quit()
return PermissionError
else:
print("MT5 Initialization Failed")
quit()
return ConnectionAbortedError
def connect_to_mt5(username, password, server, path):
# Start the MetaTrader 5 instance
if start_mt5(username, password, server, path):
print("Connected to MetaTrader 5")
else:
print("Failed to connect to MetaTrader 5")
return
# Define the symbols and timeframes
symbol = 'EURUSD'
timeframe = mt5.TIMEFRAME_H1
# Set up initial variables
lot_size = 0.01
stop_loss = 100
take_profit = 150
# Define TensorFlow neural network model
def create_neural_network_model(input_shape):
model = Sequential()
model.add(Dense(64, activation='relu', input_shape=input_shape))
model.add(Dropout(0.2))
model.add(Dense(64, activation='relu'))
model.add(Dropout(0.2))
model.add(Dense(1, activation='sigmoid'))
return model
# Define input shape for the neural network
input_shape = (10,) # Adjust the input shape based on your features and data
# Create the neural network model
neural_network_model = create_neural_network_model(input_shape)
# Compile the model
neural_network_model.compile(optimizer=Adam(
learning_rate=0.001), loss='binary_crossentropy')
def get_historical_data():
# Retrieve historical data
rates = mt5.copy_rates_from_pos(symbol, timeframe, 0, 1000)
df = pd.DataFrame(rates)
df['time'] = pd.to_datetime(df['time'], unit='s')
df.set_index('time', inplace=True)
return df
def calculate_indicators_and_detect_patterns(df):
# Calculate RSI
rsi_period = 14
df['rsi'] = talib.RSI(df['close'], rsi_period)
# Calculate MACD
macd_fast_period = 12
macd_slow_period = 26
macd_signal_period = 9
df['macd'], _, df['macd_signal'] = talib.MACD(df['close'], fastperiod=macd_fast_period,
slowperiod=macd_slow_period, signalperiod=macd_signal_period)
# Detect divergence based on RSI and MACD
df['rsi_divergence'] = np.where(
df['rsi'].diff().shift(-1) * df['macd'].diff().shift(-1) < 0, True, False)
df['macd_divergence'] = np.where(
df['macd'].diff().shift(-1) * df['rsi'].diff().shift(-1) < 0, True, False)
# Detect support and resistance levels
window = 10
df['support'] = df['low'].rolling(window).min()
df['resistance'] = df['high'].rolling(window).max()
# Determine trend direction
df['trend_200'] = df['close'].rolling(window=200).mean()
df['trend_50'] = df['close'].rolling(window=50).mean()
# Detect double tops and bottoms
df['pattern'] = 'None'
df['top_pattern'] = np.where(
(df['high'].shift(1) < df['high']) & (df['high'].shift(-1) < df['high']) &
(df['high'].shift(2) > df['high']) & (
df['high'].shift(-2) > df['high']), 'Double Top', 'None'
)
df.loc[df['top_pattern'] != 'None', 'pattern'] = df['top_pattern']
df['bottom_pattern'] = np.where(
(df['low'].shift(1) > df['low']) & (df['low'].shift(-1) > df['low']) &
(df['low'].shift(2) < df['low']) & (
df['low'].shift(-2) < df['low']), 'Double Bottom', 'None'
)
df.loc[df['bottom_pattern'] != 'None', 'pattern'] = df['bottom_pattern']
return df
def generate_signals(df):
# Determine trade signals based on divergences, patterns, and trend direction
df['signal'] = 'None'
df['divergence_signal'] = np.where((df['rsi_divergence'] == True) & (df['pattern'] != 'None'), 'Both',
np.where(df['rsi_divergence'] == True, 'RSI', 'Pattern'))
df['strongest_divergence_signal'] = df[[
'divergence_signal', 'macd_divergence']].max(axis=1)
df['support_resistance_signal'] = np.where(df['close'] > df['resistance'], 'Resistance',
np.where(df['close'] < df['support'], 'Support', 'None'))
df['trend_signal'] = np.where(df['close'] > df['trend_200'], 'Uptrend',
np.where(df['close'] < df['trend_200'], 'Downtrend', 'None'))
for i in range(1, len(df)):
prev_divergence_signal = df['divergence_signal'].iloc[i - 1]
curr_divergence_signal = df['divergence_signal'].iloc[i]
strongest_divergence_signal = df['strongest_divergence_signal'].iloc[i]
support_resistance_signal = df['support_resistance_signal'].iloc[i]
trend_signal = df['trend_signal'].iloc[i]
if strongest_divergence_signal != 'None':
df['signal'].iloc[i] = strongest_divergence_signal
elif prev_divergence_signal == curr_divergence_signal and curr_divergence_signal != 'None':
df['signal'].iloc[i] = curr_divergence_signal
else:
df['signal'].iloc[i] = support_resistance_signal
if trend_signal != 'None' and df['signal'].iloc[i] != 'None':
df['signal'].iloc[i] = trend_signal
return df
def execute_trade(signal, df):
# Implement risk management and trade execution logic based on the signals generated
# Update TensorFlow neural network model with trade outcome (loss or win)
# Calculate risk and position size based on lot size, stop loss, and take profit
risk = lot_size * stop_loss
strongest_divergence_signal = df['strongest_divergence_signal'].iloc[-1]
if strongest_divergence_signal == 'RSI':
risk *= 1.2 # Increase risk by 20% if RSI divergence is the strongest
elif strongest_divergence_signal == 'Pattern':
risk *= 1.5 # Increase risk by 50% if pattern divergence is the strongest
position_size = risk / (take_profit - stop_loss)
try:
if signal == 'Buy':
# Place a buy trade
result = mt5.ORDER_RESULT_FAIL
request = {
"action": mt5.TRADE_ACTION_DEAL,
"symbol": symbol,
"volume": lot_size,
"type": mt5.ORDER_TYPE_BUY,
"price": mt5.symbol_info_tick(symbol).ask,
"sl": mt5.symbol_info_tick(symbol).ask - stop_loss * mt5.symbol_info(symbol).point,
"tp": mt5.symbol_info_tick(symbol).ask + take_profit * mt5.symbol_info(symbol).point,
"deviation": 20,
"magic": 123456,
"comment": "Buy trade",
"type_time": mt5.ORDER_TIME_GTC,
"type_filling": mt5.ORDER_FILLING_RETURN,
}
result = mt5.order_send(request)
outcome = 'Win' if result.retcode == mt5.TRADE_RETCODE_DONE else 'Loss'
elif signal == 'Sell':
# Place a sell trade
result = mt5.ORDER_RESULT_FAIL
request = {
"action": mt5.TRADE_ACTION_DEAL,
"symbol": symbol,
"volume": lot_size,
"type": mt5.ORDER_TYPE_SELL,
"price": mt5.symbol_info_tick(symbol).bid,
"sl": mt5.symbol_info_tick(symbol).bid + stop_loss * mt5.symbol_info(symbol).point,
"tp": mt5.symbol_info_tick(symbol).bid - take_profit * mt5.symbol_info(symbol).point,
"deviation": 20,
"magic": 123456,
"comment": "Sell trade",
"type_time": mt5.ORDER_TIME_GTC,
"type_filling": mt5.ORDER_FILLING_RETURN,
}
result = mt5.order_send(request)
outcome = 'Win' if result.retcode == mt5.TRADE_RETCODE_DONE else 'Loss'
# Example trade outcome information
trade_outcome = {
'pattern': df['pattern'].iloc[-1],
'divergence_strength': strongest_divergence_signal,
'time': df.index[-1],
'trend_direction': df['trend_signal'].iloc[-1],
'indicator_used': strongest_divergence_signal,
'outcome': outcome
}
# Update TensorFlow neural network model with trade outcome
update_neural_network_model(trade_outcome)
# Example print statements for debugging
print(f"Executed {signal} trade with position size: {position_size}")
print(f"Trade outcome: {trade_outcome}")
# Additional logic for trade management, monitoring, etc.
except Exception as e:
print(f"Error executing trade: {str(e)}")
def update_neural_network_model(trade_outcome):
# Implement code to update the neural network model based on trade outcome
pattern = trade_outcome['pattern']
divergence_strength = trade_outcome['divergence_strength']
time = trade_outcome['time']
trend_direction = trade_outcome['trend_direction']
indicator_used = trade_outcome['indicator_used']
outcome = trade_outcome['outcome']
# Example update code: Append trade outcome information to a dataset for future training
trade_data = pd.DataFrame({
'pattern': [pattern],
'divergence_strength': [divergence_strength],
'time': [time],
'trend_direction': [trend_direction],
'indicator_used': [indicator_used],
'outcome': [outcome]
})
# Append the trade data to the dataset for future training
dataset = pd.read_csv('trade_dataset.csv') # Load existing dataset
updated_dataset = pd.concat([dataset, trade_data], ignore_index=True)
# Save updated dataset
updated_dataset.to_csv('trade_dataset.csv', index=False)
# Example retraining code: Retrain the neural network model with the updated dataset
# Preprocess data as per your requirements
X_train, y_train = preprocess_data(updated_dataset)
# Example retraining step
neural_network_model.fit(X_train, y_train, epochs=10, batch_size=32)
# Save the updated model weights
neural_network_model.save_weights('model_weights.h5')
def preprocess_data(dataset):
# Define the numerical features (if any)
numerical_features = [] # Update with the actual numerical feature column names
# Define the input features
input_features = dataset[[
'pattern', 'divergence_strength', 'trend_direction', 'indicator_used']]
# Convert categorical features to one-hot encoding
input_features = pd.get_dummies(input_features)
# Normalize numerical features (if any)
if numerical_features:
scaler = MinMaxScaler()
input_features[numerical_features] = scaler.fit_transform(
input_features[numerical_features])
# Extract target labels from the dataset
target_labels = dataset['outcome']
# Convert target labels to numerical representation (0s and 1s)
target_labels = target_labels.map({'Loss': 0, 'Win': 1})
# Return the preprocessed input features and target labels
return input_features, target_labels
def visualize_data(df):
plt.figure(figsize=(10, 6))
plt.plot(df.index, df['close'], label='Close')
# Add visualizations for other indicators, levels, and patterns
plt.scatter(df[df['pattern'] == 'Double Top'].index, df[df['pattern'] == 'Double Top']['high'],
color='red', marker='v', label='Double Top')
plt.scatter(df[df['pattern'] == 'Double Bottom'].index, df[df['pattern'] == 'Double Bottom']['low'],
color='green', marker='^', label='Double Bottom')
plt.legend()
plt.show()
def run_trading_bot():
# Connect to MetaTrader 5
connect_to_mt5(username='your_username', password='your_password',
server='your_server', path='your_mt5_installation_path')
# Load TensorFlow neural network model weights
neural_network_model.load_weights('model_weights.h5')
while True:
try:
# Get historical data
df = get_historical_data()
# Calculate indicators and detect patterns
df = calculate_indicators_and_detect_patterns(df)
# Generate trade signals
df = generate_signals(df)
# Execute trades
for i in range(1, len(df)):
signal = df['signal'].iloc[i]
if signal != 'None':
execute_trade(signal, df)
# Visualize data
visualize_data(df)
except Exception as e:
print(f"Error running trading bot: {str(e)}")
# Wait for the next iteration
time.sleep(60) # Adjust the time interval as needed
# Run the trading bot
run_trading_bot()
# Disconnect from MetaTrader 5
mt5.shutdown()
+6
View File
@@ -0,0 +1,6 @@
numpy
pandas
TA-Lib
matplotlib
scikit-learn
tensorflow
+30
View File
@@ -0,0 +1,30 @@
import socketio
import time
# Connect to the trading bot container
sio = socketio.Client()
# Replace with the appropriate URL and port of your trading bot container
sio.connect('http://trading_bot:8000')
# Handle events from the trading bot container
@sio.event
def connect():
print('Connected to trading bot container')
@sio.event
def disconnect():
print('Disconnected from trading bot container')
@sio.event
def send_trade_signal(signal):
print(f'Received trade signal: {signal}')
# Process the trade signal and execute trades through MetaTrader 5
# Main loop to keep the script running
while True:
time.sleep(1)
+37
View File
@@ -0,0 +1,37 @@
version: "3"
services:
metatrader_service:
container_name: metatrader
image: ejtrader/metatrader:5
restart: unless-stopped
ports:
- "5900:5900"
- "15555:15555"
- "15556:15556"
- "15557:15557"
- "15558:15558"
volumes:
- ejtraderMT:/data
trading_bot:
container_name: trading_bot
build:
context: .
dockerfile: docker/DockerFile
volumes:
- ./app:/app
depends_on:
- metatrader_service
mt5_bridge:
container_name: mt5_bridge
build:
context: .
dockerfile: docker/DockerFile.mt5_bridge
volumes: -./bridge:/bridge
depends_on:
- metatrader_service
- trading_bot
volumes:
ejtraderMT: {}
+29
View File
@@ -0,0 +1,29 @@
# Use an official Python runtime as the base image
FROM python:3.10
# Set the working directory in the container
WORKDIR /app
# Copy the requirements file to the working directory
COPY app/requirements.txt .
# Copy the Tab-Lib dependencies to the working directory
COPY app/Tab-Lib-deps/ta-lib-0.4.0-src.tar.gz .
# Extract and install Tab-Lib
RUN tar -xzf ta-lib-0.4.0-src.tar.gz && \
rm ta-lib-0.4.0-src.tar.gz && \
cd ta-lib && \
./configure --prefix=/usr && \
make && \
make install && \
cd ..
# Install the Python dependencies
RUN pip install --no-cache-dir -r requirements.txt
# Copy the application code to the container
COPY app/ .
# Run the bot script when the container launches
CMD [ "python", "bot.py" ]
+12
View File
@@ -0,0 +1,12 @@
FROM python:3.10
# Set the working directory in the container
WORKDIR /app
# Copy the bridge script to the container
COPY bridge/mt5_bridge.py .
# Install any dependencies required by the bridge script
RUN pip install python-socketio python-engineio
CMD ["python", "mt5_bridge.py"]