mirror of
https://github.com/hmaxnl/SharpRSS.git
synced 2025-01-18 21:04:21 +01:00
Reworking models.
This commit is contained in:
parent
43cb208910
commit
e4a0f4ce7d
|
@ -1,33 +0,0 @@
|
|||
using System;
|
||||
|
||||
namespace SharpRss.Models
|
||||
{
|
||||
/// <summary>
|
||||
/// To store and load data from file/database
|
||||
/// </summary>
|
||||
public class CategoryModel
|
||||
{
|
||||
public CategoryModel()
|
||||
{
|
||||
HexColor = $"#{_random.Next(0x1000000):X6}";
|
||||
CategoryId = Guid.NewGuid().ToString();
|
||||
}
|
||||
private readonly Random _random = new Random();
|
||||
|
||||
public static CategoryModel Create(string categoryName, string hexColor, string id)
|
||||
{
|
||||
CategoryModel catModel = new CategoryModel()
|
||||
{
|
||||
Name = categoryName,
|
||||
HexColor = hexColor,
|
||||
CategoryId = id
|
||||
};
|
||||
return catModel;
|
||||
}
|
||||
|
||||
public string Name { get; set; }
|
||||
public string HexColor { get; set; }
|
||||
public string PathIcon { get; set; }
|
||||
public string CategoryId { get; private set; }
|
||||
}
|
||||
}
|
|
@ -11,14 +11,13 @@ namespace SharpRss.Models
|
|||
/// </summary>
|
||||
public DateTime LastUpdated { get; set; }
|
||||
/// <summary>
|
||||
/// The feed in which the item is part.
|
||||
/// The feed in which the item is part of.
|
||||
/// </summary>
|
||||
public string FeedId { get; set; }
|
||||
/// <summary>
|
||||
/// If the item is read.
|
||||
/// </summary>
|
||||
public string Read { get; set; }
|
||||
|
||||
public bool Read { get; set; }
|
||||
public string Type { get; set; }
|
||||
public string Title { get; set; }
|
||||
public string Description { get; set; }
|
||||
|
|
|
@ -5,20 +5,8 @@ namespace SharpRss.Models
|
|||
{
|
||||
public class FeedModel
|
||||
{
|
||||
private FeedModel()
|
||||
{
|
||||
|
||||
}
|
||||
public FeedModel(string rssFeedUrl, CategoryModel? category = null)
|
||||
{
|
||||
if (category != null)
|
||||
CategoryId = category.CategoryId;
|
||||
FeedId = Guid.NewGuid().ToString();
|
||||
FeedUrl = rssFeedUrl;
|
||||
}
|
||||
public string FeedId { get; private set; }
|
||||
public string CategoryId { get; set; } = "";
|
||||
|
||||
public string FeedId { get; set; }
|
||||
public string CategoryId { get; set; }
|
||||
public string FeedType { get; set; }
|
||||
public string FeedUrl { get; set; }
|
||||
public string Description { get; set; }
|
||||
|
@ -26,16 +14,5 @@ namespace SharpRss.Models
|
|||
public string Copyright { get; set; }
|
||||
public DateTime LastUpdated { get; set; }
|
||||
public string ImageUrl { get; set; }
|
||||
|
||||
public static FeedModel Create(string url, string feedId, string categoryId)
|
||||
{
|
||||
FeedModel feedModel = new FeedModel()
|
||||
{
|
||||
FeedUrl = url,
|
||||
FeedId = feedId,
|
||||
CategoryId = categoryId
|
||||
};
|
||||
return feedModel;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
22
SharpRss/Models/GroupModel.cs
Normal file
22
SharpRss/Models/GroupModel.cs
Normal file
|
@ -0,0 +1,22 @@
|
|||
using System;
|
||||
|
||||
namespace SharpRss.Models
|
||||
{
|
||||
/// <summary>
|
||||
/// To store and load data from file/database
|
||||
/// </summary>
|
||||
public class GroupModel
|
||||
{
|
||||
/*public GroupModel()
|
||||
{
|
||||
HexColor = $"#{_random.Next(0x1000000):X6}";
|
||||
Id = Guid.NewGuid().ToString();
|
||||
}
|
||||
private readonly Random _random = new Random();*/
|
||||
|
||||
public string Name { get; set; }
|
||||
public string HexColor { get; set; }
|
||||
public string Icon { get; set; }
|
||||
public string Id { get; private set; }
|
||||
}
|
||||
}
|
|
@ -2,7 +2,6 @@ using System;
|
|||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using Dapper;
|
||||
using Microsoft.Data.Sqlite;
|
||||
|
@ -13,22 +12,30 @@ namespace SharpRss.Services
|
|||
{
|
||||
internal class DatabaseService : IDisposable
|
||||
{
|
||||
private string _connectionString => $"Data Source={Path.Combine(Environment.CurrentDirectory, "sharp_rss.db")};";
|
||||
internal DatabaseService()
|
||||
{
|
||||
_sqlConn = new SqliteConnection(_connectionString);
|
||||
InitializeDb();
|
||||
}
|
||||
private readonly SqliteConnection _sqlConn;
|
||||
private readonly string _connectionString = $"Data Source={Path.Combine(Environment.CurrentDirectory, "sharp_rss.sqlite")};";
|
||||
private readonly string _groupTable = "group_data";
|
||||
private readonly string _feedTable = "feed_data";
|
||||
private readonly string _feedItemTable = "feed_item_data";
|
||||
|
||||
public async Task<bool> AddCategoriesAsync(HashSet<CategoryModel> categories)
|
||||
public async Task RemoveGroupFromFeedsAsync(string groupId)
|
||||
{
|
||||
await _sqlConn.QueryAsync("UPDATE feed_data SET group_id=NULL WHERE group_id=@GroupId", new { GroupId = groupId });
|
||||
}
|
||||
|
||||
public async Task<bool> AddCategoriesAsync(HashSet<GroupModel> categories)
|
||||
{
|
||||
bool result = true;
|
||||
_sqlConn.Open();
|
||||
foreach (var categoryModel in categories)
|
||||
{
|
||||
await _sqlConn.QueryAsync("INSERT INTO category_data (name, hex_color, path_icon, category_id) VALUES(@catName, @hexColor, @pathIcon, @categoryId) ON CONFLICT(name) DO UPDATE SET hex_color=@hexColor, path_icon=@pathIcon",
|
||||
new { catName = categoryModel.Name, hexColor = categoryModel.HexColor, pathIcon = categoryModel.PathIcon, categoryId = categoryModel.CategoryId });
|
||||
new { catName = categoryModel.Name, hexColor = categoryModel.HexColor, pathIcon = categoryModel.Icon, categoryId = categoryModel.Id });
|
||||
}
|
||||
_sqlConn.Close();
|
||||
return result;
|
||||
|
@ -46,15 +53,18 @@ namespace SharpRss.Services
|
|||
return result;
|
||||
}
|
||||
|
||||
public async Task<HashSet<CategoryModel>> GetCategoriesAsync()
|
||||
public async Task<HashSet<GroupModel>> GetCategoriesAsync()
|
||||
{
|
||||
HashSet<CategoryModel> categories = new HashSet<CategoryModel>();
|
||||
HashSet<GroupModel> categories = new HashSet<GroupModel>();
|
||||
_sqlConn.Open();
|
||||
SqliteCommand cmd = _sqlConn.CreateCommand();
|
||||
cmd.CommandText = "SELECT * FROM category_data";
|
||||
await using SqliteDataReader reader = await cmd.ExecuteReaderAsync();
|
||||
while (reader.Read())
|
||||
categories.Add(CategoryModel.Create(reader["name"].ToString(), reader["hex_color"].ToString(), reader["category_id"].ToString()));
|
||||
{
|
||||
//categories.Add(GroupModel.Create(reader["name"].ToString(), reader["hex_color"].ToString(), reader["category_id"].ToString()));
|
||||
}
|
||||
|
||||
_sqlConn.Close();
|
||||
return categories;
|
||||
}
|
||||
|
@ -71,7 +81,9 @@ namespace SharpRss.Services
|
|||
|
||||
await using SqliteDataReader reader = await cmd.ExecuteReaderAsync();
|
||||
while (reader.Read())
|
||||
feeds.Add(FeedModel.Create(reader["url"].ToString(), reader["feed_id"].ToString(), reader["category_id"].ToString()));
|
||||
{
|
||||
//feeds.Add(FeedModel.Create(reader["url"].ToString(), reader["feed_id"].ToString(), reader["category_id"].ToString()));
|
||||
}
|
||||
_sqlConn.Close();
|
||||
return feeds;
|
||||
}
|
||||
|
@ -81,14 +93,18 @@ namespace SharpRss.Services
|
|||
Log.Verbose("Checking database...");
|
||||
HashSet<string> failed = new HashSet<string>();
|
||||
_sqlConn.Open();
|
||||
// Check category_data table
|
||||
var queryResponse = await _sqlConn.QueryAsync("CREATE TABLE IF NOT EXISTS category_data (name STRING NOT NULL, hex_color STRING NOT NULL, path_icon STRING, category_id STRING PRIMARY KEY, CONSTRAINT name UNIQUE (name))");
|
||||
Log.Verbose("Checking table: {Table}", _groupTable);
|
||||
var queryResponse = await _sqlConn.QueryAsync($"CREATE TABLE IF NOT EXISTS {_groupTable} (name STRING NOT NULL, hex_color STRING NOT NULL, icon STRING, id STRING PRIMARY KEY, CONSTRAINT name UNIQUE (name))");
|
||||
if (queryResponse.Any()) failed.Add("category_data");
|
||||
|
||||
// Check feed_data table
|
||||
queryResponse = await _sqlConn.QueryAsync("CREATE TABLE IF NOT EXISTS feed_data (url STRING NOT NULL, feed_id STRING PRIMARY KEY, category_id STRING NOT NULL DEFAULT '', CONSTRAINT url, UNIQUE (url))");
|
||||
Log.Verbose("Checking table: {Table}", _feedTable);
|
||||
queryResponse = await _sqlConn.QueryAsync($"CREATE TABLE IF NOT EXISTS {_feedTable} (url STRING NOT NULL, id STRING PRIMARY KEY, group_id STRING DEFAULT NULL, CONSTRAINT url, UNIQUE (url))");
|
||||
if (queryResponse.Any()) failed.Add("feed_data");
|
||||
|
||||
Log.Verbose("Checking table: {Table}", _feedItemTable);
|
||||
queryResponse = await _sqlConn.QueryAsync($"CREATE TABLE IF NOT EXISTS {_feedItemTable} (id STRING PRIMARY KEY, feed_id STRING NOT NULL)");
|
||||
if (queryResponse.Any()) failed.Add("feed_item_data");
|
||||
|
||||
_sqlConn.Close();
|
||||
if (failed.Any())
|
||||
{
|
||||
|
|
|
@ -1,3 +1,4 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
|
@ -18,7 +19,7 @@ namespace SharpRss.Services
|
|||
}
|
||||
private readonly DatabaseService _dbService = new DatabaseService();
|
||||
|
||||
private async void SetupTestCategoriesAndFeedsAsync()
|
||||
/*private async void SetupTestCategoriesAndFeedsAsync()
|
||||
{
|
||||
await _dbService.AddCategoriesAsync(new HashSet<CategoryModel>()
|
||||
{
|
||||
|
@ -34,56 +35,58 @@ namespace SharpRss.Services
|
|||
new FeedModel("https://journals.plos.org/plosone/feed/atom"),
|
||||
new FeedModel("https://itsfoss.com/feed")
|
||||
});
|
||||
}
|
||||
}*/
|
||||
|
||||
public async Task<Feed> GetFeedAsync(string rssUrl)
|
||||
{
|
||||
return await FeedCache.GetFeed(rssUrl);
|
||||
/*return await FeedCache.GetFeed(rssUrl);*/
|
||||
return new Feed();
|
||||
}
|
||||
|
||||
public async Task<HashSet<object>> GetAllUnsortedAsync()
|
||||
{
|
||||
HashSet<object> items = new HashSet<object>();
|
||||
var categories = await _dbService.GetCategoriesAsync();
|
||||
/*var categories = await _dbService.GetCategoriesAsync();
|
||||
var feeds = await _dbService.GetFeedsAsync(string.Empty);
|
||||
items.UnionWith(categories);
|
||||
items.UnionWith(feeds);
|
||||
items.UnionWith(feeds);*/
|
||||
return items;
|
||||
}
|
||||
|
||||
public async Task<HashSet<CategoryModel>> GetCategoriesAsync()
|
||||
public async Task<HashSet<GroupModel>> GetCategoriesAsync()
|
||||
{
|
||||
var result = await _dbService.GetCategoriesAsync();
|
||||
return result.OrderBy(x => x.Name).ToHashSet();
|
||||
/*var result = await _dbService.GetCategoriesAsync();
|
||||
return result.OrderBy(x => x.Name).ToHashSet();*/
|
||||
return new HashSet<GroupModel>();
|
||||
}
|
||||
|
||||
public async Task<HashSet<FeedModel>> GetFeedsAsync(CategoryModel? categoryModel = null)
|
||||
public async Task<HashSet<FeedModel>> GetFeedsAsync(GroupModel? categoryModel = null)
|
||||
{
|
||||
HashSet<FeedModel> feeds;
|
||||
if (categoryModel != null)
|
||||
feeds = await _dbService.GetFeedsAsync(categoryModel.CategoryId);
|
||||
HashSet<FeedModel> feeds = new HashSet<FeedModel>();
|
||||
/*if (categoryModel != null)
|
||||
feeds = await _dbService.GetFeedsAsync(categoryModel.Id);
|
||||
else
|
||||
feeds = await _dbService.GetFeedsAsync();
|
||||
feeds = await _dbService.GetFeedsAsync();*/
|
||||
return feeds;
|
||||
}
|
||||
|
||||
public async void AddCategoryAsync(string name, string? icon, string hexColor)
|
||||
{
|
||||
CategoryModel categoryModel = new CategoryModel()
|
||||
/*GroupModel groupModel = new GroupModel()
|
||||
{
|
||||
Name = name
|
||||
};
|
||||
if (icon != null)
|
||||
categoryModel.PathIcon = icon;
|
||||
groupModel.PathIcon = icon;
|
||||
if (!hexColor.IsNullEmptyWhiteSpace())
|
||||
categoryModel.HexColor = hexColor;
|
||||
await _dbService.AddCategoriesAsync(new HashSet<CategoryModel>() { categoryModel });
|
||||
groupModel.HexColor = hexColor;*/
|
||||
//await _dbService.AddCategoriesAsync(new HashSet<GroupModel>() { groupModel });
|
||||
}
|
||||
|
||||
public async void AddFeedAsync(string rssUrl, CategoryModel? category = null)
|
||||
public async void AddFeedAsync(string rssUrl, GroupModel? category = null)
|
||||
{
|
||||
FeedModel feedModel = new FeedModel(rssUrl, category);
|
||||
await _dbService.AddFeedsAsync(new HashSet<FeedModel>() { feedModel });
|
||||
//FeedModel feedModel = new FeedModel(rssUrl, category);
|
||||
//await _dbService.AddFeedsAsync(new HashSet<FeedModel>() { feedModel });
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
|
|
2
ToolQit
2
ToolQit
|
@ -1 +1 @@
|
|||
Subproject commit af3abae0445b30c3ef58579a18e6e179eaea5986
|
||||
Subproject commit b2a5173c7ffc21e83eb02c96b6e70434d7396d58
|
|
@ -3,8 +3,10 @@ using System.IO;
|
|||
using Serilog;
|
||||
using Serilog.Formatting.Json;
|
||||
using Serilog.Sinks.SystemConsole.Themes;
|
||||
using SharpRss.Models;
|
||||
using ToolQit;
|
||||
using ToolQit.Containers;
|
||||
using WebSharpRSS.Models;
|
||||
|
||||
namespace WebSharpRSS
|
||||
{
|
||||
|
|
|
@ -1,19 +1,11 @@
|
|||
using CodeHollow.FeedReader;
|
||||
using SharpRss.Models;
|
||||
using SharpRss.Models;
|
||||
using ToolQit;
|
||||
|
||||
namespace WebSharpRSS.Models
|
||||
{
|
||||
public class FeedItemData
|
||||
public class FeedItemData : FeedItemModel
|
||||
{
|
||||
public FeedItemData(FeedItem feedItem)
|
||||
{
|
||||
FeedItem = feedItem;
|
||||
}
|
||||
public FeedModel FeedModel { get; set; }
|
||||
public FeedItem FeedItem { get; set; }
|
||||
public string? Icon {get; set; }
|
||||
public string? FaviconUrl { get; set; }
|
||||
public string? CategoryColorHex { get; set; }
|
||||
public bool Read { get; set; }
|
||||
public static FeedItemData? FromModel(FeedItemModel model) => Utilities.ConvertFrom<FeedItemData, FeedItemModel>(model);
|
||||
public string HexColor { get; set; }
|
||||
}
|
||||
}
|
||||
|
|
|
@ -12,7 +12,7 @@ namespace WebSharpRSS.Models
|
|||
{
|
||||
public class TreeItemData
|
||||
{
|
||||
public TreeItemData(CategoryModel catModel, RssService rssService)
|
||||
public TreeItemData(GroupModel catModel, RssService rssService)
|
||||
{
|
||||
_service = rssService;
|
||||
CategoryModel = catModel;
|
||||
|
@ -28,7 +28,7 @@ namespace WebSharpRSS.Models
|
|||
}
|
||||
|
||||
private readonly RssService _service;
|
||||
public readonly CategoryModel? CategoryModel;
|
||||
public readonly GroupModel? CategoryModel;
|
||||
public readonly FeedModel? FeedModel;
|
||||
private HashSet<FeedModel> _feedModels;
|
||||
|
||||
|
@ -69,16 +69,16 @@ namespace WebSharpRSS.Models
|
|||
{
|
||||
Title = CategoryModel.Name;
|
||||
Icon = Icons.Material.Filled.Category;
|
||||
_feedModels = await _service.GetFeedsAsync(CategoryModel);
|
||||
/*_feedModels = await _service.GetFeedsAsync(CategoryModel);
|
||||
if (_feedModels.Any())
|
||||
Feeds = _feedModels.Select(x => new TreeItemData(x, _service)).OrderBy(x => x.Title).ToHashSet();
|
||||
Feeds = _feedModels.Select(x => new TreeItemData(x, _service)).OrderBy(x => x.Title).ToHashSet();*/
|
||||
}
|
||||
|
||||
if (FeedModel != null)
|
||||
{
|
||||
try
|
||||
{
|
||||
Feed = await _service.GetFeedAsync(FeedModel.FeedUrl);
|
||||
//Feed = await _service.GetFeedAsync(FeedModel.FeedUrl);
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
@inject FeedStateContainer _stateContainer;
|
||||
|
||||
<MudStack Spacing="2" Class="ml-2 mr-2">
|
||||
@foreach (var feedItemData in _itemDatas)
|
||||
@*@foreach (var feedItemData in _itemDatas)
|
||||
{
|
||||
<MudItem>
|
||||
<MudCard>
|
||||
|
@ -28,7 +28,7 @@
|
|||
</MudCardContent>
|
||||
</MudCard>
|
||||
</MudItem>
|
||||
}
|
||||
}*@
|
||||
</MudStack>
|
||||
|
||||
@code {
|
||||
|
@ -42,11 +42,12 @@
|
|||
UpdateFeeds();
|
||||
InvokeAsync(StateHasChanged);
|
||||
}
|
||||
private HashSet<FeedItemData> _itemDatas = new HashSet<FeedItemData>();
|
||||
private TreeItemData? _treeItemData;
|
||||
//private HashSet<FeedItemData> _itemDatas = new HashSet<FeedItemData>();
|
||||
//private TreeItemData? _treeItemData;
|
||||
private void UpdateFeeds()
|
||||
{
|
||||
if (_stateContainer.TreeItem == null) return;
|
||||
|
||||
/*if (_stateContainer.TreeItem == null) return;
|
||||
_treeItemData = _stateContainer.TreeItem;
|
||||
if (_treeItemData.Feed != null)
|
||||
{
|
||||
|
@ -62,6 +63,6 @@
|
|||
items.UnionWith(treeItem.Feed.Items.Select(x => new FeedItemData(x) { Icon = treeItem.Icon, FaviconUrl = treeItem.FaviconUrl, CategoryColorHex = _treeItemData.CategoryModel?.HexColor }));
|
||||
_itemDatas = items.OrderBy(x => x.FeedItem.PublishingDate).Reverse().ToHashSet();
|
||||
}
|
||||
}
|
||||
}*/
|
||||
}
|
||||
}
|
|
@ -6,13 +6,12 @@
|
|||
@using WebSharpRSS.Models;
|
||||
@using ToolQit.Extensions;
|
||||
|
||||
@inject NavigationManager _navManager;
|
||||
@inject FeedStateContainer _stateContainer;
|
||||
@inject RssService _rssService
|
||||
|
||||
<MudStack Spacing="2">
|
||||
<MudTreeView Items="_guideItems" @bind-SelectedValue="SelectedItem" Hover="true">
|
||||
<ItemTemplate>
|
||||
@*<ItemTemplate>
|
||||
<MudTreeViewItem @bind-Expanded="@context.IsExpanded" Items="@context.Feeds" Value="@context" CanExpand="@context.HasChild" @onclick="ItemClicked">
|
||||
<Content>
|
||||
<div style="display: grid; grid-template-columns: 1fr auto; align-items: center; width: 100%">
|
||||
|
@ -34,7 +33,7 @@
|
|||
</div>
|
||||
</Content>
|
||||
</MudTreeViewItem>
|
||||
</ItemTemplate>
|
||||
</ItemTemplate>*@
|
||||
</MudTreeView>
|
||||
</MudStack>
|
||||
|
||||
|
@ -59,8 +58,8 @@
|
|||
protected override async void OnInitialized()
|
||||
{
|
||||
Log.Verbose("Loading guide data...");
|
||||
HashSet<object> items = await _rssService.GetAllUnsortedAsync();
|
||||
_guideItems.UnionWith(items.Select(x => x is CategoryModel model ? new TreeItemData(model, _rssService) : x is FeedModel feedModel ? new TreeItemData(feedModel, _rssService) : throw new ArgumentException("Arg x is invalid!")));
|
||||
/*HashSet<object> items = await _rssService.GetAllUnsortedAsync();
|
||||
_guideItems.UnionWith(items.Select(x => x is CategoryModel model ? new TreeItemData(model, _rssService) : x is FeedModel feedModel ? new TreeItemData(feedModel, _rssService) : throw new ArgumentException("Arg x is invalid!")));*/
|
||||
|
||||
StateHasChanged();
|
||||
Log.Verbose("Guide initialized!");
|
||||
|
|
|
@ -5,6 +5,7 @@
|
|||
<Nullable>enable</Nullable>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<LangVersion>10</LangVersion>
|
||||
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
|
|
Binary file not shown.
Loading…
Reference in New Issue
Block a user