/**
* Copyright (C) 2010-2014 Leon Blakey <lord.quackstar at gmail.com>
*
* This file is part of PircBotX.
*
* PircBotX is free software: you can redistribute it and/or modify it under the
* terms of the GNU General Public License as published by the Free Software
* Foundation, either version 3 of the License, or (at your option) any later
* version.
*
* PircBotX is distributed in the hope that it will be useful, but WITHOUT ANY
* WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
* A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with
* PircBotX. If not, see <http://www.gnu.org/licenses/>.
*/
package org.pircbotx.cap;
import com.google.common.base.Charsets;
import com.google.common.collect.ImmutableList;
import lombok.ToString;
import org.apache.commons.codec.binary.Base64;
import org.pircbotx.PircBotX;
import org.pircbotx.exception.CAPException;
/**
*
* @author Leon Blakey
*/
@ToString(exclude = "password")
public class SASLCapHandler extends EnableCapHandler {
protected final String username;
protected final String password;
/**
* Create SASLCapHandler not ignoring failed authentication and throwing a
* CapException
* <p>
* @param username
* @param password
*/
public SASLCapHandler(String username, String password) {
this(username, password, false);
}
public SASLCapHandler(String username, String password, boolean ignoreFail) {
super("sasl", ignoreFail);
this.username = username;
this.password = password;
}
@Override
public boolean handleACK(PircBotX bot, ImmutableList<String> capabilities) {
if (capabilities.contains("sasl")) {
//Server acknowledges our request to use sasl
bot.sendRaw().rawLineNow("AUTHENTICATE PLAIN");
}
//If this is our ack, we still need to send user information
//If this isn't, it might be later
return false;
}
@Override
public boolean handleUnknown(PircBotX bot, String rawLine) throws CAPException {
if (rawLine.equals("AUTHENTICATE +")) {
//Server ackowledges our request to use plain authentication
byte[] rawAuth = (username + '\0' + username + '\0' + password).getBytes(Charsets.UTF_8);
//Issue #256: Use method available in commons-codec 1.3 for android, copied from encodeBase64String(byte[])
String encodedAuth = new String(Base64.encodeBase64(rawAuth, false), Charsets.UTF_8);
bot.sendRaw().rawLineNow("AUTHENTICATE " + encodedAuth);
}
//Check for 904 and 905
String[] parsedLine = rawLine.split(" ", 4);
if (parsedLine.length >= 1)
if (parsedLine[1].equals("904") || parsedLine[1].equals("905")) {
//Remove sasl as an enabled capability
bot.getEnabledCapabilities().remove("sasl");
if (!ignoreFail)
throw new CAPException(CAPException.Reason.SASLFailed, "SASL Authentication failed with message: " + parsedLine[3].substring(1));
//Pretend like nothing happened
return true;
} else if (parsedLine[1].equals("900") || parsedLine[1].equals("903"))
//Success!
return true;
return false;
}
}