2 * Copyright (C) 2011, Jamie Thompson
4 * This program is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU General Public
6 * License as published by the Free Software Foundation; either
7 * version 3 of the License, or (at your option) any later version.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * General Public License for more details.
14 * You should have received a copy of the GNU General Public
15 * License along with this program; If not, see
16 * <http://www.gnu.org/licenses/>.
21 #include "EventTypes/SMS.h"
24 #include "VEnvelope.h"
28 #include <QTextStream>
32 using namespace EventParsers::VMGEntities;
34 VMessage::VMessage(const SMSEntity* parent) :
35 SMSEntity(parent), m_Version(1.1)
39 //VMessage::VMessage(QTextStream& stream)
43 VMessage::VMessage(const SMSEntity* parent, float version) :
44 SMSEntity(parent), m_Version(version)
52 bool VMessage::Read(const QString & initialLine, QTextStream & stream, EventTypes::SMS & event)
54 if(getParent() != NULL)
56 qDebug() << "Messages cannot be nested.";
63 // Stream may or may not have a 'BEGIN' present. Swallow it if it's ours.
64 QString lineData(initialLine.length() > 0 ? initialLine : stream.readLine());
65 if(lineData.startsWith("BEGIN:"))
67 if(lineData != QString("BEGIN:") + getTagName())
69 qDebug() << "Invalid stream";
72 else // ...discard this line
73 lineData = stream.readLine();
78 if(lineData.startsWith("VERSION:"))
80 version = lineData.mid(lineData.indexOf(":")+1).toFloat();
82 else if(lineData.startsWith("X-IRMC-STATUS:"))
84 bool isRead(lineData.mid(lineData.indexOf(":") + 1) == "READ");
85 event.setIsRead(isRead);
87 else if(lineData.startsWith("X-IRMC-BOX:"))
89 QString box = lineData.mid(lineData.indexOf(":") + 1);
90 bool isOutgoing(box == "SENT");
91 if (isOutgoing == false && box != "INBOX")
93 qDebug() << "Unexpected box: " << box;
96 event.setDestination(isOutgoing ? EventTypes::SMS::SENT : EventTypes::SMS::INBOX);
98 else if(lineData.startsWith("X-NOK-DT:"))
100 QDateTime timestamp(QDateTime::fromString(
101 lineData.mid(lineData.indexOf(":") + 1),
102 "yyyyMMddThhmmssZ"));
103 timestamp.setTimeSpec(Qt::UTC);
104 event.setTimestamp(timestamp);
106 else if(lineData.startsWith("BEGIN:"))
108 iReader* reader = Factory::Instantiate(lineData, this);
109 bool valid(NULL != reader && reader->Read(lineData, stream, event));
112 // Quit processing if the nested content is not valid
116 else if(lineData.startsWith("END:"))
118 if(lineData != "END:VMSG")
120 qDebug() << getTagName() << " parser mismatch error" << lineData;
130 lineData = stream.readLine();
131 }while(!hasEnded && !stream.atEnd());
136 void VMessage::Write(QTextStream &stream, const EventTypes::SMS &event)
138 stream << "BEGIN:VMSG\n";
139 stream << "VERSION:" << m_Version << "\n";
140 stream << "X-IRMC-STATUS:" << ( event.IsRead() ? "READ" : "") << "\n";
141 stream << "X-IRMC-BOX:" << ( event.Destination() == EventTypes::SMS::SENT ? "SENT" : "INBOX") << "\n";
142 stream << "X-NOK-DT:" << event.Timestamp().toUTC().toString("yyyyMMddThhmmssZ") << "\n";
144 VEnvelope msgEnvelope(this);
146 // Add in the empty vcard for outgoing messages
147 if(event.Destination() == EventTypes::SMS::SENT)
149 VCard(this, 2.1, VCard::VCARD_LOCAL).Write(stream, event);
151 msgEnvelope.getContentWriters().append(new VCard(&msgEnvelope, 2.1, VCard::VCARD_REMOTE));
153 VEnvelope *bodyEnvelope = new VEnvelope(this);
154 bodyEnvelope->getContentWriters().append(new VBody(bodyEnvelope));
155 msgEnvelope.getContentWriters().append(bodyEnvelope);
159 VCard(this, 2.1, VCard::VCARD_REMOTE).Write(stream, event);
161 msgEnvelope.getContentWriters().append(new VBody(&msgEnvelope));
164 msgEnvelope.Write(stream, event);
166 stream << "END:VMSG\n";