2013-05-24 25 views
12

Tôi muốn sử dụng API từ xa Jenkins và tôi đang tìm giải pháp an toàn. Tôi đi qua Prevent Cross Site Request Forgery exploits và tôi muốn sử dụng nó, nhưng tôi đọc một nơi nào đó mà bạn phải thực hiện một yêu cầu crumb.Cách yêu cầu nhà phát hành Crumb cho jenkins

Có ai có thể giải thích cách nhận được yêu cầu vô giá trị để API hoạt động không?

Tôi tìm thấy số này https://github.com/entagen/jenkins-build-per-branch/pull/20 nhưng tôi vẫn không biết cách khắc phục.

phiên bản My Jenkins là 1.50.x

https://issues.jenkins-ci.org/browse/JENKINS-10374

Trả lời

21

tôi đã không thấy điều này trong các tài liệu một trong hai. Mã này được thử nghiệm với một Jenkins cũ (1.466), nhưng vẫn hoạt động.

Ban hành crumb sử dụng crumbIssuer

// left out: you need to authenticate with user & password -> sample below 
HttpGet httpGet = new HttpGet(jenkinsUrl + "crumbIssuer/api/json"); 
String crumbResponse = toString(httpclient, httpGet); 
CrumbJson crumbJson = new Gson().fromJson(crumbResponse, CrumbJson.class); 

Điều này sẽ giúp bạn có được một câu trả lời như thế này

{"crumb":"fb171d526b9cc9e25afe80b356e12cb7","crumbRequestField":".crumb"} 

này có hai mẩu thông tin bạn cần

  1. tên trường mà bạn cần phải vượt qua các mảnh vụn
  2. vụn tự nó

Nếu bây giờ bạn muốn lấy thứ gì đó từ Jenkins, hãy thêm phần đầu làm mẩu. Trong ví dụ bên dưới, tôi tìm nạp các kết quả xây dựng mới nhất.

HttpPost httpost = new HttpPost(jenkinsUrl + "rssLatest"); 
httpost.addHeader(crumbJson.crumbRequestField, crumbJson.crumb); 

Đây là mã mẫu chung. Tôi đang sử dụng gson 2.2.4 để phân tích cú pháp phản hồi và Apache's httpclient 4.2.3 cho phần còn lại.

import org.apache.http.auth.*; 
import org.apache.http.client.*; 
import org.apache.http.client.methods.*; 
import org.apache.http.impl.client.*; 

import com.google.gson.Gson; 

public class JenkinsMonitor { 

    public static void main(String[] args) throws Exception { 

     String protocol = "http"; 
     String host = "your-jenkins-host.com"; 
     int port = 8080; 
     String usernName = "username"; 
     String password = "passwort"; 

     DefaultHttpClient httpclient = new DefaultHttpClient(); 
     httpclient.getCredentialsProvider().setCredentials(
       new AuthScope(host, port), 
       new UsernamePasswordCredentials(usernName, password)); 

     String jenkinsUrl = protocol + "://" + host + ":" + port + "/jenkins/"; 

     try { 
      // get the crumb from Jenkins 
      // do this only once per HTTP session 
      // keep the crumb for every coming request 
      System.out.println("... issue crumb"); 
      HttpGet httpGet = new HttpGet(jenkinsUrl + "crumbIssuer/api/json"); 
      String crumbResponse= toString(httpclient, httpGet); 
      CrumbJson crumbJson = new Gson() 
       .fromJson(crumbResponse, CrumbJson.class); 

      // add the issued crumb to each request header 
      // the header field name is also contained in the json response 
      System.out.println("... issue rss of latest builds"); 
      HttpPost httpost = new HttpPost(jenkinsUrl + "rssLatest"); 
      httpost.addHeader(crumbJson.crumbRequestField, crumbJson.crumb); 
      toString(httpclient, httpost); 

     } finally { 
      httpclient.getConnectionManager().shutdown(); 
     } 

    } 

    // helper construct to deserialize crumb json into 
    public static class CrumbJson { 
     public String crumb; 
     public String crumbRequestField; 
    } 

    private static String toString(DefaultHttpClient client, 
     HttpRequestBase request) throws Exception { 
     ResponseHandler<String> responseHandler = new BasicResponseHandler(); 
     String responseBody = client.execute(request, responseHandler); 
     System.out.println(responseBody + "\n"); 
     return responseBody; 
    } 

} 
+0

Xác nhận trên phiên bản 2.19 của Jenkins. Vẫn đang làm việc. – teodron

2

Câu trả lời ở trên đã giúp 90%, cảm ơn đã cho chúng tôi đúng hướng.

Mất tích 10% xoay quanh tên người dùng Http & xác thực mật khẩu.

Kể từ khi api Codenameone java Tôi đã sử dụng không có lớp xác thực dưới đây:

new UsernamePasswordCredentials(usernName, password)); 

tôi đã sử dụng:

String apiKey = "yourJenkinsUsername:yourJenkinsPassword"; 
httpConnection.addRequestHeader("Authorization", "Basic " + Base64.encode(apiKey.getBytes())); 
1

Hoặc bạn có thể sử dụng python và yêu cầu thay

req = requests.get('http://JENKINS_URL/crumbIssuer/api/xml?xpath=concat(//crumbRequestField,":",//crumb)', auth=(username, password)) 

sẽ cung cấp cho bạn tên và số vụn

Jenkins-Crumb:e2e41f670dc128f378b2a010b4fcb493 
0

Đoạn mã java ở trên hoạt động rất tốt đối với tôi trên Jenkins v2.89.3 (Eclipse.org) và một cá thể Jenkins khác mà tôi sử dụng, tại v2.60.3 (khi đã bật [1]).

[1] https://wiki.jenkins.io/display/JENKINS/CSRF+Protection

Tôi đã thêm này cho một người mojo maven [2] Tôi sử dụng để đẩy những thay đổi config.xml địa phương sửa lại cho máy chủ.

[2] https://github.com/nickboldt/maven-plugins/tree/master/hudson-job-sync-plugin

Cảm ơn!

Các vấn đề liên quan