add create user, create/update agent

This commit is contained in:
Jicheng Lu 2023-09-02 00:10:46 -05:00
parent 4e3708e525
commit f5819919fc
32 changed files with 413 additions and 150 deletions

View file

@ -15,7 +15,7 @@ public interface IAgentHook
bool OnInstructionLoaded(string template, Dictionary<string, object> dict);
bool OnFunctionsLoaded(ref string functions);
bool OnFunctionsLoaded(ref List<string> functions);
bool OnSamplesLoaded(ref string samples);

View file

@ -6,6 +6,6 @@ public interface IAgentRouting
{
string AgentId { get; }
Task<Agent> LoadRouter();
RoutingRecord[] GetRoutingRecords();
RoutingRecord GetRecordByName(string name);
RoutingItem[] GetRoutingRecords();
RoutingItem GetRecordByName(string name);
}

View file

@ -21,18 +21,36 @@ public class Agent
/// <summary>
/// Functions
/// </summary>
public string Functions { get; set; }
public List<string> Functions { get; set; }
/// <summary>
/// Responses
/// </summary>
public List<string> Responses { get; set; }
/// <summary>
/// Domain knowledges
/// </summary>
public string Knowledges { get; set; }
/// <summary>
/// Routes
/// </summary>
public List<string> Routes { get; set; }
public override string ToString()
=> $"{Name} {Id}";
public Agent SetInstruction(string instruction)
{
Instruction = instruction;
return this;
}
public Agent SetFunctions(List<string> functions)
{
Functions = functions;
return this;
}
public Agent SetResponses(List<string> responses)
{
Responses = responses;
return this;
}
}

View file

@ -11,4 +11,8 @@ public interface IBotSharpRepository
IQueryable<ConversationRecord> Conversation { get; }
int Transaction<TTableInterface>(Action action);
void Add<TTableInterface>(object entity);
UserRecord GetUserByEmail(string email);
void CreateUser(UserRecord user);
void UpdateAgent(AgentRecord agent);
}

View file

@ -11,9 +11,9 @@ public class AgentRecord : RecordBase
public string Instruction { get; set; }
public string Functions { get; set; }
public List<string> Functions { get; set; }
public List<string> Routes { get; set; }
public List<string> Responses { get; set; }
[Required]
public DateTime CreatedTime { get; set; }
@ -30,7 +30,6 @@ public class AgentRecord : RecordBase
Description = agent.Description,
Instruction = agent.Instruction,
Functions = agent.Functions,
Routes = agent.Routes,
};
}
@ -43,9 +42,33 @@ public class AgentRecord : RecordBase
Description = Description,
Instruction = Instruction,
Functions = Functions,
Routes = Routes,
CreatedDateTime = CreatedTime,
UpdatedDateTime = UpdatedTime
};
}
public AgentRecord SetId(string id)
{
Id = id;
return this;
}
public AgentRecord SetInstruction(string instruction)
{
Instruction = instruction;
return this;
}
public AgentRecord SetFunctions(List<string> functions)
{
Functions = functions;
return this;
}
public AgentRecord SetResponses(List<string> responses)
{
Responses = responses;
return this;
}
}

View file

@ -0,0 +1,11 @@
namespace BotSharp.Abstraction.Repositories.Records;
public class RoutingItemRecord : RecordBase
{
public string AgentId { get; set; }
public string Name { get; set; }
public string Description { get; set; }
public List<string> RequiredFields { get; set; } = new List<string>();
public string RedirectTo { get; set; }
public bool Disabled { get; set; }
}

View file

@ -0,0 +1,7 @@
namespace BotSharp.Abstraction.Repositories.Records;
public class RoutingProfileRecord : RecordBase
{
public string Name { get; set; }
public List<string> AgentIds { get; set; }
}

View file

@ -25,7 +25,7 @@ public class UserRecord : RecordBase
public string Password { get; set; } = string.Empty;
[MaxLength(36)]
public string? ExternalId { get; set; }
public string ExternalId { get; set; }
[Required]
public DateTime UpdatedTime { get; set; } = DateTime.UtcNow;

View file

