feat: Versão com comparação de imagens
This commit is contained in:
parent
93ce4db4d7
commit
653de55fb4
42
Chat.Domain/Tools/Base64ToFormFile.cs
Normal file
42
Chat.Domain/Tools/Base64ToFormFile.cs
Normal file
@ -0,0 +1,42 @@
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Chat.Domain.Tools
|
||||
{
|
||||
public class Base64ToFormFile
|
||||
{
|
||||
public static IFormFile ConvertBase64ToFormFile(string base64String, string fileName)
|
||||
{
|
||||
// Remove o prefixo "data:image/png;base64," se existir
|
||||
if (base64String.Contains(","))
|
||||
{
|
||||
base64String = base64String.Split(',')[1];
|
||||
}
|
||||
|
||||
// Converte base64 para bytes
|
||||
byte[] bytes = Convert.FromBase64String(base64String);
|
||||
|
||||
// Cria um stream de memória com os bytes
|
||||
var stream = new MemoryStream(bytes);
|
||||
|
||||
// Cria um IFormFile usando o stream
|
||||
var formFile = new FormFile(
|
||||
baseStream: stream,
|
||||
baseStreamOffset: 0,
|
||||
length: bytes.Length,
|
||||
name: "file",
|
||||
fileName: fileName
|
||||
)
|
||||
{
|
||||
Headers = new HeaderDictionary(),
|
||||
ContentType = "image/png"
|
||||
};
|
||||
|
||||
return formFile;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -26,6 +26,7 @@
|
||||
<PackageReference Include="Serilog.Sinks.Console" Version="6.0.0" />
|
||||
<PackageReference Include="Serilog.Sinks.Grafana.Loki" Version="8.3.0" />
|
||||
<PackageReference Include="Stripe.net" Version="45.13.0" />
|
||||
<PackageReference Include="System.IdentityModel.Tokens.Jwt" Version="8.5.0" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
@ -36,6 +37,10 @@
|
||||
<None Include="wwwroot\js\notif.js" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\Chat.Domain\Chat.Domain.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<Compile Update="Resource.Designer.cs">
|
||||
<DesignTime>True</DesignTime>
|
||||
|
||||
@ -9,6 +9,8 @@ using Microsoft.AspNetCore.Antiforgery;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using System.Linq;
|
||||
using Microsoft.AspNetCore.Authentication;
|
||||
using Chat.Domain.Tools;
|
||||
using Newtonsoft.Json.Linq;
|
||||
|
||||
namespace ChatMvc.Controllers
|
||||
{
|
||||
@ -34,9 +36,9 @@ namespace ChatMvc.Controllers
|
||||
return View();
|
||||
}
|
||||
|
||||
[HttpGet("chat/proxy-response")]
|
||||
[HttpPost("chat/proxy-response")]
|
||||
[ValidateAntiForgeryToken]
|
||||
public async Task<IActionResult> ProxyResponse(string sessionId, string message)
|
||||
public async Task<IActionResult> ProxyResponse([FromForm] string sessionId, [FromForm] string message, [FromForm] IFormFile file1 = null, [FromForm] IFormFile file2 = null)
|
||||
{
|
||||
try
|
||||
{
|
||||
@ -45,24 +47,60 @@ namespace ChatMvc.Controllers
|
||||
return BadRequest("Requisição inválida");
|
||||
}
|
||||
|
||||
var userId = User.Claims.FirstOrDefault(f => f.Type == "UserId").Value;
|
||||
var name = User.Claims.FirstOrDefault(f => f.Type == "FirstName").Value;
|
||||
var company = User.Claims.FirstOrDefault(f => f.Type == "CompanyName").Value;
|
||||
var token = User.Claims.FirstOrDefault(f => f.Type == "TokenExternal").Value;
|
||||
var userId = User.Claims.FirstOrDefault(f => f.Type == "UserId")?.Value;
|
||||
var name = User.Claims.FirstOrDefault(f => f.Type == "FirstName")?.Value;
|
||||
var company = User.Claims.FirstOrDefault(f => f.Type == "CompanyName")?.Value;
|
||||
var token = User.Claims.FirstOrDefault(f => f.Type == "TokenExternal")?.Value;
|
||||
|
||||
if (string.IsNullOrEmpty(token))
|
||||
{
|
||||
return BadRequest("Token não encontrado");
|
||||
}
|
||||
|
||||
// Verificar se há arquivos e palavras-chave
|
||||
var keyWords = new[] { "diferença", "diferenças", "comparação", "comparar", "compare" };
|
||||
bool hasKeyword = keyWords.Any(k => message.ToLower().Contains(k.ToLower()));
|
||||
bool hasBothFiles = file1 != null && file2 != null;
|
||||
bool hasOneFile = file1 != null || file2 != null;
|
||||
bool isPDF = file1 != null && file1.ContentType == "application/pdf" && file2 != null && file2.ContentType == "application/pdf";
|
||||
bool isImage = file1 != null && file1.ContentType.Contains("image") && file2 != null && file2.ContentType.Contains("image");
|
||||
|
||||
// Se tem apenas um arquivo ou se tem arquivos mas não tem palavra-chave
|
||||
if ((hasOneFile && !hasBothFiles) || (hasBothFiles && !hasKeyword))
|
||||
{
|
||||
return Ok("Por favor, especifique o que deseja fazer com os arquivos. " +
|
||||
"Para comparar dois PDFs, inclua palavras como 'diferença' ou 'comparação' em sua mensagem.");
|
||||
}
|
||||
|
||||
var client = _httpClientFactory.CreateClient();
|
||||
var baseUrl = _configuration["ExternalApiBaseUrl"];
|
||||
|
||||
client.DefaultRequestHeaders.Authorization =
|
||||
new AuthenticationHeaderValue("Bearer", token.Replace("Bearer ", ""));
|
||||
|
||||
var response = await client.GetAsync(
|
||||
$"{baseUrl}/chat/response?sessionId={sessionId}&message={message}");
|
||||
var baseUrl = _configuration["ExternalApiBaseUrl"];
|
||||
|
||||
if (hasBothFiles && hasKeyword && isPDF)
|
||||
{
|
||||
var content = await CompareFiles(baseUrl, sessionId, client, file1, file2);
|
||||
return Ok(content);
|
||||
}
|
||||
else if (hasBothFiles && hasKeyword && isImage)
|
||||
{
|
||||
var content = await CompareFilesImage(baseUrl, sessionId, client, file1, file2);
|
||||
return Ok(content);
|
||||
}
|
||||
|
||||
var chatContent = new FormUrlEncodedContent(new[]
|
||||
{
|
||||
new KeyValuePair<string, string>("sessionId", sessionId),
|
||||
new KeyValuePair<string, string>("message", message)
|
||||
});
|
||||
|
||||
var response = await client.PostAsync($"{baseUrl}/chat/response", chatContent);
|
||||
|
||||
response.EnsureSuccessStatusCode();
|
||||
var content = await response.Content.ReadAsStringAsync();
|
||||
var responseContent = await response.Content.ReadAsStringAsync();
|
||||
|
||||
return Ok(content);
|
||||
return Ok(responseContent);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
@ -70,6 +108,112 @@ namespace ChatMvc.Controllers
|
||||
}
|
||||
}
|
||||
|
||||
private async Task<string> CompareFiles(string? baseUrl, string sessionId, HttpClient? client, [FromForm] IFormFile? file1 = null, [FromForm] IFormFile? file2 = null)
|
||||
{
|
||||
// Primeiro, comparar os PDFs
|
||||
var formData = new MultipartFormDataContent();
|
||||
var content1 = new StreamContent(file1.OpenReadStream());
|
||||
var content2 = new StreamContent(file2.OpenReadStream());
|
||||
content1.Headers.ContentType = new MediaTypeHeaderValue("application/pdf");
|
||||
content2.Headers.ContentType = new MediaTypeHeaderValue("application/pdf");
|
||||
formData.Add(content1, "File1", file1.FileName);
|
||||
formData.Add(content2, "File2", file2.FileName);
|
||||
|
||||
var comparisonResponse = await client.PostAsync(
|
||||
"https://localhost:7200/api/PdfComparison/compare",
|
||||
formData
|
||||
);
|
||||
|
||||
if (!comparisonResponse.IsSuccessStatusCode)
|
||||
{
|
||||
throw new Exception("Erro ao comparar os PDFs");
|
||||
}
|
||||
|
||||
var differences = await comparisonResponse.Content.ReadAsStringAsync();
|
||||
var dynamicContent = JsonConvert.DeserializeObject<dynamic>(differences);
|
||||
var formattedDifferences = FormatDifferencesForChat(dynamicContent);
|
||||
|
||||
var promptMessage = $"Ao comparar dois textos obtive as diferenças do json. Você poderia explicar e resumir: {formattedDifferences}";
|
||||
|
||||
var chatContentSend = new FormUrlEncodedContent(new[]
|
||||
{
|
||||
new KeyValuePair<string, string>("sessionId", sessionId),
|
||||
new KeyValuePair<string, string>("message", promptMessage)
|
||||
});
|
||||
|
||||
var chatResponse = await client.PostAsync($"{baseUrl}/chat/response-fromia", chatContentSend);
|
||||
|
||||
chatResponse.EnsureSuccessStatusCode();
|
||||
var content = await chatResponse.Content.ReadAsStringAsync();
|
||||
|
||||
return content;
|
||||
}
|
||||
|
||||
private async Task<string> CompareFilesImage(string? baseUrl, string sessionId, HttpClient? client, [FromForm] IFormFile? file1 = null, [FromForm] IFormFile? file2 = null)
|
||||
{
|
||||
var formData = new MultipartFormDataContent();
|
||||
var content1 = new StreamContent(file1.OpenReadStream());
|
||||
var content2 = new StreamContent(file2.OpenReadStream());
|
||||
content1.Headers.ContentType = new MediaTypeHeaderValue(file1.ContentType);
|
||||
content2.Headers.ContentType = new MediaTypeHeaderValue(file2.ContentType);
|
||||
formData.Add(content1, "Drawing1", file1.FileName);
|
||||
formData.Add(content2, "Drawing2", file2.FileName);
|
||||
|
||||
var comparisonResponse = await client.PostAsync(
|
||||
"https://localhost:7200/api/TechnicalDrawing/compare-images",
|
||||
formData
|
||||
);
|
||||
|
||||
if (!comparisonResponse.IsSuccessStatusCode)
|
||||
{
|
||||
throw new Exception("Erro ao comparar os PDFs");
|
||||
}
|
||||
|
||||
var differences = await comparisonResponse.Content.ReadAsStringAsync();
|
||||
JObject obj = JObject.Parse(differences);
|
||||
string image = obj["image"].ToString();
|
||||
|
||||
var file3 = Base64ToFormFile.ConvertBase64ToFormFile(image, "compared.png");
|
||||
|
||||
var promptMessage = $"Ao comparar dois desenhos técnicos, obtive as diferenças entre eles. Você precisa explicar e resumir estas diferenças ressaltando mudanças em medidas da peça. O arquivo ";
|
||||
|
||||
var response = "";
|
||||
using (formData = AddFormDataToResponse(sessionId, promptMessage, file1, file2, file3))
|
||||
{
|
||||
var chatResponse = await client.PostAsync($"{baseUrl}/chat/response-fromia", formData);
|
||||
chatResponse.EnsureSuccessStatusCode();
|
||||
response = await chatResponse.Content.ReadAsStringAsync();
|
||||
}
|
||||
return response;
|
||||
}
|
||||
|
||||
private MultipartFormDataContent AddFormDataToResponse(string sessionId, string message, IFormFile? file1 = null, IFormFile? file2 = null, IFormFile? file3 = null)
|
||||
{
|
||||
var formData = new MultipartFormDataContent();
|
||||
formData.Add(new StringContent(sessionId), "SessionId");
|
||||
formData.Add(new StringContent(message), "Message");
|
||||
|
||||
if (file1 != null)
|
||||
{
|
||||
var streamContent1 = new StreamContent(file1.OpenReadStream());
|
||||
formData.Add(streamContent1, "File1", file1.FileName);
|
||||
}
|
||||
|
||||
if (file2 != null)
|
||||
{
|
||||
var streamContent2 = new StreamContent(file2.OpenReadStream());
|
||||
formData.Add(streamContent2, "File2", file2.FileName);
|
||||
}
|
||||
|
||||
if (file3 != null)
|
||||
{
|
||||
var streamContent3 = new StreamContent(file3.OpenReadStream());
|
||||
formData.Add(streamContent3, "File3", file3.FileName);
|
||||
}
|
||||
|
||||
return formData;
|
||||
}
|
||||
|
||||
[HttpPost("chat/authenticate")]
|
||||
[ValidateAntiForgeryToken]
|
||||
public async Task<IActionResult> Authenticate([FromBody] AuthenticateRequest request)
|
||||
@ -125,6 +269,53 @@ namespace ChatMvc.Controllers
|
||||
return BadRequest($"Erro na autenticação: {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
private string FormatDifferencesForChat(dynamic jsonDifferences)
|
||||
{
|
||||
var sb = new StringBuilder();
|
||||
sb.AppendLine("Análise das diferenças entre os documentos:");
|
||||
sb.AppendLine();
|
||||
|
||||
try
|
||||
{
|
||||
// Focar apenas nas diferenças reais (onlyDifferences)
|
||||
var onlyDiffs = jsonDifferences.onlyDifferences;
|
||||
|
||||
if (onlyDiffs != null && onlyDiffs.Count > 0)
|
||||
{
|
||||
foreach (var diff in onlyDiffs)
|
||||
{
|
||||
string content = diff.content?.ToString() ?? "";
|
||||
string type = diff.typeName?.ToString() ?? "";
|
||||
int lineNumber = diff.lineNumber;
|
||||
|
||||
switch (type)
|
||||
{
|
||||
case "Deleted":
|
||||
sb.AppendLine($"Removido (linha {lineNumber}):");
|
||||
sb.AppendLine($"- {content}");
|
||||
break;
|
||||
case "Inserted":
|
||||
sb.AppendLine($"Adicionado (linha {lineNumber}):");
|
||||
sb.AppendLine($"+ {content}");
|
||||
break;
|
||||
}
|
||||
sb.AppendLine();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
sb.AppendLine("Nenhuma diferença significativa encontrada entre os documentos.");
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
sb.AppendLine("Erro ao processar diferenças. Resumo simplificado:");
|
||||
sb.AppendLine("As diferenças entre os documentos não puderam ser formatadas adequadamente.");
|
||||
}
|
||||
|
||||
return sb.ToString();
|
||||
}
|
||||
}
|
||||
|
||||
public class AuthenticateRequest
|
||||
|
||||
@ -1,4 +1,5 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using ChatMvc.Managers;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using System.Net.Http.Headers;
|
||||
using static System.Net.Mime.MediaTypeNames;
|
||||
@ -9,17 +10,24 @@ namespace ChatMvc.Controllers
|
||||
public class DocumentsController : Controller
|
||||
{
|
||||
private readonly HttpClient _httpClient;
|
||||
private readonly TokenManager _tokenManager;
|
||||
|
||||
public DocumentsController()
|
||||
public DocumentsController(TokenManager tokenManager)
|
||||
{
|
||||
_httpClient = new HttpClient();
|
||||
_httpClient.BaseAddress = new Uri("http://localhost:5020/");
|
||||
this._tokenManager = tokenManager;
|
||||
}
|
||||
|
||||
public async Task<IActionResult> Index()
|
||||
{
|
||||
var token = User.Claims.FirstOrDefault(f => f.Type == "TokenExternal").Value;
|
||||
|
||||
if (_tokenManager.IsTokenExpired(token)) {
|
||||
var userId = User.Claims.FirstOrDefault(f => f.Type == "TokenExternal").Value;
|
||||
token = await _tokenManager.GetToken(User);
|
||||
}
|
||||
|
||||
_httpClient.DefaultRequestHeaders.Authorization =
|
||||
new AuthenticationHeaderValue("Bearer", token.Replace("Bearer ", ""));
|
||||
|
||||
|
||||
@ -1,7 +1,9 @@
|
||||
using ChatMvc.Controllers;
|
||||
using Newtonsoft.Json;
|
||||
using Stripe.Forwarding;
|
||||
using System.IdentityModel.Tokens.Jwt;
|
||||
using System.Net.Http;
|
||||
using System.Security.Claims;
|
||||
using System.Text;
|
||||
|
||||
namespace ChatMvc.Managers
|
||||
@ -59,5 +61,61 @@ namespace ChatMvc.Managers
|
||||
return tokenResult.Token;
|
||||
|
||||
}
|
||||
|
||||
public async Task<string> GetToken(ClaimsPrincipal user)
|
||||
{
|
||||
var userId = user.Claims.FirstOrDefault(f => f.Type == "UserId")?.Value;
|
||||
var name = user.Claims.FirstOrDefault(f => f.Type == "FirstName")?.Value;
|
||||
var company = user.Claims.FirstOrDefault(f => f.Type == "CompanyName")?.Value;
|
||||
|
||||
var client = _httpClientFactory.CreateClient();
|
||||
var baseUrl = _configuration["ExternalApiBaseUrl"];
|
||||
|
||||
// Primeira requisição - newclient
|
||||
var newClientRequest = new
|
||||
{
|
||||
localId = userId,
|
||||
companyTenant = company,
|
||||
name = name
|
||||
};
|
||||
|
||||
var newClientResponse = await client.PostAsync(
|
||||
$"{baseUrl}/login/newclient",
|
||||
new StringContent(JsonConvert.SerializeObject(newClientRequest),
|
||||
Encoding.UTF8, "application/json"));
|
||||
|
||||
newClientResponse.EnsureSuccessStatusCode();
|
||||
var clientContent = await newClientResponse.Content.ReadAsStringAsync();
|
||||
var clientResult = JsonConvert.DeserializeObject<NewClientResponse>(clientContent);
|
||||
|
||||
// Segunda requisição - token
|
||||
var tokenRequest = new
|
||||
{
|
||||
clientId = userId,
|
||||
clientName = name,
|
||||
clientSecret = clientResult.Secret
|
||||
};
|
||||
|
||||
var tokenResponse = await client.PostAsync(
|
||||
$"{baseUrl}/login/token",
|
||||
new StringContent(JsonConvert.SerializeObject(tokenRequest),
|
||||
Encoding.UTF8, "application/json"));
|
||||
|
||||
tokenResponse.EnsureSuccessStatusCode();
|
||||
var tokenContent = await tokenResponse.Content.ReadAsStringAsync();
|
||||
var tokenResult = JsonConvert.DeserializeObject<TokenResponse>(tokenContent);
|
||||
|
||||
return tokenResult.Token;
|
||||
|
||||
}
|
||||
|
||||
public bool IsTokenExpired(string token)
|
||||
{
|
||||
var handler = new JwtSecurityTokenHandler();
|
||||
var jwtToken = handler.ReadJwtToken(token);
|
||||
|
||||
var expiracao = jwtToken.ValidTo;
|
||||
return expiracao < DateTime.UtcNow;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -19,7 +19,7 @@ var builder = WebApplication.CreateBuilder(args);
|
||||
Log.Logger = new LoggerConfiguration()
|
||||
.MinimumLevel.Information()
|
||||
.Enrich.FromLogContext()
|
||||
.Enrich.WithProperty("app", "blinks")
|
||||
.Enrich.WithProperty("app", "chat")
|
||||
.WriteTo.Console()
|
||||
.WriteTo.File("logs/log.txt", rollingInterval: RollingInterval.Day)
|
||||
.CreateLogger();
|
||||
|
||||
@ -18,7 +18,8 @@
|
||||
"ASPNETCORE_ENVIRONMENT": "Development"
|
||||
},
|
||||
"dotnetRunMessages": true,
|
||||
"applicationUrl": "https://192.168.0.13:7078;http://192.168.0.13:5094;https://localhost:7078;http://localhost:5094"
|
||||
"applicationUrl": "https://localhost:7078"
|
||||
//"applicationUrl": "https://192.168.0.13:7078;http://192.168.0.13:5094;https://localhost:7078;http://localhost:5094"
|
||||
},
|
||||
"IIS Express": {
|
||||
"commandName": "IISExpress",
|
||||
|
||||
@ -2,29 +2,56 @@
|
||||
ViewData["Title"] = "Chat";
|
||||
}
|
||||
|
||||
@section Styles{
|
||||
<link href="~/css/chat_index.css" rel="stylesheet" />
|
||||
@section Styles {
|
||||
<link href="~/css/chat_index.css" rel="stylesheet" />
|
||||
<style>
|
||||
.file-upload-button {
|
||||
position: relative;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.file-upload-button input[type=file] {
|
||||
position: absolute;
|
||||
top: 0;
|
||||
right: 0;
|
||||
min-width: 100%;
|
||||
min-height: 100%;
|
||||
font-size: 100px;
|
||||
text-align: right;
|
||||
filter: alpha(opacity=0);
|
||||
opacity: 0;
|
||||
outline: none;
|
||||
cursor: pointer;
|
||||
display: block;
|
||||
}
|
||||
|
||||
.selected-files {
|
||||
font-size: 0.8rem;
|
||||
margin-top: 0.5rem;
|
||||
color: #666;
|
||||
}
|
||||
</style>
|
||||
}
|
||||
|
||||
<div class="container-fluid bg-light">
|
||||
<div class="row h-100">
|
||||
<div class="col-md-10 mx-auto">
|
||||
<div class="card shadow-sm my-4" style="background-color: #f8fff8;">
|
||||
@*
|
||||
<div class="card-header bg-success text-white">
|
||||
<h5 class="mb-0">Chat</h5>
|
||||
</div>
|
||||
*@
|
||||
<div class="card-body">
|
||||
<div id="chat-messages" class="mb-4" style="height: 350px; overflow-y: auto;">
|
||||
<!-- Mensagens serão inseridas aqui -->
|
||||
</div>
|
||||
<form id="chat-form" class="mt-3">
|
||||
@Html.AntiForgeryToken()
|
||||
<div class="selected-files" id="selected-files-info"></div>
|
||||
<div class="input-group">
|
||||
<textarea id="message-input" class="form-control"
|
||||
placeholder="Digite sua mensagem... Use **texto** para negrito"
|
||||
rows="3" required></textarea>
|
||||
<button type="button" class="btn btn-outline-secondary file-upload-button">
|
||||
<i class="bi bi-paperclip"></i>
|
||||
<input type="file" id="file-input" accept="application/pdf,image/png" multiple>
|
||||
</button>
|
||||
<button type="button" class="btn btn-success" id="send-message">
|
||||
Enviar
|
||||
</button>
|
||||
@ -43,8 +70,7 @@
|
||||
const id = name + '_Web';
|
||||
const company = 'Domvs iT';
|
||||
const baseUrl = window.location.origin;
|
||||
|
||||
var token = '';
|
||||
var token = '@ViewBag.Token';
|
||||
|
||||
// Aguarda todos os recursos serem carregados
|
||||
window.addEventListener('load', async function () {
|
||||
@ -52,14 +78,18 @@
|
||||
const chatMessages = $('#chat-messages');
|
||||
const messageInput = $('#message-input');
|
||||
const chatForm = $('#chat-form');
|
||||
const fileInput = $('#file-input');
|
||||
const selectedFilesInfo = $('#selected-files-info');
|
||||
let selectedFiles = [];
|
||||
|
||||
//token = await autenticar(id, company, name);
|
||||
token = '@ViewBag.Token';
|
||||
// Configuração do Marked
|
||||
marked.setOptions({
|
||||
breaks: true,
|
||||
gfm: true
|
||||
});
|
||||
//token = '@ViewBag.Token';
|
||||
|
||||
// // Configuração do Marked
|
||||
// marked.setOptions({
|
||||
// breaks: true,
|
||||
// gfm: true
|
||||
// });
|
||||
|
||||
const msgInit = `Olá! Eu sou uma IA desenvolvida para atuar internamente na Domvs iT. Você pode:
|
||||
- Fazer perguntas sobre os serviços da Domvs iT
|
||||
@ -134,57 +164,74 @@ seu código
|
||||
// Exibe mensagem inicial
|
||||
appendMessage(msgInit, false);
|
||||
|
||||
$('#send-message').on('click', function (e) {
|
||||
// Arquivo handling
|
||||
fileInput.on('change', function (e) {
|
||||
const files = Array.from(e.target.files);
|
||||
|
||||
if (files.length > 2) {
|
||||
alert('Por favor, selecione no máximo 2 arquivos PDF/PNG.');
|
||||
fileInput.val('');
|
||||
selectedFiles = [];
|
||||
selectedFilesInfo.html('');
|
||||
return;
|
||||
}
|
||||
|
||||
if (files.some(file => file.type !== 'application/pdf' && file.type !== 'image/png')) {
|
||||
alert('Por favor, selecione apenas arquivos PDF/PNG.');
|
||||
fileInput.val('');
|
||||
selectedFiles = [];
|
||||
selectedFilesInfo.html('');
|
||||
return;
|
||||
}
|
||||
|
||||
selectedFiles = files;
|
||||
selectedFilesInfo.html(
|
||||
files.map(file => `<div>${file.name}</div>`).join('')
|
||||
);
|
||||
});
|
||||
|
||||
// Send message handling
|
||||
$('#send-message').on('click', async function (e) {
|
||||
e.preventDefault();
|
||||
const message = messageInput.val().trim();
|
||||
if (!message) return;
|
||||
|
||||
const formData = new FormData();
|
||||
formData.append('message', message);
|
||||
formData.append('sessionId', id);
|
||||
|
||||
selectedFiles.forEach((file, index) => {
|
||||
formData.append(`file${index + 1}`, file);
|
||||
});
|
||||
|
||||
appendMessage(message);
|
||||
messageInput.val('');
|
||||
$.ajax({
|
||||
url: baseUrl + '/chat/proxy-response', // Novo endpoint no controller
|
||||
type: 'GET',
|
||||
headers: {
|
||||
"X-CSRF-TOKEN": $('input[name="__RequestVerificationToken"]').val(),
|
||||
'Authorization': 'Bearer ' + token
|
||||
},
|
||||
data: {
|
||||
sessionId: id,
|
||||
message: message
|
||||
},
|
||||
success: function (response) {
|
||||
appendMessage(response, false);
|
||||
},
|
||||
error: function (xhr, status, error) {
|
||||
console.error('Erro na requisição do cliente:', error);
|
||||
console.error('Status:', xhr.status);
|
||||
console.error('Response:', xhr.responseText);
|
||||
appendMessage('Erro ao processar cliente: ' + error, false);
|
||||
}
|
||||
});
|
||||
});
|
||||
fileInput.val('');
|
||||
selectedFiles = [];
|
||||
selectedFilesInfo.html('');
|
||||
|
||||
async function autenticar(userId, company, name) {
|
||||
try {
|
||||
// Agora fazemos apenas uma requisição para o novo endpoint
|
||||
const response = await $.ajax({
|
||||
url: baseUrl + '/chat/authenticate',
|
||||
type: 'POST',
|
||||
const response = await fetch(baseUrl + '/chat/proxy-response', {
|
||||
method: 'POST',
|
||||
headers: {
|
||||
"X-CSRF-TOKEN": $('input[name="__RequestVerificationToken"]').val()
|
||||
"X-CSRF-TOKEN": $('input[name="__RequestVerificationToken"]').val(),
|
||||
'Authorization': 'Bearer ' + token,
|
||||
'X-Requested-With': 'XMLHttpRequest'
|
||||
},
|
||||
contentType: 'application/json',
|
||||
data: JSON.stringify({
|
||||
userId: userId,
|
||||
company: company,
|
||||
name: name
|
||||
})
|
||||
body: formData
|
||||
});
|
||||
return response.token;
|
||||
|
||||
if (!response.ok) {
|
||||
throw new Error('Erro na requisição');
|
||||
}
|
||||
|
||||
const responseText = await response.text();
|
||||
appendMessage(responseText, false);
|
||||
} catch (error) {
|
||||
console.error('Erro na requisição:', error);
|
||||
appendMessage('Erro ao processar mensagem: ' + error, false);
|
||||
throw error;
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
|
||||
Loading…
Reference in New Issue
Block a user