48 lines
1.5 KiB
Python
48 lines
1.5 KiB
Python
# Copyright (c) 2023-present Plane Software, Inc. and contributors
|
|
# SPDX-License-Identifier: AGPL-3.0-only
|
|
# See the LICENSE file for details.
|
|
|
|
import json
|
|
import logging
|
|
from uuid import uuid4
|
|
|
|
from django.core.serializers.json import DjangoJSONEncoder
|
|
from django.db import transaction
|
|
from django.utils import timezone
|
|
|
|
from plane.settings.redis import redis_instance
|
|
|
|
logger = logging.getLogger(__name__)
|
|
|
|
ISSUE_EVENT_CHANNEL_PREFIX = "plane:issue-events:project"
|
|
|
|
|
|
def issue_event_channel(project_id):
|
|
return f"{ISSUE_EVENT_CHANNEL_PREFIX}:{project_id}"
|
|
|
|
|
|
def publish_issue_event_on_commit(event_type, issue, actor_id=None, changed_fields=None):
|
|
payload = {
|
|
"event_id": str(uuid4()),
|
|
"type": event_type,
|
|
"workspace_id": str(issue.workspace_id),
|
|
"workspace_slug": issue.workspace.slug if getattr(issue, "workspace", None) else None,
|
|
"project_id": str(issue.project_id),
|
|
"issue_id": str(issue.id),
|
|
"sequence_id": issue.sequence_id,
|
|
"updated_at": issue.updated_at or timezone.now(),
|
|
"actor_id": str(actor_id) if actor_id else None,
|
|
"changed_fields": sorted(set(changed_fields or [])),
|
|
}
|
|
|
|
def _publish():
|
|
try:
|
|
redis_instance().publish(
|
|
issue_event_channel(issue.project_id),
|
|
json.dumps(payload, cls=DjangoJSONEncoder),
|
|
)
|
|
except Exception:
|
|
logger.exception("Failed to publish issue realtime event")
|
|
|
|
transaction.on_commit(_publish)
|