@ -2,7 +2,7 @@ using System.Text.Json.Serialization;
namespace BotSharp.Abstraction.Routing.Models;
public class RoutingRecord
public class RoutingItem
{
[JsonPropertyName("agent_id")]
public string AgentId { get; set; }

View file

@ -2,7 +2,7 @@ using System.Text.Json.Serialization;
namespace BotSharp.Abstraction.Routing.Models;
public class RoutingProfileRecord
public class RoutingProfile
{
[JsonPropertyName("name")]
public string Name { get; set; }

View file

@ -31,7 +31,7 @@ public abstract class AgentHookBase : IAgentHook
return true;
}
public virtual bool OnFunctionsLoaded(ref string functions)
public virtual bool OnFunctionsLoaded(ref List<string> functions)
{
_agent.Functions = functions;
return true;

View file

@ -1,7 +1,13 @@
using BotSharp.Abstraction.Agents.Models;
using BotSharp.Abstraction.Agents.Settings;
using BotSharp.Abstraction.Functions.Models;
using BotSharp.Abstraction.Repositories;
using BotSharp.Abstraction.Repositories.Records;
using BotSharp.Abstraction.Users.Models;
using MongoDB.Bson;
using System.IO;
using Tensorflow;
using static Tensorflow.TensorShapeProto.Types;
namespace BotSharp.Core.Agents.Services;
@ -14,7 +20,7 @@ public partial class AgentService
var record = (from a in db.Agent
join ua in db.UserAgent on a.Id equals ua.AgentId
join u in db.User on ua.UserId equals u.Id
where (ua.UserId == _user.Id || u.ExternalId == _user.Id) && a.Name == agent.Name
where u.ExternalId == _user.Id && a.Name == agent.Name
select a).FirstOrDefault();
if (record != null)
@ -23,15 +29,29 @@ public partial class AgentService
}
record = AgentRecord.FromAgent(agent);
record.Id = ObjectId.GenerateNewId().ToString();
record.Id = Guid.NewGuid().ToString();
record.CreatedTime = DateTime.UtcNow;
record.UpdatedTime = DateTime.UtcNow;
var dbSettings = _services.GetRequiredService<BotSharpDatabaseSettings>();
var agentSettings = _services.GetRequiredService<AgentSettings>();
var filePath = Path.Combine(dbSettings.FileRepository, agentSettings.DataDir);
var foundAgent = FetchAgentInfoFromFile(agent.Name, filePath);
if (foundAgent != null)
{
record.SetId(foundAgent.Id)
.SetInstruction(foundAgent.Instruction)
.SetFunctions(foundAgent.Functions)
.SetResponses(foundAgent.Responses);
}
var user = db.User.FirstOrDefault(x => x.ExternalId == _user.Id);
var userAgentRecord = new UserAgentRecord
{
UserId = user?.Id ?? ObjectId.GenerateNewId().ToString(),
AgentId = record.Id,
Id = Guid.NewGuid().ToString(),
UserId = user.Id,
AgentId = foundAgent?.Id ?? record.Id,
CreatedTime = DateTime.UtcNow,
UpdatedTime = DateTime.UtcNow
};
@ -44,4 +64,62 @@ public partial class AgentService
return record.ToAgent();
}
private JsonSerializerOptions _options = new JsonSerializerOptions
{
PropertyNameCaseInsensitive = true,
PropertyNamingPolicy = JsonNamingPolicy.CamelCase,
WriteIndented = true
};
private Agent FetchAgentInfoFromFile(string agentName, string filePath)
{
foreach (var dir in Directory.GetDirectories(filePath))
{
var agentJson = File.ReadAllText(Path.Combine(dir, "agent.json"));
var agent = JsonSerializer.Deserialize<Agent>(agentJson, _options);
if (agent != null && agent.Name == agentName)
{
var functions = FetchFunctionsFromFile(dir);
var instruction = FetchInstructionFromFile(dir);
var responses = FetchResponsesFromFile(dir);
return agent.SetInstruction(instruction).SetFunctions(functions).SetResponses(responses);
}
}
return null;
}
private string FetchInstructionFromFile(string fileDir)
{
var file = Path.Combine(fileDir, "instruction.liquid");
if (!File.Exists(file)) return null;
var instruction = File.ReadAllText(file);
return instruction;
}
private List<string> FetchFunctionsFromFile(string fileDir)
{
var file = Path.Combine(fileDir, "functions.json");
if (!File.Exists(file)) return new List<string>();
var functionsJson = File.ReadAllText(file);
var functionDefs = JsonSerializer.Deserialize<List<Abstraction.Functions.Models.FunctionDef>>(functionsJson, _options);
var functions = functionDefs.Select(x => JsonSerializer.Serialize(x, _options)).ToList();
return functions;
}
private List<string> FetchResponsesFromFile(string fileDir)
{
var responses = new List<string>();
var responseDir = Path.Combine(fileDir, "responses");
if (!Directory.Exists(responseDir)) return responses;
foreach (var file in Directory.GetFiles(responseDir))
{
responses.Add(File.ReadAllText(file));
}
return responses;
}
}

