Files
Gnuboard7/docs/backend/activity-log-hooks.md
T
2026-04-20 20:37:49 +09:00

40 KiB

활동 로그 훅 레퍼런스 (Activity Log Hooks Reference)

모든 ActivityLog 리스너가 구독하는 훅의 전체 목록 (코어 + 모듈)

TL;DR (5초 요약)

1. 코어 66훅 + 이커머스 92훅 + 게시판 32훅 + 페이지 8훅 = 총 198훅
2. Listener에서 Log::channel('activity')->info() 직접 호출 (Monolog → ActivityLogHandler → DB)
3. 스냅샷 패턴: before_update(priority 5) → 캡처, after_update → ChangeDetector로 비교
4. 사용자 행위: ActivityLogType::User (장바구니/위시리스트/쿠폰 다운로드/주문/결제)
5. 새 훅 추가 시: Listener에 구독 + lang 파일에 description_key 정의

목차

  1. 아키텍처 개요
  2. 코어 훅 (CoreActivityLogListener)
  3. 이커머스 모듈 훅
  4. 게시판 모듈 훅 (BoardActivityLogListener)
  5. 페이지 모듈 훅 (PageActivityLogListener)
  6. 스냅샷/변경감지 패턴
  7. 새 모듈에 ActivityLog 추가하기

1. 아키텍처 개요

Service → doAction('hook.name') → ActivityLogListener → Log::channel('activity') → ActivityLogHandler → DB
  • Listener: HookListenerInterface 구현, getSubscribedHooks()로 훅-메서드 매핑 정의
  • 로그 기록: Log::channel('activity')->info($action, $context) 직접 호출
  • context 구조: log_type, loggable, description_key, description_params, properties, changes
  • LogType: ActivityLogType::Admin (관리자 행위) / ActivityLogType::User (사용자 행위)
  • 변경 감지: ChangeDetector::detect($model, $snapshot) — 스냅샷과 현재 상태 비교

2. 코어 훅 (CoreActivityLogListener)

파일: app/Listeners/CoreActivityLogListener.php 총 66훅 (스냅샷 캡처용 before 훅 포함)

