2012-12-10 9 views
6

Ich habe eine einfache Thrift-basierte Java-Anwendung, die ich geschrieben habe. Es ist wirklich sehr einfach, nicht viel mehr als ein "Hello World" Nachrichtentransport mit Thrift in Java. Mir wurde gesagt, dass ich meiner Nachricht Kerberos-Unterstützung hinzufügen muss. Ich habe etwas gegoogelt und bin überrascht, dass Thrift in irgendeiner Form nicht schon Kerberos-Unterstützung hat (oder wenn es so ist, kann ich es nicht finden). Ich dachte daran, meinen eigenen Wrapper mit GSSAPI zu schreiben, aber ich kann meine Thrift-Nachricht nicht einpacken/auspacken, da dies das Thrift-Nachrichtenformat vermasselt.Kerberos für Sparsamkeit?

Hat jemand jemals Kerberized Thrift? .. oder wissen, wie es gemacht würde?

Danke, im Voraus.

+0

Es scheint, als hätte Hadoop etwas auf diesem ... – Wanderer

Antwort

11

** Also, ich denke, es gibt einen Weg, dies über die SASL/GSS APIs zu tun. Es verwirrt mich, warum ich nirgendwo im Internet großartige Beispiele dafür sehe. Ich poste jedoch ein Beispiel dessen, was ich geschaffen habe, in der Hoffnung, dass es anderen hilft ... oder dass jemand meine Illusion korrigieren kann, etwas Nützliches hier zu tun.

Beispiel Server Code:

TServerSocket serverTransport = new TServerSocket(7911); // new server on port 7911 
HelloWorldService.Processor<Iface> processor = new HelloWorldService.Processer<Iface>(new ThriftServerImpl()); // This is my thrift implementation for my server 
Map<String, String> saslProperties = new HashMap<String, String>(); // need a map for properties 
saslProperties.put(Sasl.QOP, "true"); 
saslProperties.put(Sasl.QOP, "auth-conf"); // authorization and confidentiality 

TSaslServerTransport.Factory saslTransportFactory = new TSaslServerTransport.Factory();  // Creating the server definition 
saslTransportFactory.addServerDefinition(
      "GSSAPI",  // tell SASL to use GSSAPI, which supports Kerberos 
      "myserviceprincipal", // base kerberos principal name - myprincipal/[email protected] 
      "my.server.com", // kerberos principal server - myprincipal/[email protected] 
      saslProps,  // Properties set, above 
      new SaslRpcServer.SaslGssCallbackHandler())); // I don't know what this really does... but I stole it from Hadoop and it works.. so there. 

Tserver server = new TThreadPoolServer(newTThreadPoolSErver.Args(serverTransport).transportFactory(saslTrasnportFactory).processor(processor)); 

server.serve(); // Thrift server start 

Beispiel-Client-Code

TTransport transport = new TSocket("my.server.com", 7911); // client to connect to server and port 
saslProperties.put(Sasl.QOP, "true"); 
saslProperties.put(Sasl.QOP, "auth-conf"); // authorization and confidentiality 

TTransport saslTransport = new TSaslTransport(
      "GSSAPI",  // tell SASL to use GSSAPI, which supports Kerberos 
      null,   // authorizationid - null 
      "myserviceprincipal", // base kerberos principal name - myprincipal/[email protected] 
      "my.server.com", // kerberos principal server - myprincipal/[email protected] 
      saslProps,  // Properties set, above 
      null,   // callback handler - null 
      transport);  // underlying transport 

TProtocol protocol = new TBinaryProtocol(saslTransport); // set up our new Thrift protocol 

HelloWorldService.Client client = new HelloWorldService.Client(protocol); // Setup our thrift client 
saslTransport.open(); 

String response = client.hello("Hi There"); // send message 

System.out.println("response = " + response); 

transport.close(); 

Andere condsiderations:

* I sowohl mehrere Java-Eigenschaften festgelegt auf dem Client und dem Server.
- java.security.krb5.realm = MY.REALM // Bereichsname
- java.security.krb5.kdc = my.kdc.com // KDC-Server
- javax.security.auth.useSubjectCredsOnly = false // Lassen Sie JAAS das TGT bekommen.
- java.security.auth.login.config = /etc/myapp/conf/jaas.conf - erforderliche jaas-Datei
- sun.security.krb5.debug = true // half bei der Diagnose von Problemen.
* Die oben angegebene Datei jaas.conf muss zwei Einträge haben (möglicherweise nur einen pro Server ...). Ich kann mich nicht erinnern, wo ich diese gewonnenen Informationen aus .. aber hier ist meine Datei:

com.sun.security.jgss.initiate { 
    com.sun.security.auth.module.Krb5LoginModule required 
    useKeyTab=true 
    keyTab="/etc/myapp/conf/myapp.keytab" 
    useTicketCache=true 
    principal="myuserprincipal" 
    debug=true; 
}; 

com.sun.security.jgss.accept { 
    com.sun.security.auth.module.Krb5LoginModule required 
    useKeyTab=true 
    keyTab="/etc/myapp/conf/myapp.keytab" 
    useTicketCache=false 
    principal="myserviceprincipal/my.server.com" 
    debug=true; 
}; 

(zurück zu Überlegungen ....)
* Trotz einer Sasl.QOP von „auth-conf“ mit .. Die erste (?) Nachricht, die übertragen wird, ist nicht verschlüsselt. Vielleicht ist das nur ein Händedruck oder so etwas. Die verbleibenden Nachrichten scheinen verschlüsselt zu sein, aber dieser erste gibt eine hässliche Nachricht auf der Konsole aus: "Keine Verschlüsselung wurde von Peer durchgeführt". Es wäre schön, diese Nachricht nicht zu bekommen, da sie die Trauer auf die Straße bringen wird (berechtigt oder nicht).

Wie auch immer, ich hoffe, das hilft jemandem ... oder alternativ kann einige Verbesserungen provozieren, die mir helfen werden. :) Kaum zu glauben, dass ich 2-3 Tage damit verbracht habe, und nur eine kleine Menge Code kam heraus, aber ich wusste weder Kerberos noch Thrift sehr gut, als ich anfing.

Danke fürs Lesen.