version 3
This commit is contained in:
@@ -70,6 +70,10 @@ public class DailyReportService : IDailyReportService
|
||||
throw new InvalidOperationException($"دستگاه با شناسه {request.DeviceId} یافت نشد");
|
||||
}
|
||||
|
||||
// Get device settings (including ProductType if available)
|
||||
var deviceSettings = await _context.DeviceSettings
|
||||
.FirstOrDefaultAsync(ds => ds.DeviceId == request.DeviceId, cancellationToken);
|
||||
|
||||
// Query telemetry data for the specified date
|
||||
var telemetryRecords = await _context.TelemetryRecords
|
||||
.Where(t => t.DeviceId == request.DeviceId && t.PersianDate == request.PersianDate)
|
||||
@@ -115,7 +119,15 @@ public class DailyReportService : IDailyReportService
|
||||
}
|
||||
|
||||
// Prepare the question for AI
|
||||
var question = $@"این دادههای تلمتری یک روز ({request.PersianDate}) از یک گلخانه هوشمند هستند:
|
||||
var productTypeInfo = !string.IsNullOrWhiteSpace(deviceSettings?.ProductType)
|
||||
? $" محصول کشت شده: {deviceSettings.ProductType}."
|
||||
: string.Empty;
|
||||
|
||||
var areaInfo = deviceSettings?.AreaSquareMeters != null
|
||||
? $" مساحت گلخانه: {deviceSettings.AreaSquareMeters:F1} متر مربع."
|
||||
: string.Empty;
|
||||
|
||||
var question = $@"این دادههای تلمتری یک روز ({request.PersianDate}) از یک گلخانه هوشمند هستند.{productTypeInfo}{areaInfo}
|
||||
|
||||
{dataBuilder}
|
||||
|
||||
@@ -123,7 +135,7 @@ public class DailyReportService : IDailyReportService
|
||||
1. وضعیت کلی دما، رطوبت، نور و کیفیت هوا
|
||||
2. روندهای مشاهده شده در طول روز
|
||||
3. هر گونه نکته یا هشدار مهم
|
||||
4. پیشنهادات برای بهبود شرایط گلخانه
|
||||
4. پیشنهادات برای بهبود شرایط گلخانه{(productTypeInfo != string.Empty ? " و رشد بهتر محصول" : string.Empty)}
|
||||
|
||||
خلاصه و مفید باش (حداکثر 300 کلمه).";
|
||||
|
||||
@@ -133,12 +145,16 @@ public class DailyReportService : IDailyReportService
|
||||
|
||||
try
|
||||
{
|
||||
var systemMessage = !string.IsNullOrWhiteSpace(deviceSettings?.ProductType)
|
||||
? $"تو یک متخصص کشاورزی و گلخانه هستی که در کشت {deviceSettings.ProductType} تخصص داری و دادههای تلمتری رو تحلیل میکنی."
|
||||
: "تو یک متخصص کشاورزی و گلخانه هستی که دادههای تلمتری رو تحلیل میکنی.";
|
||||
|
||||
var chatRequest = new ChatRequest
|
||||
{
|
||||
Model = "deepseek-chat",
|
||||
Messages = new List<ChatMessage>
|
||||
{
|
||||
new() { Role = "system", Content = "تو یک متخصص کشاورزی و گلخانه هستی که دادههای تلمتری رو تحلیل میکنی." },
|
||||
new() { Role = "system", Content = systemMessage },
|
||||
new() { Role = "user", Content = question }
|
||||
},
|
||||
Temperature = 0.7
|
||||
@@ -225,5 +241,239 @@ public class DailyReportService : IDailyReportService
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
public async Task<DailyReportResponse> GetWeeklyAnalysisAsync(
|
||||
WeeklyAnalysisRequest request,
|
||||
CancellationToken cancellationToken)
|
||||
{
|
||||
// Get device info
|
||||
var device = await _context.Devices
|
||||
.FirstOrDefaultAsync(d => d.Id == request.DeviceId, cancellationToken);
|
||||
|
||||
if (device == null)
|
||||
{
|
||||
throw new InvalidOperationException($"دستگاه با شناسه {request.DeviceId} یافت نشد");
|
||||
}
|
||||
|
||||
// Get device settings
|
||||
var deviceSettings = await _context.DeviceSettings
|
||||
.FirstOrDefaultAsync(ds => ds.DeviceId == request.DeviceId, cancellationToken);
|
||||
|
||||
// Query telemetry data for the week
|
||||
var telemetryRecords = await _context.TelemetryRecords
|
||||
.Where(t => t.DeviceId == request.DeviceId &&
|
||||
string.Compare(t.PersianDate, request.StartDate) >= 0 &&
|
||||
string.Compare(t.PersianDate, request.EndDate) <= 0)
|
||||
.OrderBy(t => t.TimestampUtc)
|
||||
.Select(t => new
|
||||
{
|
||||
t.TimestampUtc,
|
||||
t.TemperatureC,
|
||||
t.HumidityPercent,
|
||||
t.Lux,
|
||||
t.GasPPM,
|
||||
t.PersianDate
|
||||
})
|
||||
.ToListAsync(cancellationToken);
|
||||
|
||||
if (telemetryRecords.Count == 0)
|
||||
{
|
||||
throw new InvalidOperationException(
|
||||
$"هیچ رکوردی برای دستگاه {request.DeviceId} در بازه {request.StartDate} تا {request.EndDate} یافت نشد");
|
||||
}
|
||||
|
||||
// Sample 1 per 100 records
|
||||
var sampledRecords = telemetryRecords
|
||||
.Select((record, index) => new { record, index })
|
||||
.Where(x => x.index % 100 == 0)
|
||||
.Select(x => x.record)
|
||||
.ToList();
|
||||
|
||||
_logger.LogInformation(
|
||||
"تعداد {TotalCount} رکورد یافت شد. نمونهبرداری هفتگی: {SampledCount} رکورد",
|
||||
telemetryRecords.Count, sampledRecords.Count);
|
||||
|
||||
// Build the data string
|
||||
var dataBuilder = new StringBuilder();
|
||||
dataBuilder.AppendLine("تاریخ | زمان | دما (°C) | رطوبت (%) | نور (Lux) | CO (PPM)");
|
||||
dataBuilder.AppendLine("---------|----------|----------|-----------|-----------|----------");
|
||||
|
||||
foreach (var record in sampledRecords)
|
||||
{
|
||||
var localTime = record.TimestampUtc.AddHours(3.5);
|
||||
dataBuilder.AppendLine(
|
||||
$"{record.PersianDate} | {localTime:HH:mm} | {record.TemperatureC:F1} | {record.HumidityPercent:F1} | {record.Lux:F1} | {record.GasPPM}");
|
||||
}
|
||||
|
||||
// Prepare AI prompt
|
||||
var productTypeInfo = !string.IsNullOrWhiteSpace(deviceSettings?.ProductType)
|
||||
? $" محصول کشت شده: {deviceSettings.ProductType}."
|
||||
: string.Empty;
|
||||
|
||||
var areaInfo = deviceSettings?.AreaSquareMeters != null
|
||||
? $" مساحت گلخانه: {deviceSettings.AreaSquareMeters:F1} متر مربع."
|
||||
: string.Empty;
|
||||
|
||||
var question = $@"این دادههای تلمتری یک هفته ({request.StartDate} تا {request.EndDate}) از یک گلخانه هوشمند هستند.{productTypeInfo}{areaInfo}
|
||||
|
||||
{dataBuilder}
|
||||
|
||||
لطفاً یک تحلیل جامع هفتگی بده که شامل:
|
||||
1. خلاصه روند هفتگی دما، رطوبت، نور و کیفیت هوا
|
||||
2. مقایسه شرایط در روزهای مختلف هفته
|
||||
3. نکات و هشدارهای مهم
|
||||
4. توصیهها برای هفته آینده
|
||||
|
||||
خلاصه و کاربردی باش (حداکثر 500 کلمه).";
|
||||
|
||||
var systemMessage = !string.IsNullOrWhiteSpace(deviceSettings?.ProductType)
|
||||
? $"تو یک متخصص کشاورزی و گلخانه هستی که در کشت {deviceSettings.ProductType} تخصص داری و دادههای تلمتری رو تحلیل میکنی."
|
||||
: "تو یک متخصص کشاورزی و گلخانه هستی که دادههای تلمتری رو تحلیل میکنی.";
|
||||
|
||||
// Send to DeepSeek
|
||||
var stopwatch = Stopwatch.StartNew();
|
||||
var chatRequest = new ChatRequest
|
||||
{
|
||||
Model = "deepseek-chat",
|
||||
Messages = new List<ChatMessage>
|
||||
{
|
||||
new() { Role = "system", Content = systemMessage },
|
||||
new() { Role = "user", Content = question }
|
||||
},
|
||||
Temperature = 0.7
|
||||
};
|
||||
|
||||
var aiResponse = await _deepSeekService.AskAsync(chatRequest, cancellationToken);
|
||||
stopwatch.Stop();
|
||||
|
||||
if (aiResponse?.Choices == null || aiResponse.Choices.Count == 0 ||
|
||||
string.IsNullOrWhiteSpace(aiResponse.Choices[0].Message?.Content))
|
||||
{
|
||||
throw new InvalidOperationException("پاسخ نامعتبر از سرویس هوش مصنوعی");
|
||||
}
|
||||
|
||||
return new DailyReportResponse
|
||||
{
|
||||
Id = 0,
|
||||
DeviceId = request.DeviceId,
|
||||
DeviceName = device.DeviceName,
|
||||
PersianDate = $"{request.StartDate} تا {request.EndDate}",
|
||||
Analysis = aiResponse.Choices[0].Message!.Content,
|
||||
RecordCount = telemetryRecords.Count,
|
||||
SampledRecordCount = sampledRecords.Count,
|
||||
TotalTokens = aiResponse.Usage?.TotalTokens ?? 0,
|
||||
CreatedAt = DateTime.UtcNow,
|
||||
FromCache = false
|
||||
};
|
||||
}
|
||||
|
||||
public async Task<DailyReportResponse> GetMonthlyAnalysisAsync(
|
||||
MonthlyAnalysisRequest request,
|
||||
CancellationToken cancellationToken)
|
||||
{
|
||||
// Get device info
|
||||
var device = await _context.Devices
|
||||
.FirstOrDefaultAsync(d => d.Id == request.DeviceId, cancellationToken);
|
||||
|
||||
if (device == null)
|
||||
{
|
||||
throw new InvalidOperationException($"دستگاه با شناسه {request.DeviceId} یافت نشد");
|
||||
}
|
||||
|
||||
// Get device settings
|
||||
var deviceSettings = await _context.DeviceSettings
|
||||
.FirstOrDefaultAsync(ds => ds.DeviceId == request.DeviceId, cancellationToken);
|
||||
|
||||
// Get all daily reports for this month
|
||||
var dailyReports = await _context.DailyReports
|
||||
.Where(dr => dr.DeviceId == request.DeviceId &&
|
||||
dr.PersianYear == request.Year &&
|
||||
dr.PersianMonth == request.Month)
|
||||
.OrderBy(dr => dr.PersianDay)
|
||||
.Select(dr => new { dr.PersianDate, dr.Analysis })
|
||||
.ToListAsync(cancellationToken);
|
||||
|
||||
if (dailyReports.Count == 0)
|
||||
{
|
||||
throw new InvalidOperationException(
|
||||
$"هیچ تحلیل روزانهای برای دستگاه {request.DeviceId} در ماه {request.Month} سال {request.Year} یافت نشد");
|
||||
}
|
||||
|
||||
// Build summary of daily analyses
|
||||
var summaryBuilder = new StringBuilder();
|
||||
summaryBuilder.AppendLine($"تحلیلهای روزانه ماه {request.Month} سال {request.Year}:");
|
||||
summaryBuilder.AppendLine();
|
||||
|
||||
foreach (var report in dailyReports)
|
||||
{
|
||||
summaryBuilder.AppendLine($"📅 {report.PersianDate}:");
|
||||
summaryBuilder.AppendLine(report.Analysis);
|
||||
summaryBuilder.AppendLine();
|
||||
summaryBuilder.AppendLine("---");
|
||||
summaryBuilder.AppendLine();
|
||||
}
|
||||
|
||||
// Prepare AI prompt
|
||||
var productTypeInfo = !string.IsNullOrWhiteSpace(deviceSettings?.ProductType)
|
||||
? $" محصول کشت شده: {deviceSettings.ProductType}."
|
||||
: string.Empty;
|
||||
|
||||
var areaInfo = deviceSettings?.AreaSquareMeters != null
|
||||
? $" مساحت گلخانه: {deviceSettings.AreaSquareMeters:F1} متر مربع."
|
||||
: string.Empty;
|
||||
|
||||
var question = $@"این تحلیلهای روزانه یک ماه ({request.Month}/{request.Year}) از یک گلخانه هوشمند هستند.{productTypeInfo}{areaInfo}
|
||||
|
||||
{summaryBuilder}
|
||||
|
||||
لطفاً یک تحلیل جامع ماهانه بده که شامل:
|
||||
1. خلاصه کلی عملکرد ماه
|
||||
2. روندهای اصلی و تغییرات مهم
|
||||
3. نقاط قوت و ضعف
|
||||
4. توصیههای کلیدی برای ماه آینده
|
||||
5. نکات مهم برای بهبود بهرهوری
|
||||
|
||||
جامع و کاربردی باش (حداکثر 800 کلمه).";
|
||||
|
||||
var systemMessage = !string.IsNullOrWhiteSpace(deviceSettings?.ProductType)
|
||||
? $"تو یک متخصص کشاورزی و گلخانه هستی که در کشت {deviceSettings.ProductType} تخصص داری. تحلیلهای روزانه رو بررسی کن و یک جمعبندی ماهانه جامع ارائه بده."
|
||||
: "تو یک متخصص کشاورزی و گلخانه هستی. تحلیلهای روزانه رو بررسی کن و یک جمعبندی ماهانه جامع ارائه بده.";
|
||||
|
||||
// Send to DeepSeek
|
||||
var stopwatch = Stopwatch.StartNew();
|
||||
var chatRequest = new ChatRequest
|
||||
{
|
||||
Model = "deepseek-chat",
|
||||
Messages = new List<ChatMessage>
|
||||
{
|
||||
new() { Role = "system", Content = systemMessage },
|
||||
new() { Role = "user", Content = question }
|
||||
},
|
||||
Temperature = 0.7
|
||||
};
|
||||
|
||||
var aiResponse = await _deepSeekService.AskAsync(chatRequest, cancellationToken);
|
||||
stopwatch.Stop();
|
||||
|
||||
if (aiResponse?.Choices == null || aiResponse.Choices.Count == 0 ||
|
||||
string.IsNullOrWhiteSpace(aiResponse.Choices[0].Message?.Content))
|
||||
{
|
||||
throw new InvalidOperationException("پاسخ نامعتبر از سرویس هوش مصنوعی");
|
||||
}
|
||||
|
||||
return new DailyReportResponse
|
||||
{
|
||||
Id = 0,
|
||||
DeviceId = request.DeviceId,
|
||||
DeviceName = device.DeviceName,
|
||||
PersianDate = $"ماه {request.Month} سال {request.Year}",
|
||||
Analysis = aiResponse.Choices[0].Message!.Content,
|
||||
RecordCount = dailyReports.Count,
|
||||
SampledRecordCount = dailyReports.Count,
|
||||
TotalTokens = aiResponse.Usage?.TotalTokens ?? 0,
|
||||
CreatedAt = DateTime.UtcNow,
|
||||
FromCache = false
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user