View file

@ -30,7 +30,7 @@ public partial class AgentService
hook.OnInstructionLoaded(agent.Instruction, templateDict);
}
if (!string.IsNullOrEmpty(agent.Functions))
if (agent.Functions != null && agent.Functions.Any())
{
var functions = agent.Functions;
hook.OnFunctionsLoaded(ref functions);

View file

@ -10,41 +10,30 @@ public partial class AgentService
{
var db = _services.GetRequiredService<IBotSharpRepository>();
db.Transaction<IBotSharpTable>(delegate
{
var record = (from a in db.Agent
join ua in db.UserAgent on a.Id equals ua.AgentId
join u in db.User on ua.UserId equals u.Id
where (ua.UserId == _user.Id || u.ExternalId == _user.Id) &&
a.Id == agent.Id
select a).FirstOrDefault();
var record = (from a in db.Agent
join ua in db.UserAgent on a.Id equals ua.AgentId
join u in db.User on ua.UserId equals u.Id
where (ua.UserId == _user.Id || u.ExternalId == _user.Id) &&
a.Id == agent.Id
select a).FirstOrDefault();
if (record == null) return;
if (record == null) return;
record.Name = agent.Name;
record.Name = agent.Name;
if (!string.IsNullOrEmpty(agent.Description))
record.Description = agent.Description;
if (!string.IsNullOrEmpty(agent.Description))
record.Description = agent.Description;
if (!string.IsNullOrEmpty(agent.Instruction))
record.Instruction = agent.Instruction;
if (!string.IsNullOrEmpty(agent.Instruction))
record.Instruction = agent.Instruction;
if (!string.IsNullOrEmpty(agent.Functions))
record.Functions = agent.Functions;
if (agent.Functions != null && agent.Functions.Any())
record.Functions = agent.Functions;
if (!agent.Routes.IsEmpty())
record.Routes = agent.Routes;
if (agent.Responses != null && agent.Responses.Any())
record.Responses = agent.Responses;
record.UpdatedTime = DateTime.UtcNow;
db.Add<IBotSharpTable>(record);
});
// Save instruction to file
//var dir = GetAgentDataDir(agent.Id);
//var instructionFile = Path.Combine(dir, "instruction.txt");
//File.WriteAllText(instructionFile, agent.Instruction);
//var samplesFile = Path.Combine(dir, "samples.txt");
//File.WriteAllText(samplesFile, agent.Samples);
db.UpdateAgent(record);
await Task.CompletedTask;
}
}

View file

@ -92,25 +92,27 @@ public class ConversationStateService : IConversationStateService, IDisposable
public void Save()
{
var states = new StringBuilder();
var conversation = _db.Conversation.FirstOrDefault(x => x.Id == _conversationId);
//var states = new StringBuilder();
//var conversation = _db.Conversation.FirstOrDefault(x => x.Id == _conversationId);
var states = new List<string>();
foreach (var dic in _state)
{
//states.Add($"{dic.Key}={dic.Value}");
states.AppendLine($"{dic.Key}={dic.Value}");
states.Add($"{dic.Key}={dic.Value}");
//states.AppendLine($"{dic.Key}={dic.Value}");
}
//File.WriteAllLines(_file, states);
File.WriteAllLines(_file, states);
_logger.LogInformation($"Saved state {_conversationId}");
if (conversation != null)
{
conversation.State = states.ToString();
_db.Transaction<IBotSharpTable>(delegate
{
_db.Add<IBotSharpTable>(conversation);
});
}
//if (conversation != null)
//{
// conversation.State = states.ToString();
// _db.Transaction<IBotSharpTable>(delegate
// {
// _db.Add<IBotSharpTable>(conversation);
// });
//}
}
public void CleanState()
@ -134,7 +136,13 @@ public class ConversationStateService : IConversationStateService, IDisposable
{
Directory.CreateDirectory(dir);
}
return Path.Combine(dir, "state.dict");
var stateFile = Path.Combine(dir, "state.dict");
if (!File.Exists(stateFile))
{
File.WriteAllText(stateFile, "");
}
return stateFile;
}
private string GetConversationState(string conversationId)