User (9훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
core.user.before_update captureUserSnapshot (스냅샷 캡처) - -
core.user.after_create handleUserAfterCreate user.create Admin User
core.user.after_update handleUserAfterUpdate user.update Admin User
core.user.after_delete handleUserAfterDelete user.delete Admin User
core.user.after_withdraw handleUserAfterWithdraw user.withdraw Admin User
core.user.after_show handleUserAfterShow user.show Admin User
core.user.after_list handleUserAfterList user.list Admin -
core.user.after_search handleUserAfterSearch user.search Admin -
sirsoft-core.user.after_bulk_update handleUserAfterBulkUpdate user.bulk_update Admin -

Auth (6훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
core.auth.after_login handleAuthAfterLogin auth.login User User
core.auth.logout handleAuthLogout auth.logout User User
core.auth.register handleAuthRegister auth.register User User
core.auth.forgot_password handleAuthForgotPassword auth.forgot_password User -
core.auth.reset_password handleAuthResetPassword auth.reset_password User -
core.auth.record_consents handleAuthRecordConsents auth.record_consents User User

Role (6훅, 스냅샷 포함)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
core.role.before_update captureRoleSnapshot (스냅샷 캡처) - -
core.role.after_create handleRoleAfterCreate role.create Admin Role
core.role.after_update handleRoleAfterUpdate role.update Admin Role
core.role.after_delete handleRoleAfterDelete role.delete Admin Role
core.role.after_sync_permissions handleRoleAfterSyncPermissions role.sync_permissions Admin Role
core.role.after_toggle_status handleRoleAfterToggleStatus role.toggle_status Admin Role

Menu (7훅, 스냅샷 포함)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
core.menu.before_update captureMenuSnapshot (스냅샷 캡처) - -
core.menu.after_create handleMenuAfterCreate menu.create Admin Menu
core.menu.after_update handleMenuAfterUpdate menu.update Admin Menu
core.menu.after_delete handleMenuAfterDelete menu.delete Admin Menu
core.menu.after_update_order handleMenuAfterUpdateOrder menu.update_order Admin -
core.menu.after_toggle_status handleMenuAfterToggleStatus menu.toggle_status Admin Menu
core.menu.after_sync_roles handleMenuAfterSyncRoles menu.sync_roles Admin Menu

Settings (2훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
core.settings.after_save handleSettingsAfterSave settings.save Admin -
core.settings.after_set handleSettingsAfterSet settings.set Admin -

Schedule (7훅, 스냅샷 포함)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
core.schedule.before_update captureScheduleSnapshot (스냅샷 캡처) - -
core.schedule.after_create handleScheduleAfterCreate schedule.create Admin Schedule
core.schedule.after_update handleScheduleAfterUpdate schedule.update Admin Schedule
core.schedule.after_delete handleScheduleAfterDelete schedule.delete Admin Schedule
core.schedule.after_run handleScheduleAfterRun schedule.run Admin Schedule
core.schedule.after_bulk_update handleScheduleAfterBulkUpdate schedule.bulk_update Admin -
core.schedule.after_bulk_delete handleScheduleAfterBulkDelete schedule.bulk_delete Admin -

Attachment (3훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
core.attachment.after_upload handleAttachmentAfterUpload attachment.upload Admin Attachment
core.attachment.after_delete handleAttachmentAfterDelete attachment.delete Admin Attachment
core.attachment.after_bulk_delete handleAttachmentAfterBulkDelete attachment.bulk_delete Admin -

Module (6훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
core.modules.after_install handleModuleAfterInstall module.install Admin -
core.modules.after_activate handleModuleAfterActivate module.activate Admin -
core.modules.after_deactivate handleModuleAfterDeactivate module.deactivate Admin -
core.modules.after_uninstall handleModuleAfterUninstall module.uninstall Admin -
core.modules.after_update handleModuleAfterUpdate module.update Admin -
core.modules.after_refresh_layouts handleModuleAfterRefreshLayouts module.refresh_layouts Admin -

Plugin (5훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
core.plugins.after_install handlePluginAfterInstall plugin.install Admin -
core.plugins.after_activate handlePluginAfterActivate plugin.activate Admin -
core.plugins.after_deactivate handlePluginAfterDeactivate plugin.deactivate Admin -
core.plugins.after_uninstall handlePluginAfterUninstall plugin.uninstall Admin -
core.plugins.after_update handlePluginAfterUpdate plugin.update Admin -

Template (6훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
core.templates.after_install handleTemplateAfterInstall template.install Admin -
core.templates.after_activate handleTemplateAfterActivate template.activate Admin -
core.templates.after_deactivate handleTemplateAfterDeactivate template.deactivate Admin -
core.templates.after_uninstall handleTemplateAfterUninstall template.uninstall Admin -
core.templates.after_version_update handleTemplateAfterVersionUpdate template.version_update Admin -
core.templates.after_refresh_layouts handleTemplateAfterRefreshLayouts template.refresh_layouts Admin -

Layout (2훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
core.layout.after_update handleLayoutAfterUpdate layout.update Admin -
core.layout.after_version_restore handleLayoutAfterVersionRestore layout.version_restore Admin -

Module Settings (2훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
core.module_settings.after_save handleModuleSettingsAfterSave module_settings.save Admin -
core.module_settings.after_reset handleModuleSettingsAfterReset module_settings.reset Admin -

Plugin Settings (2훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
core.plugin_settings.after_save handlePluginSettingsAfterSave plugin_settings.save Admin -
core.plugin_settings.after_reset handlePluginSettingsAfterReset plugin_settings.reset Admin -

3. 이커머스 모듈 훅

모듈: sirsoft-ecommerce 총 92훅 (7개 Listener)

3.1 OrderActivityLogListener (21훅)

파일: modules/_bundled/sirsoft-ecommerce/src/Listeners/OrderActivityLogListener.php

OrderService (8훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.order.before_update captureOrderSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.order.after_update handleOrderAfterUpdate order.update Admin Order
sirsoft-ecommerce.order.after_delete handleOrderAfterDelete order.delete Admin Order
sirsoft-ecommerce.order.after_bulk_update handleOrderAfterBulkUpdate order.bulk_update Admin -
sirsoft-ecommerce.order.after_bulk_status_update handleOrderAfterBulkStatusUpdate order.bulk_status_update Admin -
sirsoft-ecommerce.order.after_bulk_shipping_update handleOrderAfterBulkShippingUpdate order.bulk_shipping_update Admin -
sirsoft-ecommerce.order.after_update_shipping_address handleOrderAfterUpdateShippingAddress order.update_shipping_address Admin Order
sirsoft-ecommerce.order.after_send_email handleOrderAfterSendEmail order.send_email Admin -

OrderOptionService (2훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.order_option.after_status_change handleOrderOptionAfterStatusChange order_option.status_change Admin OrderOption
sirsoft-ecommerce.order_option.after_bulk_status_change handleOrderOptionAfterBulkStatusChange order_option.bulk_status_change Admin -

OrderCancellationService (5훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.order.before_cancel captureOrderCancelSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.order.after_cancel handleOrderAfterCancel order.cancel Admin Order
sirsoft-ecommerce.order.after_partial_cancel handleOrderAfterPartialCancel order.partial_cancel Admin Order
sirsoft-ecommerce.coupon.restore handleCouponRestore coupon.restore Admin Order
sirsoft-ecommerce.mileage.restore handleMileageRestore mileage.restore Admin Order

OrderProcessingService (6훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.order.after_create handleOrderAfterCreate order.create User Order
sirsoft-ecommerce.order.after_payment_complete handleOrderAfterPaymentComplete order.payment_complete User Order
sirsoft-ecommerce.order.payment_failed handleOrderAfterPaymentFailed order.payment_failed User Order
sirsoft-ecommerce.coupon.use handleCouponUse coupon.use User Order
sirsoft-ecommerce.mileage.use handleMileageUse mileage.use User Order
sirsoft-ecommerce.mileage.earn handleMileageEarn mileage.earn User Order

3.2 ProductActivityLogListener (10훅)

파일: modules/_bundled/sirsoft-ecommerce/src/Listeners/ProductActivityLogListener.php

이 리스너는 ProductLogService를 사용하는 별도 패턴입니다 (Log::channel 대신).

훅 이름 Listener 메서드 Priority 비고
sirsoft-ecommerce.product.after_create logCreated 50 상품 생성 로그
sirsoft-ecommerce.product.before_update captureSnapshot 5 스냅샷 캡처
sirsoft-ecommerce.product.after_update logUpdated 50 변경사항 비교 후 로그
sirsoft-ecommerce.product.before_delete logDeleted 50 삭제 전 로그 기록
sirsoft-ecommerce.product.before_bulk_update captureProductBulkUpdateSnapshot 5 일괄 수정 전 스냅샷
sirsoft-ecommerce.product.after_bulk_update handleProductAfterBulkUpdate 20 일괄 수정 로그
sirsoft-ecommerce.product.before_bulk_price_update captureProductBulkPriceSnapshot 5 일괄 가격 수정 전 스냅샷
sirsoft-ecommerce.product.after_bulk_price_update handleProductAfterBulkPriceUpdate 20 일괄 가격 수정 로그
sirsoft-ecommerce.product.before_bulk_stock_update captureProductBulkStockSnapshot 5 일괄 재고 수정 전 스냅샷
sirsoft-ecommerce.product.after_bulk_stock_update handleProductAfterBulkStockUpdate 20 일괄 재고 수정 로그

3.3 CouponActivityLogListener (6훅)

파일: modules/_bundled/sirsoft-ecommerce/src/Listeners/CouponActivityLogListener.php

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.coupon.after_create handleAfterCreate coupon.create Admin Coupon
sirsoft-ecommerce.coupon.before_update captureCouponSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.coupon.after_update handleAfterUpdate coupon.update Admin Coupon
sirsoft-ecommerce.coupon.after_delete handleAfterDelete coupon.delete Admin -
sirsoft-ecommerce.coupon.before_bulk_status captureCouponBulkStatusSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.coupon.after_bulk_status handleAfterBulkStatus coupon.bulk_status Admin -

3.4 ShippingPolicyActivityLogListener (8훅)

파일: modules/_bundled/sirsoft-ecommerce/src/Listeners/ShippingPolicyActivityLogListener.php

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.shipping_policy.after_create handleAfterCreate shipping_policy.create Admin ShippingPolicy
sirsoft-ecommerce.shipping_policy.before_update captureSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.shipping_policy.after_update handleAfterUpdate shipping_policy.update Admin ShippingPolicy
sirsoft-ecommerce.shipping_policy.after_delete handleAfterDelete shipping_policy.delete Admin -
sirsoft-ecommerce.shipping_policy.after_toggle_active handleAfterToggleActive shipping_policy.toggle_active Admin ShippingPolicy
sirsoft-ecommerce.shipping_policy.after_set_default handleAfterSetDefault shipping_policy.set_default Admin ShippingPolicy
sirsoft-ecommerce.shipping_policy.after_bulk_delete handleAfterBulkDelete shipping_policy.bulk_delete Admin -
sirsoft-ecommerce.shipping_policy.after_bulk_toggle_active handleAfterBulkToggleActive shipping_policy.bulk_toggle_active Admin -

3.5 CategoryActivityLogListener (6훅)

파일: modules/_bundled/sirsoft-ecommerce/src/Listeners/CategoryActivityLogListener.php

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.category.after_create handleAfterCreate category.create Admin Category
sirsoft-ecommerce.category.before_update captureCategorySnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.category.after_update handleAfterUpdate category.update Admin Category
sirsoft-ecommerce.category.after_delete handleAfterDelete category.delete Admin -
sirsoft-ecommerce.category.after_toggle_status handleAfterToggleStatus category.toggle_status Admin Category
sirsoft-ecommerce.category.after_reorder handleAfterReorder category.reorder Admin -

3.6 EcommerceAdminActivityLogListener (51훅)

파일: modules/_bundled/sirsoft-ecommerce/src/Listeners/EcommerceAdminActivityLogListener.php

Brand (5훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.brand.after_create handleBrandAfterCreate brand.create Admin Brand
sirsoft-ecommerce.brand.before_update captureBrandSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.brand.after_update handleBrandAfterUpdate brand.update Admin Brand
sirsoft-ecommerce.brand.after_delete handleBrandAfterDelete brand.delete Admin Brand
sirsoft-ecommerce.brand.after_toggle_status handleBrandAfterToggleStatus brand.toggle_status Admin Brand

ProductLabel (5훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.label.after_create handleLabelAfterCreate label.create Admin ProductLabel
sirsoft-ecommerce.label.before_update captureLabelSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.label.after_update handleLabelAfterUpdate label.update Admin ProductLabel
sirsoft-ecommerce.label.after_delete handleLabelAfterDelete label.delete Admin ProductLabel
sirsoft-ecommerce.label.after_toggle_status handleLabelAfterToggleStatus label.toggle_status Admin ProductLabel

ProductCommonInfo (4훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.product-common-info.after_create handleCommonInfoAfterCreate common_info.create Admin ProductCommonInfo
sirsoft-ecommerce.product-common-info.before_update captureCommonInfoSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.product-common-info.after_update handleCommonInfoAfterUpdate common_info.update Admin ProductCommonInfo
sirsoft-ecommerce.product-common-info.after_delete handleCommonInfoAfterDelete common_info.delete Admin ProductCommonInfo

ProductNoticeTemplate (5훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.product-notice-template.after_create handleNoticeTemplateAfterCreate notice_template.create Admin ProductNoticeTemplate
sirsoft-ecommerce.product-notice-template.before_update captureNoticeTemplateSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.product-notice-template.after_update handleNoticeTemplateAfterUpdate notice_template.update Admin ProductNoticeTemplate
sirsoft-ecommerce.product-notice-template.after_delete handleNoticeTemplateAfterDelete notice_template.delete Admin ProductNoticeTemplate
sirsoft-ecommerce.product-notice-template.after_copy handleNoticeTemplateAfterCopy notice_template.copy Admin ProductNoticeTemplate

ExtraFeeTemplate (10훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.extra_fee_template.after_create handleExtraFeeAfterCreate extra_fee_template.create Admin ExtraFeeTemplate
sirsoft-ecommerce.extra_fee_template.before_update captureExtraFeeSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.extra_fee_template.after_update handleExtraFeeAfterUpdate extra_fee_template.update Admin ExtraFeeTemplate
sirsoft-ecommerce.extra_fee_template.after_delete handleExtraFeeAfterDelete extra_fee_template.delete Admin ExtraFeeTemplate
sirsoft-ecommerce.extra_fee_template.after_toggle_active handleExtraFeeAfterToggleActive extra_fee_template.toggle_active Admin ExtraFeeTemplate
sirsoft-ecommerce.extra_fee_template.before_bulk_delete captureExtraFeeBulkDeleteSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.extra_fee_template.after_bulk_delete handleExtraFeeAfterBulkDelete extra_fee_template.bulk_delete Admin -
sirsoft-ecommerce.extra_fee_template.before_bulk_toggle_active captureExtraFeeBulkToggleSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.extra_fee_template.after_bulk_toggle_active handleExtraFeeAfterBulkToggleActive extra_fee_template.bulk_toggle_active Admin -
sirsoft-ecommerce.extra_fee_template.after_bulk_create handleExtraFeeAfterBulkCreate extra_fee_template.bulk_create Admin -

ShippingCarrier (5훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.shipping_carrier.after_create handleCarrierAfterCreate shipping_carrier.create Admin ShippingCarrier
sirsoft-ecommerce.shipping_carrier.before_update captureCarrierSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.shipping_carrier.after_update handleCarrierAfterUpdate shipping_carrier.update Admin ShippingCarrier
sirsoft-ecommerce.shipping_carrier.after_delete handleCarrierAfterDelete shipping_carrier.delete Admin ShippingCarrier
sirsoft-ecommerce.shipping_carrier.after_toggle_status handleCarrierAfterToggleStatus shipping_carrier.toggle_status Admin ShippingCarrier

ProductImage (3훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.product-image.after_upload handleImageAfterUpload product_image.upload Admin ProductImage
sirsoft-ecommerce.product-image.after_delete handleImageAfterDelete product_image.delete Admin ProductImage
sirsoft-ecommerce.product-image.after_reorder handleImageAfterReorder product_image.reorder Admin -

ShippingPolicy Bulk (4훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.shipping_policy.before_bulk_delete captureShippingPolicyBulkDeleteSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.shipping_policy.after_bulk_delete handleShippingPolicyAfterBulkDelete shipping_policy.bulk_delete Admin -
sirsoft-ecommerce.shipping_policy.before_bulk_toggle_active captureShippingPolicyBulkToggleSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.shipping_policy.after_bulk_toggle_active handleShippingPolicyAfterBulkToggleActive shipping_policy.bulk_toggle_active Admin -

ProductOption (6훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.product_option.before_bulk_price_update captureOptionBulkPriceSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.product_option.after_bulk_price_update handleOptionAfterBulkPriceUpdate product_option.bulk_price_update Admin -
sirsoft-ecommerce.product_option.before_bulk_stock_update captureOptionBulkStockSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.product_option.after_bulk_stock_update handleOptionAfterBulkStockUpdate product_option.bulk_stock_update Admin -
sirsoft-ecommerce.option.before_bulk_update captureOptionBulkUpdateSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.option.after_bulk_update handleOptionAfterBulkUpdate product_option.bulk_update Admin -

ProductReview (4훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.product-review.after_create handleReviewAfterCreate review.create Admin ProductReview
sirsoft-ecommerce.product-review.after_delete handleReviewAfterDelete review.delete Admin ProductReview
sirsoft-ecommerce.product-review.before_bulk_delete captureReviewBulkDeleteSnapshot (스냅샷 캡처) - -
sirsoft-ecommerce.product-review.after_bulk_delete handleReviewAfterBulkDelete product_review.bulk_delete Admin -

3.7 EcommerceUserActivityLogListener (7훅)

파일: modules/_bundled/sirsoft-ecommerce/src/Listeners/EcommerceUserActivityLogListener.php

Cart (5훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.cart.after_add handleCartAfterAdd cart.add User Cart
sirsoft-ecommerce.cart.after_update_quantity handleCartAfterUpdateQuantity cart.update_quantity User Cart
sirsoft-ecommerce.cart.after_change_option handleCartAfterChangeOption cart.change_option User Cart
sirsoft-ecommerce.cart.after_delete handleCartAfterDelete cart.delete User -
sirsoft-ecommerce.cart.after_delete_all handleCartAfterDeleteAll cart.delete_all User -

Wishlist (1훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.wishlist.after_toggle handleWishlistAfterToggle wishlist.add / wishlist.remove User Product

User Coupon (1훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-ecommerce.user_coupon.after_download handleUserCouponAfterDownload user_coupon.download User CouponIssue

4. 게시판 모듈 훅 (BoardActivityLogListener)

파일: modules/_bundled/sirsoft-board/src/Listeners/BoardActivityLogListener.php 총 32훅

Board (6훅, 스냅샷 포함)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-board.board.after_create handleBoardAfterCreate board.create Admin Board
sirsoft-board.board.before_update captureBoardSnapshot (스냅샷 캡처) - -
sirsoft-board.board.after_update handleBoardAfterUpdate board.update Admin Board
sirsoft-board.board.after_delete handleBoardAfterDelete board.delete Admin Board
sirsoft-board.board.after_add_to_menu handleBoardAfterAddToMenu board.add_to_menu Admin Board
sirsoft-board.settings.after_bulk_apply handleSettingsAfterBulkApply board_settings.bulk_apply Admin -

BoardType (4훅, 스냅샷 포함)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-board.board_type.after_create handleBoardTypeAfterCreate board_type.create Admin BoardType
sirsoft-board.board_type.before_update captureBoardTypeSnapshot (스냅샷 캡처) - -
sirsoft-board.board_type.after_update handleBoardTypeAfterUpdate board_type.update Admin BoardType
sirsoft-board.board_type.after_delete handleBoardTypeAfterDelete board_type.delete Admin BoardType

Post (6훅, 스냅샷 포함)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-board.post.after_create handlePostAfterCreate post.create Admin Post
sirsoft-board.post.before_update capturePostSnapshot (스냅샷 캡처) - -
sirsoft-board.post.after_update handlePostAfterUpdate post.update Admin Post
sirsoft-board.post.after_delete handlePostAfterDelete post.delete Admin Post
sirsoft-board.post.after_blind handlePostAfterBlind post.blind Admin Post
sirsoft-board.post.after_restore handlePostAfterRestore post.restore Admin Post

Comment (6훅, 스냅샷 포함)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-board.comment.after_create handleCommentAfterCreate comment.create Admin Comment
sirsoft-board.comment.before_update captureCommentSnapshot (스냅샷 캡처) - -
sirsoft-board.comment.after_update handleCommentAfterUpdate comment.update Admin Comment
sirsoft-board.comment.after_delete handleCommentAfterDelete comment.delete Admin Comment
sirsoft-board.comment.after_blind handleCommentAfterBlind comment.blind Admin Comment
sirsoft-board.comment.after_restore handleCommentAfterRestore comment.restore Admin Comment

Attachment (2훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-board.attachment.after_upload handleAttachmentAfterUpload attachment.upload Admin Attachment
sirsoft-board.attachment.after_delete handleAttachmentAfterDelete attachment.delete Admin Attachment

Report (8훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-board.report.after_create handleReportAfterCreate report.create Admin Report
sirsoft-board.report.after_update_status handleReportAfterUpdateStatus report.update_status Admin Report
sirsoft-board.report.before_bulk_update_status captureReportBulkStatusSnapshot (스냅샷 캡처) - -
sirsoft-board.report.after_bulk_update_status handleReportAfterBulkUpdateStatus report.bulk_update_status Admin -
sirsoft-board.report.after_delete handleReportAfterDelete report.delete Admin Report
sirsoft-board.report.after_restore_content handleReportAfterRestoreContent report.restore_content Admin Report
sirsoft-board.report.after_blind_content handleReportAfterBlindContent report.blind_content Admin Report
sirsoft-board.report.after_delete_content handleReportAfterDeleteContent report.delete_content Admin Report

5. 페이지 모듈 훅 (PageActivityLogListener)

파일: modules/_bundled/sirsoft-page/src/Listeners/PageActivityLogListener.php 총 8훅

Page (6훅, 스냅샷 포함)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-page.page.after_create handlePageAfterCreate page.create Admin Page
sirsoft-page.page.before_update capturePageSnapshot (스냅샷 캡처) - -
sirsoft-page.page.after_update handlePageAfterUpdate page.update Admin Page
sirsoft-page.page.after_delete handlePageAfterDelete page.delete Admin Page
sirsoft-page.page.after_publish handlePageAfterPublish page.publish / page.unpublish Admin Page
sirsoft-page.page.after_restore handlePageAfterRestore page.restore Admin Page

PageAttachment (2훅)

훅 이름 Listener 메서드 Action (DB) LogType Loggable
sirsoft-page.attachment.after_upload handleAttachmentAfterUpload page_attachment.upload Admin PageAttachment
sirsoft-page.attachment.after_delete handleAttachmentAfterDelete page_attachment.delete Admin PageAttachment

6. 스냅샷/변경감지 패턴

ActivityLog에서 수정(update) 작업의 변경 이력을 기록하려면 스냅샷 패턴을 사용합니다.

동작 흐름

1. Service에서 before_update 훅 발행 (doAction)
2. Listener의 캡처 메서드 실행 (priority: 5, 다른 리스너보다 먼저)
   → 현재 모델 상태를 $snapshots 배열에 저장
3. Service에서 실제 DB 업데이트 수행
4. Service에서 after_update 훅 발행 (doAction)
5. Listener의 핸들러 메서드 실행 (priority: 20)
   → ChangeDetector::detect($model, $snapshot) 호출
   → 변경된 필드만 추출하여 로그 기록
   → 스냅샷 정리 (unset)

코드 예시

// 1. getSubscribedHooks()에서 before/after 쌍 등록
public static function getSubscribedHooks(): array
{
    return [
        'my-module.entity.before_update' => ['method' => 'captureSnapshot', 'priority' => 5],
        'my-module.entity.after_update' => ['method' => 'handleAfterUpdate', 'priority' => 20],
    ];
}

// 2. 스냅샷 캡처 (before_update, priority 5)
public function captureSnapshot(Model $entity, array $data): void
{
    $this->snapshots['entity_' . $entity->id] = $entity->toArray();
}

// 3. 변경 감지 + 로그 기록 (after_update, priority 20)
public function handleAfterUpdate(Model $entity): void
{
    $snapshot = $this->snapshots['entity_' . $entity->id] ?? null;
    $changes = ChangeDetector::detect($entity, $snapshot);

    Log::channel('activity')->info('entity.update', [
        'log_type' => ActivityLogType::Admin,
        'loggable' => $entity,
        'description_key' => 'my-module::activity_log.description.entity_update',
        'description_params' => ['entity_id' => $entity->id],
        'changes' => $changes,
    ]);

    unset($this->snapshots['entity_' . $entity->id]);
}

ChangeDetector

파일: app/ActivityLog/ChangeDetector.php

  • 모델의 $activityLogFields 속성에 정의된 필드만 비교
  • 각 필드의 label_key (다국어 키)를 포함한 구조화된 변경 이력 생성
  • BackedEnum 자동 변환 지원
  • 스냅샷이 null이면 null 반환 (변경 없음)

ProductActivityLogListener의 별도 패턴

ProductActivityLogListener는 ProductLogService를 주입받아 사용하는 별도 패턴입니다:

  • ChangeDetector 대신 자체 detectChanges() 메서드로 변경 감지
  • 해시 비교로 옵션/추가옵션/이미지 변경 감지
  • Log::channel('activity') 대신 ProductLogService를 통해 처리로그 테이블에 기록

7. 새 모듈에 ActivityLog 추가하기

Step 1: Listener 클래스 생성

<?php

namespace Modules\Vendor\MyModule\Listeners;

use App\ActivityLog\ChangeDetector;
use App\Contracts\Extension\HookListenerInterface;
use App\Enums\ActivityLogType;
use Illuminate\Support\Facades\Log;

class MyModuleActivityLogListener implements HookListenerInterface
{
    private array $snapshots = [];

    public static function getSubscribedHooks(): array
    {
        return [
            'vendor-mymodule.entity.after_create' => ['method' => 'handleAfterCreate', 'priority' => 20],
            'vendor-mymodule.entity.before_update' => ['method' => 'captureSnapshot', 'priority' => 5],
            'vendor-mymodule.entity.after_update' => ['method' => 'handleAfterUpdate', 'priority' => 20],
            'vendor-mymodule.entity.after_delete' => ['method' => 'handleAfterDelete', 'priority' => 20],
        ];
    }

    public function handle(...$args): void
    {
        // 개별 메서드에서 처리
    }

    // ... 각 핸들러 메서드 구현
}

Step 2: module.php에 Listener 등록

// module.php의 listeners 배열에 추가
'listeners' => [
    MyModuleActivityLogListener::class,
],

Step 3: 다국어 파일에 description_key 정의

// lang/ko/activity_log.php
return [
    'description' => [
        'entity_create' => ':entity_name 엔티티가 생성되었습니다.',
        'entity_update' => ':entity_name 엔티티가 수정되었습니다.',
        'entity_delete' => ':entity_name 엔티티가 삭제되었습니다.',
    ],
];

Step 4: 모델에 $activityLogFields 정의 (ChangeDetector 사용 시)

// Model 클래스에 추가
protected array $activityLogFields = [
    'name' => ['label_key' => 'vendor-mymodule::activity_log.fields.name'],
    'status' => ['label_key' => 'vendor-mymodule::activity_log.fields.status'],
];

Step 5: 테스트 작성

// tests/Unit/Listeners/MyModuleActivityLogListenerTest.php
class MyModuleActivityLogListenerTest extends TestCase
{
    public function test_getSubscribedHooks_returns_expected_hooks(): void
    {
        $hooks = MyModuleActivityLogListener::getSubscribedHooks();

        $this->assertArrayHasKey('vendor-mymodule.entity.after_create', $hooks);
        $this->assertArrayHasKey('vendor-mymodule.entity.before_update', $hooks);
        // ...
    }

    public function test_handleAfterCreate_logs_activity(): void
    {
        Log::shouldReceive('channel')
            ->with('activity')
            ->andReturnSelf();
        Log::shouldReceive('info')
            ->once()
            ->with('entity.create', Mockery::type('array'));

        $listener = new MyModuleActivityLogListener();
        $listener->handleAfterCreate($entity, $data);
    }
}

훅 네이밍 규칙

패턴 용도 Priority
{module}.{entity}.before_update 스냅샷 캡처 5 (높은 우선순위)
{module}.{entity}.after_create 생성 로그 20
{module}.{entity}.after_update 수정 로그 (변경감지) 20
{module}.{entity}.after_delete 삭제 로그 20
{module}.{entity}.after_bulk_* 일괄 작업 로그 20
{module}.{entity}.after_toggle_* 상태 전환 로그 20

context 구조

키 타입 설명 필수
log_type ActivityLogType Admin 또는 User O
loggable Model 대상 모델 (polymorphic) -
description_key string 다국어 설명 키 O
description_params array 설명 파라미터 -
properties array 추가 속성 (JSON) -
changes array|null ChangeDetector 결과 -