如何在JMeter中对SAML请求进行Deflate压缩及Base64编码处理
问题原因
你收到AADSTS750056: SAML message was not properly base64-encoded报错的核心原因是操作顺序错误:从响应头提取的SAMLRequest本身已经是Base64编码后再做URL编码的结果,直接对其再次执行Base64编码会导致内容不符合Microsoft AD的SAML 2.0格式要求。
处理方案
分两种场景选择对应方案:
场景1:不需要修改SAML原始内容
你提供的示例中,事务1的SAMLRequest仅做了URL编码,不需要额外编解码操作,直接对提取到的参数做URL解码即可得到事务2需要的格式。
JMeter中直接使用内置__urldecode函数处理:
${__urldecode(${你提取的SAMLRequest变量名},)}
解码后的值可直接传入事务2的请求参数中使用。
场景2:需要修改SAML原始XML内容
如果需要修改SAML请求中的属性、断言地址等内容,需完成完整的解压缩、修改、重压缩流程,在事务1后添加JSR223后置处理器,选择Groovy语言,填入以下代码:
import java.util.zip.Inflater import java.util.zip.Deflater import org.apache.commons.codec.binary.Base64 // 提取原始SAMLRequest参数(替换为你实际的变量名) String rawSaml = vars.get("raw_SAMLRequest") // 第一步:URL解码 String urlDecodedSaml = URLDecoder.decode(rawSaml, "UTF-8") // 第二步:Base64解码得到压缩后的字节流 byte[] compressedBytes = Base64.decodeBase64(urlDecodedSaml) // 第三步:Inflate解压缩得到原始SAML XML(启用nowrap模式符合SAML规范) Inflater inflater = new Inflater(true) inflater.setInput(compressedBytes) byte[] xmlBytes = new byte[10240] int xmlLen = inflater.inflate(xmlBytes) inflater.end() String samlXml = new String(xmlBytes, 0, xmlLen, "UTF-8") // --------------------- // 此处添加你的XML修改逻辑,例如: // samlXml = samlXml.replace("oldAssertionURL", "newAssertionURL") // --------------------- // 第四步:Deflate压缩修改后的XML(启用nowrap模式) Deflater deflater = new Deflater(Deflater.DEFAULT_COMPRESSION, true) deflater.setInput(samlXml.getBytes("UTF-8")) deflater.finish() byte[] compressedOutput = new byte[10240] int compressedLen = deflater.deflate(compressedOutput) deflater.end() // 第五步:Base64编码得到处理后的SAMLRequest String processedSaml = Base64.encodeBase64String(compressedOutput, 0, compressedLen) // 存入变量供后续请求调用 vars.put("processed_SAMLRequest", processedSaml)
注意事项
- Deflater/Inflater实例化时第二个参数必须设为
true,即启用nowrap模式,符合SAML 2.0的压缩规范,否则会导致AD识别失败 - 不需要修改SAML内容时不要做多余的编解码操作,避免引入格式错误
内容的提问来源于stack exchange,提问作者Mahaveer
相关产品推荐
相关产品推荐

