chore(brand): rename the product to ReplyPier

The upstream project name is gone from code, assets, docs and build
output: brand strings, domains (replypier.site and its app/api/docs/help
subdomains), env prefixes, image and network names, the widget's public
JS API (window.ReplyPier, replypierId/BaseUrl/Config/Token), CSS tokens
(--rp-*), file and directory names, and the WordPress plugin package.

- widget loader is now webclient/replypier.min.js; both bundles rebuilt
  from source (backend/assets/widget.{js,css}, frontend/public/webclient)
- NOTICE, llms.txt, CONTRIBUTING, HELP_CENTER_INFRA and config.dev.js
  rewritten rather than string-swapped; the demo config no longer ships
  the previous vendor's Firebase/Razorpay/Google keys
- new migration replypier_ai_model_001 adds REPLYPIER to the managed
  AIModelType and rewrites pre-rename rows
- local compose project, database, role and volume renamed; LOCAL_DEPLOY
  documents carrying the old local data over
This commit is contained in:
WangShen007 committed 2026-10-26 00:51:03 +08:00
1 parent ff0a09f0e5
commit 54b949b392
1156 files changed
+7292 -7147

No files matched your search

+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -283,7 +283,7 @@ class TestRefusalDetection:
"I can only assist with questions related to freetest. How can I help?",
"I can only help with questions about Acme — what do you need?",
"Sorry, I can only assist with inquiries about our products.",
"I can only help with ChatterMate topics.",
"I can only help with ReplyPier topics.",
])
def test_recognises_decline_variants(self, reply):
assert looks_like_scope_refusal(reply) is True
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -15,7 +15,7 @@ limitations under the License.
"""
"""
ChatterMate - Ticket investigator agent tests
ReplyPier - Ticket investigator agent tests
"""
import pytest
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+37 -37
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -153,7 +153,7 @@ def mock_validate_model_selection(model_type: str, model_name: str):
detail={
"error": "Unsupported provider",
"type": "invalid_provider",
"details": "Currently only these providers are supported: GROQ, OPENAI, CHATTERMATE"
"details": "Currently only these providers are supported: GROQ, OPENAI, REPLYPIER"
}
)
return original_validate(model_type, model_name)
@@ -318,16 +318,16 @@ def test_setup_ai_groq(client, db, test_user):
assert data["config"]["model_name"] == "llama-3.3-70b-versatile"
@patch.dict(os.environ, {
'CHATTERMATE_API_KEY': 'test_chattermate_key',
'CHATTERMATE_MODEL_NAME': 'gpt-4o-mini'
'REPLYPIER_API_KEY': 'test_replypier_key',
'REPLYPIER_MODEL_NAME': 'gpt-4o-mini'
})
@patch('app.api.ai_setup.HAS_ENTERPRISE', True)
def test_setup_ai_chattermate_success(client, db, test_user):
"""Test successful ChatterMate AI setup"""
def test_setup_ai_replypier_success(client, db, test_user):
"""Test successful ReplyPier AI setup"""
config_data = {
"model_type": "CHATTERMATE",
"model_name": "chattermate",
"api_key": "any_key" # This will be ignored for ChatterMate
"model_type": "REPLYPIER",
"model_name": "replypier",
"api_key": "any_key" # This will be ignored for ReplyPier
}
response = client.post(
@@ -337,16 +337,16 @@ def test_setup_ai_chattermate_success(client, db, test_user):
assert response.status_code == 200
data = response.json()
assert data["message"] == "AI configuration completed successfully"
assert data["config"]["model_type"] == "CHATTERMATE"
assert data["config"]["model_type"] == "REPLYPIER"
assert data["config"]["model_name"] == "gpt-4o-mini"
@patch.dict(os.environ, {}, clear=True) # Clear environment variables
@patch('app.api.ai_setup.HAS_ENTERPRISE', True)
def test_setup_ai_chattermate_missing_key(client, db, test_user):
"""Test ChatterMate AI setup with missing API key"""
def test_setup_ai_replypier_missing_key(client, db, test_user):
"""Test ReplyPier AI setup with missing API key"""
config_data = {
"model_type": "CHATTERMATE",
"model_name": "chattermate",
"model_type": "REPLYPIER",
"model_name": "replypier",
"api_key": "any_key"
}
@@ -355,7 +355,7 @@ def test_setup_ai_chattermate_missing_key(client, db, test_user):
json=config_data
)
assert response.status_code == 500
assert "ChatterMate API configuration missing" in response.json()["detail"]
assert "ReplyPier API configuration missing" in response.json()["detail"]
def test_setup_ai_general_exception(client, db, test_user):
"""Test setup AI with general exception"""
@@ -432,8 +432,8 @@ def test_get_providers(client, db, test_user):
# Newly enabled providers are present alongside OpenAI/Groq
for expected in ("OPENAI", "GROQ", "ANTHROPIC", "GOOGLE", "MISTRAL", "XAI", "DEEPSEEK", "OPENAI_COMPATIBLE"):
assert expected in providers, f"{expected} missing from /providers"
# ChatterMate (managed) is not a user-selectable BYO-key provider
assert "CHATTERMATE" not in providers
# ReplyPier (managed) is not a user-selectable BYO-key provider
assert "REPLYPIER" not in providers
# Each provider exposes suggested models and BYO-key metadata
openai = providers["OPENAI"]
assert openai["requires_api_key"] is True
@@ -616,15 +616,15 @@ def test_update_ai_config_validation_exception(client, db, test_user, test_ai_co
assert data["detail"]["type"] == "api_key_validation_error"
@patch.dict(os.environ, {
'CHATTERMATE_API_KEY': 'test_chattermate_key',
'CHATTERMATE_MODEL_NAME': 'gpt-4o-mini'
'REPLYPIER_API_KEY': 'test_replypier_key',
'REPLYPIER_MODEL_NAME': 'gpt-4o-mini'
})
@patch('app.api.ai_setup.HAS_ENTERPRISE', True)
def test_update_ai_config_chattermate_success(client, db, test_user, test_ai_config):
"""Test successful ChatterMate AI config update"""
def test_update_ai_config_replypier_success(client, db, test_user, test_ai_config):
"""Test successful ReplyPier AI config update"""
update_data = {
"model_type": "CHATTERMATE",
"model_name": "chattermate"
"model_type": "REPLYPIER",
"model_name": "replypier"
}
response = client.put(
@@ -634,15 +634,15 @@ def test_update_ai_config_chattermate_success(client, db, test_user, test_ai_con
assert response.status_code == 200
data = response.json()
assert data["message"] == "AI configuration updated successfully"
assert data["config"]["model_type"] == "CHATTERMATE"
assert data["config"]["model_type"] == "REPLYPIER"
@patch.dict(os.environ, {}, clear=True)
@patch('app.api.ai_setup.HAS_ENTERPRISE', True)
def test_update_ai_config_chattermate_missing_key(client, db, test_user, test_ai_config):
"""Test ChatterMate AI config update with missing API key"""
def test_update_ai_config_replypier_missing_key(client, db, test_user, test_ai_config):
"""Test ReplyPier AI config update with missing API key"""
update_data = {
"model_type": "CHATTERMATE",
"model_name": "chattermate"
"model_type": "REPLYPIER",
"model_name": "replypier"
}
response = client.put(
@@ -650,7 +650,7 @@ def test_update_ai_config_chattermate_missing_key(client, db, test_user, test_ai
json=update_data
)
assert response.status_code == 500
assert "ChatterMate API configuration missing" in response.json()["detail"]
assert "ReplyPier API configuration missing" in response.json()["detail"]
def test_update_ai_config_general_exception(client, db, test_user, test_ai_config):
"""Test update AI config with general exception"""
@@ -670,11 +670,11 @@ def test_update_ai_config_general_exception(client, db, test_user, test_ai_confi
assert response.status_code == 500
assert response.json()["detail"] == "Failed to update AI configuration"
def test_validate_model_selection_chattermate():
"""Test validate_model_selection with ChatterMate"""
def test_validate_model_selection_replypier():
"""Test validate_model_selection with ReplyPier"""
# Should not raise any exception
ai_setup_router.validate_model_selection("CHATTERMATE", "chattermate")
ai_setup_router.validate_model_selection("chattermate", "CHATTERMATE")
ai_setup_router.validate_model_selection("REPLYPIER", "replypier")
ai_setup_router.validate_model_selection("replypier", "REPLYPIER")
def test_validate_model_selection_groq_valid():
"""Test validate_model_selection with valid Groq model"""
@@ -726,18 +726,18 @@ def test_validate_model_selection_unsupported_provider():
def test_setup_ai_unsupported_model_type(client, db, test_user):
"""Test setup AI with unsupported model type for API key validation"""
config_data = {
"model_type": "CHATTERMATE",
"model_name": "some-model", # Invalid model name for ChatterMate
"model_type": "REPLYPIER",
"model_name": "some-model", # Invalid model name for ReplyPier
"api_key": "test_valid_key"
}
# When HAS_ENTERPRISE is False, ChatterMate should be rejected by validation
# When HAS_ENTERPRISE is False, ReplyPier should be rejected by validation
with patch('app.api.ai_setup.HAS_ENTERPRISE', False):
response = client.post(
"/api/ai/setup",
json=config_data
)
# Should fail validation because CHATTERMATE with non-"chattermate" model name is invalid
# Should fail validation because REPLYPIER with non-"replypier" model name is invalid
assert response.status_code == 400
data = response.json()
assert "error" in data["detail"]
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+3 -3
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -152,7 +152,7 @@ def test_faq_seo_fields_round_trip(client):
created = client.post(f"{BASE}/faqs", json={
"question": "What does it cost?", "answer": "From $19.",
"slug": "Pricing & Plans!", "meta_title": "Pricing",
"meta_description": "What ChatterMate costs.",
"meta_description": "What ReplyPier costs.",
})
assert created.status_code == 201
# A hand-typed slug is normalized the same way a generated one is.
@@ -163,7 +163,7 @@ def test_faq_seo_fields_round_trip(client):
updated = client.put(f"{BASE}/faqs/{faq_id}", json={"slug": "our-pricing"})
assert updated.json()["slug"] == "our-pricing"
# Untouched overrides survive a partial update.
assert updated.json()["meta_description"] == "What ChatterMate costs."
assert updated.json()["meta_description"] == "What ReplyPier costs."
def test_faq_slug_is_deduped_but_stable_for_its_own_row(client):
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+15 -15
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -34,7 +34,7 @@ from app.models.help_center import HelpCenterSettings
from app.repositories.faq import FAQRepository
from app.services.help_center_public import contrast_ink, resolve_help_center, slug_for_host
HOST = "test-org.chattermate.help"
HOST = "test-org.help.replypier.site"
@pytest.fixture(autouse=True)
@@ -108,9 +108,9 @@ def path_client(db, monkeypatch):
# ---------- helpers ----------
def test_slug_for_host():
assert slug_for_host("acme.chattermate.help") == "acme"
assert slug_for_host("a.b.chattermate.help") is None
assert slug_for_host("chattermate.help") is None
assert slug_for_host("acme.help.replypier.site") == "acme"
assert slug_for_host("a.b.help.replypier.site") is None
assert slug_for_host("help.replypier.site") is None
assert slug_for_host("help.acme.com") is None
@@ -279,7 +279,7 @@ def test_widget_embed_points_at_this_install(
client, db, test_organization, help_center, test_widget, monkeypatch
):
"""The loader falls back to the API URL baked in at build time (the vendor
cloud) unless the page sets window.chattermateBaseUrl. Without it, a
cloud) unless the page sets window.replypierBaseUrl. Without it, a
self-hosted help center asks the wrong backend for its widget and the
visitor gets "Chat Unavailable"."""
monkeypatch.setattr(settings, "BACKEND_URL", "https://api.selfhosted.example")
@@ -287,8 +287,8 @@ def test_widget_embed_points_at_this_install(
db.commit()
r = client.get("/", headers={"host": HOST})
assert f'window.chattermateId = "{test_widget.id}"' in r.text
assert 'window.chattermateBaseUrl = "https://api.selfhosted.example/api/v1"' in r.text
assert f'window.replypierId = "{test_widget.id}"' in r.text
assert 'window.replypierBaseUrl = "https://api.selfhosted.example/api/v1"' in r.text
def test_custom_domain_page_is_self_contained(
@@ -316,7 +316,7 @@ def test_custom_domain_page_is_self_contained(
'<meta property="og:image" content="https://help.customer.com/api/v1/uploads/help_center/logo.png">'
in r.text
)
assert 'window.chattermateBaseUrl = "https://api.selfhosted.example/api/v1"' in r.text
assert 'window.replypierBaseUrl = "https://api.selfhosted.example/api/v1"' in r.text
def test_og_card_degrades_without_a_logo(client, db, test_organization, help_center):
@@ -336,7 +336,7 @@ def test_search_filters_results(client, db, test_organization, help_center):
def test_disabled_or_unknown_hosts_404(client, db, test_organization, help_center):
assert client.get("/", headers={"host": "nope.chattermate.help"}).status_code == 404
assert client.get("/", headers={"host": "nope.help.replypier.site"}).status_code == 404
help_center.enabled = False
db.commit()
assert client.get("/", headers={"host": HOST}).status_code == 404
@@ -480,9 +480,9 @@ def test_ask_unanswerable_503(client, db, test_organization, help_center, test_a
# ---------- host dispatch ----------
def test_is_help_center_host_matches_subdomains_only():
assert is_help_center_host("acme.chattermate.help") is True
assert is_help_center_host("chattermate.help") is False
assert is_help_center_host("api.chattermate.chat") is False
assert is_help_center_host("acme.help.replypier.site") is True
assert is_help_center_host("help.replypier.site") is False
assert is_help_center_host("api.replypier.site") is False
assert is_help_center_host("") is False
@@ -566,7 +566,7 @@ def test_preserved_path_drives_canonical_and_json_ld(
r = client.get(MIGRATED_PATH, headers={"host": HOST})
expected = f"https://test-org.chattermate.help{MIGRATED_PATH}"
expected = f"https://test-org.help.replypier.site{MIGRATED_PATH}"
assert f'<link rel="canonical" href="{expected}">' in r.text
assert f'<meta property="og:url" content="{expected}">' in r.text
graph = json.loads(re.search(
@@ -583,7 +583,7 @@ def test_sitemap_lists_the_preserved_path(client, db, test_organization, help_ce
r = client.get("/sitemap.xml", headers={"host": HOST})
assert f"<loc>https://test-org.chattermate.help{MIGRATED_PATH}</loc>" in r.text
assert f"<loc>https://test-org.help.replypier.site{MIGRATED_PATH}</loc>" in r.text
assert "/a/how-do-i-reset-my-password" not in r.text
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -30,7 +30,7 @@ ASK = "/health/help-center-domain"
def test_allows_slug_subdomain():
# {slug}.HELP_CENTER_BASE_DOMAIN is a help-center host without any DB lookup.
assert client.get(ASK, params={"domain": "acme.chattermate.help"}).status_code == 200
assert client.get(ASK, params={"domain": "acme.help.replypier.site"}).status_code == 200
def test_allows_verified_custom_domain():
@@ -53,4 +53,4 @@ def test_rejects_missing_or_empty_domain():
def test_normalizes_host_with_port_and_uppercase():
# SNI can arrive with a port / mixed case; normalize_host must canonicalize
# it so the slug match still succeeds.
assert client.get(ASK, params={"domain": "ACME.chattermate.help:443"}).status_code == 200
assert client.get(ASK, params={"domain": "ACME.help.replypier.site:443"}).status_code == 200
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+2 -2
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -15,7 +15,7 @@ limitations under the License.
"""
"""
ChatterMate - MCP Tool API Tests
ReplyPier - MCP Tool API Tests
"""
import pytest
+2 -2
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -426,7 +426,7 @@ class TestTemplateManagement:
assert graph.await_count == 1
class TestEmbeddedSignupConfig:
"""Embedded Signup onboards a number under ChatterMate's own approved Meta
"""Embedded Signup onboards a number under ReplyPier's own approved Meta
app, so without a config id it structurally cannot work — that is the whole
gate. Like every other integration, it is not restricted by plan."""
+8 -8
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -40,8 +40,8 @@ from app.repositories.channels import ChannelAccountRepository
BASE = "/api/v1/channels/meta"
WEBHOOK = "/api/v1/webhooks/meta"
OUR_SECRET = "chattermate-app-secret"
OUR_APP_ID = "APP_CHATTERMATE"
OUR_SECRET = "replypier-app-secret"
OUR_APP_ID = "APP_REPLYPIER"
THEIR_SECRET = "customer-app-secret"
THEIR_APP_ID = "APP_THEIRS"
OVERRIDE_RELEASED = {"webhook_configuration": {"override_callback_uri": ""}}
@@ -133,7 +133,7 @@ class TestOwnAppWebhook:
@pytest.mark.parametrize("secret", [OUR_SECRET, "guess"])
def test_any_other_secret_is_refused(self, client, db, test_organization, secret):
"""ChatterMate's own secret included: this address answers to one app only."""
"""ReplyPier's own secret included: this address answers to one app only."""
account = _account(db, test_organization.id)
response, process, _ = _post(client, account.id, _wa_message(), secret)
assert response.status_code == 403
@@ -163,7 +163,7 @@ class TestOwnAppWebhook:
db.commit()
_account(db, other_org.id, external_id="PN-THEIRS") # same app id, other org
_account(db, test_organization.id, external_id="PN-OTHER-APP", app_id="APP_ELSE")
_account(db, test_organization.id, external_id="PN-SHARED", app_id=None) # via ChatterMate's app
_account(db, test_organization.id, external_id="PN-SHARED", app_id=None) # via ReplyPier's app
for number in ("PN-THEIRS", "PN-OTHER-APP", "PN-SHARED"):
response, process, status = _post(client, ours.id, _wa_message(number))
assert response.status_code == 200
@@ -208,7 +208,7 @@ class TestOwnAppWebhook:
"hub.mode": "subscribe", "hub.verify_token": token, "hub.challenge": "42"})
assert bad.status_code == 403
def test_no_handshake_for_an_account_from_chattermates_app(self, client, db, test_organization):
def test_no_handshake_for_an_account_from_replypiers_app(self, client, db, test_organization):
account = _account(db, test_organization.id, app_id=None)
response = client.get(f"{WEBHOOK}/{account.id}", params={
"hub.mode": "subscribe", "hub.verify_token": account.webhook_secret, "hub.challenge": "42"})
@@ -311,8 +311,8 @@ class TestConnect:
assert response.json()["webhook_url"] is None
assert APP_ID_SETTING not in (_stored(db)[0].settings or {})
def test_chattermates_own_app_needs_no_address(self, client, db):
"""A self-hoster's number in the app ChatterMate runs on already
def test_replypiers_own_app_needs_no_address(self, client, db):
"""A self-hoster's number in the app ReplyPier runs on already
reaches the shared address: nothing is stored or re-pointed."""
response, _, graph_post = _connect_whatsapp(client, app=(True, {"id": OUR_APP_ID}))
assert response.status_code == 200
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+2 -2
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -277,7 +277,7 @@ def test_parse_dm_with_thread_keys_by_thread(adapter):
assert m.external_conversation_id == "D7:1719999999.0001"
DASH = "https://app.chattermate.chat"
DASH = "https://app.replypier.site"
class TestHomeView:
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
+3 -3
View File
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -81,7 +81,7 @@ def test_configure_socketio_with_redis_enabled(mock_redis_manager, mock_settings
configure_socketio()
mock_redis_manager.assert_called_once_with(
"redis://localhost:6379", write_only=False, channel='chattermate', redis_options=REDIS_OPTIONS,
"redis://localhost:6379", write_only=False, channel='replypier', redis_options=REDIS_OPTIONS,
)
assert sio.manager is mock_redis_instance
mock_redis_instance.set_server.assert_called_once_with(sio)
@@ -99,7 +99,7 @@ def test_configure_socketio_with_elasticache(mock_redis_manager, mock_settings,
configure_socketio()
mock_redis_manager.assert_called_once_with(
"rediss://my-cluster.cache.amazonaws.com:6379", write_only=False, channel='chattermate',
"rediss://my-cluster.cache.amazonaws.com:6379", write_only=False, channel='replypier',
redis_options={**REDIS_OPTIONS, 'ssl_cert_reqs': None},
)
@@ -1,5 +1,5 @@
"""
Copyright 2024-2026 ChatterMate
Copyright 2024-2026 ReplyPier
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
Loaded 100 of 1156 files, more files were not shown because too many files have changed in this diff. Show more