View file

@ -29,10 +29,13 @@ public class ConversationStorage : IConversationStorage
public void Append(string conversationId, string agentId, RoleDialogModel dialog)
{
var dialogs = GetConversationDialogs(conversationId);
var sb = new StringBuilder(dialogs);
//var dialogs = GetConversationDialogs(conversationId);
//var sb = new StringBuilder(dialogs);
var db = _services.GetRequiredService<IBotSharpRepository>();
var conversationFile = GetStorageFile(conversationId);
var sb = new StringBuilder();
if (dialog.Role == AgentRole.Function)
{
var args = dialog.FunctionArgs.Replace("\r", " ").Replace("\n", " ").Trim();
@ -60,15 +63,15 @@ public class ConversationStorage : IConversationStorage
}
var updatedDialogs = sb.ToString();
//File.AppendAllText(conversationFile, conversation);
File.AppendAllText(conversationFile, updatedDialogs);
var conversation = db.Conversation.FirstOrDefault(x => x.Id == conversationId);
conversation.AgentId = agentId;
conversation.Dialog = updatedDialogs;
db.Transaction<IBotSharpTable>(delegate
{
db.Add<IBotSharpTable>(conversation);
});
//var conversation = db.Conversation.FirstOrDefault(x => x.Id == conversationId);
//conversation.AgentId = agentId;
//conversation.Dialog = updatedDialogs;
//db.Transaction<IBotSharpTable>(delegate
//{
// db.Add<IBotSharpTable>(conversation);
//});
}
public List<RoleDialogModel> GetDialogs(string conversationId)

View file

@ -11,6 +11,21 @@ public class BotSharpDbContext : Database, IBotSharpRepository
public IQueryable<UserAgentRecord> UserAgent => Table<UserAgentRecord>();
public IQueryable<ConversationRecord> Conversation => Table<ConversationRecord>();
public void UpdateAgent(AgentRecord agent)
{
throw new NotImplementedException();
}
public void CreateUser(UserRecord user)
{
throw new NotImplementedException();
}
public UserRecord GetUserByEmail(string email)
{
throw new NotImplementedException();
}
public int Transaction<TTableInterface>(Action action)
{
DatabaseFacade database = base.GetMaster(typeof(TTableInterface)).Database;

View file

@ -1,8 +1,8 @@
using BotSharp.Abstraction.Functions.Models;
using BotSharp.Abstraction.Repositories;
using BotSharp.Abstraction.Repositories.Records;
using System.IO;
using System.Text.Json;
namespace BotSharp.Core.Repository;
public class FileRepository : IBotSharpRepository
@ -220,4 +220,60 @@ public class FileRepository : IBotSharpRepository
return _changedTableNames.Count;
}
public UserRecord GetUserByEmail(string email)
{
return User.FirstOrDefault(x => x.Email == email);
}
public void CreateUser(UserRecord user)
{
var userId = Guid.NewGuid().ToString();
var dir = Path.Combine(_dbSettings.FileRepository, "users", userId);
if (!Directory.Exists(dir))
{
Directory.CreateDirectory(dir);
}
var path = Path.Combine(dir, "user.json");
File.WriteAllText(path, JsonSerializer.Serialize(user, _options));
}
public void UpdateAgent(AgentRecord agent)
{
if (agent == null) return;
var dir = GetAgentDataDir(agent.Id);
if (!string.IsNullOrEmpty(agent.Instruction))
{
var instructionFile = Path.Combine(dir, "instruction.liquid");
File.WriteAllText(instructionFile, agent.Instruction);
}
if (agent.Functions != null || agent.Functions.Any())
{
var functionFile = Path.Combine(dir, "functions.json");
var functions = new List<string>();
foreach (var function in agent.Functions)
{
var functionDef = JsonSerializer.Deserialize<FunctionDef>(function, _options);
functions.Add(JsonSerializer.Serialize(functionDef, _options));
}
var functionText = JsonSerializer.Serialize(functions, _options);
File.WriteAllText(functionFile, functionText);
}
}
private string GetAgentDataDir(string agentId)
{
var dbSettings = _services.GetRequiredService<BotSharpDatabaseSettings>();
var agentSettings = _services.GetRequiredService<AgentSettings>();
var dir = Path.Combine(dbSettings.FileRepository, agentSettings.DataDir, agentId);
if (!Directory.Exists(dir))
{
Directory.CreateDirectory(dir);
}
return dir;
}
}

