- Admin
- #1
Hi,
I'm planning to write a plugin for MediaPortal 2, that supports users to find the right media items with help of AI frameworks.
Following is used:
- OpenAI Framework
- ChatGPT3.5 Client
- Model: text-davinci-003
- OpenAI API
It makes mostly sense in combination of speech control which is not existing/working for MP2 as complex questions are uncomfortable to enter with remote control.
- In first step I want to only limit this to existing local media items in the MP2-DB
- In second step (only if first one works well) it could be extended to all media items, also not in MP2-DB existent ones
- You can perform easy filter actions for year, gerne, actors, ... (E.g.: "Show me all movies from the genre Thriller", ...)
- You can perform complex filter actions (E.g.: "Show me all movies, that contain cowboys", "Show me movies with blue-skinned aliens", ...)
What does the program do yet:
- The C# WPF application reads movie titles from MP2 SQLite database table (M_MOVIEITEM) and displays the complete list of movie titles on the right side of the window (I first concentrate only on the movie title)
- It then uses the OpenAI GPT-3 API to find the best movie match based on a search question entered by the user (Restiction: Learning date are from 12/2021, all titles after that can currently not be considered)
- The result is now displayed in a ListBox named resultListBox, which allows for multiple matches to be shown. The GetBestMovieMatches method returns a list of best matches, and the resultListBox.ItemsSource is set to this list for display.
XML:
<Window x:Class="MovieSearchApp.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Movie Search" Height="350" Width="500">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<!-- Left Column: Movie List -->
<ListBox x:Name="movieListBox" Grid.Column="0" Margin="10"/>
<!-- Right Column: Search and Result -->
<StackPanel Grid.Column="1" Margin="10">
<Label Content="Enter search query:"/>
<TextBox x:Name="searchTextBox" Width="200" Margin="0,0,0,10"/>
<Button Content="OK" Click="SearchButton_Click"/>
<Label Content="Best Movie Matches:" Margin="0,20,0,0"/>
<ListBox x:Name="resultListBox" Width="200" Height="60"/>
</StackPanel>
</Grid>
</Window>
MainWindow.xaml.cs
C#:
using System;
using System.Collections.Generic;
using System.Data.SQLite;
using System.Net.Http;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
namespace MovieSearchApp
{
public partial class MainWindow : Window
{
private const string ConnectionString = "Data Source=C:\\ProgramData\\Team MediaPortal\\MP2-Server\\Database\\Datastore.s3db;Version=3;";
private const string OpenAIApiKey = "your_openai_api_key";
private const string OpenAIEndpoint = "https://api.openai.com/v1/engines/davinci-codex/completions";
public MainWindow()
{
InitializeComponent();
PopulateMovieList();
}
private void PopulateMovieList()
{
using (SQLiteConnection connection = new SQLiteConnection(ConnectionString))
{
connection.Open();
string sql = "SELECT MOVIENAME FROM M_MOVIEITEM;";
using (SQLiteCommand command = new SQLiteCommand(sql, connection))
using (SQLiteDataReader reader = command.ExecuteReader())
{
while (reader.Read())
{
string movieTitle = reader["MOVIENAME"].ToString();
movieListBox.Items.Add(movieTitle);
}
}
}
}
private async void SearchButton_Click(object sender, RoutedEventArgs e)
{
try
{
string searchQuery = searchTextBox.Text.Trim();
if (string.IsNullOrEmpty(searchQuery))
{
MessageBox.Show("Please enter a search query.");
return;
}
// Use ChatGPT to generate responses based on the search question
List<string> bestMatches = await GetBestMovieMatches(searchQuery);
// Display the results
resultListBox.ItemsSource = bestMatches;
}
catch (Exception ex)
{
MessageBox.Show($"An error occurred: {ex.Message}");
}
}
private async Task<List<string>> GetBestMovieMatches(string searchQuery)
{
List<string> bestMatches = new List<string>();
foreach (string movieTitle in movieListBox.Items)
{
// Use ChatGPT to determine the match
string generatedText = await GenerateResponseWithGPT(searchQuery, movieTitle);
// You can add your matching logic here based on the generated text
// For simplicity, we're using the whole generated text as the match
if (!string.IsNullOrEmpty(generatedText))
{
bestMatches.Add(generatedText);
}
}
return bestMatches;
}
private async Task<string> GenerateResponseWithGPT(string searchQuery, string movieTitle)
{
using (HttpClient client = new HttpClient())
{
client.DefaultRequestHeaders.Add("Authorization", $"Bearer {OpenAIApiKey}");
string prompt = $"Find the best movie match for the search query: {searchQuery}. Movie Title: {movieTitle}";
var requestData = new
{
prompt,
max_tokens = 50,
temperature = 0.7
};
string requestDataJson = Newtonsoft.Json.JsonConvert.SerializeObject(requestData);
var content = new StringContent(requestDataJson, Encoding.UTF8, "application/json");
HttpResponseMessage response = await client.PostAsync(OpenAIEndpoint, content);
if (response.IsSuccessStatusCode)
{
string responseJson = await response.Content.ReadAsStringAsync();
dynamic responseData = Newtonsoft.Json.JsonConvert.DeserializeObject(responseJson);
string generatedText = responseData.choices[0].text;
return generatedText;
}
else
{
throw new Exception($"ChatGPT API request failed. Status code: {response.StatusCode}");
}
}
}
}
}
Does anyone have a OpenAI API (1/user is free) and can support me writing/testing?
Make sure to replace "database.db" with the actual path to your SQLite database file (I kept mine in the code, as this will not change for most users) and "your_openai_api_key" with your OpenAI API key.
Last edited: