bincimap

Log | Files | Refs | LICENSE

operator-status.cc (5076B)


      1 /* -*- Mode: c++; -*- */
      2 /*  --------------------------------------------------------------------
      3  *  Filename:
      4  *    operator-status.cc
      5  *  
      6  *  Description:
      7  *    Implementation of the STATUS command.
      8  *
      9  *  Authors:
     10  *    Andreas Aardal Hanssen <andreas-binc curly bincimap spot org>
     11  *
     12  *  Bugs:
     13  *
     14  *  ChangeLog:
     15  *
     16  *  --------------------------------------------------------------------
     17  *  Copyright 2002-2005 Andreas Aardal Hanssen
     18  *
     19  *  This program is free software; you can redistribute it and/or modify
     20  *  it under the terms of the GNU General Public License as published by
     21  *  the Free Software Foundation; either version 2 of the License, or
     22  *  (at your option) any later version.
     23  *
     24  *  This program is distributed in the hope that it will be useful,
     25  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
     26  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     27  *  GNU General Public License for more details.
     28  *
     29  *  You should have received a copy of the GNU General Public License
     30  *  along with this program; if not, write to the Free Software
     31  *  Foundation, Inc., 59 Temple Street #330, Boston, MA 02111-1307, USA.
     32  *  --------------------------------------------------------------------
     33  */
     34 #ifdef HAVE_CONFIG_H
     35 #include <config.h>
     36 #endif
     37 
     38 #include <string>
     39 #include <iostream>
     40 
     41 #include <dirent.h>
     42 #include <sys/stat.h>
     43 #include <sys/types.h>
     44 
     45 #include "io.h"
     46 #include "mailbox.h"
     47 #include "status.h"
     48 #include "storage.h"
     49 #include "convert.h"
     50 
     51 #include "recursivedescent.h"
     52 
     53 #include "session.h"
     54 #include "depot.h"
     55 #include "operators.h"
     56 
     57 using namespace ::std;
     58 using namespace Binc;
     59 
     60 //----------------------------------------------------------------------
     61 StatusOperator::StatusOperator(void)
     62 {
     63 }
     64 
     65 //----------------------------------------------------------------------
     66 StatusOperator::~StatusOperator(void)
     67 {
     68 }
     69 
     70 //----------------------------------------------------------------------
     71 const string StatusOperator::getName(void) const
     72 {
     73   return "STATUS";
     74 }
     75 
     76 //----------------------------------------------------------------------
     77 int StatusOperator::getState(void) const
     78 {
     79   return Session::AUTHENTICATED | Session::SELECTED;
     80 }
     81 
     82 //------------------------------------------------------------------------
     83 Operator::ProcessResult StatusOperator::process(Depot &depot,
     84 						Request &command)
     85 {
     86   IO &com = IOFactory::getInstance().get(1);
     87   Session &session = Session::getInstance();
     88 
     89   Status status;
     90   if (!depot.getStatus(command.getMailbox(), status)) {
     91     session.setLastError(depot.getLastError());
     92     return NO;
     93   }
     94 
     95   com << "* STATUS " << toImapString(command.getMailbox()) << " (";
     96     
     97   string prefix;
     98   for (vector<string>::const_iterator i = command.statuses.begin();
     99        i != command.statuses.end(); ++i) {
    100     string tmp = *i;
    101     uppercase(tmp);
    102     if (tmp == "UIDNEXT") {
    103       com << prefix << "UIDNEXT " << status.getUidNext(); prefix = " ";
    104     } else if (tmp == "MESSAGES") {
    105       com << prefix << "MESSAGES " << status.getMessages(); prefix = " ";
    106     } else if (tmp == "RECENT") {
    107       com << prefix << "RECENT " << status.getRecent(); prefix = " ";
    108     } else if (tmp == "UIDVALIDITY") {
    109       com << prefix << "UIDVALIDITY " << status.getUidValidity(); prefix = " ";
    110     } else if (tmp == "UNSEEN") {
    111       com << prefix << "UNSEEN " << status.getUnseen(); prefix = " ";
    112     }
    113   }
    114   com << ")" << endl;
    115 
    116   return OK;
    117 }
    118 
    119 //----------------------------------------------------------------------
    120 Operator::ParseResult StatusOperator::parse(Request &c_in) const
    121 {
    122   Session &session = Session::getInstance();
    123 
    124   if (c_in.getUidMode())
    125     return REJECT;
    126 
    127   Operator::ParseResult res;
    128   if ((res = expectSPACE()) != ACCEPT) {
    129     session.setLastError("Expected SPACE");
    130     return res;
    131   }
    132 
    133   string mailbox;
    134   if ((res = expectMailbox(mailbox)) != ACCEPT) {
    135     session.setLastError("Expected mailbox");
    136     return res;
    137   }
    138 
    139   c_in.setMailbox(mailbox);
    140 
    141   if ((res = expectSPACE()) != ACCEPT) {
    142     session.setLastError("Expected SPACE");
    143     return res;
    144   }
    145 
    146   if ((res = expectThisString("(")) != ACCEPT) {
    147     session.setLastError("Expected (");
    148     return res;
    149   }
    150 
    151   while (1) {
    152     if ((res = expectThisString("MESSAGES")) == ACCEPT)
    153       c_in.getStatuses().push_back("MESSAGES");
    154     else if ((res = expectThisString("RECENT")) == ACCEPT)
    155       c_in.getStatuses().push_back("RECENT");
    156     else if ((res = expectThisString("UIDNEXT")) == ACCEPT)
    157       c_in.getStatuses().push_back("UIDNEXT");
    158     else if ((res = expectThisString("UIDVALIDITY")) == ACCEPT)
    159       c_in.getStatuses().push_back("UIDVALIDITY");
    160     else if ((res = expectThisString("UNSEEN")) == ACCEPT)
    161       c_in.getStatuses().push_back("UNSEEN");
    162     else {
    163       session.setLastError("Expected status_att");
    164       return res;
    165     }
    166 
    167     if (expectSPACE() != ACCEPT)
    168       break;
    169   }
    170 
    171   if ((res = expectThisString(")")) != ACCEPT) {
    172     session.setLastError("Expected )");
    173     return res;
    174   }
    175 
    176   if ((res = expectCRLF()) != ACCEPT) {
    177     session.setLastError("Expected CRLF");
    178     return ERROR;
    179   }
    180 
    181   return ACCEPT;
    182 }