Files
xamxam/.phpunit.result.cache
Pontoporeia ae66c2baad Integrate Monolog: replace four logging systems with single PSR-3 factory
- Add monolog/monolog dependency (^3.10)  
- Create app/Logger.php central factory with channels: app, admin, error, audit
- Each channel gets RotatingFileHandler (30-day retention) with pass-through LineFormatter
  preserving existing JSON format contracts
- Rewrite AppLogger as thin facade delegating to Logger::get('app')
- Rewrite ErrorHandler::log() to delegate to Logger::get('error')
- Rewrite AdminLogger file output to delegate to Logger::get('admin'), keep DB writes
- Add Monolog file shadow to Audit via Logger::get('audit') (Option A per monolog-plan)
- Log level controlled by LOG_LEVEL env var (defaults: DEBUG in cli-server, WARNING otherwise)
- Graceful NullHandler fallback when log directory is not writable
- Update SystemController LOG_FILES: remove php_error, add app/admin/error/audit
- JSON app logs parsed to readable one-liners in the log viewer
- Remove nginx config tab (parametres + fragment + template + css)
- Friendly empty-state message when app log files don't exist yet (notYet)
- PHP tail fallback when exec() unavailable
- All 228 PHPUnit tests pass, no call sites changed
2026-05-20 12:28:31 +02:00

1 line
15 KiB
Plaintext

