import type { ChargingStation } from '../../src/charging-station/ChargingStation.js'
import { AvailabilityType, RegistrationStatusEnumType } from '../../src/types/index.js'
-import { withMockTimers } from '../helpers/TestLifecycleHelpers.js'
+import { standardCleanup, withMockTimers } from '../helpers/TestLifecycleHelpers.js'
import { cleanupChargingStation, createMockChargingStation } from './ChargingStationTestUtils.js'
// Alias for tests that reference createRealChargingStation
station = undefined
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
station = undefined
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
station = undefined
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
station = undefined
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
// Assert
const parsed = mocks.webSocket.getSentMessagesAsJson()
expect(parsed.length).toBe(1)
- expect(parsed[0]).toEqual([2, 'uuid-1', 'Heartbeat', {}])
+ expect(parsed[0]).toStrictEqual([2, 'uuid-1', 'Heartbeat', {}])
})
await it('should clear captured messages via clearMessages()', () => {
station = undefined
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
import type { ChargingStation } from '../../src/charging-station/ChargingStation.js'
import { RegistrationStatusEnumType } from '../../src/types/index.js'
+import { standardCleanup } from '../helpers/TestLifecycleHelpers.js'
import { cleanupChargingStation, createMockChargingStation } from './ChargingStationTestUtils.js'
// Alias for tests that reference createRealChargingStation
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
station = undefined
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
station = undefined
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
station = undefined
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
station = undefined
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
station = undefined
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
import type { ChargingStation } from '../../src/charging-station/ChargingStation.js'
+import { standardCleanup } from '../helpers/TestLifecycleHelpers.js'
import { cleanupChargingStation, createMockChargingStation } from './ChargingStationTestUtils.js'
await describe('ChargingStation Lifecycle', async () => {
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
import type { ChargingStation } from '../../src/charging-station/ChargingStation.js'
import { RegistrationStatusEnumType } from '../../src/types/index.js'
+import { standardCleanup } from '../helpers/TestLifecycleHelpers.js'
import { cleanupChargingStation, createMockChargingStation } from './ChargingStationTestUtils.js'
await describe('ChargingStation Error Recovery and Resilience', async () => {
})
afterEach(() => {
+ standardCleanup()
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
if (station != null) {
cleanupChargingStation(station)
})
afterEach(() => {
+ standardCleanup()
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
if (station != null) {
cleanupChargingStation(station)
import type { ChargingStation } from '../../src/charging-station/ChargingStation.js'
-import { withMockTimers } from '../helpers/TestLifecycleHelpers.js'
+import { standardCleanup, withMockTimers } from '../helpers/TestLifecycleHelpers.js'
import { cleanupChargingStation, createMockChargingStation } from './ChargingStationTestUtils.js'
await describe('ChargingStation Transaction Management', async () => {
station = undefined
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
station = undefined
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
station = undefined
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
station = undefined
})
afterEach(() => {
+ standardCleanup()
if (station != null) {
cleanupChargingStation(station)
}
// Store some data in cache
mocks1.idTagsCache.setIdTags('test-file.json', ['tag1', 'tag2'])
- expect(mocks1.idTagsCache.getIdTags('test-file.json')).toEqual(['tag1', 'tag2'])
+ expect(mocks1.idTagsCache.getIdTags('test-file.json')).toStrictEqual(['tag1', 'tag2'])
// Cleanup first station
cleanupChargingStation(result1.station)
HashAlgorithmEnumType,
InstallCertificateUseEnumType,
} from '../../../../src/types/index.js'
+import { standardCleanup } from '../../../helpers/TestLifecycleHelpers.js'
const TEST_STATION_HASH_ID = 'test-station-hash-12345'
const TEST_CERT_TYPE = InstallCertificateUseEnumType.CSMSRootCertificate
force: true,
recursive: true,
})
+ standardCleanup()
})
await describe('storeCertificate', async () => {
} from '../../../../src/types/index.js'
import { StandardParametersKey } from '../../../../src/types/ocpp/Configuration.js'
import { Constants } from '../../../../src/utils/index.js'
+import { standardCleanup } from '../../../../tests/helpers/TestLifecycleHelpers.js'
import { createChargingStation } from '../../../ChargingStationFactory.js'
import {
TEST_CHARGE_POINT_MODEL,
// Reset singleton state after each test to ensure test isolation
afterEach(() => {
+ standardCleanup()
OCPP20VariableManager.getInstance().resetRuntimeOverrides()
})
const types =
heartbeatEntry.variableAttribute?.map((a: { type?: string; value?: string }) => a.type) ??
[]
- expect(types).toEqual([AttributeEnumType.Actual])
+ expect(types).toStrictEqual([AttributeEnumType.Actual])
}
// Boolean variable (AuthorizeRemoteStart) should only include Actual
const authorizeRemoteStartEntry = reportData.find(
authorizeRemoteStartEntry.variableAttribute?.map(
(a: { type?: string; value?: string }) => a.type
) ?? []
- expect(types).toEqual([AttributeEnumType.Actual])
+ expect(types).toStrictEqual([AttributeEnumType.Actual])
}
})
ReasonCodeEnumType,
} from '../../../../src/types/index.js'
import { Constants } from '../../../../src/utils/index.js'
+import { standardCleanup } from '../../../../tests/helpers/TestLifecycleHelpers.js'
import { createChargingStation } from '../../../ChargingStationFactory.js'
import {
TEST_CHARGING_STATION_BASE_NAME,
// Reset singleton state after each test to ensure test isolation
afterEach(() => {
+ standardCleanup()
OCPP20VariableManager.getInstance().resetRuntimeOverrides()
})
type OCPP20IdTokenType,
} from '../../../../src/types/ocpp/2.0/Transaction.js'
import { OCPPVersion } from '../../../../src/types/ocpp/OCPPVersion.js'
+import { standardCleanup } from '../../../../tests/helpers/TestLifecycleHelpers.js'
await describe('G03 - Remote Start Pre-Authorization', async () => {
let service: OCPP20IncomingRequestService | undefined
})
afterEach(() => {
- // Reset service and mock charging station state
+ standardCleanup()
mockChargingStation = undefined
service = undefined
})
OCPP20IdTokenEnumType,
} from '../../../../src/types/ocpp/2.0/Transaction.js'
import { Constants } from '../../../../src/utils/index.js'
+import { standardCleanup } from '../../../../tests/helpers/TestLifecycleHelpers.js'
import { createChargingStation } from '../../../ChargingStationFactory.js'
import { TEST_CHARGING_STATION_BASE_NAME } from '../../ChargingStationTestConstants.js'
import { createMockAuthService } from '../auth/helpers/MockFactories.js'
})
afterEach(() => {
+ standardCleanup()
OCPPAuthServiceFactory.clearAllInstances()
})
OCPP20ReasonEnumType,
} from '../../../../src/types/ocpp/2.0/Transaction.js'
import { Constants } from '../../../../src/utils/index.js'
+import { standardCleanup } from '../../../../tests/helpers/TestLifecycleHelpers.js'
import { createChargingStation } from '../../../ChargingStationFactory.js'
import { TEST_CHARGING_STATION_BASE_NAME } from '../../ChargingStationTestConstants.js'
import { createMockAuthService } from '../auth/helpers/MockFactories.js'
})
afterEach(() => {
+ standardCleanup()
OCPPAuthServiceFactory.clearAllInstances()
})
expect(Object.values(RequestStartStopStatusEnumType)).toContain(response.status)
// OCPP 2.0 RequestStopTransaction response should only contain status
- expect(Object.keys(response as object)).toEqual(['status'])
+ expect(Object.keys(response as object)).toStrictEqual(['status'])
})
await it('should handle custom data in request payload', async () => {
SetVariableStatusEnumType,
} from '../../../../src/types/index.js'
import { Constants } from '../../../../src/utils/index.js'
+import { standardCleanup } from '../../../../tests/helpers/TestLifecycleHelpers.js'
import { createChargingStation } from '../../../ChargingStationFactory.js'
import {
TEST_CHARGING_STATION_BASE_NAME,
// Reset singleton state after each test to ensure test isolation
afterEach(() => {
+ standardCleanup()
OCPP20VariableManager.getInstance().resetRuntimeOverrides()
})
)
// All payloads should be identical empty objects
- expect(payload1).toEqual(payload2)
- expect(payload2).toEqual(payload3)
+ expect(payload1).toStrictEqual(payload2)
+ expect(payload2).toStrictEqual(payload3)
expect(JSON.stringify(payload1)).toBe('{}')
expect(JSON.stringify(payload2)).toBe('{}')
expect(JSON.stringify(payload3)).toBe('{}')
// According to OCPP 2.0 specification, HeartBeat request should be an empty object
// This validates compliance with the official OCPP 2.0 standard
expect(payload).toBeDefined()
- expect(payload).toEqual({})
+ expect(payload).toStrictEqual({})
expect(has('constructor', payload)).toBe(false)
// Ensure it's a plain object and not an instance of another type
expect(payload.requestId).toBe(456)
expect(payload.seqNo).toBe(1)
expect(payload.tbc).toBe(false)
- expect(payload.reportData).toEqual(reportData)
+ expect(payload.reportData).toStrictEqual(reportData)
expect(Array.isArray(payload.reportData)).toBe(true)
expect(payload.reportData).toHaveLength(1)
})
expect(payload.requestId).toBe(789)
expect(payload.seqNo).toBe(2)
expect(payload.tbc).toBe(true)
- expect(payload.reportData).toEqual(reportData)
+ expect(payload.reportData).toStrictEqual(reportData)
expect(Array.isArray(payload.reportData)).toBe(true)
expect(payload.reportData).toHaveLength(3)
})
expect(payload.requestId).toBe(999)
expect(payload.seqNo).toBe(0)
expect(payload.tbc).toBe(true)
- expect(payload.reportData).toEqual(reportData)
+ expect(payload.reportData).toStrictEqual(reportData)
expect(Array.isArray(payload.reportData)).toBe(true)
expect(payload.reportData).toHaveLength(1)
})
expect(payload.requestId).toBe(100)
expect(payload.seqNo).toBe(0)
expect(payload.tbc).toBe(false)
- expect(payload.reportData).toEqual([])
+ expect(payload.reportData).toStrictEqual([])
expect(Array.isArray(payload.reportData)).toBe(true)
expect(payload.reportData).toHaveLength(0)
})
const expectedKeys = ['generatedAt', 'reportData', 'requestId', 'seqNo', 'tbc']
const actualKeys = Object.keys(payload as object).sort()
expectedKeys.sort()
- expect(actualKeys).toEqual(expectedKeys)
+ expect(actualKeys).toStrictEqual(expectedKeys)
})
})
expect(cachedResult).toBeDefined()
expect(cachedResult?.status).toBe(AuthorizationStatus.ACCEPTED)
- expect(cachedResult?.timestamp).toEqual(mockResult.timestamp)
+ expect(cachedResult?.timestamp).toStrictEqual(mockResult.timestamp)
})
await it('should track cache hits in statistics', async () => {
import { AuthComponentFactory } from '../../../../../src/charging-station/ocpp/auth/factories/AuthComponentFactory.js'
import { OCPPVersion } from '../../../../../src/types/ocpp/OCPPVersion.js'
import { createChargingStation } from '../../../../ChargingStationFactory.js'
+import { standardCleanup } from '../../../../helpers/TestLifecycleHelpers.js'
await describe('AuthComponentFactory', async () => {
afterEach(() => {
- // Cleanup handled by test isolation - each test creates its own instances
+ standardCleanup()
})
await describe('createAdapters', async () => {
import { OCPPAuthServiceFactory } from '../../../../../src/charging-station/ocpp/auth/services/OCPPAuthServiceFactory.js'
import { OCPPVersion } from '../../../../../src/types/ocpp/OCPPVersion.js'
+import { standardCleanup } from '../../../../helpers/TestLifecycleHelpers.js'
import { createMockAuthServiceTestStation } from '../helpers/MockFactories.js'
await describe('OCPPAuthServiceFactory', async () => {
// Clear all cached instances after each test to ensure test isolation
afterEach(() => {
OCPPAuthServiceFactory.clearAllInstances()
+ standardCleanup()
})
await describe('getInstance', async () => {
type UnifiedIdentifier,
} from '../../../../../src/charging-station/ocpp/auth/types/AuthTypes.js'
import { OCPPVersion } from '../../../../../src/types/ocpp/OCPPVersion.js'
+import { standardCleanup } from '../../../../helpers/TestLifecycleHelpers.js'
import { createMockAuthServiceTestStation } from '../helpers/MockFactories.js'
await describe('OCPPAuthServiceImpl', async () => {
afterEach(() => {
- // Cleanup handled by test isolation - each test creates its own mock station
+ standardCleanup()
})
await describe('constructor', async () => {
const request = AuthHelpers.createAuthRequest(identifier, context, undefined, metadata)
- expect(request.metadata).toEqual({ source: 'test' })
+ expect(request.metadata).toStrictEqual({ source: 'test' })
})
})
expect(result.status).toBe(AuthorizationStatus.EXPIRED)
expect(result.method).toBe(AuthenticationMethod.REMOTE_AUTHORIZATION)
- expect(result.additionalInfo).toEqual({ reason: 'Token expired on 2024-01-01' })
+ expect(result.additionalInfo).toStrictEqual({ reason: 'Token expired on 2024-01-01' })
})
})
expect(merged?.status).toBe(AuthorizationStatus.BLOCKED)
expect(merged?.method).toBe(AuthenticationMethod.LOCAL_LIST)
expect(merged?.isOffline).toBe(true)
- expect(merged?.additionalInfo).toEqual({
+ expect(merged?.additionalInfo).toStrictEqual({
attemptedMethods: 'LocalList, RemoteAuthorization',
totalAttempts: 2,
})
const sanitized = AuthHelpers.sanitizeForLogging(result)
- expect(sanitized).toEqual({
+ expect(sanitized).toStrictEqual({
hasExpiryDate: true,
hasGroupId: true,
hasPersonalMessage: true,
const sanitized = AuthHelpers.sanitizeForLogging(result)
- expect(sanitized).toEqual({
+ expect(sanitized).toStrictEqual({
hasExpiryDate: false,
hasGroupId: false,
hasPersonalMessage: false,
expect(res.body).toBeDefined()
const parsedBody = JSON.parse(res.body ?? '{}') as Record<string, unknown>
expect(parsedBody.status).toBe('success')
- expect(parsedBody.hashIdsSucceeded).toEqual(['station-1', 'station-2'])
+ expect(parsedBody.hashIdsSucceeded).toStrictEqual(['station-1', 'station-2'])
})
await it('should include error details in failure response', () => {
const parsedBody = JSON.parse(res.body ?? '{}') as Record<string, unknown>
expect(parsedBody.status).toBe('failure')
expect(parsedBody.errorMessage).toBe('Test error')
- expect(parsedBody.hashIdsFailed).toEqual(['station-1'])
+ expect(parsedBody.hashIdsFailed).toStrictEqual(['station-1'])
})
await it('should create server with valid HTTP configuration', () => {
await it('should generate valid UUIDs and validate them correctly', () => {
const uuid = generateUUID()
expect(uuid).toBeDefined()
- expect(uuid.length).toEqual(36)
+ expect(uuid.length).toStrictEqual(36)
expect(validateUUID(uuid)).toBe(true)
expect(validateUUID('abcdef00-0000-4000-9000-000000000000')).toBe(true)
expect(validateUUID('abcdef00-0000-4000-a000-000000000000')).toBe(true)
expect(convertToInt(null)).toBe(0)
expect(convertToInt(0)).toBe(0)
const randomInteger = randomInt(Constants.MAX_RANDOM_INTEGER)
- expect(convertToInt(randomInteger)).toEqual(randomInteger)
+ expect(convertToInt(randomInteger)).toStrictEqual(randomInteger)
expect(convertToInt('-1')).toBe(-1)
expect(convertToInt('1')).toBe(1)
expect(convertToInt('1.1')).toBe(1)
expect(convertToFloat(null)).toBe(0)
expect(convertToFloat(0)).toBe(0)
const randomFloat = getRandomFloat()
- expect(convertToFloat(randomFloat)).toEqual(randomFloat)
+ expect(convertToFloat(randomFloat)).toStrictEqual(randomFloat)
expect(convertToFloat('-1')).toBe(-1)
expect(convertToFloat('1')).toBe(1)
expect(convertToFloat('1.1')).toBe(1.1)
expect(typeof randomFloat === 'number').toBe(true)
expect(randomFloat).toBeGreaterThanOrEqual(0)
expect(randomFloat).toBeLessThanOrEqual(Number.MAX_VALUE)
- expect(randomFloat).not.toEqual(getRandomFloat())
+ expect(randomFloat).not.toStrictEqual(getRandomFloat())
expect(() => getRandomFloat(0, 1)).toThrow(new RangeError('Invalid interval'))
expect(() => getRandomFloat(Number.POSITIVE_INFINITY, Number.NEGATIVE_INFINITY)).toThrow(
new RangeError('Invalid interval')
extractTimeSeriesValues(
new CircularBuffer<TimestampedData>(Array, Constants.DEFAULT_CIRCULAR_BUFFER_CAPACITY)
)
- ).toEqual([])
+ ).toStrictEqual([])
const circularBuffer = new CircularBuffer<TimestampedData>(
Array,
Constants.DEFAULT_CIRCULAR_BUFFER_CAPACITY
circularBuffer.push({ timestamp: Date.now(), value: 1.1 })
circularBuffer.push({ timestamp: Date.now(), value: 2.2 })
circularBuffer.push({ timestamp: Date.now(), value: 3.3 })
- expect(extractTimeSeriesValues(circularBuffer)).toEqual([1.1, 2.2, 3.3])
+ expect(extractTimeSeriesValues(circularBuffer)).toStrictEqual([1.1, 2.2, 3.3])
})
await it('should correctly identify async functions from other types', () => {