Introduction
NGOs and activist organizations in Turkey face escalating surveillance and communication restrictions. Following repeated internet shutdowns during protests and increased social media blocking, digital security is no longer optional, it is operational necessity. This guide provides developers and power users with practical implementations for establishing secure, resilient communication channels.
The threat model includes ISP-level traffic analysis, messaging app metadata collection, SIM-card tracking, and physical device seizure. Effective communication security requires addressing each vector systematically. Turkey’s Information and Communication Technologies Authority (BTK) maintains real-time filtering infrastructure capable of blocking VPN protocols, specific IP ranges, and application fingerprints within hours of a judicial order. Your architecture must assume each individual tool may fail and build redundancy accordingly.
Prerequisites
Before you begin, make sure you have the following ready:
- A computer running macOS, Linux, or Windows
- Terminal or command-line access
- Administrator or sudo privileges (for system-level changes)
- A stable internet connection for downloading tools
Step 1 - End-to-End Encrypted Messaging
Signal remains the gold standard for encrypted messaging. Unlike WhatsApp, Signal’s protocol is open-source and audited, with minimal metadata retention. However, Signal requires a phone number, which creates identification risk.
For higher-risk scenarios, consider Session, a messenger that operates without phone numbers, using the Signal protocol on the onion routing network:
Verify Session builds (for advanced users compiling from source)
git clone https://github.com/oxen-io/session-desktop.git
cd session-desktop
npm install && npm run build:linux
Configure Session with a dedicated device, never linked to your primary phone number. Generate a random display name and store your seed phrase in a password manager, not on the device itself.
Element on Matrix provides a third option with federated infrastructure. Unlike centralized apps, Matrix allows your organization to control its own server. Even if Turkish authorities compel one homeserver to comply, federated rooms continue functioning across other servers. See the self-hosted Matrix Synapse server guide for full deployment instructions.
Choosing Messenger by Risk Level
Not every team member operates at the same risk level. Structure your communication stack in tiers:
| Risk Level | Recommended Tool | Rationale |
|---|---|---|
| Low (public coordination) | Signal with disappearing messages | Widely available, audited |
| Medium (internal organizing) | Session or Matrix | No phone number / self-hosted |
| High (sensitive operations) | Matrix over Tor onion service | No identifying metadata |
| Extreme (device seizure likely) | Briar over Bluetooth | No internet required |
Deploy the appropriate tier for each activity rather than relying on a single tool for everything.
Self-Hosted Matrix Deployment
For organizations wanting infrastructure control, Matrix with Element clients provides a decentralized alternative. Running your own homeserver means controlling which data gets logged:
docker-compose.yml for minimal Matrix deployment
version: '3'
services:
synapse:
image: matrixdotorg/synapse:latest
container_name: synapse
ports:
- "8008:8008"
volumes:
- ./synapse:/data
environment:
- SYNAPSE_REGISTRATION_SECRET=your-secure-random-secret
- SYNAPSE_REPORT_STATISTICS=no
Run this behind Tor onion services to hide server existence:
nginx configuration for Tor onion service
location / {
proxy_pass http://localhost:8008;
proxy_set_header X-Forwarded-For $remote_addr;
proxy_set_header X-Real-IP $remote_addr;
}
Step 2 - Network Resilience: Tor and Mesh Networks
Tor Onion Services
Hosting your communication infrastructure as Tor onion services prevents network-level blocking and provides strong anonymity. Create an onion service configuration:
/etc/tor/torrc configuration
HiddenServiceDir /var/lib/tor/hidden_service/
HiddenServicePort 80 127.0.0.1:8080
HiddenServicePort 443 127.0.0.1:8443
Your .onion URL becomes your organization’s private address, inaccessible from regular internet connections but functional even during censorship events.
Tor bridges add an additional layer when the standard Tor network is blocked. Configure obfs4 bridges in Tor Browser or the standalone Tor daemon:
/etc/tor/torrc. obfs4 bridge configuration
UseBridges 1
ClientTransportPlugin obfs4 exec /usr/bin/obfs4proxy
Bridge obfs4 <BRIDGE_IP>:<PORT> <FINGERPRINT> cert=<CERT> iat-mode=0
Request fresh bridge addresses from bridges.torproject.org or by emailing bridges@torproject.org from a ProtonMail or Gmail account. Turkey’s BTK periodically blocks known bridge lists, so maintain at least three active bridge addresses.
Briar for Mesh Messaging
When internet access is completely blocked, Briar enables bluetooth and Wi-Fi direct messaging between nearby devices. Install via F-Droid:
Add F-Droid repository (for paranoid users)
Download Briar APK from briarproject.org
Verify GPG signature before installation
Briar propagates messages through the network as devices come within range, creating resilient communication without central infrastructure. During the 2022 and 2023 Turkish blackout events, activists using Briar maintained local coordination while internet users lost contact. Pre-exchange contacts before any anticipated connectivity disruption, Briar contact pairing requires an initial internet connection or physical proximity.
VPN Selection and Protocol Hardening
Commercial VPNs face aggressive blocking in Turkey. Providers using WireGuard or OpenVPN on default ports are frequently disrupted. Prefer providers offering:
- Shadowsocks or V2Ray obfuscation. traffic looks like HTTPS
- Stealth/obfuscated mode. protocol fingerprint masking
- Onion over VPN. routes your VPN through Tor for extra resilience
If running your own WireGuard server outside Turkey, disguise the traffic:
Install shadowsocks-libev on your VPN server
sudo apt install shadowsocks-libev
/etc/shadowsocks-libev/config.json
{
"server": "0.0.0.0",
"server_port": 443,
"password": "strong-random-password",
"method": "chacha20-ietf-poly1305",
"plugin": "obfs-server",
"plugin_opts": "obfs=tls"
}
Port 443 with TLS obfuscation is the most resilient option, blocking it would disable standard HTTPS traffic, which carries severe economic and political costs for any government.
Step 3 - Secure File Transfer and Storage
Onion-Share for Sensitive Document Transfer
Onion-Share creates temporary, anonymous file transfer servers accessible only through Tor:
Install on Linux
sudo apt install onionshare
Create a persistent sharing link
onionshare --persistent --title "NGO-Docs-Transfer" /path/to/documents/
The generated link works for one-time or persistent sharing, with automatic Tor circuit rotation. Recipients need Tor Browser, no additional software or accounts required. This is significantly safer than emailing attachments through providers subject to Turkish judicial data requests.
Encrypted Cloud Storage
Avoid US-based cloud services with questionable data disclosure policies. Tresorit (Swiss-based, end-to-end encrypted) and Filen (German-based, zero-knowledge) provide geographic jurisdictions with stronger privacy protections.
For self-hosted alternatives, Nextcloud with end-to-end encrypted folders provides fine-grained control. Deploy on a server outside Turkey and access through a Tor onion service address for maximum resistance to blocking.
Step 4 - Operational Security Practices
Device Security Fundamentals
- Enable full-disk encryption on all devices: ```bash Linux sudo cryptsetup luksFormat /dev/sdX
macOS (FileVault) sudo fdesetup enable
2. Use separate devices for sensitive communications. A dedicated "operations phone" with:
- No SIM card (use Wi-Fi only)
- Privacy-focused ROM (GrapheneOS or CalyxOS)
- No Google Play Services
- All network toggles disabled when not in use
3. Duress PIN. GrapheneOS supports a secondary PIN that wipes the device or opens a clean profile. Configure this before any high-risk activity.
Metadata Protection
Metadata can be as revealing as content. Minimize exposure by:
- Using Tor Browser for all research activities
- Configuring your phone to randomize MAC addresses on every Wi-Fi join
- Avoiding SMS/standard calls entirely, Turkish operators retain CDRs (call detail records) for years
- Rotating Signal numbers periodically; use eSIM providers outside Turkey for registration
- Stripping EXIF data from all photos before sharing (ExifTool handles batch processing)
```bash
Strip EXIF from all JPEGs in a directory
exiftool -all= /path/to/photos/*.jpg
Communication Protocol Hardening
For advanced users running self-hosted solutions, implement these Nginx headers:
security headers for Matrix/Element deployment
add_header X-Frame-Options "DENY" always;
add_header X-Content-Type-Options "nosniff" always;
add_header Referrer-Policy "no-referrer" always;
add_header Content-Security-Policy "default-src 'none'; frame-ancestors 'none'" always;
Also enable HSTS to prevent SSL stripping attacks, which can expose onion service hostnames in HTTP redirects:
add_header Strict-Transport-Security "max-age=63072000; includeSubDomains; preload" always;
Step 5 - Emergency Protocols
Communication Contingency Planning
Establish pre-agreed communication methods for different threat scenarios:
| Scenario | Primary | Secondary | Tertiary |
|---|---|---|---|
| Internet active | Signal | Matrix | Email (PGP) |
| Social media blocked | Tor Browser | VPN | None |
| Internet shutdown | Briar | Mesh network | Physical dead drops |
| Mass arrests | Pre-arranged signal | Time-delayed messages | None |
Run quarterly drills switching between tiers so team members are comfortable with each tool before they need it under pressure. Document the protocols in encrypted storage, not in Google Docs or shared cloud drives.
Signal Dead Man’s Switch
Configure a dead man switch using automated scripts:
#!/usr/bin/env python3
signal-auto-delete.py - Example concept
import subprocess
import schedule
import time
def check_and_delete():
# Check last message timestamp
# If exceeded threshold, delete local messages
subprocess.run(["rm", "-rf", "~/.config/Signal/"])
schedule.every(24).hours.do(check_and_delete)
while True:
schedule.run_pending()
time.sleep(60)
This ensures messages are automatically purged if you cannot access your device.
Device Seizure Protocol
Train all team members on a three-step response to device seizure risk:
- Remote wipe: Enable remote wipe on all organization devices through a self-hosted MDM (Headwind MDM or similar) so you can trigger wipes from any internet connection if a device is detained.
- Pre-commitment deletion: Set disappearing message timers on all active conversations. One week is a reasonable default; reduce to 24 hours for sensitive operations.
- Key rotation: After any device is seized, treat all keys that device held as compromised. Rotate Signal safety numbers, Matrix verification, and any stored passwords immediately.
Troubleshooting
Configuration changes not taking effect
Restart the relevant service or application after making changes. Some settings require a full system reboot. Verify the configuration file path is correct and the syntax is valid.
Permission denied errors
Run the command with sudo for system-level operations, or check that your user account has the necessary permissions. On macOS, you may need to grant terminal access in System Settings > Privacy & Security.
Connection or network-related failures
Check your internet connection and firewall settings. If using a VPN, try disconnecting temporarily to isolate the issue. Verify that the target server or service is accessible from your network.
Frequently Asked Questions
How long does it take to activists and ngos?
For a straightforward setup, expect 30 minutes to 2 hours depending on your familiarity with the tools involved. Complex configurations with custom requirements may take longer. Having your credentials and environment ready before starting saves significant time.
What are the most common mistakes to avoid?
The most frequent issues are skipping prerequisite steps, using outdated package versions, and not reading error messages carefully. Follow the steps in order, verify each one works before moving on, and check the official documentation if something behaves unexpectedly.
Do I need prior experience to follow this guide?
Basic familiarity with the relevant tools and command line is helpful but not strictly required. Each step is explained with context. If you get stuck, the official documentation for each tool covers fundamentals that may fill in knowledge gaps.
Is this approach secure enough for production?
The patterns shown here follow standard practices, but production deployments need additional hardening. Add rate limiting, input validation, proper secret management, and monitoring before going live. Consider a security review if your application handles sensitive user data.
Where can I get help if I run into issues?
Start with the official documentation for each tool mentioned. Stack Overflow and GitHub Issues are good next steps for specific error messages. Community forums and Discord servers for the relevant tools often have active members who can help with setup problems.
Related Articles
- Set Up Secure Communication For Labor Strike: Practical
- Set Up Secure Communication for Labor Strike Organizing
- Best Encrypted Communication For Activists
- Lawyer Client Privilege Digital Communication Secure Setup
- Secure Communication Plan Template for Organizations
- AI Coding Assistant Session Data Lifecycle Built by theluckystrike. More at zovo.one