如何使用 Groovy 代码在响应正文中删除 Gerrit 的 REST API 魔法前缀?
How do you remove Gerrit's REST API's magic prefix in the response body with Groovy code?
我的代码:
@Grab('org.codehaus.groovy.modules.http-builder:http-builder:0.7')
@Grab('oauth.signpost:signpost-core:1.2.1.2')
@Grab('oauth.signpost:signpost-commonshttp4:1.2.1.2')
import groovyx.net.http.RESTClient
import static groovyx.net.http.ContentType.*
def gerrit = new RESTClient('http://localhost:8080/gerrit')
gerrit.auth.basic "gerrit", "password123"
gerrit.get( path: 'changes/1234/reviewers' )
根据https://gerrit-review.googlesource.com/Documentation/rest-api.html#authentication
"To prevent against Cross Site Script Inclusion (XSSI) attacks, the JSON response body starts with a magic prefix line that must be stripped before feeding the rest of the response body to a JSON parser:"
)]}'
[ ... valid JSON ... ]
我的错误:
WARNING: Error parsing 'application/json; charset=UTF-8' response
groovy.json.JsonException: Unable to determine the current character, it is not a string, number, array, or object
The current character read is ')' with an int value of 41
Unable to determine the current character, it is not a string, number, array, or object
line number 1
index number 0
)]}'
抱歉,我对 Groovy 不是很熟悉,但是除非您想修改源代码并推出自己的版本,否则无法从 Gerrit 中删除此前缀。
解决方案是使用不同的Groovy API获取原始数据,去掉前5个字符,然后将其输入Groovy JSON 解析器。再次抱歉,但我无法帮助解决 Groovy API 可能是一个选项的问题。
如文档所述,这些字符有时很烦人,但这是 Gerrit 的一项重要安全功能,可防止任何 XSS 黑客攻击。
我找到了答案。
@Grab('org.codehaus.groovy.modules.http-builder:http-builder:0.7')
@Grab('oauth.signpost:signpost-core:1.2.1.2')
@Grab('oauth.signpost:signpost-commonshttp4:1.2.1.2')
import groovyx.net.http.RESTClient
import static groovyx.net.http.Method.*
import static groovyx.net.http.ContentType.*
import groovy.json.JsonSlurper
public class GerritRestClient {
def gerrit
GerritRestClient(config) {
def username = config.username
def password = config.password
this.gerrit = new RESTClient(config.endpoint)
this.gerrit.auth.basic config.username, config.password
}
def sendRequest(path) {
this.gerrit.request(GET,TEXT) { req ->
uri.path = path // overrides any path in the default URL
response.success = { resp, json ->
assert resp.status == 200
def fixedJson = json.text.replaceAll('\)]}\'', '').trim() // remove magic prefix
def jsonSlurper = new JsonSlurper()
return jsonSlurper.parseText(fixedJson) // parse the fixed json body and return
}
// called only for a 404 (not found) status code:
response.failure = { resp ->
println "My response handler got response: ${resp.statusLine}"
return null
}
}
}
def getChangeReviewers(changeNumber) {
def requestPath = "changes/${changeNumber}/reviewers"
return sendRequest(requestPath)
}
}
我的代码:
@Grab('org.codehaus.groovy.modules.http-builder:http-builder:0.7')
@Grab('oauth.signpost:signpost-core:1.2.1.2')
@Grab('oauth.signpost:signpost-commonshttp4:1.2.1.2')
import groovyx.net.http.RESTClient
import static groovyx.net.http.ContentType.*
def gerrit = new RESTClient('http://localhost:8080/gerrit')
gerrit.auth.basic "gerrit", "password123"
gerrit.get( path: 'changes/1234/reviewers' )
根据https://gerrit-review.googlesource.com/Documentation/rest-api.html#authentication
"To prevent against Cross Site Script Inclusion (XSSI) attacks, the JSON response body starts with a magic prefix line that must be stripped before feeding the rest of the response body to a JSON parser:"
)]}'
[ ... valid JSON ... ]
我的错误:
WARNING: Error parsing 'application/json; charset=UTF-8' response
groovy.json.JsonException: Unable to determine the current character, it is not a string, number, array, or object
The current character read is ')' with an int value of 41
Unable to determine the current character, it is not a string, number, array, or object
line number 1
index number 0
)]}'
抱歉,我对 Groovy 不是很熟悉,但是除非您想修改源代码并推出自己的版本,否则无法从 Gerrit 中删除此前缀。
解决方案是使用不同的Groovy API获取原始数据,去掉前5个字符,然后将其输入Groovy JSON 解析器。再次抱歉,但我无法帮助解决 Groovy API 可能是一个选项的问题。
如文档所述,这些字符有时很烦人,但这是 Gerrit 的一项重要安全功能,可防止任何 XSS 黑客攻击。
我找到了答案。
@Grab('org.codehaus.groovy.modules.http-builder:http-builder:0.7')
@Grab('oauth.signpost:signpost-core:1.2.1.2')
@Grab('oauth.signpost:signpost-commonshttp4:1.2.1.2')
import groovyx.net.http.RESTClient
import static groovyx.net.http.Method.*
import static groovyx.net.http.ContentType.*
import groovy.json.JsonSlurper
public class GerritRestClient {
def gerrit
GerritRestClient(config) {
def username = config.username
def password = config.password
this.gerrit = new RESTClient(config.endpoint)
this.gerrit.auth.basic config.username, config.password
}
def sendRequest(path) {
this.gerrit.request(GET,TEXT) { req ->
uri.path = path // overrides any path in the default URL
response.success = { resp, json ->
assert resp.status == 200
def fixedJson = json.text.replaceAll('\)]}\'', '').trim() // remove magic prefix
def jsonSlurper = new JsonSlurper()
return jsonSlurper.parseText(fixedJson) // parse the fixed json body and return
}
// called only for a 404 (not found) status code:
response.failure = { resp ->
println "My response handler got response: ${resp.statusLine}"
return null
}
}
}
def getChangeReviewers(changeNumber) {
def requestPath = "changes/${changeNumber}/reviewers"
return sendRequest(requestPath)
}
}