View file

@ -29,12 +29,12 @@ public class Router : IAgentRouting
return await agentService.LoadAgent(AgentId);
}
public RoutingRecord[] GetRoutingRecords()
public RoutingItem[] GetRoutingRecords()
{
var agentSettings = _services.GetRequiredService<AgentSettings>();
var dbSettings = _services.GetRequiredService<BotSharpDatabaseSettings>();
var filePath = Path.Combine(dbSettings.FileRepository, agentSettings.DataDir, _settings.RouterId, "route.json");
var records = JsonSerializer.Deserialize<RoutingRecord[]>(File.ReadAllText(filePath));
var filePath = Path.Combine(dbSettings.FileRepository, agentSettings.DataDir, "route.json");
var records = JsonSerializer.Deserialize<RoutingItem[]>(File.ReadAllText(filePath));
// check if routing profile is specified
filePath = Path.Combine(dbSettings.FileRepository, agentSettings.DataDir, "routing-profile.json");
@ -42,7 +42,7 @@ public class Router : IAgentRouting
{
var state = _services.GetRequiredService<IConversationStateService>();
var name = state.GetState("channel");
var profiles = JsonSerializer.Deserialize<RoutingProfileRecord[]>(File.ReadAllText(filePath));
var profiles = JsonSerializer.Deserialize<RoutingProfile[]>(File.ReadAllText(filePath));
var spcificedProfile = profiles.FirstOrDefault(x => x.Name == name);
if (spcificedProfile != null)
{
@ -53,7 +53,7 @@ public class Router : IAgentRouting
return records;
}
public RoutingRecord GetRecordByName(string name)
public RoutingItem GetRecordByName(string name)
{
return GetRoutingRecords().First(x => x.Name.ToLower() == name.ToLower());
}

View file

@ -17,7 +17,7 @@ public class TemplateRender : ITemplateRender
_logger = logger;
_options = new TemplateOptions();
_options.MemberAccessStrategy.MemberNameStrategy = MemberNameStrategies.SnakeCase;
_options.MemberAccessStrategy.Register<RoutingRecord>();
_options.MemberAccessStrategy.Register<RoutingItem>();
}
public string Render(string template, Dictionary<string, object> dict)

View file

@ -22,7 +22,7 @@ public class UserService : IUserService
public async Task<User> CreateUser(User user)
{
var db = _services.GetRequiredService<IBotSharpRepository>();
var record = db.User.FirstOrDefault(x => x.Email == user.Email.ToLower());
var record = db.GetUserByEmail(user.Email);
if (record != null)
{
return record.ToUser();
@ -34,11 +34,7 @@ public class UserService : IUserService
record.Password = Utilities.HashText(user.Password, record.Salt);
record.ExternalId = _user.Id;
db.Transaction<IBotSharpTable>(delegate
{
db.Add<IBotSharpTable>(record);
});
db.CreateUser(record);
return record.ToUser();
}

View file

@ -7,8 +7,7 @@ public class AgentCreationModel
public string Name { get; set; }
public string Description { get; set; }
public string Instruction { get; set; }
public string Functions { get; set; }
public List<string> Routes { get; set; }
public List<string> Functions { get; set; }
public Agent ToAgent()
{
@ -18,7 +17,6 @@ public class AgentCreationModel
Description = Description,
Instruction = Instruction,
Functions = Functions,
Routes = Routes
};
}
}

