From 3e383cbbef6be79f26eb00c872f04d86481ec5f4 Mon Sep 17 00:00:00 2001 From: Emre KARA Date: Wed, 7 May 2025 10:01:51 +0300 Subject: [PATCH] Refactor telemetry data handling and remove unused dependencies --- .../Volo/Abp/Modularity/AbpModule.cs | 2 +- .../Activity/ActivityDataProvider.cs | 205 +++++++----------- .../Activity/ActivityPropertyNameConstants.cs | 1 - .../Activity/IActivityDataProvider.cs | 8 +- .../Abp/Telemetry/ApplicationInfoProvider.cs | 2 +- .../Volo/Abp/Telemetry/TelemetryDataSender.cs | 46 +++- 6 files changed, 134 insertions(+), 130 deletions(-) diff --git a/framework/src/Volo.Abp.Core/Volo/Abp/Modularity/AbpModule.cs b/framework/src/Volo.Abp.Core/Volo/Abp/Modularity/AbpModule.cs index 832142703c..5275347c16 100644 --- a/framework/src/Volo.Abp.Core/Volo/Abp/Modularity/AbpModule.cs +++ b/framework/src/Volo.Abp.Core/Volo/Abp/Modularity/AbpModule.cs @@ -113,7 +113,7 @@ public abstract class AbpModule : await using var _ = telemetryService.TrackActivity(ActivityNameConsts.ApplicationRun, activity => { - activity.Add(ActivityPropertyNameConstants.Assembly, assembly); + activity.Add(ActivityPropertyNameConstants.Assembly, assembly.Location); activity.Add(ActivityPropertyNameConstants.ProjectId, packageMetadata.ProjectId!); activity.Add(ActivityPropertyNameConstants.ProjectType, packageMetadata.Role!); activity.Add(ActivityPropertyNameConstants.SolutionPath, packageMetadata.AbpSlnPath ?? string.Empty); diff --git a/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/Activity/ActivityDataProvider.cs b/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/Activity/ActivityDataProvider.cs index 27355a1df9..29c80e264c 100644 --- a/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/Activity/ActivityDataProvider.cs +++ b/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/Activity/ActivityDataProvider.cs @@ -17,83 +17,47 @@ namespace Volo.Abp.Telemetry.Activity; public class ActivityDataProvider : IActivityDataProvider, IScopedDependency { - private readonly IActivityStorage _activityStorage; private readonly IDeviceInfoProvider _deviceInfoProvider; private readonly ISoftwareInfoProvider _softwareInfoProvider; private readonly ApplicationInfoProvider _applicationInfoProvider; - public ActivityDataProvider(IActivityStorage activityStorage, IDeviceInfoProvider deviceInfoProvider, + public ActivityDataProvider(IDeviceInfoProvider deviceInfoProvider, ISoftwareInfoProvider softwareInfoProvider, ApplicationInfoProvider applicationInfoProvider) { - _activityStorage = activityStorage; _deviceInfoProvider = deviceInfoProvider; _softwareInfoProvider = softwareInfoProvider; _applicationInfoProvider = applicationInfoProvider; } - public virtual async Task AddExtraInformationAsync(ActivityData activityData, - CancellationToken cancellationToken = default) - { - try - { - var (isFirstSession, sessionId) = await _activityStorage.GetOrCreateSessionInfoAsync(cancellationToken); - - activityData.Add(ActivityPropertyNameConstants.SessionId, sessionId); - activityData.Add(ActivityPropertyNameConstants.IsFirstSession, isFirstSession); - - var lastDeviceInfoSendTime = await _activityStorage.GetLastDeviceInfoSendTimeAsync(cancellationToken); - activityData.Add(ActivityPropertyNameConstants.DeviceId, await _deviceInfoProvider.GetDeviceIdAsync()); - - if (lastDeviceInfoSendTime is null || DateTimeOffset.UtcNow - lastDeviceInfoSendTime > TimeSpan.FromDays(7)) - { - await AddDeviceInformationAsync(activityData); - } - - if (activityData.TryGetValue(ActivityPropertyNameConstants.Assembly, out var value)) - { - var assembly = value as Assembly; - if (assembly != null) - { - AddApplicationInformation(activityData, assembly); - } - } - - await AddSolutionInformationAsync(activityData); - return activityData; - } - catch - { - return activityData; - } - } - - private async Task AddDeviceInformationAsync(ActivityData activityData) + public async Task AddDeviceInformationAsync(ActivityData activityData, + CancellationToken cancellationToken = default) { + activityData.Add(ActivityPropertyNameConstants.DeviceId, await _deviceInfoProvider.GetDeviceIdAsync()); activityData.Add(ActivityPropertyNameConstants.DeviceType, _deviceInfoProvider.GetDeviceType()); activityData.Add(ActivityPropertyNameConstants.DeviceLanguage, _deviceInfoProvider.GetLanguage()); activityData.Add(ActivityPropertyNameConstants.OperatingSystem, _deviceInfoProvider.GetOperatingSystem()); activityData.Add(ActivityPropertyNameConstants.CountryIsoCode, _deviceInfoProvider.GetCountry()); - var softwareList = await _softwareInfoProvider.GetSoftwareInfoAsync(); + var softwareList = await _softwareInfoProvider.GetSoftwareInfoAsync(cancellationToken); activityData.Add(ActivityPropertyNameConstants.InstalledSoftwares, softwareList); - await _activityStorage.MarkDeviceInfoAsSentAsync(); } - private void AddApplicationInformation(ActivityData activityData, Assembly assembly) + public void AddApplicationInformation(ActivityData activityData, Assembly assembly) { - var info = _applicationInfoProvider.Scan(assembly); + var info = _applicationInfoProvider.ExtractApplicationInfo(assembly); activityData.Add(ActivityPropertyNameConstants.ControllerCount, info.ControllerCount); activityData.Add(ActivityPropertyNameConstants.EntityCount, info.EntityCount); activityData.Add(ActivityPropertyNameConstants.AbpModuleCount, info.AbpModuleCount); activityData.Add(ActivityPropertyNameConstants.PermissionCount, info.PermissionCount); activityData.Add(ActivityPropertyNameConstants.AppServiceCount, info.AppServiceCount); - + activityData.Remove(ActivityPropertyNameConstants.Assembly); } - private async Task AddSolutionInformationAsync(ActivityData activityData) + public async Task AddSolutionInformationAsync(ActivityData activityData, + CancellationToken cancellationToken = default) { if (activityData.TryGetValue(ActivityPropertyNameConstants.SolutionPath, out var value)) { @@ -116,99 +80,94 @@ public class ActivityDataProvider : IActivityDataProvider, IScopedDependency activityData.Add(ActivityPropertyNameConstants.SolutionId, solutionId); - var lastSolutionInfoSendTime = await _activityStorage.GetLastSolutionInfoSendTimeAsync(solutionId); - if (lastSolutionInfoSendTime is null || - DateTimeOffset.UtcNow - lastSolutionInfoSendTime > TimeSpan.FromDays(7)) + if (root.TryGetProperty("creatingStudioConfiguration", out var config)) { - if (root.TryGetProperty("creatingStudioConfiguration", out var config)) - { - activityData.Add(ActivityPropertyNameConstants.Template, - MapSolutionTemplate(config.GetProperty("template").GetString())); - activityData.Add(ActivityPropertyNameConstants.CreatedAbpStudioVersion, - config.GetProperty("createdAbpStudioVersion").GetString()!); - activityData.Add(ActivityPropertyNameConstants.IsTiered, config.GetProperty("Tiered").GetBoolean()); - activityData.Add(ActivityPropertyNameConstants.UiFramework, - MapUiFramework(config.GetProperty("uiFramework").GetString())); - activityData.Add(ActivityPropertyNameConstants.DatabaseProvider, - MapDatabaseProvider(config.GetProperty("databaseProvider").GetString())); - activityData.Add(ActivityPropertyNameConstants.DatabaseManagementSystem, - MapDbms(config.GetProperty("databaseManagementSystem").GetString())); - activityData.Add(ActivityPropertyNameConstants.IsSeparateTenantSchema, - config.GetProperty("separateTenantSchema").GetBoolean()); - activityData.Add(ActivityPropertyNameConstants.Theme, - MapUiTheme(config.GetProperty("theme").GetString())); - activityData.Add(ActivityPropertyNameConstants.ThemeStyle, - MapUiThemeStyle(config.GetProperty("themeStyle").GetString())); - activityData.Add(ActivityPropertyNameConstants.MobileFramework, - MapMobileApp(config.GetProperty("mobileFramework").GetString())); - activityData.Add(ActivityPropertyNameConstants.HasPublicWebsite, - config.GetProperty("publicWebsite").GetBoolean()); - activityData.Add(ActivityPropertyNameConstants.IncludeTests, - config.GetProperty("includeTests").GetBoolean()); - activityData.Add(ActivityPropertyNameConstants.MultiTenancy, - config.GetProperty("multiTenancy").GetBoolean()); - activityData.Add(ActivityPropertyNameConstants.DynamicLocalization, - config.GetProperty("dynamicLocalization").GetBoolean()); - activityData.Add(ActivityPropertyNameConstants.KubernetesConfiguration, - config.GetProperty("kubernetesConfiguration").GetBoolean()); - activityData.Add(ActivityPropertyNameConstants.GrafanaDashboard, - config.GetProperty("grafanaDashboard").GetBoolean()); - activityData.Add(ActivityPropertyNameConstants.SocialLogins, - config.GetProperty("socialLogin").GetBoolean()); - } + activityData.Add(ActivityPropertyNameConstants.Template, + MapSolutionTemplate(config.GetProperty("template").GetString())); + activityData.Add(ActivityPropertyNameConstants.CreatedAbpStudioVersion, + config.GetProperty("createdAbpStudioVersion").GetString()!); + activityData.Add(ActivityPropertyNameConstants.IsTiered, config.GetProperty("Tiered").GetBoolean()); + activityData.Add(ActivityPropertyNameConstants.UiFramework, + MapUiFramework(config.GetProperty("uiFramework").GetString())); + activityData.Add(ActivityPropertyNameConstants.DatabaseProvider, + MapDatabaseProvider(config.GetProperty("databaseProvider").GetString())); + activityData.Add(ActivityPropertyNameConstants.DatabaseManagementSystem, + MapDbms(config.GetProperty("databaseManagementSystem").GetString())); + activityData.Add(ActivityPropertyNameConstants.IsSeparateTenantSchema, + config.GetProperty("separateTenantSchema").GetBoolean()); + activityData.Add(ActivityPropertyNameConstants.Theme, + MapUiTheme(config.GetProperty("theme").GetString())); + activityData.Add(ActivityPropertyNameConstants.ThemeStyle, + MapUiThemeStyle(config.GetProperty("themeStyle").GetString())); + activityData.Add(ActivityPropertyNameConstants.MobileFramework, + MapMobileApp(config.GetProperty("mobileFramework").GetString())); + activityData.Add(ActivityPropertyNameConstants.HasPublicWebsite, + config.GetProperty("publicWebsite").GetBoolean()); + activityData.Add(ActivityPropertyNameConstants.IncludeTests, + config.GetProperty("includeTests").GetBoolean()); + activityData.Add(ActivityPropertyNameConstants.MultiTenancy, + config.GetProperty("multiTenancy").GetBoolean()); + activityData.Add(ActivityPropertyNameConstants.DynamicLocalization, + config.GetProperty("dynamicLocalization").GetBoolean()); + activityData.Add(ActivityPropertyNameConstants.KubernetesConfiguration, + config.GetProperty("kubernetesConfiguration").GetBoolean()); + activityData.Add(ActivityPropertyNameConstants.GrafanaDashboard, + config.GetProperty("grafanaDashboard").GetBoolean()); + activityData.Add(ActivityPropertyNameConstants.SocialLogins, + config.GetProperty("socialLogin").GetBoolean()); + } - var modules = new List(); + var modules = new List(); - if (root.TryGetProperty("modules", out var modulesElement) && - modulesElement.ValueKind == JsonValueKind.Object) + if (root.TryGetProperty("modules", out var modulesElement) && + modulesElement.ValueKind == JsonValueKind.Object) + { + foreach (var moduleProperty in modulesElement.EnumerateObject()) { - foreach (var moduleProperty in modulesElement.EnumerateObject()) + var name = moduleProperty.Name; + if (!moduleProperty.Value.TryGetProperty("path", out var pathElement)) { - var name = moduleProperty.Name; - if (!moduleProperty.Value.TryGetProperty("path", out var pathElement)) - { - continue; - } + continue; + } - var path = pathElement.GetString(); - if (path.IsNullOrEmpty() || !File.Exists(path)) - { - continue; - } + var path = pathElement.GetString(); + if (path.IsNullOrEmpty() || !File.Exists(path)) + { + continue; + } + + var moduleJson = File.ReadAllText(path); + using var moduleDoc = JsonDocument.Parse(moduleJson); - var moduleJson = File.ReadAllText(path); - using var moduleDoc = JsonDocument.Parse(moduleJson); + if (!moduleDoc.RootElement.TryGetProperty("imports", out var importsElement) || + importsElement.ValueKind != JsonValueKind.Object) + { + continue; + } - if (!moduleDoc.RootElement.TryGetProperty("imports", out var importsElement) || - importsElement.ValueKind != JsonValueKind.Object) + foreach (var importProperty in importsElement.EnumerateObject()) + { + var importValue = importProperty.Value; + + var version = importValue.GetProperty("version").GetString(); + var creationTime = importValue.TryGetProperty("creationTime", out var ct) + ? DateTimeOffset.Parse(ct.GetString()!) + : (DateTimeOffset?)null; + + if (modules.Any(x => x.ModuleName == name && x.Version == version)) { continue; } - foreach (var importProperty in importsElement.EnumerateObject()) + modules.Add(new SolutionModuleInstallationInfo { - var importValue = importProperty.Value; - - var version = importValue.GetProperty("version").GetString(); - var creationTime = importValue.TryGetProperty("creationTime", out var ct) - ? DateTimeOffset.Parse(ct.GetString()!) - : (DateTimeOffset?)null; - - if (modules.Any(x => x.ModuleName == name && x.Version == version)) - { - continue; - } - - modules.Add(new SolutionModuleInstallationInfo - { - ModuleName = name, Version = version, InstallationTime = creationTime - }); - } + ModuleName = name, Version = version, InstallationTime = creationTime + }); } - - activityData.Add(ActivityPropertyNameConstants.InstalledModules, modules); } + + activityData.Add(ActivityPropertyNameConstants.InstalledModules, modules); } } } diff --git a/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/Activity/ActivityPropertyNameConstants.cs b/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/Activity/ActivityPropertyNameConstants.cs index e772463dcc..56aef26a46 100644 --- a/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/Activity/ActivityPropertyNameConstants.cs +++ b/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/Activity/ActivityPropertyNameConstants.cs @@ -36,7 +36,6 @@ public static class ActivityPropertyNameConstants public const string GrafanaDashboard = nameof(GrafanaDashboard); public const string SocialLogins = nameof(SocialLogins); public const string InstalledModules = nameof(InstalledModules); - public const string ProjectAssemblyForScan = nameof(ProjectAssemblyForScan); public const string SolutionPath = nameof(SolutionPath); public const string Assembly = nameof(Assembly); } \ No newline at end of file diff --git a/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/Activity/IActivityDataProvider.cs b/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/Activity/IActivityDataProvider.cs index afd79b7540..de3a671365 100644 --- a/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/Activity/IActivityDataProvider.cs +++ b/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/Activity/IActivityDataProvider.cs @@ -1,9 +1,13 @@ -using System.Threading; +using System.Reflection; +using System.Threading; using System.Threading.Tasks; namespace Volo.Abp.Telemetry.Activity; public interface IActivityDataProvider { - Task AddExtraInformationAsync(ActivityData activityData, CancellationToken cancellationToken = default); + Task AddDeviceInformationAsync(ActivityData activityData, CancellationToken cancellationToken = default); + void AddApplicationInformation(ActivityData activityData, Assembly assembly); + + Task AddSolutionInformationAsync(ActivityData activityData, CancellationToken cancellationToken = default); } \ No newline at end of file diff --git a/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/ApplicationInfoProvider.cs b/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/ApplicationInfoProvider.cs index 2d577189f6..76b84e3f82 100644 --- a/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/ApplicationInfoProvider.cs +++ b/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/ApplicationInfoProvider.cs @@ -7,7 +7,7 @@ namespace Volo.Abp.Telemetry; public class ApplicationInfoProvider : ISingletonDependency { - public ApplicationInfo Scan(Assembly assembly) + public ApplicationInfo ExtractApplicationInfo(Assembly assembly) { var types = assembly.GetTypes(); diff --git a/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/TelemetryDataSender.cs b/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/TelemetryDataSender.cs index cf71614035..5066b49716 100644 --- a/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/TelemetryDataSender.cs +++ b/framework/src/Volo.Abp.Core/Volo/Abp/Telemetry/TelemetryDataSender.cs @@ -3,8 +3,10 @@ using System.IO; using System.Net.Http; using System.Net.Http.Headers; using System.Net.Mime; +using System.Reflection; using System.Text; using System.Text.Json; +using System.Threading; using System.Threading.Tasks; using Shared; using Volo.Abp.DependencyInjection; @@ -38,7 +40,7 @@ public class TelemetryDataSender : ITelemetryDataSender , IScopedDependency if (activities.Count > 0) { - await _activityDataProvider.AddExtraInformationAsync(activities[0]); + await AddExtraInformationAsync(activities[0]); foreach (var activity in activities) { await httpClient.PostAsync(ApiUrl, @@ -48,7 +50,47 @@ public class TelemetryDataSender : ITelemetryDataSender , IScopedDependency await _activityStorage.MarkActivitiesAsSentAsync(); } } - + + private async Task AddExtraInformationAsync(ActivityData activityData) + { + try + { + var (isFirstSession, sessionId) = await _activityStorage.GetOrCreateSessionInfoAsync(); + + activityData.Add(ActivityPropertyNameConstants.SessionId, sessionId); + activityData.Add(ActivityPropertyNameConstants.IsFirstSession, isFirstSession); + + var lastDeviceInfoSendTime = await _activityStorage.GetLastDeviceInfoSendTimeAsync(); + + if (lastDeviceInfoSendTime is null || DateTimeOffset.UtcNow - lastDeviceInfoSendTime > TimeSpan.FromDays(7)) + { + await _activityDataProvider.AddDeviceInformationAsync(activityData); + await _activityStorage.MarkDeviceInfoAsSentAsync(); + + } + + if (activityData.TryGetValue(ActivityPropertyNameConstants.Assembly, out var assemblyLocation)) + { + _activityDataProvider.AddApplicationInformation(activityData, Assembly.LoadFrom((string) assemblyLocation)); + } + + if (activityData.TryGetValue(ActivityPropertyNameConstants.SolutionPath, out var path)) + { + var solutionPath = path as string; + if (string.IsNullOrEmpty(solutionPath) || !File.Exists(solutionPath)) + { + return; + } + + await _activityDataProvider.AddSolutionInformationAsync(activityData); + } + + } + catch + { + //ignored + } + } private static void AddAbpAuthenticationTokenAsync(HttpClient httpClient) { if (!File.Exists(AbpTelemetryPaths.AccessToken))