// Copyright (c) 2023, the Dart project authors. Please see the AUTHORS file // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. import 'dart:mirrors'; import 'package:test/test.dart'; import 'package:unified_analytics/src/enums.dart'; import 'package:unified_analytics/src/event.dart'; import 'package:unified_analytics/unified_analytics.dart'; void main() { test('Event.analysisStatistics constructed', () { Event generateEvent() => Event.analysisStatistics( workingDuration: 'workingDuration', withFineDependencies: false, changedFileEventCount: 1, removedFileEventCount: 2, changedFileUniqueCount: 3, removedFileUniqueCount: 4, immediateFileCountPercentiles: 'immediateFileCountPercentiles', immediateFileLineCountPercentiles: 'immediateFileLineCountPercentiles', transitiveFileCountPercentiles: 'transitiveFileCountPercentiles', transitiveFileLineCountPercentiles: 'transitiveFileLineCountPercentiles', produceErrorsPotentialFileCount: 10, produceErrorsPotentialFileLineCount: 11, produceErrorsActualFileCount: 12, produceErrorsActualFileLineCount: 13, produceErrorsDurationMs: 14, produceErrorsElementsDurationMs: 15, libraryDiagnosticsBundleFailures: 'id1:1,id2:2', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.analysisStatistics); expect(constructedEvent.eventData['workingDuration'], 'workingDuration'); expect(constructedEvent.eventData['withFineDependencies'], false); expect(constructedEvent.eventData['changedFileEventCount'], 1); expect(constructedEvent.eventData['removedFileEventCount'], 2); expect(constructedEvent.eventData['changedFileUniqueCount'], 3); expect(constructedEvent.eventData['removedFileUniqueCount'], 4); expect(constructedEvent.eventData['immediateFileCountPercentiles'], 'immediateFileCountPercentiles'); expect(constructedEvent.eventData['immediateFileLineCountPercentiles'], 'immediateFileLineCountPercentiles'); expect(constructedEvent.eventData['transitiveFileCountPercentiles'], 'transitiveFileCountPercentiles'); expect(constructedEvent.eventData['transitiveFileLineCountPercentiles'], 'transitiveFileLineCountPercentiles'); expect(constructedEvent.eventData['produceErrorsPotentialFileCount'], 10); expect( constructedEvent.eventData['produceErrorsPotentialFileLineCount'], 11); expect(constructedEvent.eventData['produceErrorsActualFileCount'], 12); expect(constructedEvent.eventData['produceErrorsActualFileLineCount'], 13); expect(constructedEvent.eventData['produceErrorsDurationMs'], 14); expect(constructedEvent.eventData['produceErrorsElementsDurationMs'], 15); expect( constructedEvent.eventData['libraryDiagnosticsBundleFailures'], 'id1:1,id2:2', ); expect(constructedEvent.eventData.length, 17); }); test('Event.analyticsCollectionEnabled constructed', () { Event generateEvent() => Event.analyticsCollectionEnabled(status: false); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.analyticsCollectionEnabled); expect(constructedEvent.eventData['status'], false); expect(constructedEvent.eventData.length, 1); }); test('Event.clientNotification constructed', () { Event generateEvent() => Event.clientNotification( duration: 'duration', latency: 'latency', method: 'method', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.clientNotification); expect(constructedEvent.eventData['duration'], 'duration'); expect(constructedEvent.eventData['latency'], 'latency'); expect(constructedEvent.eventData['method'], 'method'); expect(constructedEvent.eventData.length, 3); }); test('Event.clientRequest constructed', () { Event generateEvent() => Event.clientRequest( duration: 'duration', latency: 'latency', method: 'method', added: 'added', excluded: 'excluded', files: 'files', included: 'included', openWorkspacePaths: 'openWorkspacePaths', removed: 'removed', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.clientRequest); expect(constructedEvent.eventData['duration'], 'duration'); expect(constructedEvent.eventData['latency'], 'latency'); expect(constructedEvent.eventData['method'], 'method'); expect(constructedEvent.eventData['added'], 'added'); expect(constructedEvent.eventData['excluded'], 'excluded'); expect(constructedEvent.eventData['files'], 'files'); expect(constructedEvent.eventData['included'], 'included'); expect( constructedEvent.eventData['openWorkspacePaths'], 'openWorkspacePaths'); expect(constructedEvent.eventData['removed'], 'removed'); expect(constructedEvent.eventData.length, 9); }); test('Event.commandExecuted constructed', () { Event generateEvent() => Event.commandExecuted( count: 5, name: 'name', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.commandExecuted); expect(constructedEvent.eventData['count'], 5); expect(constructedEvent.eventData['name'], 'name'); expect(constructedEvent.eventData.length, 2); }); test('Event.contextStructure constructed', () { Event generateEvent() => Event.contextStructure( immediateFileCount: 1, immediateFileLineCount: 2, numberOfContexts: 3, transitiveFileCount: 4, transitiveFileLineCount: 5, transitiveFileUniqueCount: 6, transitiveFileUniqueLineCount: 7, libraryCycleLibraryCounts: 'a', libraryCycleLineCounts: 'b', contextWorkspaceType: '[0,1,2]', numberOfPackagesInWorkspace: '32', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.contextStructure); expect(constructedEvent.eventData['immediateFileCount'], 1); expect(constructedEvent.eventData['immediateFileLineCount'], 2); expect(constructedEvent.eventData['numberOfContexts'], 3); expect(constructedEvent.eventData['transitiveFileCount'], 4); expect(constructedEvent.eventData['transitiveFileLineCount'], 5); expect(constructedEvent.eventData['transitiveFileUniqueCount'], 6); expect(constructedEvent.eventData['transitiveFileUniqueLineCount'], 7); expect(constructedEvent.eventData['libraryCycleLibraryCounts'], 'a'); expect(constructedEvent.eventData['libraryCycleLineCounts'], 'b'); expect(constructedEvent.eventData['contextWorkspaceType'], '[0,1,2]'); expect(constructedEvent.eventData['numberOfPackagesInWorkspace'], '32'); expect(constructedEvent.eventData.length, 11); }); test('Event.dartCliCommandExecuted constructed', () { Event generateEvent() => Event.dartCliCommandExecuted( name: 'name', enabledExperiments: 'enabledExperiments', exitCode: 0, ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.dartCliCommandExecuted); expect(constructedEvent.eventData['name'], 'name'); expect( constructedEvent.eventData['enabledExperiments'], 'enabledExperiments'); expect(constructedEvent.eventData['exitCode'], 0); expect(constructedEvent.eventData.length, 3); }); test('Event.doctorValidatorResult constructed', () { Event generateEvent() => Event.doctorValidatorResult( validatorName: 'validatorName', result: 'success', partOfGroupedValidator: false, doctorInvocationId: 123, statusInfo: 'statusInfo', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.doctorValidatorResult); expect(constructedEvent.eventData['validatorName'], 'validatorName'); expect(constructedEvent.eventData['result'], 'success'); expect(constructedEvent.eventData['partOfGroupedValidator'], false); expect(constructedEvent.eventData['doctorInvocationId'], 123); expect(constructedEvent.eventData['statusInfo'], 'statusInfo'); expect(constructedEvent.eventData.length, 5); }); test('Event.hotReloadTime constructed', () { Event generateEvent() => Event.hotReloadTime(timeMs: 500); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.hotReloadTime); expect(constructedEvent.eventData['timeMs'], 500); expect(constructedEvent.eventData.length, 1); }); test('Event.lintUsageCount constructed', () { Event generateEvent() => Event.lintUsageCount( count: 5, name: 'name', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.lintUsageCount); expect(constructedEvent.eventData['count'], 5); expect(constructedEvent.eventData['name'], 'name'); expect(constructedEvent.eventData.length, 2); }); test('Event.memoryInfo constructed', () { Event generateEvent() => Event.memoryInfo( rss: 4, periodSec: 5, mbPerSec: 5.55, ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.memoryInfo); expect(constructedEvent.eventData['rss'], 4); expect(constructedEvent.eventData['periodSec'], 5); expect(constructedEvent.eventData['mbPerSec'], 5.55); expect(constructedEvent.eventData.length, 3); }); test('Event.pluginRequest constructed', () { Event generateEvent() => Event.pluginRequest( duration: 'duration', method: 'method', pluginId: 'pluginId', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.pluginRequest); expect(constructedEvent.eventData['duration'], 'duration'); expect(constructedEvent.eventData['method'], 'method'); expect(constructedEvent.eventData['pluginId'], 'pluginId'); expect(constructedEvent.eventData.length, 3); }); test('Event.pluginUse constructed', () { Event generateEvent() => Event.pluginUse( count: 5, enabled: 'enabled', pluginId: 'pluginId', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.pluginUse); expect(constructedEvent.eventData['count'], 5); expect(constructedEvent.eventData['enabled'], 'enabled'); expect(constructedEvent.eventData['pluginId'], 'pluginId'); expect(constructedEvent.eventData.length, 3); }); test('Event.pubGet constructed', () { Event generateEvent() => Event.pubGet( packageName: 'packageName', version: 'version', dependencyType: 'dependencyType', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.pubGet); expect(constructedEvent.eventData['packageName'], 'packageName'); expect(constructedEvent.eventData['version'], 'version'); expect(constructedEvent.eventData['dependencyType'], 'dependencyType'); expect(constructedEvent.eventData.length, 3); }); test('Event.serverSession constructed', () { Event generateEvent() => Event.serverSession( clientId: 'clientId', clientVersion: 'clientVersion', duration: 5, flags: 'flags', parameters: 'parameters', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.serverSession); expect(constructedEvent.eventData['clientId'], 'clientId'); expect(constructedEvent.eventData['clientVersion'], 'clientVersion'); expect(constructedEvent.eventData['duration'], 5); expect(constructedEvent.eventData['flags'], 'flags'); expect(constructedEvent.eventData['parameters'], 'parameters'); expect(constructedEvent.eventData.length, 5); }); test('Event.severityAdjustment constructed', () { Event generateEvent() => Event.severityAdjustment( diagnostic: 'diagnostic', adjustments: 'adjustments', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.severityAdjustment); expect(constructedEvent.eventData['diagnostic'], 'diagnostic'); expect(constructedEvent.eventData['adjustments'], 'adjustments'); expect(constructedEvent.eventData.length, 2); }); test('Event.surveyAction constructed', () { Event generateEvent() => Event.surveyAction( surveyId: 'surveyId', status: 'status', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.surveyAction); expect(constructedEvent.eventData['surveyId'], 'surveyId'); expect(constructedEvent.eventData['status'], 'status'); expect(constructedEvent.eventData.length, 2); }); test('Event.surveyShown constructed', () { Event generateEvent() => Event.surveyShown(surveyId: 'surveyId'); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.surveyShown); expect(constructedEvent.eventData['surveyId'], 'surveyId'); expect(constructedEvent.eventData.length, 1); }); test('Event.flutterBuildInfo constructed', () { Event generateEvent() => Event.flutterBuildInfo( label: 'label', buildType: 'buildType', command: 'command', settings: 'settings', error: 'error', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.flutterBuildInfo); expect(constructedEvent.eventData['label'], 'label'); expect(constructedEvent.eventData['buildType'], 'buildType'); expect(constructedEvent.eventData['command'], 'command'); expect(constructedEvent.eventData['settings'], 'settings'); expect(constructedEvent.eventData['error'], 'error'); expect(constructedEvent.eventData.length, 5); }); test('Event.hotRunnerInfo constructed', () { Event generateEvent() => Event.hotRunnerInfo( label: 'label', targetPlatform: 'targetPlatform', sdkName: 'sdkName', emulator: false, fullRestart: true, reason: 'reason', finalLibraryCount: 5, syncedLibraryCount: 6, syncedClassesCount: 7, syncedProceduresCount: 8, syncedBytes: 9, invalidatedSourcesCount: 10, transferTimeInMs: 11, overallTimeInMs: 12, compileTimeInMs: 13, findInvalidatedTimeInMs: 14, scannedSourcesCount: 15, reassembleTimeInMs: 16, reloadVMTimeInMs: 17, ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.hotRunnerInfo); expect(constructedEvent.eventData['label'], 'label'); expect(constructedEvent.eventData['targetPlatform'], 'targetPlatform'); expect(constructedEvent.eventData['sdkName'], 'sdkName'); expect(constructedEvent.eventData['emulator'], false); expect(constructedEvent.eventData['fullRestart'], true); expect(constructedEvent.eventData['reason'], 'reason'); expect(constructedEvent.eventData['finalLibraryCount'], 5); expect(constructedEvent.eventData['syncedLibraryCount'], 6); expect(constructedEvent.eventData['syncedClassesCount'], 7); expect(constructedEvent.eventData['syncedProceduresCount'], 8); expect(constructedEvent.eventData['syncedBytes'], 9); expect(constructedEvent.eventData['invalidatedSourcesCount'], 10); expect(constructedEvent.eventData['transferTimeInMs'], 11); expect(constructedEvent.eventData['overallTimeInMs'], 12); expect(constructedEvent.eventData['compileTimeInMs'], 13); expect(constructedEvent.eventData['findInvalidatedTimeInMs'], 14); expect(constructedEvent.eventData['scannedSourcesCount'], 15); expect(constructedEvent.eventData['reassembleTimeInMs'], 16); expect(constructedEvent.eventData['reloadVMTimeInMs'], 17); expect(constructedEvent.eventData.length, 19); }); test('Event.flutterCommandResult constructed', () { Event generateEvent() => Event.flutterCommandResult( commandPath: 'commandPath', result: 'result', commandHasTerminal: true, maxRss: 123, ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.flutterCommandResult); expect(constructedEvent.eventData['commandPath'], 'commandPath'); expect(constructedEvent.eventData['result'], 'result'); expect(constructedEvent.eventData['commandHasTerminal'], true); expect(constructedEvent.eventData['maxRss'], 123); expect(constructedEvent.eventData.length, 4); }); test('Event.flutterWasmDryRun constructed no findings', () { Event generateEventNoFindings() => Event.flutterWasmDryRun( result: 'success', exitCode: 123, ); final constructedEvent1 = generateEventNoFindings(); expect(generateEventNoFindings, returnsNormally); expect(constructedEvent1.eventName, DashEvent.flutterWasmDryRun); expect(constructedEvent1.eventData['result'], 'success'); expect(constructedEvent1.eventData['exitCode'], 123); expect(constructedEvent1.eventData.length, 2); }); test('Event.flutterWasmDryRun constructed with findings', () { Event generateEventNoFindings() => Event.flutterWasmDryRun( result: 'success', exitCode: 123, ); final constructedEvent1 = generateEventNoFindings(); expect(generateEventNoFindings, returnsNormally); expect(constructedEvent1.eventName, DashEvent.flutterWasmDryRun); expect(constructedEvent1.eventData['result'], 'success'); expect(constructedEvent1.eventData['exitCode'], 123); expect(constructedEvent1.eventData.length, 2); Event generateEventFindings() => Event.flutterWasmDryRun( result: 'success', exitCode: 123, findingsSummary: '1,2,3'); final constructedEvent2 = generateEventFindings(); expect(generateEventFindings, returnsNormally); expect(constructedEvent2.eventName, DashEvent.flutterWasmDryRun); expect(constructedEvent2.eventData['result'], 'success'); expect(constructedEvent2.eventData['exitCode'], 123); expect(constructedEvent2.eventData['findings'], '1,2,3'); expect(constructedEvent2.eventData.length, 3); }); test('Event.flutterWasmDryRunPackage constructed', () { Event generateEvent() => Event.flutterWasmDryRunPackage( result: 'success', exitCode: 123, findingsInfo: { '0': '-ph,pkg1:1.2.3,pkg2:5.4.3', '1': '-p,pkg3:9.2.44,pkg4:6.4.3', }); final constructedEvent1 = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent1.eventName, DashEvent.flutterWasmDryRunPackage); expect(constructedEvent1.eventData['result'], 'success'); expect(constructedEvent1.eventData['exitCode'], 123); expect(constructedEvent1.eventData['0'], '-ph,pkg1:1.2.3,pkg2:5.4.3'); expect(constructedEvent1.eventData['1'], '-p,pkg3:9.2.44,pkg4:6.4.3'); expect(constructedEvent1.eventData.length, 4); }); test('Event.flutterInjectDarwinPlugins constructed', () { Event generateEvent() => Event.flutterInjectDarwinPlugins( platform: 'ios', isModule: true, swiftPackageManagerUsable: true, swiftPackageManagerFeatureEnabled: true, projectDisabledSwiftPackageManager: false, projectHasSwiftPackageManagerIntegration: true, pluginCount: 123, swiftPackageCount: 456, podCount: 678, ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.flutterInjectDarwinPlugins); expect(constructedEvent.eventData['platform'], 'ios'); expect(constructedEvent.eventData['isModule'], isTrue); expect(constructedEvent.eventData['swiftPackageManagerUsable'], isTrue); expect(constructedEvent.eventData['swiftPackageManagerFeatureEnabled'], isTrue); expect(constructedEvent.eventData['projectDisabledSwiftPackageManager'], isFalse); expect( constructedEvent.eventData['projectHasSwiftPackageManagerIntegration'], isTrue); expect(constructedEvent.eventData['pluginCount'], 123); expect(constructedEvent.eventData['swiftPackageCount'], 456); expect(constructedEvent.eventData['podCount'], 678); expect(constructedEvent.eventData.length, 9); }); test('Event.codeSizeAnalysis constructed', () { Event generateEvent() => Event.codeSizeAnalysis(platform: 'platform'); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.codeSizeAnalysis); expect(constructedEvent.eventData['platform'], 'platform'); expect(constructedEvent.eventData.length, 1); }); test('Event.appleUsageEvent constructed', () { Event generateEvent() => Event.appleUsageEvent( workflow: 'workflow', parameter: 'parameter', result: 'result', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.appleUsageEvent); expect(constructedEvent.eventData['workflow'], 'workflow'); expect(constructedEvent.eventData['parameter'], 'parameter'); expect(constructedEvent.eventData['result'], 'result'); expect(constructedEvent.eventData.length, 3); }); test('Event.exception constructed', () { Event generateEvent() => Event.exception( exception: 'exception', data: {'foo': 'bar', 'baz': 1, 'shouldBeRemoved': null}, ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.exception); expect(constructedEvent.eventData['exception'], 'exception'); expect(constructedEvent.eventData['foo'], 'bar'); expect(constructedEvent.eventData['baz'], 1); expect(constructedEvent.eventData.length, 3); }); test('Event.exception constructor works when no data is provided', () { Event generateEvent() => Event.exception( exception: 'exception', ); expect(generateEvent, returnsNormally); }); test('Event.timing constructed', () { Event generateEvent() => Event.timing( workflow: 'workflow', variableName: 'variableName', elapsedMilliseconds: 123, label: 'label', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.timing); expect(constructedEvent.eventData['workflow'], 'workflow'); expect(constructedEvent.eventData['variableName'], 'variableName'); expect(constructedEvent.eventData['elapsedMilliseconds'], 123); expect(constructedEvent.eventData['label'], 'label'); expect(constructedEvent.eventData.length, 4); }); test('Event.commandUsageValues constructed', () { Event generateEvent() => Event.commandUsageValues( workflow: 'workflow', commandHasTerminal: true, buildBundleTargetPlatform: 'buildBundleTargetPlatform', buildBundleIsModule: true, buildAarProjectType: 'buildAarProjectType', buildAarTargetPlatform: 'buildAarTargetPlatform', buildApkTargetPlatform: 'buildApkTargetPlatform', buildApkBuildMode: 'buildApkBuildMode', buildApkSplitPerAbi: true, buildAppBundleTargetPlatform: 'buildAppBundleTargetPlatform', buildAppBundleBuildMode: 'buildAppBundleBuildMode', createProjectType: 'createProjectType', createAndroidLanguage: 'createAndroidLanguage', createIosLanguage: 'createIosLanguage', packagesNumberPlugins: 123, packagesProjectModule: true, packagesAndroidEmbeddingVersion: 'packagesAndroidEmbeddingVersion', runIsEmulator: true, runTargetName: 'runTargetName', runTargetOsVersion: 'runTargetOsVersion', runModeName: 'runModeName', runProjectModule: true, runProjectHostLanguage: 'runProjectHostLanguage', runAndroidEmbeddingVersion: 'runAndroidEmbeddingVersion', runEnableImpeller: true, runIOSInterfaceType: 'runIOSInterfaceType', runIsTest: true, ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.commandUsageValues); expect(constructedEvent.eventData['workflow'], 'workflow'); expect(constructedEvent.eventData['buildBundleTargetPlatform'], 'buildBundleTargetPlatform'); expect(constructedEvent.eventData['buildBundleIsModule'], true); expect(constructedEvent.eventData['buildAarProjectType'], 'buildAarProjectType'); expect(constructedEvent.eventData['buildAarTargetPlatform'], 'buildAarTargetPlatform'); expect(constructedEvent.eventData['buildApkTargetPlatform'], 'buildApkTargetPlatform'); expect( constructedEvent.eventData['buildApkBuildMode'], 'buildApkBuildMode'); expect(constructedEvent.eventData['buildApkSplitPerAbi'], true); expect(constructedEvent.eventData['buildAppBundleTargetPlatform'], 'buildAppBundleTargetPlatform'); expect(constructedEvent.eventData['buildAppBundleBuildMode'], 'buildAppBundleBuildMode'); expect( constructedEvent.eventData['createProjectType'], 'createProjectType'); expect(constructedEvent.eventData['createAndroidLanguage'], 'createAndroidLanguage'); expect( constructedEvent.eventData['createIosLanguage'], 'createIosLanguage'); expect(constructedEvent.eventData['packagesNumberPlugins'], 123); expect(constructedEvent.eventData['packagesProjectModule'], true); expect(constructedEvent.eventData['packagesAndroidEmbeddingVersion'], 'packagesAndroidEmbeddingVersion'); expect(constructedEvent.eventData['runIsEmulator'], true); expect(constructedEvent.eventData['runTargetName'], 'runTargetName'); expect( constructedEvent.eventData['runTargetOsVersion'], 'runTargetOsVersion'); expect(constructedEvent.eventData['runModeName'], 'runModeName'); expect(constructedEvent.eventData['runProjectModule'], true); expect(constructedEvent.eventData['runProjectHostLanguage'], 'runProjectHostLanguage'); expect(constructedEvent.eventData['runAndroidEmbeddingVersion'], 'runAndroidEmbeddingVersion'); expect(constructedEvent.eventData['runEnableImpeller'], true); expect(constructedEvent.eventData['runIOSInterfaceType'], 'runIOSInterfaceType'); expect(constructedEvent.eventData.length, 27); }); test('Event.analyticsException constructed', () { Event generateEvent() => Event.analyticsException( workflow: 'workflow', error: 'error', description: 'description', ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventName, DashEvent.analyticsException); expect(constructedEvent.eventData['workflow'], 'workflow'); expect(constructedEvent.eventData['error'], 'error'); expect(constructedEvent.eventData['description'], 'description'); expect(constructedEvent.eventData.length, 3); }); test('Event.devtoolsEvent constructed', () { Event generateEvent() => Event.devtoolsEvent( screen: 'screen', eventCategory: 'eventCategory', label: 'label', value: 1, userInitiatedInteraction: true, g3Username: 'g3Username', userApp: 'userApp', userBuild: 'userBuild', userPlatform: 'userPlatform', devtoolsPlatform: 'devtoolsPlatform', devtoolsChrome: 'devtoolsChrome', devtoolsVersion: 'devtoolsVersion', ideLaunched: 'ideLaunched', isExternalBuild: 'isExternalBuild', isEmbedded: 'isEmbedded', ideLaunchedFeature: 'ideLaunchedFeature', isWasm: 'true', additionalMetrics: _TestMetrics( stringField: 'test', intField: 100, boolField: false, ), ); final constructedEvent = generateEvent(); expect(generateEvent, returnsNormally); expect(constructedEvent.eventData['screen'], 'screen'); expect(constructedEvent.eventData['eventCategory'], 'eventCategory'); expect(constructedEvent.eventData['label'], 'label'); expect(constructedEvent.eventData['value'], 1); expect(constructedEvent.eventData['userInitiatedInteraction'], true); expect(constructedEvent.eventData['g3Username'], 'g3Username'); expect(constructedEvent.eventData['userApp'], 'userApp'); expect(constructedEvent.eventData['userBuild'], 'userBuild'); expect(constructedEvent.eventData['userPlatform'], 'userPlatform'); expect(constructedEvent.eventData['devtoolsPlatform'], 'devtoolsPlatform'); expect(constructedEvent.eventData['devtoolsChrome'], 'devtoolsChrome'); expect(constructedEvent.eventData['devtoolsVersion'], 'devtoolsVersion'); expect(constructedEvent.eventData['ideLaunched'], 'ideLaunched'); expect(constructedEvent.eventData['isExternalBuild'], 'isExternalBuild'); expect(constructedEvent.eventData['isEmbedded'], 'isEmbedded'); expect( constructedEvent.eventData['ideLaunchedFeature'], 'ideLaunchedFeature', ); expect(constructedEvent.eventData['isWasm'], 'true'); expect(constructedEvent.eventData['stringField'], 'test'); expect(constructedEvent.eventData['intField'], 100); expect(constructedEvent.eventData['boolField'], false); expect(constructedEvent.eventData.containsKey('nullableField'), false); expect(constructedEvent.eventData.length, 20); }); test('Event.dartMCPEvent constructed', () { final event = Event.dartMCPEvent( client: 'test client', clientVersion: '1.0.0', serverVersion: '1.1.0', type: 'some_event', additionalData: _TestMetrics(boolField: true, stringField: 'hello', intField: 1)); expect( event.eventData, equals({ 'client': 'test client', 'clientVersion': '1.0.0', 'serverVersion': '1.1.0', 'type': 'some_event', 'boolField': true, 'stringField': 'hello', 'intField': 1, })); }); test('Confirm all constructors were checked', () { var constructorCount = 0; for (final declaration in reflectClass(Event).declarations.keys) { // Count public constructors but omit private constructors if (declaration.toString().contains('Event.') && !declaration.toString().contains('Event._')) { constructorCount++; } } // Change this integer below if your PR either adds or removes // an Event constructor final eventsAccountedForInTests = 32; expect(eventsAccountedForInTests, constructorCount, reason: 'If you added or removed an event constructor, ' 'ensure you have updated ' '`pkgs/unified_analytics/test/event_test.dart` ' 'to reflect the changes made'); }); test('Serializing event to json successful', () { final event = Event.analyticsException( workflow: 'workflow', error: 'error', description: 'description', ); final expectedResult = '{"eventName":"analytics_exception",' '"eventData":{"workflow":"workflow",' '"error":"error",' '"description":"description"}}'; expect(event.toJson(), expectedResult); }); test('Deserializing string to event successful', () { final eventJson = '{"eventName":"analytics_exception",' '"eventData":{"workflow":"workflow",' '"error":"error",' '"description":"description"}}'; final eventConstructed = Event.fromJson(eventJson); expect(eventConstructed, isNotNull); eventConstructed!; expect(eventConstructed.eventName, DashEvent.analyticsException); expect(eventConstructed.eventData, { 'workflow': 'workflow', 'error': 'error', 'description': 'description', }); }); test('Deserializing string to event unsuccessful for invalid eventName', () { final eventJson = '{"eventName":"NOT_VALID_NAME",' '"eventData":{"workflow":"workflow",' '"error":"error",' '"description":"description"}}'; final eventConstructed = Event.fromJson(eventJson); expect(eventConstructed, isNull); }); test('Deserializing string to event unsuccessful for invalid eventData', () { final eventJson = '{"eventName":"analytics_exception",' '"eventData": "not_valid_event_data"}'; final eventConstructed = Event.fromJson(eventJson); expect(eventConstructed, isNull); }); } final class _TestMetrics extends CustomMetrics { _TestMetrics({ required this.stringField, required this.intField, required this.boolField, }); final String stringField; final int intField; final bool boolField; @override Map toMap() => { 'stringField': stringField, 'intField': intField, 'boolField': boolField, }; }