View file

@ -20,12 +20,12 @@ public class AgentUpdateModel
/// <summary>
/// Functions
/// </summary>
public string? Functions { get; set; }
public List<string> Functions { get; set; }
/// <summary>
/// Routes
/// </summary>
public List<string>? Routes { get; set; }
public List<string> Responses { get; set; }
public Agent ToAgent()
{
@ -43,11 +43,11 @@ public class AgentUpdateModel
if (Samples != null)
agent.Samples = Samples;
if (Functions != null)
if (Functions != null && Functions.Any())
agent.Functions = Functions;
if (!Routes.IsEmpty())
agent.Routes = Routes;
if (Responses != null && Responses.Any())
agent.Responses = Responses;
return agent;
}

View file

@ -8,8 +8,8 @@ public class AgentViewModel
public string Name { get; set; }
public string Description { get; set; }
public string Instruction { get; set; }
public string Functions { get; set; }
public List<string> Routes { get; set; }
public List<string> Functions { get; set; }
public List<string> Responses { get; set; }
public DateTime UpdatedDateTime { get; set; }
public static AgentViewModel FromAgent(Agent agent)
@ -21,7 +21,7 @@ public class AgentViewModel
Description = agent.Description,
Instruction = agent.Instruction,
Functions = agent.Functions,
Routes = agent.Routes,
Responses = agent.Responses,
UpdatedDateTime = agent.UpdatedDateTime
};
}

View file

@ -69,17 +69,13 @@ public class ChatCompletionProvider : IChatCompletion
return samples;
}
public List<FunctionDef> GetFunctions(string functionsJson)
public List<FunctionDef> GetFunctions(List<string> functionsJson)
{
var functions = new List<FunctionDef>();
if (!string.IsNullOrEmpty(functionsJson))
var functions = functionsJson?.Select(x => JsonSerializer.Deserialize<FunctionDef>(x, new JsonSerializerOptions
{
functions = JsonSerializer.Deserialize<List<FunctionDef>>(functionsJson, new JsonSerializerOptions
{
PropertyNameCaseInsensitive = true,
AllowTrailingCommas = true
});
}
PropertyNameCaseInsensitive = true,
AllowTrailingCommas = true
}))?.ToList() ?? new List<FunctionDef>();
return functions;
}

View file

@ -69,17 +69,13 @@ public class GPT4CompletionProvider : IChatCompletion
return samples;
}
public List<FunctionDef> GetFunctions(string functionsJson)
public List<FunctionDef> GetFunctions(List<string> functionsJson)
{
var functions = new List<FunctionDef>();
if (!string.IsNullOrEmpty(functionsJson))
var functions = functionsJson?.Select(x => JsonSerializer.Deserialize<FunctionDef>(x, new JsonSerializerOptions
{
functions = JsonSerializer.Deserialize<List<FunctionDef>>(functionsJson, new JsonSerializerOptions
{
PropertyNameCaseInsensitive = true,
AllowTrailingCommas = true
});
}
PropertyNameCaseInsensitive = true,
AllowTrailingCommas = true
}))?.ToList() ?? new List<FunctionDef>();
return functions;
}

View file

