use of com.zimbra.cs.session.Session in project zm-mailbox by Zimbra.
the class DocumentHandler method updateAuthenticatedAccount.
/** Updates the {@link ZimbraSoapContext} to treat the specified account
* as the request's authenticated account. If the new account differs
* from the previously authenticated account, we forget about all other
* {@link Session}s. (Those sessions are not deleted from the cache,
* though perhaps that's the right thing to do...) If requested, also
* creates a new Session object associated with the given account.
*
* @param zsc The parsed SOAP header for the auth request.
* @param authToken The new auth token created for the user.
* @param context The <code>SoapEngine</code>'s request state.
* @param getSession Whether to try to generate a new Session.
* @return A new Session object of the appropriate type, or <tt>null</tt>. */
public Session updateAuthenticatedAccount(ZimbraSoapContext zsc, AuthToken authToken, Map<String, Object> context, boolean getSession) {
String oldAccountId = zsc.getAuthtokenAccountId();
String accountId = authToken.getAccountId();
if (accountId != null && !accountId.equals(oldAccountId)) {
zsc.clearSessionInfo();
}
zsc.setAuthToken(authToken);
Session session = (getSession ? getSession(zsc) : null);
if (context != null) {
context.put(SoapEngine.ZIMBRA_SESSION, session);
}
return session;
}
use of com.zimbra.cs.session.Session in project zm-mailbox by Zimbra.
the class GetSessions method getResult.
public CachedResult getResult(AdminSession adminSession, Type type, boolean refresh, final SortBy sortBy) {
List<Session> sessions = SessionCache.getActiveSessions(type);
CachedResult result = (adminSession == null || refresh) ? null : (CachedResult) adminSession.getData(SESSION_KEY);
if (result != null && result.type == type && result.sortBy == sortBy)
return result;
Provisioning prov = Provisioning.getInstance();
result = new CachedResult();
result.type = type;
result.sortBy = sortBy;
result.sessions = new ArrayList<SessionInfo>(sessions.size());
for (Session s : sessions) {
result.sessions.add(new SessionInfo(s, getName(prov, s.getAuthenticatedAccountId())));
}
// SORT
Comparator<SessionInfo> comparator = new Comparator<SessionInfo>() {
public int compare(SessionInfo a, SessionInfo b) {
long diff;
switch(sortBy) {
case nameAsc:
return a.getAccountName().compareToIgnoreCase(b.getAccountName());
case nameDesc:
return -a.getAccountName().compareToIgnoreCase(b.getAccountName());
case accessedAsc:
diff = a.getAccessed() - b.getAccessed();
return diff == 0 ? 0 : diff > 0 ? 1 : -1;
case accessedDesc:
diff = a.getAccessed() - b.getAccessed();
return diff == 0 ? 0 : diff > 0 ? -1 : 1;
case createdAsc:
diff = a.getAccessed() - b.getAccessed();
return diff == 0 ? 0 : diff > 0 ? 1 : -1;
case createdDesc:
diff = a.getAccessed() - b.getAccessed();
return diff == 0 ? 0 : diff > 0 ? -1 : 1;
default:
return 0;
}
}
};
Collections.sort(result.sessions, comparator);
if (adminSession != null)
adminSession.setData(SESSION_KEY, result);
return result;
}
use of com.zimbra.cs.session.Session in project zm-mailbox by Zimbra.
the class ItemAction method forceRemoteSession.
private Account forceRemoteSession(ZimbraSoapContext zsc, Map<String, Object> context, OperationContext octxt, String op, Element action) throws ServiceException {
// only proxying notification from the user's home-server master session
if (!zsc.isNotificationEnabled()) {
return null;
}
Session session = (Session) context.get(SoapEngine.ZIMBRA_SESSION);
if (session instanceof SoapSession.DelegateSession) {
session = ((SoapSession.DelegateSession) session).getParentSession();
}
if (!(session instanceof SoapSession) || session.getMailbox() == null) {
return null;
}
SoapSession ss = (SoapSession) session;
// only have to worry about operations where things can get created in other mailboxes (regular notification works for all other cases)
if (!op.equals(OP_MOVE) && !op.equals(OP_COPY) && !op.equals(OP_SPAM) && !op.equals(OP_RENAME) && !op.equals(OP_UPDATE)) {
return null;
}
String folderStr = action.getAttribute(MailConstants.A_FOLDER, null);
if (folderStr == null) {
return null;
}
// recursively dereference mountpoints to find ultimate target folder
ItemId iidFolder = new ItemId(folderStr, zsc), iidRequested = iidFolder;
Account owner = null;
int hopCount = 0;
ZAuthToken zat = null;
while (hopCount < ZimbraSoapContext.MAX_HOP_COUNT) {
owner = Provisioning.getInstance().getAccountById(iidFolder.getAccountId());
if (Provisioning.onLocalServer(owner)) {
try {
Mailbox mbox = MailboxManager.getInstance().getMailboxByAccount(owner);
Folder folder = mbox.getFolderById(octxt, iidFolder.getId());
if (!(folder instanceof Mountpoint))
break;
iidFolder = ((Mountpoint) folder).getTarget();
} catch (ServiceException e) {
// could be a PERM_DENIED, could be something else -- this is not the right place to fail, however
break;
}
} else {
if (zat == null) {
AuthToken at = AuthToken.getCsrfUnsecuredAuthToken(zsc.getAuthToken());
String pxyAuthToken = at.getProxyAuthToken();
zat = pxyAuthToken == null ? at.toZAuthToken() : new ZAuthToken(pxyAuthToken);
}
ZMailbox.Options zoptions = new ZMailbox.Options(zat, AccountUtil.getSoapUri(owner));
zoptions.setNoSession(true);
zoptions.setTargetAccount(owner.getId());
zoptions.setTargetAccountBy(Key.AccountBy.id);
ZMailbox zmbx = ZMailbox.getMailbox(zoptions);
ZFolder zfolder = zmbx.getFolderById(iidFolder.toString(zsc.getAuthtokenAccountId()));
if (!(zfolder instanceof ZMountpoint))
break;
iidFolder = new ItemId(((ZMountpoint) zfolder).getCanonicalRemoteId(), zsc.getAuthtokenAccountId());
}
hopCount++;
}
if (hopCount >= ZimbraSoapContext.MAX_HOP_COUNT) {
throw MailServiceException.TOO_MANY_HOPS(iidRequested);
}
// avoid dereferencing the mountpoint again later on
action.addAttribute(MailConstants.A_FOLDER, iidFolder.toString());
// fault in a session to listen in on the target folder's mailbox
if (iidFolder.belongsTo(session.getAuthenticatedAccountId())) {
return null;
} else if (iidFolder.isLocal()) {
ss.getDelegateSession(iidFolder.getAccountId());
return null;
} else {
try {
proxyRequest(zsc.createElement(MailConstants.NO_OP_REQUEST), context, owner.getId());
return owner;
} catch (ServiceException e) {
return null;
}
}
}
use of com.zimbra.cs.session.Session in project zm-mailbox by Zimbra.
the class ImapSessionManager method duplicateExistingSession.
private static List<ImapMessage> duplicateExistingSession(int folderId, List<Session> sessionList) {
for (Session session : sessionList) {
ImapSession i4listener = (ImapSession) session;
if (i4listener.getFolderId() == folderId) {
// FIXME: may want to prefer loaded folders over paged-out folders
synchronized (i4listener) {
ImapFolder i4selected;
try {
i4selected = i4listener.getImapFolder();
} catch (ImapSessionClosedException e) {
return null;
}
if (i4selected == null) {
// cache miss
return null;
}
// found a matching session, so just copy its contents!
ZimbraLog.imap.info("copying message data from existing session: %s", i4listener.getPath());
final List<ImapMessage> i4list = new ArrayList<ImapMessage>(i4selected.getSize());
i4selected.traverse(new Function<ImapMessage, Void>() {
@Override
public Void apply(ImapMessage i4msg) {
if (!i4msg.isExpunged()) {
i4list.add(new ImapMessage(i4msg));
}
return null;
}
});
// XXX: watch out for deadlock between this and the SessionCache
if (!i4listener.isInteractive()) {
i4listener.unregister();
}
return i4list;
}
}
}
return null;
}
use of com.zimbra.cs.session.Session in project zm-mailbox by Zimbra.
the class ImapSessionManager method openFolder.
Pair<ImapSession, InitialFolderValues> openFolder(ImapPath path, byte params, ImapHandler handler) throws ServiceException {
ZimbraLog.imap.debug("opening folder: %s", path);
if (!path.isSelectable()) {
throw ServiceException.PERM_DENIED("cannot select folder: " + path);
}
if ((params & ImapFolder.SELECT_CONDSTORE) != 0) {
handler.activateExtension(ImapExtension.CONDSTORE);
}
Folder folder = (Folder) path.getFolder();
int folderId = folder.getId();
Mailbox mbox = folder.getMailbox();
// don't have a session when the folder is loaded...
OperationContext octxt = handler.getCredentials().getContext();
mbox.beginTrackingImap();
List<ImapMessage> i4list = null;
// *always* recalculate the contents of search folders
if (folder instanceof SearchFolder) {
i4list = loadVirtualFolder(octxt, (SearchFolder) folder);
}
mbox.lock.lock();
try {
// need mInitialRecent to be set *before* loading the folder so we can determine what's \Recent
folder = mbox.getFolderById(octxt, folderId);
int recentCutoff = folder.getImapRECENTCutoff();
if (i4list == null) {
List<Session> listeners = mbox.getListeners(Session.Type.IMAP);
// first option is to duplicate an existing registered session
// (could try to just activate an inactive session, but this logic is simpler for now)
i4list = duplicateExistingSession(folderId, listeners);
// no matching session means we next check for serialized folder data
if (i4list == null) {
i4list = duplicateSerializedFolder(folder);
} else if (CONSISTENCY_CHECK) {
Collections.sort(i4list);
//sort only if using list from duplicated session which may be out of order
//if loaded from serialized folder order _should_ already be OK since no changes have occurred
}
// do the consistency check, if requested
if (CONSISTENCY_CHECK) {
i4list = consistencyCheck(i4list, mbox, octxt, folder);
}
// no matching serialized session means we have to go to the DB to get the messages
if (i4list == null) {
i4list = mbox.openImapFolder(octxt, folderId);
}
}
Collections.sort(i4list);
// check messages for imapUid <= 0 and assign new IMAP IDs if necessary
renumberMessages(octxt, mbox, i4list);
ImapFolder i4folder = new ImapFolder(path, params, handler);
// don't rely on the <code>Folder</code> object being updated in place
folder = mbox.getFolderById(octxt, folderId);
// can't set these until *after* loading the folder because UID renumbering affects them
InitialFolderValues initial = new InitialFolderValues(folder);
for (ImapMessage i4msg : i4list) {
i4folder.cache(i4msg, i4msg.imapUid > recentCutoff);
if (initial.firstUnread == -1 && (i4msg.flags & Flag.BITMASK_UNREAD) != 0) {
initial.firstUnread = i4msg.sequence;
}
}
i4folder.setInitialSize();
ZimbraLog.imap.debug("Folder with id=%s added message list %s", folderId, i4list);
ImapSession session = null;
try {
session = new ImapSession(i4folder, handler);
session.register();
sessions.put(session, session);
return new Pair<ImapSession, InitialFolderValues>(session, initial);
} catch (ServiceException e) {
if (session != null) {
session.unregister();
}
throw e;
}
} finally {
mbox.lock.release();
}
}
Aggregations