import yfinance as yf import pandas as pd import numpy as np import tensorflow as tf from tensorflow.keras import layers, models import matplotlib.pyplot as plt import gradio as gr from datetime import datetime, timedelta # Ensure matplotlib does not require a display environment import matplotlib matplotlib.use('Agg') # Define the stock tickers STOCK_TICKERS = [ 'AAPL', 'GOOGL', 'MSFT', 'AMZN', 'TSLA', 'FB', 'NVDA', 'JPM', 'V', 'DIS' ] def fetch_data(ticker, start_date, end_date): """ Fetch historical stock data from yfinance. Args: ticker (str): Stock ticker symbol. start_date (str): Start date in 'YYYY-MM-DD'. end_date (str): End date in 'YYYY-MM-DD'. Returns: pd.DataFrame: Historical stock data. """ data = yf.download(ticker, start=start_date, end=end_date) return data def preprocess_data(data): """ Preprocess the stock data for model training. Args: data (pd.DataFrame): Raw stock data. Returns: np.ndarray, np.ndarray: Features and labels. """ # Calculate moving averages data['MA10'] = data['Close'].rolling(window=10).mean() data['MA20'] = data['Close'].rolling(window=20).mean() # Drop NaN values data = data.dropna() # Features: Close, MA10, MA20 features = data[['Close', 'MA10', 'MA20']].values # Labels: 1 if next day's Close > today's Close, else 0 data['Target'] = np.where(data['Close'].shift(-1) > data['Close'], 1, 0) labels = data['Target'].values[:-1] features = features[:-1] return features, labels def build_model(input_shape): """ Build and compile the TensorFlow model. Args: input_shape (int): Number of features. Returns: tf.keras.Model: Compiled model. """ model = models.Sequential([ layers.Dense(64, activation='relu', input_shape=(input_shape,)), layers.Dense(32, activation='relu'), layers.Dense(1, activation='sigmoid') # Binary classification ]) model.compile(optimizer='adam', loss='binary_crossentropy', metrics=['accuracy']) return model # Train the model for each stock ticker and store in a dictionary models_dict = {} for ticker in STOCK_TICKERS: # Fetch data for the past 5 years end = datetime.today() start = end - timedelta(days=5*365) data = fetch_data(ticker, start.strftime('%Y-%m-%d'), end.strftime('%Y-%m-%d')) if data.empty: print(f"No data found for {ticker}. Skipping...") continue features, labels = preprocess_data(data) model = build_model(features.shape[1]) model.fit(features, labels, epochs=10, batch_size=32, verbose=0) models_dict[ticker] = model print(f"Model trained for {ticker}") def predict_stock(ticker, start_date, end_date): """ Predict whether to Buy or Sell the stock based on user input. Args: ticker (str): Selected stock ticker. start_date (str): Training start date. end_date (str): Training end date. Returns: dict: Prediction results and graph. """ # Fetch data data = fetch_data(ticker, start_date, end_date) if data.empty: return { "Percentage Change": "No data available for the selected dates.", "Highest Price": "N/A", "Lowest Price": "N/A", "Prediction": "N/A", "Graph": None } # Preprocess data features, labels = preprocess_data(data) if features.size == 0: return { "Percentage Change": "Insufficient data after preprocessing.", "Highest Price": "N/A", "Lowest Price": "N/A", "Prediction": "N/A", "Graph": None } # Get the latest features for prediction latest_data = data[['Close', 'MA10', 'MA20']].values[-1].reshape(1, -1) # Predict using the trained model model = models_dict.get(ticker) if not model: return { "Percentage Change": "Model not found for the selected ticker.", "Highest Price": "N/A", "Lowest Price": "N/A", "Prediction": "N/A", "Graph": None } prediction = model.predict(latest_data) prediction_label = "Buy" if prediction[0][0] > 0.5 else "Sell" # Calculate percentage change start_close = data['Close'].iloc[0] latest_close = data['Close'].iloc[-1] percent_change = ((latest_close - start_close) / start_close) * 100 # Highest and Lowest values highest = data['Close'].max() lowest = data['Close'].min() # Plot historical data plt.figure(figsize=(10,5)) plt.plot(data.index, data['Close'], label='Historical Close') # Predict future 3 months (approx 63 trading days) future_days = 63 # For simplicity, we'll extend the latest close with random walk future_prices = [latest_close] for _ in range(future_days): change_percent = np.random.uniform(-0.02, 0.02) # Simulate small changes new_price = future_prices[-1] * (1 + change_percent) future_prices.append(new_price) future_dates = pd.date_range(data.index[-1] + timedelta(days=1), periods=future_days+1, freq='B') plt.plot(future_dates, future_prices[1:], label='Predicted Close') plt.xlabel('Date') plt.ylabel('Price') plt.title(f'{ticker} Historical and Predicted Performance') plt.legend() plt.tight_layout() plt.savefig('performance.png') plt.close() # Prepare the result result = { "Percentage Change": f"{percent_change:.2f}%", "Highest Price": f"${highest:.2f}", "Lowest Price": f"${lowest:.2f}", "Prediction": prediction_label, "Graph": 'performance.png' } return result # Define Gradio Interface iface = gr.Interface( fn=predict_stock, inputs=[ gr.Dropdown(choices=STOCK_TICKERS, label="Select Stock Ticker"), gr.DatePicker(label="Start Date"), gr.DatePicker(label="End Date") ], outputs=[ gr.Textbox(label="Percentage Change"), gr.Textbox(label="Highest Price"), gr.Textbox(label="Lowest Price"), gr.Textbox(label="Buy/Sell Prediction"), gr.Image(label="Performance Graph") ], title="📈 Stock Buy/Sell Prediction App", description=( "Select a stock ticker and a date range to predict whether to **Buy** or **Sell** the stock. " "View the percentage change, highest and lowest prices, and a performance graph." ) ) # Launch the app iface.launch() from tensorflow.keras.models import Sequential from tensorflow.keras.layers import Dense, Input def create_model(input_shape): model = Sequential() model.add(Input(shape=(input_shape,))) # Explicitly define input shape model.add(Dense(64, activation='relu')) model.add(Dense(32, activation='relu')) model.add(Dense(1, activation='sigmoid')) model.compile(optimizer='adam', loss='binary_crossentropy', metrics=['accuracy']) return model data.loc[:, 'Target'] = np.where(data['Close'].shift(-1) > data['Close'], 1, 0) import gradio as gr def predict_stock(ticker, start_date, end_date): # Your prediction logic return "Prediction result" interface = gr.Interface( fn=predict_stock, inputs=[ gr.inputs.Dropdown(['AAPL', 'MSFT', 'GOOG', 'AMZN', 'TSLA'], label="Stock Ticker"), gr.inputs.Date(label="Start Date"), # Replace DatePicker with Date gr.inputs.Date(label="End Date") ], outputs="text" ) interface.launch()