{"version":2,"defects":{"CryptoTest::testEncryptDecryptEmptyString":7,"CryptoTest::testDecryptWithTamperedCiphertextReturnsEmpty":7,"EmailObfuscatorTest::testEmailTextReplacesBareEmail":7,"SystemControllerHelpersTest::testHumanBytesOneMB":7,"SystemControllerHelpersTest::testHumanBytesOneGB":7,"CryptoTest::testEncryptEmptyStringProducesCiphertext":7,"DatabaseExtendedTest::testFindOrCreateAuthorCreatesNew":7,"DatabaseExtendedTest::testFindOrCreateAuthorIdempotent":7,"DatabaseExtendedTest::testFindOrCreateAuthorWithEmail":7,"DatabaseExtendedTest::testFindOrCreateAuthorRejectsCSVArtefacts":7,"DatabaseExtendedTest::testDeduplicateLanguagesMergesCaseInsensitiveDupes":7,"RateLimitExtendedTest::testGetRemainingDecrements":7,"RateLimitExtendedTest::testGetRemainingAtLimit":7,"RateLimitExtendedTest::testGetRemainingReturnsZeroAfterExhaustion":7,"RateLimitExtendedTest::testGetResetTimePositiveAfterHits":7,"ThesisCreateValidationTest::testDuplicateTagsAreDeduplicated":8},"times":{"CryptoTest::testEncryptDecryptRoundTrip":0.035,"CryptoTest::testEncryptDecryptWithUnicode":0.002,"CryptoTest::testEncryptDecryptMultiline":0.002,"CryptoTest::testDifferentPlaintextsProduceDifferentCiphertexts":0.002,"CryptoTest::testSamePlaintextProducesDifferentCiphertexts":0.002,"CryptoTest::testIsEncryptedRecognizesEncryptedValue":0.01,"CryptoTest::testIsEncryptedRejectsPlaintext":0.003,"CryptoTest::testIsEncryptedReturnsFalseForEmptyString":0.003,"CryptoTest::testIsEncryptedRejectsInvalidBase64":0.002,"CryptoTest::testEncryptDecryptEmptyString":0.008,"CryptoTest::testDecryptEmptyStringReturnsEmpty":0.002,"CryptoTest::testDecryptInvalidBase64ReturnsInputGracefully":0.002,"CryptoTest::testDecryptTooShortBlobReturnsInputGracefully":0.002,"CryptoTest::testDecryptWithTamperedCiphertextReturnsEmpty":0.002,"CryptoTest::testDecryptValidBlobTamperedTagReturnsEmpty":0.005,"EmailObfuscatorTest::testEncodeContainsNoAtSign":0.015,"EmailObfuscatorTest::testEncodeOutputIsNumericEntities":0.002,"EmailObfuscatorTest::testEmailReturnsObfuscatedAddress":0.002,"EmailObfuscatorTest::testMailtoBuildsCorrectHrefStructure":0.007,"EmailObfuscatorTest::testEmailTextReplacesBareEmail":0.003,"EmailObfuscatorTest::testEmailTextReplacesMultipleEmails":0.004,"EmailObfuscatorTest::testMailtoInTextReplacesMailtoLinks":0.002,"EmailObfuscatorTest::testObfuscateHtmlReplacesAnchorTag":0.003,"EmailObfuscatorTest::testObfuscateHtmlKeepsNonMailtoLinksUnchanged":0.002,"EmailObfuscatorTest::testObfuscateHtmlPreservesCustomLinkText":0.002,"EmailObfuscatorTest::testEmptyStringReturnsEmpty":0.001,"EmailObfuscatorTest::testStringWithNoEmailsIsUnchanged":0.001,"EmailObfuscatorTest::testAlreadyObfuscatedContentIsNotDoubleEncoded":0.002,"EmailObfuscatorTest::testMultipleEmailsInOneString":0.002,"EmailObfuscatorTest::testEmailWithPlusSign":0.011,"StudentEmailTest::testBuildHtmlReturnsNonEmptyString":0.053,"StudentEmailTest::testBuildHtmlContainsKeyFields":0.006,"StudentEmailTest::testBuildHtmlEscapesSpecialCharacters":0.006,"StudentEmailTest::testBuildHtmlHandlesMissingOptionalFields":0.008,"StudentEmailTest::testBuildHtmlHandlesNullFieldsGracefully":0.003,"StudentEmailTest::testBuildHtmlHandlesEmptyArray":0.004,"StudentEmailTest::testBuildHtmlContainsLabelFields":0.005,"SystemControllerHelpersTest::testHumanBytesZero":0.219,"SystemControllerHelpersTest::testHumanBytesBelowOneKB":0.004,"SystemControllerHelpersTest::testHumanBytesOneKB":0.003,"SystemControllerHelpersTest::testHumanBytesOneMB":0.003,"SystemControllerHelpersTest::testHumanBytesOneGB":0.004,"SystemControllerHelpersTest::testHumanBytes1523MB":0.003,"SystemControllerHelpersTest::testHumanBytes2500GB":0.003,"SystemControllerHelpersTest::testDiskColorBelowWarning":0.005,"SystemControllerHelpersTest::testDiskColorWarning":0.005,"SystemControllerHelpersTest::testDiskColorCritical":0.005,"SystemControllerHelpersTest::testLogLineClassCrit":0.003,"SystemControllerHelpersTest::testLogLineClassError":0.003,"SystemControllerHelpersTest::testLogLineClassWarn":0.003,"SystemControllerHelpersTest::testLogLineClassNotice":0.009,"SystemControllerHelpersTest::testLogLineClassHttp500":0.003,"SystemControllerHelpersTest::testLogLineClassHttp300":0.002,"SystemControllerHelpersTest::testLogLineClassDefault":0.003,"SystemControllerHelpersTest::testNginxLineClassComment":0.003,"SystemControllerHelpersTest::testNginxLineClassBlock":0.004,"SystemControllerHelpersTest::testNginxLineClassDirective":0.003,"SystemControllerHelpersTest::testStatusLabelActive":0.004,"SystemControllerHelpersTest::testStatusLabelInactive":0.003,"SystemControllerHelpersTest::testStatusLabelFailed":0.003,"SystemControllerHelpersTest::testStatusLabelWarn":0.004,"SystemControllerHelpersTest::testStatusLabelUnknown":0.003,"SystemControllerHelpersTest::testStatusClassOk":0.005,"SystemControllerHelpersTest::testStatusClassWarn":0.003,"SystemControllerHelpersTest::testStatusClassError":0.009,"SystemControllerHelpersTest::testStatusClassUnknown":0.004,"TfeControllerOgTest::testBuildOgTagsReturnsAllRequiredKeys":0.003,"TfeControllerOgTest::testBuildOgTagsTitleIncludesAuthors":0.006,"TfeControllerOgTest::testBuildOgTagsImageEmptyWhenNoFiles":0.003,"TfeControllerOgTest::testBuildOgTagsImageFromCover":0.003,"TfeControllerOgTest::testBuildOgTagsImageFallbackToFirstImage":0.007,"TfeControllerOgTest::testBuildOgTagsUrlIncludesThesisId":0.004,"TfeControllerOgTest::testBuildOgTagsPublishedTimeFormatted":0.003,"TfeControllerOgTest::testBuildOgTagsPublishedTimeEmptyWhenNoYear":0.007,"TfeControllerOgTest::testBuildMetaDescriptionTruncatesLongSynopsis":0.007,"TfeControllerOgTest::testBuildMetaDescriptionKeepsShortSynopsis":0.011,"TfeControllerOgTest::testBuildMetaDescriptionEmptySynopsisReturnsDefault":0.004,"TfeControllerOgTest::testBuildMetaDescriptionStripsHtmlTags":0.004,"CryptoTest::testEncryptEmptyStringProducesCiphertext":0.003,"DatabaseExtendedTest::testEscapeLikeStringViaSearchConditions":0.003,"DatabaseExtendedTest::testBuildSearchConditionsEmptyParams":0.003,"DatabaseExtendedTest::testBuildSearchConditionsWithQuery":0.002,"DatabaseExtendedTest::testBuildSearchConditionsWithYear":0.002,"DatabaseExtendedTest::testBuildSearchConditionsWithAllFilters":0.002,"DatabaseExtendedTest::testFindDuplicateThesisExactMatch":0.003,"DatabaseExtendedTest::testFindDuplicateThesisMissesDifferentTitle":0.003,"DatabaseExtendedTest::testFindDuplicateThesisMissesDifferentYear":0.008,"DatabaseExtendedTest::testFindDuplicateThesisEmptyAuthorNamesReturnsNull":0.004,"DatabaseExtendedTest::testFindDuplicateThesisEmptyTable":0.004,"DatabaseExtendedTest::testFindDuplicateThesisNearDuplicateByLevenshtein":0.003,"DatabaseExtendedTest::testGenerateThesisIdentifierFirstInYear":0.002,"DatabaseExtendedTest::testGenerateThesisIdentifierIncrementsCorrectly":0.002,"DatabaseExtendedTest::testGenerateThesisIdentifierUsesMaxNotCount":0.002,"DatabaseExtendedTest::testGetCoverPathsForThesesReturnsPaths":0.002,"DatabaseExtendedTest::testGetCoverPathsForThesesReturnsEmptyForUnknownIds":0.009,"DatabaseExtendedTest::testGetCoverPathsForThesesEmptyInputReturnsEmpty":0.005,"DatabaseExtendedTest::testGetCoverPathsForThesesMultipleTheses":0.01,"DatabaseExtendedTest::testFindOrCreateAuthorCreatesNew":0.002,"DatabaseExtendedTest::testFindOrCreateAuthorIdempotent":0.002,"DatabaseExtendedTest::testFindOrCreateAuthorWithEmail":0.007,"DatabaseExtendedTest::testFindOrCreateAuthorRejectsCSVArtefacts":0.003,"DatabaseExtendedTest::testDeduplicateLanguagesMergesCaseInsensitiveDupes":0.003,"DatabaseExtendedTest::testRenameLanguageUpdatesName":0.053,"DatabaseExtendedTest::testMergeLanguageReassignsTheses":0.003,"DatabaseExtendedTest::testRenameTagUpdatesName":0.008,"DatabaseExtendedTest::testMergeTagReassignsTheses":0.003,"RateLimitExtendedTest::testCheckKeyCountsPerKey":0.061,"RateLimitExtendedTest::testCheckKeyDoesNotAffectDefaultCheck":0.004,"RateLimitExtendedTest::testGetRemainingDecrements":0,"RateLimitExtendedTest::testGetRemainingAtLimit":0,"RateLimitExtendedTest::testGetRemainingUsesClientIdentifier":0.001,"RateLimitExtendedTest::testCheckUsesConsistentIdentifier":0,"RateLimitExtendedTest::testGetRemainingReturnsZeroAfterExhaustion":0.003,"RateLimitExtendedTest::testGetResetTimeReturnsZeroWhenNoData":0.007,"RateLimitExtendedTest::testGetResetTimePositiveAfterHits":0.003,"RateLimitExtendedTest::testCleanupRemovesOldFiles":0.003,"ShareLinkExtendedTest::testListActiveReturnsOnlyActiveLinks":0.372,"ShareLinkExtendedTest::testListArchivedReturnsOnlyArchivedLinks":0.295,"ShareLinkExtendedTest::testFindBySlugHit":0.302,"ShareLinkExtendedTest::testFindBySlugMiss":0.002,"ShareLinkExtendedTest::testSetPasswordAndDecryptRoundTrip":0.3,"ShareLinkExtendedTest::testGetDecryptedPasswordOnNonexistentId":0.002,"ShareLinkExtendedTest::testUpdateChangesNameAndExpiration":0.323,"ShareLinkExtendedTest::testUpdateOnlyNameLeavesExpirationUnchanged":0.334,"ShareLinkExtendedTest::testUpdateClearsExpiration":0.326,"ShareLinkExtendedTest::testCreateWithLockedYear":0.312,"ShareLinkExtendedTest::testCreateWithInvalidLockedYearRejected":0.309,"ShareLinkExtendedTest::testUpdateLockedYear":0.33,"ShareLinkExtendedTest::testUpdateClearLockedYear":0.31,"ShareLinkExtendedTest::testIncrementUsage":0.316,"ShareLinkExtendedTest::testCreateDefaultsToTfeWhenInvalidObjet":0.332,"ShareLinkExtendedTest::testCreateAcceptsValidObjet":0.322,"RateLimitExtendedTest::testGetRemainingStartsAtMax":0.002,"RateLimitExtendedTest::testCheckDecrementsRemainingForSameIp":0.003,"RateLimitExtendedTest::testCheckAndCheckKeyAreIndependent":0.002,"RateLimitExtendedTest::testMultipleChecksFromSameClient":0.002,"AutofocusFieldForErrorTest::testCreateAutofocusTitle":1.349,"AutofocusFieldForErrorTest::testCreateAutofocusAuthors":0.002,"AutofocusFieldForErrorTest::testCreateAutofocusSynopsis":0.002,"AutofocusFieldForErrorTest::testCreateAutofocusYear":0.002,"AutofocusFieldForErrorTest::testCreateAutofocusOrientation":0.002,"AutofocusFieldForErrorTest::testCreateAutofocusAP":0.002,"AutofocusFieldForErrorTest::testCreateAutofocusFinality":0.002,"AutofocusFieldForErrorTest::testCreateAutofocusLanguages":0.002,"AutofocusFieldForErrorTest::testCreateAutofocusPromoteur":0.002,"AutofocusFieldForErrorTest::testCreateAutofocusLecteurInterne":0.002,"AutofocusFieldForErrorTest::testCreateAutofocusLecteurExterne":0.001,"AutofocusFieldForErrorTest::testCreateAutofocusFormats":0.002,"AutofocusFieldForErrorTest::testCreateAutofocusLicense":0.002,"AutofocusFieldForErrorTest::testCreateAutofocusUrl":0.002,"AutofocusFieldForErrorTest::testCreateAutofocusTags":0.002,"AutofocusFieldForErrorTest::testCreateAutofocusUnknownErrorReturnsNull":0.007,"AutofocusFieldForErrorTest::testEditAutofocusTitle":0.215,"AutofocusFieldForErrorTest::testEditAutofocusYear":0.003,"AutofocusFieldForErrorTest::testEditAutofocusSynopsis":0.006,"AutofocusFieldForErrorTest::testEditAutofocusAuthors":0.003,"AutofocusFieldForErrorTest::testEditAutofocusUnknownErrorReturnsNull":0.003,"AutofocusFieldForErrorTest::testCreateDoesNotLeakEditFieldNames":0.004,"ThesisCreateValidationTest::testValidSubmissionReturnsCleanedData":0.011,"ThesisCreateValidationTest::testMissingTitleThrowsException":0.006,"ThesisCreateValidationTest::testMissingAuthorsThrowsException":0.006,"ThesisCreateValidationTest::testMissingSynopsisThrowsException":0.004,"ThesisCreateValidationTest::testMissingOrientationInNonAdminModeThrowsException":0.014,"ThesisCreateValidationTest::testMissingAPProgramInNonAdminModeThrowsException":0.013,"ThesisCreateValidationTest::testMissingFinalityInNonAdminModeThrowsException":0.006,"ThesisCreateValidationTest::testInvalidYearFormatRejected":0.006,"ThesisCreateValidationTest::testYearZeroRejected":0.005,"ThesisCreateValidationTest::testYearBefore2000Rejected":0.005,"ThesisCreateValidationTest::testFarFutureYearRejected":0.006,"ThesisCreateValidationTest::testCurrentYearAccepted":0.005,"ThesisCreateValidationTest::testMalformedUrlRejected":0.003,"ThesisCreateValidationTest::testValidUrlAccepted":0.002,"ThesisCreateValidationTest::testDuplicateTagsAreDeduplicated":0.005,"ThesisCreateValidationTest::testMaxTenKeywordsEnforced":0.004,"ThesisCreateValidationTest::testXssPayloadStrippedFromTitle":0.007,"ThesisCreateValidationTest::testHtmlInSynopsisStripped":0.005,"ThesisCreateValidationTest::testMultipleAuthorsAreSorted":0.007,"ThesisCreateValidationTest::testMissingPromoteurInNonAdminModeThrowsException":0.003,"ThesisCreateValidationTest::testMissingLecteurInterneInNonAdminModeThrowsException":0.003,"ThesisCreateValidationTest::testMissingLanguagesInNonAdminModeThrowsException":0.004,"ThesisCreateValidationTest::testMissingFormatsInNonAdminModeThrowsException":0.003,"ThesisCreateValidationTest::testMissingLicenseWithLibreAccessThrowsException":0.009,"ThesisEditValidationTest::testLoadReturnsDataForKnownId":0.007,"ThesisEditValidationTest::testLoadThrowsOnUnknownId":0.005,"ThesisEditValidationTest::testLoadThrowsOnInvalidId":0.002,"ThesisEditValidationTest::testLoadThrowsOnNegativeId":0.002,"ThesisEditValidationTest::testCollectJuryMembersEmptyInput":0.002,"ThesisEditValidationTest::testCollectJuryMembersSinglePromoteur":0.002,"ThesisEditValidationTest::testCollectJuryMembersPromoteurUlb":0.002,"ThesisEditValidationTest::testCollectJuryMembersLecteurs":0.002,"ThesisEditValidationTest::testCollectJuryMembersDeduplicatesEmptyStrings":0.003,"ThesisEditValidationTest::testCollectJuryMembersScalarPromoteurAccepted":0.008,"ThesisEditValidationTest::testHandleWebsiteUrlStoresValidUrl":0.005,"ThesisEditValidationTest::testHandleWebsiteUrlSkipsInvalidUrl":0.003,"ThesisEditValidationTest::testHandleWebsiteUrlSkipsEmptyUrl":0.003,"ThesisEditValidationTest::testHandleWebsiteUrlNormalisesHttp":0.003,"ErrorHandlerTest::testFkThesesTableMentionsAllPossibleFields":0.794,"ErrorHandlerTest::testFkApPrograms":0.002,"ErrorHandlerTest::testFkFinalityTypes":0.001,"ErrorHandlerTest::testFkThesisLanguages":0.001,"ErrorHandlerTest::testFkThesisFormats":0.003,"ErrorHandlerTest::testFkThesisTags":0.005,"ErrorHandlerTest::testFkThesisSupervisors":0.002,"ErrorHandlerTest::testFkAccessTypes":0.002,"ErrorHandlerTest::testFkLicenseTypes":0.002,"ErrorHandlerTest::testFkAuthors":0.002,"ErrorHandlerTest::testFkQuotedTableName":0.002,"ErrorHandlerTest::testFkQuotedLanguages":0.002,"ErrorHandlerTest::testFkQuotedFormatTypes":0.001,"ErrorHandlerTest::testFkReferencesTags":0.001,"ErrorHandlerTest::testFkReferencesOrientations":0.001,"ErrorHandlerTest::testFkUnknownTableGenericFallback":0.001,"ErrorHandlerTest::testFkEmptyMessageGenericFallback":0.002,"ErrorHandlerTest::testUniqueConstraint":0.002,"ErrorHandlerTest::testNotNullConstraint":0.003,"ErrorHandlerTest::testGenericPdoError":0.004,"ErrorHandlerTest::testDuplicateThesisExceptionPassesThrough":0.009,"ErrorHandlerTest::testValidationExceptionPassesThrough":0.003,"ErrorHandlerTest::testGenericExceptionPassesThrough":0.002,"ErrorHandlerTest::testTypeErrorReturnsGeneric":0.002,"ErrorHandlerTest::testLogWithContext":0.024,"ErrorHandlerTest::testLogWithNullValues":0.003,"ErrorHandlerTest::testLogWithEmptyExtra":0.002,"ErrorHandlerTest::testFkQuotedColumnNames":0.002,"ErrorHandlerTest::testFkUpdateStatement":0.002,"ErrorHandlerTest::testFkWithReferencesAndInsert":0.002,"PureLogicTest::testSplitJuryByRoleAllRoles":0.064,"PureLogicTest::testSplitJuryByRoleEmptyNameSkipped":0.004,"PureLogicTest::testSplitJuryByRoleEmptyJury":0.002,"PureLogicTest::testCollectCaptionPathsVttByMime":0.002,"PureLogicTest::testCollectCaptionPathsVttByExtension":0.002,"PureLogicTest::testCollectCaptionPathsNoVttReturnsEmpty":0.002,"PureLogicTest::testDetectFileTypeByMime":0.002,"PureLogicTest::testDetectFileTypeByExtensionFallback":0.002,"SearchControllerTest::testHandleSearchReturnsCoverMapKey":0.058,"SearchControllerTest::testCoverMapContainsKnownThesis":0.007}}