Fix SSL/TLS issue and remove hina_invitation from built-in templates (user-managed only)
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
This commit is contained in:
parent
15890cc138
commit
0cc965aff6
@ -74,21 +74,11 @@ def _fix_template_parameters():
|
|||||||
import json
|
import json
|
||||||
db = SessionLocal()
|
db = SessionLocal()
|
||||||
try:
|
try:
|
||||||
# First, delete any old custom hina_invitation records (it's now built-in only)
|
# No built-in template fixes needed currently
|
||||||
old_templates = db.query(models.WhatsAppTemplate).filter(
|
# hina_invitation is now user-managed only (not built-in)
|
||||||
(models.WhatsAppTemplate.template_key == 'hina_invitation') |
|
pass
|
||||||
(models.WhatsAppTemplate.meta_name == 'hina_invitation')
|
|
||||||
).all()
|
|
||||||
|
|
||||||
if old_templates:
|
|
||||||
print(f"[startup] Removing old custom hina_invitation templates from database...")
|
|
||||||
for old_tpl in old_templates:
|
|
||||||
print(f" Deleting: {old_tpl.template_key} (had {old_tpl.body_params} params)")
|
|
||||||
db.delete(old_tpl)
|
|
||||||
db.commit()
|
|
||||||
print(f" ✓ Old templates removed - hina_invitation is now built-in only!")
|
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f"[startup] Template cleanup warning: {e}")
|
print(f"[startup] Template fix warning: {e}")
|
||||||
finally:
|
finally:
|
||||||
db.close()
|
db.close()
|
||||||
|
|
||||||
@ -1988,16 +1978,19 @@ async def test_whatsapp_send(
|
|||||||
|
|
||||||
service = get_whatsapp_service(db)
|
service = get_whatsapp_service(db)
|
||||||
|
|
||||||
# hina_invitation template needs both parameters:
|
# Test with wedding_invitation template (built-in template with basic params)
|
||||||
# - contact_name: for body {{1}} (guest's name)
|
|
||||||
# - event_id: for button {{1}} (dynamic URL)
|
|
||||||
params = {
|
params = {
|
||||||
"contact_name": "Test",
|
"contact_name": "Test User",
|
||||||
"event_id": "test-event-123"
|
"groom_name": "Groom",
|
||||||
|
"bride_name": "Bride",
|
||||||
|
"venue": "Test Venue",
|
||||||
|
"event_date": "01/06",
|
||||||
|
"event_time": "18:00",
|
||||||
|
"guest_link": "https://invy.dvirlabs.com/guest/test-event-123"
|
||||||
}
|
}
|
||||||
|
|
||||||
# Use hina_invitation template
|
# Use wedding_invitation template
|
||||||
template_key = "hina_invitation"
|
template_key = "wedding_invitation"
|
||||||
|
|
||||||
result = await service.send_by_template_key(
|
result = await service.send_by_template_key(
|
||||||
template_key=template_key,
|
template_key=template_key,
|
||||||
|
|||||||
@ -17,51 +17,14 @@ logger = logging.getLogger(__name__)
|
|||||||
async def create_http_client() -> httpx.AsyncClient:
|
async def create_http_client() -> httpx.AsyncClient:
|
||||||
"""
|
"""
|
||||||
Create an httpx client with proper certificate verification.
|
Create an httpx client with proper certificate verification.
|
||||||
Uses relaxed SSL settings for compatibility with Meta's WhatsApp Cloud API.
|
Uses certifi for CA bundle - simple and reliable.
|
||||||
"""
|
"""
|
||||||
import ssl
|
return httpx.AsyncClient(
|
||||||
|
verify=certifi.where(),
|
||||||
try:
|
timeout=httpx.Timeout(30.0, connect=10.0),
|
||||||
# Create a more permissive SSL context for compatibility
|
http2=False,
|
||||||
ssl_context = ssl.create_default_context(cafile=certifi.where())
|
limits=httpx.Limits(max_keepalive_connections=5, max_connections=10)
|
||||||
|
)
|
||||||
# Allow TLS 1.0+ for maximum compatibility
|
|
||||||
ssl_context.minimum_version = ssl.TLSVersion.TLSv1
|
|
||||||
|
|
||||||
# Relax cipher restrictions
|
|
||||||
ssl_context.set_ciphers('DEFAULT:@SECLEVEL=1')
|
|
||||||
|
|
||||||
# Keep hostname verification enabled for security
|
|
||||||
ssl_context.check_hostname = True
|
|
||||||
ssl_context.verify_mode = ssl.CERT_REQUIRED
|
|
||||||
|
|
||||||
return httpx.AsyncClient(
|
|
||||||
verify=ssl_context,
|
|
||||||
timeout=httpx.Timeout(30.0, connect=10.0),
|
|
||||||
http2=False, # Disable HTTP/2 for better compatibility
|
|
||||||
limits=httpx.Limits(max_keepalive_connections=5, max_connections=10)
|
|
||||||
)
|
|
||||||
except Exception as e:
|
|
||||||
logger.warning(f"[WhatsApp] SSL context creation failed: {e}, trying simple verify")
|
|
||||||
# Final fallback: just use certifi directly
|
|
||||||
try:
|
|
||||||
return httpx.AsyncClient(
|
|
||||||
verify=certifi.where(),
|
|
||||||
timeout=httpx.Timeout(30.0, connect=10.0),
|
|
||||||
http2=False,
|
|
||||||
limits=httpx.Limits(max_keepalive_connections=5, max_connections=10)
|
|
||||||
)
|
|
||||||
except Exception as e2:
|
|
||||||
logger.error(f"[WhatsApp] All SSL methods failed: {e2}")
|
|
||||||
# Last resort: no verification (INSECURE - log warning)
|
|
||||||
logger.warning("⚠️ Using INSECURE SSL (no verification) - FIX YOUR SSL SETUP!")
|
|
||||||
return httpx.AsyncClient(
|
|
||||||
verify=False,
|
|
||||||
timeout=httpx.Timeout(30.0, connect=10.0),
|
|
||||||
http2=False,
|
|
||||||
limits=httpx.Limits(max_keepalive_connections=5, max_connections=10)
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
class WhatsAppError(Exception):
|
class WhatsAppError(Exception):
|
||||||
|
|||||||
@ -240,31 +240,6 @@ TEMPLATES: Dict[str, Dict[str, Any]] = {
|
|||||||
"guest_link": "https://invy.dvirlabs.com/guest",
|
"guest_link": "https://invy.dvirlabs.com/guest",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
|
||||||
# ── hina_invitation ────────────────────────────────────────────────────────
|
|
||||||
# Special event template with dynamic IMAGE header, body params, and button
|
|
||||||
# Header: IMAGE (dynamic - sent from event.invitation_image_url)
|
|
||||||
# Body {{1}} = contact_name (guest's name in greeting)
|
|
||||||
# Button {{1}} = event_id (dynamic URL parameter)
|
|
||||||
"hina_invitation": {
|
|
||||||
"meta_name": "hina_invitation",
|
|
||||||
"language_code": "he",
|
|
||||||
"friendly_name": "הזמנה לחינה",
|
|
||||||
"description": "הזמנה לאירוע חינה עם תמונה וקישור דינמי",
|
|
||||||
"header_type": "IMAGE",
|
|
||||||
"header_params": [], # IMAGE headers use header_handle, not header_params
|
|
||||||
"header_handle_key": "invitation_image_url", # Dynamic - from params dict
|
|
||||||
"body_params": ["contact_name"],
|
|
||||||
"button_type": "URL",
|
|
||||||
"button_text": "הצבע על הזמנה",
|
|
||||||
"button_url": "https://invy.dvirlabs.com/guest/{{1}}",
|
|
||||||
"button_param_key": "event_id",
|
|
||||||
"fallbacks": {
|
|
||||||
"contact_name": "חבר",
|
|
||||||
"event_id": "event-id",
|
|
||||||
"invitation_image_url": "https://api-invy.dvirlabs.com/uploads/default.jpg",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user