PySpark最佳实践:如何去除Web请求日志中的URL参数?
PySpark移除Web日志URL参数解决方案
最优实现方案(内置函数,性能最优)
你要的效果可以直接用PySpark内置的regexp_replace函数实现,无需自定义UDF,处理大数据量时性能远高于UDF方案:
from pyspark.sql.functions import regexp_replace # 直接替换原weblog列,也可以自定义新列名存储处理结果 processed_sdf = sdf.withColumn( "weblog", # 正则匹配?开头到HTTP/之前的所有内容,替换为单个? regexp_replace("weblog", r"\?(.*?)(?=HTTP/)", "?") ) # 输出验证结果 processed_sdf.show(truncate=False)
正则规则说明:
\?:匹配日志中的?符号(.*?):非贪婪匹配任意字符(?=HTTP/):正向零宽断言,匹配到HTTP/就停止,不会删除HTTP/及后面的内容
类“两列相减”实现方案
如果你需要先提取URL参数单独存为一列,再做替换,可以用如下写法,PySpark没有原生字符串相减语法,可通过提取+替换实现:
from pyspark.sql.functions import regexp_extract, concat, lit, col sdf_with_params = sdf.withColumn( # 提取?到HTTP/之间的参数内容,存为url_parameters列 "url_parameters", regexp_extract("weblog", r"\?(.*?)(?=HTTP/)", 1) ).withColumn( "Result", # 把原日志中?+参数的部分替换为单个? regexp_replace("weblog", concat(lit("?"), col("url_parameters")), "?") )
原方案失效原因
你之前用urllib的urlsplit方案失效,是因为该工具是用来解析纯URL字符串的,你的日志行包含请求方法、HTTP版本、UA等非URL内容,无法被urlsplit正确识别拆分,自然无法拿到正确的query参数部分。
内容的提问来源于stack exchange,提问作者Mario
相关产品推荐
相关产品推荐

