This commit is contained in:
2026-04-24 00:33:50 +03:30
parent 8786470134
commit 5efd41754a
46 changed files with 1104 additions and 4 deletions
@@ -0,0 +1,21 @@
using System;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Metadata.Builders;
using xAiApi.AI.Models.Entities;
namespace xAiApi.AI.Configuration.Entities
{
public class XAiConversationConfiguration : IEntityTypeConfiguration<XAiConversation>
{
public void Configure(EntityTypeBuilder<XAiConversation> builder)
{
//
// Configure Navigations ...
builder
.HasMany(x => x.Messages)
.WithOne(x => x.Conversation)
.HasForeignKey(x => x.ConversationId)
.OnDelete(DeleteBehavior.NoAction);
}
}
}
@@ -0,0 +1,13 @@
using System;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Metadata.Builders;
using xAiApi.AI.Models.Entities;
namespace xAiApi.AI.Configuration.Entities
{
public class XAiMessageConfiguration : IEntityTypeConfiguration<XAiMessage>
{
public void Configure(EntityTypeBuilder<XAiMessage> builder)
{ }
}
}
@@ -0,0 +1,21 @@
using System;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Metadata.Builders;
using xAiApi.AI.Models.Entities;
namespace xAiApi.AI.Configuration.Entities
{
public class XAiProjectConfiguration : IEntityTypeConfiguration<XAiProject>
{
public void Configure(EntityTypeBuilder<XAiProject> builder)
{
//
// Configure Navigations ...
builder
.HasMany(x => x.Conversations)
.WithOne(x => x.Project)
.HasForeignKey(x => x.ProjectId)
.OnDelete(DeleteBehavior.NoAction);
}
}
}
+1
View File
@@ -15,6 +15,7 @@ namespace xAiApi.AI.DI
this IServiceCollection services
)
{
//
services.AddSingleton<IXAIService, XAIService>();
}
@@ -0,0 +1,9 @@
using xAiApi.AI.Interfaces.Entities;
using xAiApi.AI.Models.Entities;
using xDataService.Events;
namespace xAiApi.AI.DataHelper.Events
{
public class XAiConversationEvents : XBaseRepositoryEvents<XAiConversation>, IXAiConversationEvents
{ }
}
+9
View File
@@ -0,0 +1,9 @@
using xAiApi.AI.Interfaces.Entities;
using xAiApi.AI.Models.Entities;
using xDataService.Events;
namespace xAiApi.AI.DataHelper.Events
{
public class XAiMessageEvents : XBaseRepositoryEvents<XAiMessage>, IXAiMessageEvents
{ }
}
+9
View File
@@ -0,0 +1,9 @@
using xAiApi.AI.Interfaces.Entities;
using xAiApi.AI.Models.Entities;
using xDataService.Events;
namespace xAiApi.AI.DataHelper.Events
{
public class XAiProjectEvents : XBaseRepositoryEvents<XAiProject>, IXAiProjectEvents
{ }
}
@@ -0,0 +1,27 @@
using System;
using xAiApi.AI.Interfaces.Entities;
using xAiApi.AI.Models.Entities;
using xDataService.Configuration;
using xDataService.GraphQL;
namespace xAiApi.AI.DataHelper.GraphQL
{
public class XAiConversationGraphQLTypeHelper : XBaseGraphQLTypeHelper<XAiConversation, Guid>, IXAiConversationGraphQLTypeHelper
{
public XAiConversationGraphQLTypeHelper(
XDataServiceConfiguration configuration
) : base(configuration)
{ }
public override string GetInQueryCollectionName()
{
return "aiConversations";
}
public override string GetInQuerySingleName()
{
return "aiConversation";
}
}
}
@@ -0,0 +1,23 @@
using System;
using GraphQL.Types;
using xAiApi.AI.Interfaces.Entities;
using xAiApi.AI.Models.Entities;
using xDataService.Configuration;
using xDataService.GraphQL;
namespace xAiApi.AI.DataHelper.GraphQL
{
public class XAiConversationGraphQuery : XBaseGraphQLQuery<XAiConversation, Guid, XAiConversationGraphType, GuidGraphType>
{
public XAiConversationGraphQuery(
XDataServiceConfiguration configuration,
IXAiConversationRepository repository,
IXAiConversationGraphQLTypeHelper helper
) : base(
configuration,
repository,
helper
)
{ }
}
}
@@ -0,0 +1,13 @@
using System;
using GraphQL.Types;
namespace xAiApi.AI.DataHelper.GraphQL
{
public class XAiConversationGraphSchema : Schema
{
public XAiConversationGraphSchema(IServiceProvider services) : base(services)
{
Query = (XAiConversationGraphQuery)services.GetService(typeof(XAiConversationGraphQuery));
}
}
}
@@ -0,0 +1,17 @@
using System;
using xAiApi.AI.Models.Entities;
using xDataService.GraphQL;
namespace xAiApi.AI.DataHelper.GraphQL
{
public class XAiConversationGraphType : XBaseGraphObjectType<XAiConversation, Guid>
{
public XAiConversationGraphType() : base()
{
Field(x => x.Title);
Field(x => x.Messages);
Field(x => x.CreatedOn);
Field(x => x.UpdatedAt);
}
}
}
@@ -0,0 +1,26 @@
using System;
using xAiApi.AI.Interfaces.Entities;
using xAiApi.AI.Models.Entities;
using xDataService.Configuration;
using xDataService.GraphQL;
namespace xAiApi.AI.DataHelper.GraphQL
{
public class XAiMessageGraphQLTypeHelper : XBaseGraphQLTypeHelper<XAiMessage, Guid>, IXAiMessageGraphQLTypeHelper
{
public XAiMessageGraphQLTypeHelper(
XDataServiceConfiguration configuration
) : base(configuration)
{ }
public override string GetInQueryCollectionName()
{
return "aiMessages";
}
public override string GetInQuerySingleName()
{
return "aiMessage";
}
}
}
@@ -0,0 +1,23 @@
using System;
using GraphQL.Types;
using xAiApi.AI.Interfaces.Entities;
using xAiApi.AI.Models.Entities;
using xDataService.Configuration;
using xDataService.GraphQL;
namespace xAiApi.AI.DataHelper.GraphQL
{
public class XAiMessageGraphQuery : XBaseGraphQLQuery<XAiMessage, Guid, XAiMessageGraphType, GuidGraphType>
{
public XAiMessageGraphQuery(
XDataServiceConfiguration configuration,
IXAiMessageRepository repository,
IXAiMessageGraphQLTypeHelper helper
) : base(
configuration,
repository,
helper
)
{ }
}
}
@@ -0,0 +1,13 @@
using System;
using GraphQL.Types;
namespace xAiApi.AI.DataHelper.GraphQL
{
public class XAiMessageGraphSchema : Schema
{
public XAiMessageGraphSchema(IServiceProvider services) : base(services)
{
Query = (XAiMessageGraphQuery)services.GetService(typeof(XAiMessageGraphQuery));
}
}
}
@@ -0,0 +1,19 @@
using System;
using xAiApi.AI.Models.Entities;
using xDataService.GraphQL;
namespace xAiApi.AI.DataHelper.GraphQL
{
public class XAiMessageGraphType : XBaseGraphObjectType<XAiMessage, Guid>
{
public XAiMessageGraphType() : base()
{
Field(x => x.Role);
Field(x => x.Content);
Field(x => x.Metadata);
Field(x => x.CreatedOn);
Field(x => x.UpdatedAt);
Field(x => x.ConversationId);
}
}
}
@@ -0,0 +1,27 @@
using System;
using xAiApi.AI.Interfaces.Entities;
using xAiApi.AI.Models.Entities;
using xDataService.Configuration;
using xDataService.GraphQL;
namespace xAiApi.AI.DataHelper.GraphQL
{
public class XAiProjectGraphQLTypeHelper : XBaseGraphQLTypeHelper<XAiProject, Guid>, IXAiProjectGraphQLTypeHelper
{
public XAiProjectGraphQLTypeHelper(
XDataServiceConfiguration configuration
) : base(configuration)
{ }
public override string GetInQueryCollectionName()
{
return "aiProjects";
}
public override string GetInQuerySingleName()
{
return "aiProjects";
}
}
}
@@ -0,0 +1,23 @@
using System;
using GraphQL.Types;
using xAiApi.AI.Interfaces.Entities;
using xAiApi.AI.Models.Entities;
using xDataService.Configuration;
using xDataService.GraphQL;
namespace xAiApi.AI.DataHelper.GraphQL
{
public class XAiProjectGraphQuery : XBaseGraphQLQuery<XAiProject, Guid, XAiProjectGraphType, GuidGraphType>
{
public XAiProjectGraphQuery(
XDataServiceConfiguration configuration,
IXAiProjectRepository repository,
IXAiProjectGraphQLTypeHelper helper
) : base(
configuration,
repository,
helper
)
{ }
}
}
@@ -0,0 +1,13 @@
using System;
using GraphQL.Types;
namespace xAiApi.AI.DataHelper.GraphQL
{
public class XAiProjectGraphSchema : Schema
{
public XAiProjectGraphSchema(IServiceProvider services) : base(services)
{
Query = (XAiProjectGraphQuery)services.GetService(typeof(XAiProjectGraphQuery));
}
}
}
@@ -0,0 +1,19 @@
using System;
using xAiApi.AI.Models.Entities;
using xDataService.GraphQL;
namespace xAiApi.AI.DataHelper.GraphQL
{
public class XAiProjectGraphType : XBaseGraphObjectType<XAiProject, Guid>
{
public XAiProjectGraphType() : base()
{
Field(x => x.Title);
Field(x => x.Prompt);
Field(x => x.CreatedOn);
Field(x => x.UpdatedAt);
Field(x => x.Description);
Field(x => x.Conversations);
}
}
}
+162
View File
@@ -0,0 +1,162 @@
using Microsoft.Extensions.AI;
using xAiApi.AI.Constants;
using xCommons.Extensions;
namespace xAiApi.AI.Extensions
{
/// <summary>
/// Extensions for ChatRole ...
/// </summary>
public static class ChatRoleExtensions
{
/// <summary>
/// Normalize an String to Propper Chat Role Value ...
/// <see cref="XAiChatRoles"/>>
/// </summary>
/// <param name="source"></param>
/// <returns></returns>
public static string GetChatRoleTitle(this string source)
{
//
var result = XAiChatRoles.None;
//
if (source.ToNormalString() == XAiChatRoles.None.ToNormalString())
{
result = XAiChatRoles.None;
}
else if (source.ToNormalString() == XAiChatRoles.User.ToNormalString())
{
result = XAiChatRoles.User;
}
else if (source.ToNormalString() == XAiChatRoles.Tool.ToNormalString())
{
result = XAiChatRoles.Tool;
}
else if (source.ToNormalString() == XAiChatRoles.System.ToNormalString())
{
result = XAiChatRoles.System;
}
else if (source.ToNormalString() == XAiChatRoles.Assistant.ToNormalString())
{
result = XAiChatRoles.Assistant;
}
//
return result;
}
/// <summary>
/// Get Chat Role Title from Chat Role Class ...
/// <see cref="XAiChatRoles"/>
/// </summary>
/// <param name="source"></param>
/// <returns></returns>
public static string GetRole(this ChatRole source)
{
//
var result = source.Value
.GetChatRoleTitle();
//
return result;
}
/// <summary>
/// Generate Chat Role Class Based on role Title ...
/// </summary>
/// <param name="source"></param>
/// <returns></returns>
public static ChatRole ToChatRole(this string source)
{
//
var role = source.GetChatRoleTitle();
ChatRole result = new ChatRole(role);
//
return result;
}
/// <summary>
/// Extract Chat Role Enum from Chat Role ...
/// <see cref="ChatRole"/>
/// <see cref="XAiChatRole"/>
/// </summary>
/// <param name="source"></param>
/// <returns></returns>
public static XAiChatRole ToChatRole(this ChatRole source)
{
//
var role = source
.GetRole()
.GetChatRoleTitle();
//
XAiChatRole result = XAiChatRole.User;
//
if (role == XAiChatRoles.User)
{
result = XAiChatRole.User;
}
else if (role == XAiChatRoles.Tool)
{
result = XAiChatRole.Tool;
}
else if (role == XAiChatRoles.System)
{
result = XAiChatRole.System;
}
else if (role == XAiChatRoles.Assistant)
{
result = XAiChatRole.Assistant;
}
//
return result;
}
/// <summary>
/// Validate an String as Chat Role ...
/// </summary>
/// <param name="source"></param>
/// <returns></returns>
public static bool IsValid(this string source)
{
//
var result =
source != XAiChatRoles.None &&
source.ToNormalString() != XAiChatRoles.None.ToNormalString();
//
return result;
}
/// <summary>
/// Validate Role ...
/// <see cref="XAiChatRole"/>>
/// </summary>
/// <param name="source"></param>
/// <returns></returns>
public static bool IsValid(this XAiChatRole source)
{
//
var result = source != XAiChatRole.None;
return result;
}
/// <summary>
/// Validate Role ...
/// <see cref="ChatRole"/>>
/// </summary>
/// <param name="source"></param>
/// <returns></returns>
public static bool IsValid(this ChatRole source)
{
//
var role = source.ToChatRole();
var result = role.IsValid();
return result;
}
}
}
+13
View File
@@ -0,0 +1,13 @@
using System;
using Microsoft.Extensions.Logging;
using xAiApi.AI.Models.Entities;
using xPushService.Base;
namespace xAiApi.AI.Hubs
{
public class XAiConversationEntityHub : XBaseEntityHub<XAiConversation, Guid>
{
public XAiConversationEntityHub(ILogger<XBaseHub> logger) : base(logger)
{ }
}
}
+13
View File
@@ -0,0 +1,13 @@
using System;
using Microsoft.Extensions.Logging;
using xAiApi.AI.Models.Entities;
using xPushService.Base;
namespace xAiApi.AI.Hubs
{
public class XAiMessageEntityHub : XBaseEntityHub<XAiMessage, Guid>
{
public XAiMessageEntityHub(ILogger<XBaseHub> logger) : base(logger)
{ }
}
}
+13
View File
@@ -0,0 +1,13 @@
using System;
using Microsoft.Extensions.Logging;
using xAiApi.AI.Models.Entities;
using xPushService.Base;
namespace xAiApi.AI.Hubs
{
public class XAiProjectEntityHub : XBaseEntityHub<XAiProject, Guid>
{
public XAiProjectEntityHub(ILogger<XBaseHub> logger) : base(logger)
{ }
}
}
@@ -0,0 +1,8 @@
using xAiApi.AI.Models.Entities;
using xDataService.Interfaces;
namespace xAiApi.AI.Interfaces.Entities
{
public interface IXAiConversationEvents : IXBaseRepositoryEvents<XAiConversation>
{ }
}
@@ -0,0 +1,9 @@
using System;
using xAiApi.AI.Models.Entities;
using xDataService.Interfaces;
namespace xAiApi.AI.Interfaces.Entities
{
public interface IXAiConversationGraphQLTypeHelper : IXBaseGraphQLTypeHelper<XAiConversation, Guid>
{ }
}
@@ -0,0 +1,9 @@
using System;
using xAiApi.AI.Models.Entities;
using xDataService.Interfaces;
namespace xAiApi.AI.Interfaces.Entities
{
public interface IXAiConversationRepository : IXBaseRepository<XAiConversation, Guid>
{ }
}
@@ -0,0 +1,8 @@
using xAiApi.AI.Models.Entities;
using xDataService.Interfaces;
namespace xAiApi.AI.Interfaces.Entities
{
public interface IXAiMessageEvents : IXBaseRepositoryEvents<XAiMessage>
{ }
}
@@ -0,0 +1,9 @@
using System;
using xAiApi.AI.Models.Entities;
using xDataService.Interfaces;
namespace xAiApi.AI.Interfaces.Entities
{
public interface IXAiMessageGraphQLTypeHelper : IXBaseGraphQLTypeHelper<XAiMessage, Guid>
{ }
}
@@ -0,0 +1,9 @@
using System;
using xAiApi.AI.Models.Entities;
using xDataService.Interfaces;
namespace xAiApi.AI.Interfaces.Entities
{
public interface IXAiMessageRepository : IXBaseRepository<XAiMessage, Guid>
{ }
}
@@ -0,0 +1,8 @@
using xAiApi.AI.Models.Entities;
using xDataService.Interfaces;
namespace xAiApi.AI.Interfaces.Entities
{
public interface IXAiProjectEvents : IXBaseRepositoryEvents<XAiProject>
{ }
}
@@ -0,0 +1,9 @@
using System;
using xAiApi.AI.Models.Entities;
using xDataService.Interfaces;
namespace xAiApi.AI.Interfaces.Entities
{
public interface IXAiProjectGraphQLTypeHelper : IXBaseGraphQLTypeHelper<XAiProject, Guid>
{ }
}
@@ -0,0 +1,9 @@
using System;
using xAiApi.AI.Models.Entities;
using xDataService.Interfaces;
namespace xAiApi.AI.Interfaces.Entities
{
public interface IXAiProjectRepository : IXBaseRepository<XAiProject, Guid>
{ }
}
+10
View File
@@ -0,0 +1,10 @@
namespace xAiApi.AI.Interfaces
{
/// <summary>
/// Provide Ai Capabilities Using AI Service ...
/// </summary>
public interface IXAiProvider
{
}
}
+42
View File
@@ -0,0 +1,42 @@
using System;
using System.Collections.Generic;
using xModels.Base;
namespace xAiApi.AI.Models.Entities
{
/// <summary>
/// Conversation Describe ...
/// </summary>
public class XAiConversation : XBaseGuidIDEntity
{
/// <summary>
/// Title of Conversation ...
/// </summary>
public string Title { get; set; }
/// <summary>
/// Created Time ...
/// </summary>
public DateTime CreatedOn { get; set; }
/// <summary>
/// Updated Time ...
/// </summary>
public DateTime UpdatedAt { get; set; }
/// <summary>
/// Messages of Conversation ...
/// </summary>
public IEnumerable<XAiMessage> Messages { get; set; }
/// <summary>
/// Project ID ...
/// </summary>
public Guid ProjectId { get; set; }
/// <summary>
/// Project ...
/// </summary>
public XAiProject Project { get; set; }
}
}
+71 -4
View File
@@ -1,12 +1,79 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using System.ComponentModel.DataAnnotations.Schema;
using xModels.Base;
using xCommons.Extensions;
using xAiModels.Constants;
namespace xAiApi.AI.Models.Entities
{
public class XAiMessage
/// <summary>
/// Message Model of Ai ...
/// </summary>
public class XAiMessage : XBaseGuidIDEntity
{
/// <summary>
/// Message of Chat ...
/// </summary>
public string Content { get; set; }
/// <summary>
/// Role of Message ...
/// </summary>
public XAiChatRole Role { get; set; }
/// <summary>
/// Created Time ...
/// </summary>
public DateTime CreatedOn { get; set; }
/// <summary>
/// Updated Time ...
/// </summary>
public DateTime UpdatedAt { get; set; }
/// <summary>
/// Conversation Id ...
/// </summary>
public Guid ConversationId { get; set; }
/// <summary>
/// Conversation ...
/// </summary>
public XAiConversation Conversation { get; set; }
//
#region Meta Data Property ...
private string _metadata;
/// <summary>
/// Meta Data of Message ...
/// </summary>
[NotMapped]
public IDictionary<string, object> Metadata { get; private set; } = null;
/// <summary>
/// Meta Data of MEssage in Json ...
/// </summary>
public string MeatDatas
{
//
get => _metadata;
//
set
{
//
// Converts Json String to Dictionary ...
if (!value.IsNullOrEmpty())
{
Metadata = value.FromJSON<IDictionary<string, object>>();
}
//
_metadata = value;
}
}
#endregion
}
}
+39
View File
@@ -0,0 +1,39 @@
using System;
using System.Collections.Generic;
using xModels.Base;
namespace xAiApi.AI.Models.Entities
{
public class XAiProject : XBaseGuidIDEntity
{
/// <summary>
/// Title of Project ...
/// </summary>
public string Title { get; set; }
/// <summary>
/// Description of Project ...
/// </summary>
public string Description { get; set; }
/// <summary>
/// a Prompt for Project Start ...
/// </summary>
public string Prompt { get; set; }
/// <summary>
/// Created Time ...
/// </summary>
public DateTime CreatedOn { get; set; }
/// <summary>
/// Updated Time ...
/// </summary>
public DateTime UpdatedAt { get; set; }
/// <summary>
/// Conversations ...
/// </summary>
public IEnumerable<XAiConversation> Conversations { get; set; }
}
}