Coding
PromptBeginner5 minmarkdown
Nano Banana Pro
Agent skill for nano-banana-pro
7
Integrate Dapr building blocks for event-driven microservices - Pub/Sub, State Management, Secrets, Service Invocation, and Jobs API. Use when implementing event-driven architecture for Phase 5. (project)
Sign in to like and favorite skills
constitution-prompt-phase-5.mddapr --versiondapr init or dapr init -k for Kubernetesdapr-components/ directorydapr run commands| Building Block | Purpose | Phase 5 Usage |
|---|---|---|
| Pub/Sub | Event messaging | Task events, reminders, audit logs |
| State | Key-value storage | Cache, session state |
| Secrets | Secret management | API keys, DB credentials |
| Service Invocation | Service-to-service calls | Microservice communication |
| Jobs API | Scheduled tasks | Recurring task scheduling |
Create
dapr-components/pubsub.yaml:
apiVersion: dapr.io/v1alpha1 kind: Component metadata: name: taskpubsub namespace: todo-app spec: type: pubsub.kafka version: v1 metadata: - name: brokers value: "kafka:9092" - name: consumerGroup value: "todo-consumer-group" - name: authType value: "none" - name: disableTls value: "true" scopes: - backend - notification-service - recurring-service - audit-service
Create
dapr-components/statestore.yaml:
apiVersion: dapr.io/v1alpha1 kind: Component metadata: name: statestore namespace: todo-app spec: type: state.redis version: v1 metadata: - name: redisHost value: "redis:6379" - name: redisPassword value: "" - name: actorStateStore value: "true" scopes: - backend
Create
dapr-components/secrets.yaml:
apiVersion: dapr.io/v1alpha1 kind: Component metadata: name: kubernetes-secrets namespace: todo-app spec: type: secretstores.kubernetes version: v1 metadata: []
uv add dapr dapr-ext-fastapi
from dapr.clients import DaprClient async def publish_task_event(event_type: str, task_data: dict): """Publish task event to Kafka via Dapr.""" with DaprClient() as client: client.publish_event( pubsub_name="taskpubsub", topic_name="task-events", data=json.dumps({ "event_type": event_type, "task": task_data, "timestamp": datetime.utcnow().isoformat() }), data_content_type="application/json" )
from dapr.ext.fastapi import DaprApp from fastapi import FastAPI app = FastAPI() dapr_app = DaprApp(app) @dapr_app.subscribe(pubsub="taskpubsub", topic="task-events") async def handle_task_event(event: dict): """Handle incoming task events.""" event_type = event.get("event_type") task_data = event.get("task") if event_type == "task.created": await process_new_task(task_data) elif event_type == "task.completed": await process_completed_task(task_data)
from dapr.clients import DaprClient async def save_state(key: str, value: dict): """Save state to Dapr state store.""" with DaprClient() as client: client.save_state( store_name="statestore", key=key, value=json.dumps(value) ) async def get_state(key: str) -> dict | None: """Get state from Dapr state store.""" with DaprClient() as client: state = client.get_state(store_name="statestore", key=key) return json.loads(state.data) if state.data else None
from dapr.clients import DaprClient async def invoke_notification_service(user_id: str, message: str): """Invoke notification service via Dapr.""" with DaprClient() as client: response = client.invoke_method( app_id="notification-service", method_name="send", data=json.dumps({ "user_id": user_id, "message": message }), http_verb="POST" ) return response.json()
from dapr.clients import DaprClient async def schedule_reminder(reminder_id: str, due_at: datetime): """Schedule a reminder using Dapr Jobs API.""" with DaprClient() as client: # Create a scheduled job client.start_workflow( workflow_component="dapr", workflow_name="reminder-workflow", input={ "reminder_id": reminder_id, "scheduled_time": due_at.isoformat() } )
apiVersion: apps/v1 kind: Deployment metadata: name: backend spec: template: metadata: annotations: dapr.io/enabled: "true" dapr.io/app-id: "backend" dapr.io/app-port: "8000" dapr.io/enable-api-logging: "true" dapr.io/log-level: "info" dapr.io/config: "dapr-config" spec: containers: - name: backend image: evolution-todo/backend:latest
# Run backend with Dapr dapr run --app-id backend \ --app-port 8000 \ --dapr-http-port 3500 \ --components-path ./dapr-components \ -- uv run uvicorn src.main:app --host 0.0.0.0 --port 8000 # Run notification service with Dapr dapr run --app-id notification-service \ --app-port 8002 \ --dapr-http-port 3502 \ --components-path ./dapr-components \ -- uv run uvicorn services.notification.main:app --host 0.0.0.0 --port 8002
# Publish test event dapr publish --publish-app-id backend \ --pubsub taskpubsub \ --topic task-events \ --data '{"event_type":"task.created","task":{"id":"123","title":"Test"}}'
dapr --version)dapr init or dapr init -k)dapr-components/dapr, dapr-ext-fastapi)| Topic | Publisher | Subscribers | Purpose |
|---|---|---|---|
| Backend | Notification, Audit, WebSocket | Task CRUD events |
| Recurring Service | Notification, Backend | Reminder triggers |
| All Services | Audit Service | Audit logging |
| Issue | Cause | Solution |
|---|---|---|
| Sidecar not starting | Missing annotations | Add |
| Pub/Sub not working | Component not loaded | Check component scope |
| Connection refused | Wrong port | Verify matches app |
| State not persisting | Redis not running | Start Redis container |