开放网络干扰观测组织 (OONI) 是一个非营利性的自由软件项目,旨在支持记录全球互联网审查制度的分散式努力。OONI 提供免费的软件工具,供用户测试他们的互联网连接质量、检测审查制度和测量网络干扰。这些测试可以揭示被阻止或限制的网站、应用程序或服务,并帮助识别技术审查方法。
OONI 使用 ClickHouse 作为其数据存储和分析引擎,处理大量数据。ClickHouse 使 OONI 能够对其网络测量测试收集的大量数据执行复杂的查询。它还支持生成可视化效果,这有助于识别数据中的趋势和模式。
OONI 的使命和全球影响力
OONI 成立至今已有十年以上,旨在提高全球互联网审查制度的透明度。他们的工具之一 OONI Probe 允许用户运行网络实验,以确定哪些网站、即时通讯应用程序和规避工具在其网络上受到限制。
OONI 收集其全球志愿者网络生成的数据,对其进行分析,以开放数据形式发布,并制作研究报告,将调查结果置于特定国家、地区和正在进行的社会或政治事件的背景下。该组织还与全球 43 个合作伙伴组织合作,传播调查结果,开展宣传,并支持政策制定和法律行动。
从 PostgreSQL 到 ClickHouse:提高性能并简化架构
OONI 测量聚合工具包 (MAT) 显示在中国、伊朗、缅甸和俄罗斯 twitter.com 的屏蔽情况 (查看仪表板)。
OONI Explorer 是一个开放数据平台,用户可以通过它浏览收集的数据,了解审查制度的技术实施方式。他们需要一个解决方案,可以简化他们的架构,同时处理复杂的数据可视化,并支持对其 10 亿+ 行数据集进行搜索和聚合。
在使用 ClickHouse 之前,OONI 使用平面文件、MongoDB 和 PostgreSQL 来存储测量实验的元数据。然而,由于其庞大的数据集,他们面临性能问题。随着数据集增长到数亿行,性能问题开始出现,需要从 OLTP 数据库迁移到 OLAP 数据库。
数据管道:将 ClickHouse 集成到 OONI 的工作流程中
ClickHouse 简化了 OONI 的架构,使研究人员更容易访问数据。OONI 的首席开发人员 Arturo Filastò 表示:“仅使用一个主表就简化了我们的架构,这使我们能够更快地迭代,并直接在数据集上运行任何查询。” Filastò 还指出,ClickHouse 的效率显着提高了他们的调查效率。“将所有数据放在 ClickHouse 中意味着我们可以快速回答问题,而无需等待数小时才能完成查询,从而显着改善了我们的内部数据分析任务。”
OONI 数据管道的架构涉及在用户设备上运行的探针,这些探针定期执行测量并将结果上传到 OONI 的测量收集 API。
原始数据(压缩的 JSON 文件)存储在 S3 上,而元数据存储在单个大表中。此表包含用于分析和聚合的所有相关元数据,例如国家、网络、时间戳、目标和分析结果。这个大表的架构如下
CREATE TABLE fastpath
(
`measurement_uid` String,
`report_id` String,
`input` String,
`probe_cc` String,
`probe_asn` Int32,
`test_name` String,
`test_start_time` DateTime,
`measurement_start_time` DateTime,
`filename` String,
`scores` String,
`platform` String,
`anomaly` String,
`confirmed` String,
`msm_failure` String,
`domain` String,
`software_name` String,
`software_version` String,
`control_failure` String,
`blocking_general` Float32,
`blocking_type` String,
`test_version` String,
`test_runtime` Float32,
`architecture` String,
`engine_name` String,
`engine_version` String
)
ENGINE = ReplacingMergeTree
ORDER BY (measurement_start_time, report_id, input)
SETTINGS index_granularity = 8192;
它的大小为 14 亿条记录和 32 列,在许多聚合查询中使用,这些查询为 OONI 测量聚合工具包 (MAT) 及其内部数据分析工具提供支持。在数据集上运行的聚合查询基于用户可配置的参数构建,并且在高层具有以下结构
SELECT
countIf(anomaly = 't' AND confirmed = 'f' AND msm_failure = 'f') AS anomaly_count,
countIf(confirmed = 't' AND msm_failure = 'f') AS confirmed_count,
countIf(msm_failure = 't') AS failure_count,
countIf(anomaly = 'f' AND confirmed = 'f' AND msm_failure = 'f') AS ok_count,
COUNT(*) AS measurement_count,
[user configured grouping parameter_a],
[user configured grouping parameter_b]
WHERE
[user configured filter]
GROUP BY [user configured grouping parameter_a], [user configured grouping parameter_b]
这是一个更实际的例子,读者可以尝试。OONI UI 上的以下可视化效果生成了下面编写的查询 - https://explorer.ooni.org/chart/mat?test_name=web_connectivity&axis_x=measurement_start_day&since=2023-04-12&until=2023-05-12&time_grain=day
SELECT
countIf (anomaly = 't' AND confirmed = 'f'
AND msm_failure = 'f') AS anomaly_count,
countIf (confirmed = 't' AND msm_failure = 'f') AS confirmed_count,
countIf (msm_failure = 't') AS failure_count,
countIf (anomaly = 'f' AND confirmed = 'f'
AND msm_failure = 'f') AS ok_count,
COUNT(*) AS measurement_count,
toDate (measurement_start_time) AS measurement_start_day
FROM fastpath
WHERE
measurement_start_time >= '2023-04-12 00:00:00'
AND measurement_start_time < '2023-05-12 00:00:00'
AND test_name IN ['web_connectivity']
GROUP BY measurement_start_day
ORDER BY measurement_start_day
此查询在 600 毫秒内扫描了大约 5900 万行。
通过切换到 ClickHouse,他们发现某些曾经在 PostgreSQL 上运行长达 20 分钟的繁重查询,在 ClickHouse 中仅需数百毫秒。他们还看到数据库的磁盘大小减少了 2 倍。
当使用 PostgreSQL 进行实验元数据存储时,他们在构建 MAT 时遇到了性能问题,并且无法直接查询 SQL 表进行聚合。为了克服这个问题,他们使用了带有预计算计数的计数器表,但是这种方法仍然复杂且效率低下。ClickHouse 使他们能够直接在数据集上执行聚合,而无需维护中间计数器表示,从而简化了数据管道。
借助 ClickHouse,OONI 改进了其架构,以实现更快的数据访问和分析。这允许实时发布测量结果,帮助人权捍卫者快速响应世界各地的审查事件。
了解更多:https://ooni.org/