use of org.jivesoftware.openfire.user.UserNotFoundException in project Openfire by igniterealtime.
the class IQRegisterHandler method handleIQ.
@Override
public IQ handleIQ(IQ packet) throws PacketException, UnauthorizedException {
ClientSession session = sessionManager.getSession(packet.getFrom());
IQ reply = null;
// If no session was found then answer an error (if possible)
if (session == null) {
Log.error("Error during registration. Session not found in " + sessionManager.getPreAuthenticatedKeys() + " for key " + packet.getFrom());
// This error packet will probably won't make it through
reply = IQ.createResultIQ(packet);
reply.setChildElement(packet.getChildElement().createCopy());
reply.setError(PacketError.Condition.internal_server_error);
return reply;
}
if (IQ.Type.get.equals(packet.getType())) {
// If inband registration is not allowed, return an error.
if (!registrationEnabled) {
reply = IQ.createResultIQ(packet);
reply.setChildElement(packet.getChildElement().createCopy());
reply.setError(PacketError.Condition.forbidden);
} else {
reply = IQ.createResultIQ(packet);
if (session.getStatus() == Session.STATUS_AUTHENTICATED) {
try {
User user = userManager.getUser(session.getUsername());
Element currentRegistration = probeResult.createCopy();
currentRegistration.addElement("registered");
currentRegistration.element("username").setText(user.getUsername());
currentRegistration.element("password").setText("");
currentRegistration.element("email").setText(user.getEmail() == null ? "" : user.getEmail());
currentRegistration.element("name").setText(user.getName());
Element form = currentRegistration.element(QName.get("x", "jabber:x:data"));
Iterator fields = form.elementIterator("field");
Element field;
while (fields.hasNext()) {
field = (Element) fields.next();
if ("username".equals(field.attributeValue("var"))) {
field.addElement("value").addText(user.getUsername());
} else if ("name".equals(field.attributeValue("var"))) {
field.addElement("value").addText(user.getName());
} else if ("email".equals(field.attributeValue("var"))) {
field.addElement("value").addText(user.getEmail() == null ? "" : user.getEmail());
}
}
reply.setChildElement(currentRegistration);
} catch (UserNotFoundException e) {
reply.setChildElement(probeResult.createCopy());
}
} else {
// This is a workaround. Since we don't want to have an incorrect TO attribute
// value we need to clean up the TO attribute. The TO attribute will contain an
// incorrect value since we are setting a fake JID until the user actually
// authenticates with the server.
reply.setTo((JID) null);
reply.setChildElement(probeResult.createCopy());
}
}
} else if (IQ.Type.set.equals(packet.getType())) {
try {
Element iqElement = packet.getChildElement();
if (iqElement.element("remove") != null) {
// If inband registration is not allowed, return an error.
if (!registrationEnabled) {
reply = IQ.createResultIQ(packet);
reply.setChildElement(packet.getChildElement().createCopy());
reply.setError(PacketError.Condition.forbidden);
} else {
if (session.getStatus() == Session.STATUS_AUTHENTICATED) {
User user = userManager.getUser(session.getUsername());
// Delete the user
userManager.deleteUser(user);
// Delete the roster of the user
rosterManager.deleteRoster(session.getAddress());
// Delete the user from all the Groups
GroupManager.getInstance().deleteUser(user);
reply = IQ.createResultIQ(packet);
session.process(reply);
// Take a quick nap so that the client can process the result
Thread.sleep(10);
// Close the user's connection
final StreamError error = new StreamError(StreamError.Condition.not_authorized);
for (ClientSession sess : sessionManager.getSessions(user.getUsername())) {
sess.deliverRawText(error.toXML());
sess.close();
}
// The reply has been sent so clean up the variable
reply = null;
} else {
throw new UnauthorizedException();
}
}
} else {
String username;
String password = null;
String email = null;
String name = null;
User newUser;
DataForm registrationForm;
FormField field;
Element formElement = iqElement.element("x");
// Check if a form was used to provide the registration info
if (formElement != null) {
// Get the sent form
registrationForm = new DataForm(formElement);
// Get the username sent in the form
List<String> values = registrationForm.getField("username").getValues();
username = (!values.isEmpty() ? values.get(0) : " ");
// Get the password sent in the form
field = registrationForm.getField("password");
if (field != null) {
values = field.getValues();
password = (!values.isEmpty() ? values.get(0) : " ");
}
// Get the email sent in the form
field = registrationForm.getField("email");
if (field != null) {
values = field.getValues();
email = (!values.isEmpty() ? values.get(0) : " ");
}
// Get the name sent in the form
field = registrationForm.getField("name");
if (field != null) {
values = field.getValues();
name = (!values.isEmpty() ? values.get(0) : " ");
}
} else {
// Get the registration info from the query elements
username = iqElement.elementText("username");
password = iqElement.elementText("password");
email = iqElement.elementText("email");
name = iqElement.elementText("name");
}
if (email != null && email.matches("\\s*")) {
email = null;
}
if (name != null && name.matches("\\s*")) {
name = null;
}
// stringprep validity now.
if (username != null) {
Stringprep.nodeprep(username);
}
if (session.getStatus() == Session.STATUS_AUTHENTICATED) {
// Flag that indicates if the user is *only* changing his password
boolean onlyPassword = false;
if (iqElement.elements().size() == 2 && iqElement.element("username") != null && iqElement.element("password") != null) {
onlyPassword = true;
}
// If users are not allowed to change their password, return an error.
if (password != null && !canChangePassword) {
reply = IQ.createResultIQ(packet);
reply.setChildElement(packet.getChildElement().createCopy());
reply.setError(PacketError.Condition.forbidden);
return reply;
} else // If inband registration is not allowed, return an error.
if (!onlyPassword && !registrationEnabled) {
reply = IQ.createResultIQ(packet);
reply.setChildElement(packet.getChildElement().createCopy());
reply.setError(PacketError.Condition.forbidden);
return reply;
} else {
User user = userManager.getUser(session.getUsername());
if (user.getUsername().equalsIgnoreCase(username)) {
if (password != null && password.trim().length() > 0) {
user.setPassword(password);
}
if (!onlyPassword) {
user.setEmail(email);
}
newUser = user;
} else if (password != null && password.trim().length() > 0) {
// An admin can create new accounts when logged in.
newUser = userManager.createUser(username, password, null, email);
} else {
// Deny registration of users with no password
reply = IQ.createResultIQ(packet);
reply.setChildElement(packet.getChildElement().createCopy());
reply.setError(PacketError.Condition.not_acceptable);
return reply;
}
}
} else {
// If inband registration is not allowed, return an error.
if (!registrationEnabled) {
reply = IQ.createResultIQ(packet);
reply.setChildElement(packet.getChildElement().createCopy());
reply.setError(PacketError.Condition.forbidden);
return reply;
} else // information was not provided
if (password == null || password.trim().length() == 0) {
reply = IQ.createResultIQ(packet);
reply.setChildElement(packet.getChildElement().createCopy());
reply.setError(PacketError.Condition.not_acceptable);
return reply;
} else {
// Create the new account
newUser = userManager.createUser(username, password, name, email);
}
}
// Set and save the extra user info (e.g. full name, etc.)
if (newUser != null && name != null && !name.equals(newUser.getName())) {
newUser.setName(name);
}
reply = IQ.createResultIQ(packet);
}
} catch (UserAlreadyExistsException e) {
reply = IQ.createResultIQ(packet);
reply.setChildElement(packet.getChildElement().createCopy());
reply.setError(PacketError.Condition.conflict);
} catch (UserNotFoundException e) {
reply = IQ.createResultIQ(packet);
reply.setChildElement(packet.getChildElement().createCopy());
reply.setError(PacketError.Condition.bad_request);
} catch (StringprepException e) {
// The specified username is not correct according to the stringprep specs
reply = IQ.createResultIQ(packet);
reply.setChildElement(packet.getChildElement().createCopy());
reply.setError(PacketError.Condition.jid_malformed);
} catch (IllegalArgumentException e) {
// At least one of the fields passed in is not valid
reply = IQ.createResultIQ(packet);
reply.setChildElement(packet.getChildElement().createCopy());
reply.setError(PacketError.Condition.not_acceptable);
Log.warn(e.getMessage(), e);
} catch (UnsupportedOperationException e) {
// The User provider is read-only so this operation is not allowed
reply = IQ.createResultIQ(packet);
reply.setChildElement(packet.getChildElement().createCopy());
reply.setError(PacketError.Condition.not_allowed);
} catch (Exception e) {
// Some unexpected error happened so return an internal_server_error
reply = IQ.createResultIQ(packet);
reply.setChildElement(packet.getChildElement().createCopy());
reply.setError(PacketError.Condition.internal_server_error);
Log.error(e.getMessage(), e);
}
}
if (reply != null) {
// why is this done here instead of letting the iq handler do it?
session.process(reply);
}
return null;
}
use of org.jivesoftware.openfire.user.UserNotFoundException in project Openfire by igniterealtime.
the class IQRosterHandler method manageRoster.
/**
* The packet is a typical 'set' or 'get' update targeted at the server.
* Notice that the set could be a roster removal in which case we have to
* generate a local roster removal update as well as a new roster removal
* to send to the the roster item's owner.
*
* @param packet The packet that triggered this update
* @return Either a response to the roster update or null if the packet is corrupt and the session was closed down
*/
private IQ manageRoster(org.xmpp.packet.Roster packet) throws UnauthorizedException, UserAlreadyExistsException, SharedGroupException {
IQ returnPacket = null;
JID sender = packet.getFrom();
IQ.Type type = packet.getType();
try {
if ((sender.getNode() == null || !RosterManager.isRosterServiceEnabled() || !userManager.isRegisteredUser(sender.getNode())) && IQ.Type.get == type) {
// If anonymous user asks for his roster or roster service is disabled then
// return an empty roster
IQ reply = IQ.createResultIQ(packet);
reply.setChildElement("query", "jabber:iq:roster");
return reply;
}
if (!localServer.isLocal(sender)) {
// Sender belongs to a remote server so discard this IQ request
Log.warn("Discarding IQ roster packet of remote user: " + packet);
return null;
}
Roster cachedRoster = userManager.getUser(sender.getNode()).getRoster();
if (IQ.Type.get == type) {
returnPacket = cachedRoster.getReset();
returnPacket.setType(IQ.Type.result);
returnPacket.setTo(sender);
returnPacket.setID(packet.getID());
// Force delivery of the response because we need to trigger
// a presence probe from all contacts
deliverer.deliver(returnPacket);
returnPacket = null;
} else if (IQ.Type.set == type) {
returnPacket = IQ.createResultIQ(packet);
// The <query/> element contains more than one <item/> child element.
if (packet.getItems().size() > 1) {
returnPacket.setError(new PacketError(PacketError.Condition.bad_request, PacketError.Type.modify, "Query contains more than one item"));
} else {
for (org.xmpp.packet.Roster.Item item : packet.getItems()) {
if (item.getSubscription() == org.xmpp.packet.Roster.Subscription.remove) {
if (removeItem(cachedRoster, packet.getFrom(), item) == null) {
// RFC 6121 2.5.3. Error Cases: If the value of the 'jid' attribute specifies an item that is not in the roster, then the server MUST return an <item-not-found/> stanza error.
returnPacket.setError(PacketError.Condition.item_not_found);
}
} else {
PacketError error = checkGroups(item.getGroups());
if (error != null) {
returnPacket.setError(error);
} else {
if (cachedRoster.isRosterItem(item.getJID())) {
// existing item
RosterItem cachedItem = cachedRoster.getRosterItem(item.getJID());
cachedItem.setAsCopyOf(item);
cachedRoster.updateRosterItem(cachedItem);
} else {
// new item
cachedRoster.createRosterItem(item);
}
}
}
}
}
}
} catch (UserNotFoundException e) {
throw new UnauthorizedException(e);
}
return returnPacket;
}
use of org.jivesoftware.openfire.user.UserNotFoundException in project Openfire by igniterealtime.
the class IQLastActivityHandler method handleIQ.
@Override
public IQ handleIQ(IQ packet) throws UnauthorizedException {
IQ reply = IQ.createResultIQ(packet);
Element lastActivity = reply.setChildElement("query", NAMESPACE);
String sender = packet.getFrom().getNode();
// Check if any of the usernames is null
if (sender == null) {
reply.setError(PacketError.Condition.forbidden);
return reply;
}
if (packet.getTo() != null && packet.getTo().getNode() == null && XMPPServer.getInstance().isLocal(packet.getTo())) {
// http://xmpp.org/extensions/xep-0012.html#server
// When the last activity query is sent to a server or component (i.e., to a JID of the form <domain.tld>),
// the information contained in the IQ reply reflects the uptime of the JID sending the reply.
// The seconds attribute specifies how long the host has been running since it was last (re-)started.
long uptime = XMPPServer.getInstance().getServerInfo().getLastStarted().getTime();
long lastActivityTime = (System.currentTimeMillis() - uptime) / 1000;
lastActivity.addAttribute("seconds", String.valueOf(lastActivityTime));
return reply;
}
// If the 'to' attribute is null, treat the IQ on behalf of the account from which received the stanza
// in accordance with RFC 6120 ยง 10.3.3.
String username = packet.getTo() == null ? packet.getFrom().getNode() : packet.getTo().getNode();
try {
if (username != null) {
// Check that the user requesting this information is subscribed to the user's presence
if (presenceManager.canProbePresence(packet.getFrom(), username)) {
if (sessionManager.getSessions(username).isEmpty()) {
User user = UserManager.getInstance().getUser(username);
// The user is offline so answer the user's "last available time and the
// status message of the last unavailable presence received from the user"
long lastActivityTime = presenceManager.getLastActivity(user);
if (lastActivityTime > -1) {
// Convert it to seconds
lastActivityTime = lastActivityTime / 1000;
}
lastActivity.addAttribute("seconds", String.valueOf(lastActivityTime));
String lastStatus = presenceManager.getLastPresenceStatus(user);
if (lastStatus != null && lastStatus.length() > 0) {
lastActivity.setText(lastStatus);
}
} else {
// The user is online so answer seconds=0
lastActivity.addAttribute("seconds", "0");
}
} else {
reply.setError(PacketError.Condition.forbidden);
}
}
} catch (UserNotFoundException e) {
reply.setError(PacketError.Condition.forbidden);
}
return reply;
}
use of org.jivesoftware.openfire.user.UserNotFoundException in project Openfire by igniterealtime.
the class PresenceSubscribeHandler method manageSub.
/**
* Manage the subscription request. This method updates a user's roster
* state, storing any changes made, and updating the roster owner if changes
* occured.
*
* @param target The roster target's jid (the item's jid to be changed)
* @param isSending True if the request is being sent by the owner
* @param type The subscription change type (subscribe, unsubscribe, etc.)
* @param roster The Roster that is updated.
* @return <tt>true</tt> if the subscription state has changed.
*/
private boolean manageSub(JID target, boolean isSending, Presence.Type type, Roster roster) throws UserAlreadyExistsException, SharedGroupException {
RosterItem item = null;
RosterItem.AskType oldAsk;
RosterItem.SubType oldSub = null;
RosterItem.RecvType oldRecv;
boolean newItem = false;
try {
if (roster.isRosterItem(target)) {
item = roster.getRosterItem(target);
} else {
if (Presence.Type.unsubscribed == type || Presence.Type.unsubscribe == type || Presence.Type.subscribed == type) {
// subscription approval from an unknown user
return false;
}
item = roster.createRosterItem(target, false, true);
newItem = true;
}
// Get a snapshot of the item state
oldAsk = item.getAskStatus();
oldSub = item.getSubStatus();
oldRecv = item.getRecvStatus();
// Update the item state based in the received presence type
updateState(item, type, isSending);
// Update the roster IF the item state has changed
if (oldAsk != item.getAskStatus() || oldSub != item.getSubStatus() || oldRecv != item.getRecvStatus()) {
roster.updateRosterItem(item);
} else if (newItem) {
// Do not push items with a state of "None + Pending In"
if (item.getSubStatus() != RosterItem.SUB_NONE || item.getRecvStatus() != RosterItem.RECV_SUBSCRIBE) {
roster.broadcast(item, false);
}
}
} catch (UserNotFoundException e) {
// Should be there because we just checked that it's an item
Log.error(LocaleUtils.getLocalizedString("admin.error"), e);
}
return oldSub != item.getSubStatus();
}
use of org.jivesoftware.openfire.user.UserNotFoundException in project Openfire by igniterealtime.
the class PresenceUpdateHandler method broadcastUpdate.
/**
* Broadcast the given update to all subscribers. We need to:
* <ul>
* <li>Query the roster table for subscribers</li>
* <li>Iterate through the list and send the update to each subscriber</li>
* </ul>
* <p/>
* Is there a safe way to cache the query results while maintaining
* integrity with roster changes?
*
* @param update The update to broadcast
*/
private void broadcastUpdate(Presence update) {
if (update.getFrom() == null) {
return;
}
if (localServer.isLocal(update.getFrom())) {
// Do nothing if roster service is disabled
if (!RosterManager.isRosterServiceEnabled()) {
return;
}
// Local updates can simply run through the roster of the local user
String name = update.getFrom().getNode();
try {
if (name != null && !"".equals(name)) {
Roster roster = rosterManager.getRoster(name);
roster.broadcastPresence(update);
}
} catch (UserNotFoundException e) {
Log.warn("Presence being sent from unknown user " + name, e);
} catch (PacketException e) {
Log.error(LocaleUtils.getLocalizedString("admin.error"), e);
}
} else {
// Foreign updates will do a reverse lookup of entries in rosters
// on the server
Log.warn("Presence requested from server " + localServer.getServerInfo().getXMPPDomain() + " by unknown user: " + update.getFrom());
}
}
Aggregations