@ -4,9 +4,9 @@ public class AgentCollection : MongoBase
{
public string Name { get; set; }
public string Description { get; set; }
public string Functions { get; set; }
public string Instruction { get; set; }
public List<string> Routes { get; set; }
public List<string> Functions { get; set; }
public List<string> Responses { get; set; }
public DateTime CreatedTime { get; set; }
public DateTime UpdatedTime { get; set; }

View file

@ -2,8 +2,8 @@ namespace BotSharp.Plugin.MongoStorage.Collections;
public class ConversationCollection : MongoBase
{
public string AgentId { get; set; }
public string UserId { get; set; }
public Guid AgentId { get; set; }
public Guid UserId { get; set; }
public string Title { get; set; }
public string Dialog { get; set; }
public string State { get; set; }

View file

@ -2,8 +2,8 @@ namespace BotSharp.Plugin.MongoStorage.Collections;
public class UserAgentCollection : MongoBase
{
public string UserId { get; set; }
public string AgentId { get; set; }
public Guid UserId { get; set; }
public Guid AgentId { get; set; }
public DateTime CreatedTime { get; set; }
public DateTime UpdatedTime { get; set; }

View file

@ -6,6 +6,6 @@ namespace BotSharp.Plugin.MongoStorage;
[BsonIgnoreExtraElements(Inherited = true)]
public class MongoBase
{
[BsonId(IdGenerator = typeof(StringObjectIdGenerator))]
public string Id { get; set; }
[BsonId(IdGenerator = typeof(GuidGenerator))]
public Guid Id { get; set; }
}

View file

@ -6,12 +6,12 @@ public class MongoStoragePlugin : IBotSharpPlugin
{
public void RegisterDI(IServiceCollection services, IConfiguration config)
{
//services.AddScoped((IServiceProvider x) =>
//{
// var dbSettings = x.GetRequiredService<BotSharpDatabaseSettings>();
// return new MongoDbContext(dbSettings.MongoDb);
//});
services.AddScoped((IServiceProvider x) =>
{
var dbSettings = x.GetRequiredService<BotSharpDatabaseSettings>();
return new MongoDbContext(dbSettings.MongoDb);
});
//services.AddScoped<IBotSharpRepository, MongoRepository>();
services.AddScoped<IBotSharpRepository, MongoRepository>();
}
}

View file

@ -32,12 +32,12 @@ public class MongoRepository : IBotSharpRepository
var agentDocs = _dc.Agents?.AsQueryable()?.ToList() ?? new List<AgentCollection>();
_agents = agentDocs.Select(x => new AgentRecord
{
Id = x.Id?.ToString(),
Id = x.Id.ToString(),
Name = x.Name,
Description = x.Description,
Instruction = x.Instruction,
Functions = x.Functions,
Routes = x.Routes,
Responses = x.Responses,
CreatedTime = x.CreatedTime,
UpdatedTime = x.UpdatedTime
}).ToList();
@ -59,7 +59,7 @@ public class MongoRepository : IBotSharpRepository
var userDocs = _dc.Users?.AsQueryable()?.ToList() ?? new List<UserCollection>();
_users = userDocs.Select(x => new UserRecord
{
Id = x.Id?.ToString(),
Id = x.Id.ToString(),
FirstName = x.FirstName,
LastName = x.LastName,
Email = x.Email,
@ -87,9 +87,9 @@ public class MongoRepository : IBotSharpRepository
var userDocs = _dc.UserAgents?.AsQueryable()?.ToList() ?? new List<UserAgentCollection>();
_userAgents = userDocs.Select(x => new UserAgentRecord
{
Id = x.Id?.ToString(),
AgentId = x.AgentId,
UserId = x.UserId,
Id = x.Id.ToString(),
AgentId = x.AgentId.ToString(),
UserId = x.UserId.ToString(),
CreatedTime = x.CreatedTime,
UpdatedTime = x.UpdatedTime
}).ToList();
@ -111,9 +111,9 @@ public class MongoRepository : IBotSharpRepository
var conversationDocs = _dc.Conversations?.AsQueryable()?.ToList() ?? new List<ConversationCollection>();
_conversations = conversationDocs.Select(x => new ConversationRecord
{
Id = x.Id?.ToString(),
AgentId = x.AgentId,
UserId = x.UserId,
Id = x.Id.ToString(),
AgentId = x.AgentId.ToString(),
UserId = x.UserId.ToString(),
Title = x.Title,
Dialog = x.Dialog,
State = x.State,
@ -161,9 +161,9 @@ public class MongoRepository : IBotSharpRepository
{
var conversations = _conversations.Select(x => new ConversationCollection
{
Id = x.Id.IfNullOrEmptyAs(ObjectId.GenerateNewId().ToString()),
AgentId = x.AgentId,
UserId = x.UserId,
Id = string.IsNullOrEmpty(x.Id) ? Guid.NewGuid() : new Guid(x.Id),
AgentId = Guid.Parse(x.AgentId),
UserId = Guid.Parse(x.UserId),
Title = x.Title,
Dialog = x.Dialog,
State = x.State,
@ -189,12 +189,12 @@ public class MongoRepository : IBotSharpRepository
{
var agents = _agents.Select(x => new AgentCollection
{
Id = x.Id.IfNullOrEmptyAs(ObjectId.GenerateNewId().ToString()),
Id = string.IsNullOrEmpty(x.Id) ? Guid.NewGuid() : new Guid(x.Id),
Name = x.Name,
Description = x.Description,
Instruction = x.Instruction,
Functions = x.Functions,
Routes = x.Routes,
Responses = x.Responses,
CreatedTime = x.CreatedTime,
UpdatedTime = x.UpdatedTime
}).ToList();
@ -207,7 +207,7 @@ public class MongoRepository : IBotSharpRepository
.Set(x => x.Description, agent.Description)
.Set(x => x.Instruction, agent.Instruction)
.Set(x => x.Functions, agent.Functions)
.Set(x => x.Routes, agent.Routes)
.Set(x => x.Responses, agent.Responses)
.Set(x => x.CreatedTime, agent.CreatedTime)
.Set(x => x.UpdatedTime, agent.UpdatedTime);
_dc.Agents.UpdateOne(filter, update, _options);
@ -217,7 +217,7 @@ public class MongoRepository : IBotSharpRepository
{
var users = _users.Select(x => new UserCollection
{
Id = x.Id.IfNullOrEmptyAs(ObjectId.GenerateNewId().ToString()),
Id = string.IsNullOrEmpty(x.Id) ? Guid.NewGuid() : new Guid(x.Id),
FirstName = x.FirstName,
LastName = x.LastName,
Salt = x.Salt,
@ -247,9 +247,9 @@ public class MongoRepository : IBotSharpRepository
{
var userAgents = _userAgents.Select(x => new UserAgentCollection
{
Id = x.Id.IfNullOrEmptyAs(ObjectId.GenerateNewId().ToString()),
AgentId = x.AgentId,
UserId = x.UserId,
Id = string.IsNullOrEmpty(x.Id) ? Guid.NewGuid() : new Guid(x.Id),
AgentId = Guid.Parse(x.AgentId),
UserId = Guid.Parse(x.UserId),
CreatedTime = x.CreatedTime,
UpdatedTime = x.UpdatedTime
}).ToList();
@ -269,4 +269,69 @@ public class MongoRepository : IBotSharpRepository
return _changedTableNames.Count;
}
public UserRecord GetUserByEmail(string email)
{
var user = User.FirstOrDefault(x => x.Email == email);
return user != null ? new UserRecord
{
Id = user.Id.ToString(),
FirstName = user.FirstName,
LastName = user.LastName,
Email = user.Email,
Password = user.Password,
Salt = user.Salt,
ExternalId = user.ExternalId,
CreatedTime = user.CreatedTime,
UpdatedTime = user.UpdatedTime
} : null;
}
public void CreateUser(UserRecord user)
{
if (user == null) return;
var userCollection = new UserCollection
{
Id = Guid.NewGuid(),
FirstName = user.FirstName,
LastName = user.LastName,
Salt = user.Salt,
Password = user.Password,
Email = user.Email,
ExternalId = user.ExternalId,
CreatedTime = DateTime.UtcNow,
UpdatedTime = DateTime.UtcNow
};
_dc.Users.InsertOne(userCollection);
}
public void UpdateAgent(AgentRecord agent)
{
if (agent == null || string.IsNullOrEmpty(agent.Id)) return;
var agentCollection = new AgentCollection
{
Id = Guid.Parse(agent.Id),
Name = agent.Name,
Description = agent.Description,
Instruction = agent.Instruction,
Functions = agent.Functions,
Responses = agent.Responses,
UpdatedTime = DateTime.UtcNow
};
var filter = Builders<AgentCollection>.Filter.Eq(x => x.Id, Guid.Parse(agent.Id));
var update = Builders<AgentCollection>.Update
.Set(x => x.Name, agent.Name)
.Set(x => x.Description, agent.Description)
.Set(x => x.Instruction, agent.Instruction)
.Set(x => x.Functions, agent.Functions)
.Set(x => x.Responses, agent.Responses)
.Set(x => x.UpdatedTime, agent.UpdatedTime);
_dc.Agents.UpdateOne(filter, update, _options);
}
}