1 | /* |
2 | * akonadi_serializer_kalarm.cpp - Akonadi resource serializer for KAlarm |
3 | * Copyright © 2009-2012 by David Jarvie <djarvie@kde.org> |
4 | * |
5 | * This library is free software; you can redistribute it and/or modify it |
6 | * under the terms of the GNU Library General Public License as published by |
7 | * the Free Software Foundation; either version 2 of the License, or (at your |
8 | * option) any later version. |
9 | * |
10 | * This library is distributed in the hope that it will be useful, but WITHOUT |
11 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or |
12 | * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public |
13 | * License for more details. |
14 | * |
15 | * You should have received a copy of the GNU Library General Public License |
16 | * along with this library; see the file COPYING.LIB. If not, write to the |
17 | * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA |
18 | * 02110-1301, USA. |
19 | */ |
20 | |
21 | #include "akonadi_serializer_kalarm.h" |
22 | #include "kaeventformatter.h" |
23 | |
24 | #include <kalarmcal/eventattribute.h> |
25 | #include <kalarmcal/kacalendar.h> |
26 | #include <kalarmcal/kaevent.h> |
27 | |
28 | #include <akonadi/item.h> |
29 | #include <akonadi/abstractdifferencesreporter.h> |
30 | #include <akonadi/attributefactory.h> |
31 | |
32 | #include <klocale.h> |
33 | #include <kdebug.h> |
34 | |
35 | #include <QtCore/qplugin.h> |
36 | |
37 | using namespace Akonadi; |
38 | using namespace KAlarmCal; |
39 | |
40 | |
41 | // Convert from backend data stream to a KAEvent, and set it into the item's payload. |
42 | bool SerializerPluginKAlarm::deserialize(Item& item, const QByteArray& label, QIODevice& data, int version) |
43 | { |
44 | Q_UNUSED(version); |
45 | |
46 | if (label != Item::FullPayload) |
47 | return false; |
48 | |
49 | KCalCore::Incidence::Ptr i = mFormat.fromString(QString::fromUtf8(data.readAll())); |
50 | if (!i) |
51 | { |
52 | kWarning(5954) << "Failed to parse incidence!" ; |
53 | data.seek(0); |
54 | kWarning(5954) << QString::fromUtf8(data.readAll()); |
55 | return false; |
56 | } |
57 | if (i->type() != KCalCore::Incidence::TypeEvent) |
58 | { |
59 | kWarning(5954) << "Incidence with uid" << i->uid() << "is not an Event!" ; |
60 | data.seek(0); |
61 | return false; |
62 | } |
63 | KAEvent event(i.staticCast<KCalCore::Event>()); |
64 | const QString mime = CalEvent::mimeType(event.category()); |
65 | if (mime.isEmpty() || !event.isValid()) |
66 | { |
67 | kWarning(5954) << "Event with uid" << event.id() << "contains no usable alarms!" ; |
68 | data.seek(0); |
69 | return false; |
70 | } |
71 | event.setItemId(item.id()); |
72 | |
73 | // Set additional event data contained in attributes |
74 | if (mRegistered.isEmpty()) |
75 | { |
76 | AttributeFactory::registerAttribute<KAlarmCal::EventAttribute>(); |
77 | mRegistered = QLatin1String("x" ); // set to any non-null string |
78 | } |
79 | const EventAttribute dummy; |
80 | if (item.hasAttribute(dummy.type())) |
81 | { |
82 | Attribute* a = item.attribute(dummy.type()); |
83 | if (!a) |
84 | kError(5954) << "deserialize(): Event with uid" << event.id() << "contains null attribute" ; |
85 | else |
86 | { |
87 | EventAttribute* evAttr = dynamic_cast<EventAttribute*>(a); |
88 | if (!evAttr) |
89 | { |
90 | // Registering EventAttribute doesn't work in the serializer |
91 | // unless the application also registers it. This doesn't |
92 | // matter unless the application uses KAEvent class. |
93 | kError(5954) << "deserialize(): Event with uid" << event.id() << "contains unknown type EventAttribute (application must call AttributeFactory::registerAttribute())" ; |
94 | } |
95 | else |
96 | { |
97 | KAEvent::CmdErrType err = evAttr->commandError(); |
98 | event.setCommandError(err); |
99 | } |
100 | } |
101 | } |
102 | |
103 | item.setMimeType(mime); |
104 | item.setPayload<KAEvent>(event); |
105 | return true; |
106 | } |
107 | |
108 | // Convert an item's KAEvent payload to backend data stream. |
109 | void SerializerPluginKAlarm::serialize(const Item& item, const QByteArray& label, QIODevice& data, int& version) |
110 | { |
111 | Q_UNUSED(version); |
112 | |
113 | if (label != Item::FullPayload || !item.hasPayload<KAEvent>()) |
114 | return; |
115 | const KAEvent e = item.payload<KAEvent>(); |
116 | KCalCore::Event::Ptr kcalEvent(new KCalCore::Event); |
117 | e.updateKCalEvent(kcalEvent, KAEvent::UID_SET); |
118 | QByteArray head = "BEGIN:VCALENDAR\nPRODID:" ; |
119 | head += KACalendar::icalProductId(); |
120 | head += "\nVERSION:2.0\nX-KDE-KALARM-VERSION:" ; |
121 | head += KAEvent::currentCalendarVersionString(); |
122 | head += '\n'; |
123 | data.write(head); |
124 | data.write(mFormat.toString(kcalEvent.staticCast<KCalCore::Incidence>()).toUtf8()); |
125 | data.write("\nEND:VCALENDAR" ); |
126 | } |
127 | |
128 | #include <kglobal.h> |
129 | |
130 | void SerializerPluginKAlarm::compare(AbstractDifferencesReporter* reporter, const Item& left, const Item& right) |
131 | { |
132 | Q_ASSERT(reporter); |
133 | Q_ASSERT(left.hasPayload<KAEvent>()); |
134 | Q_ASSERT(right.hasPayload<KAEvent>()); |
135 | |
136 | KAEvent eventL = left.payload<KAEvent>(); |
137 | KAEvent eventR = right.payload<KAEvent>(); |
138 | // Note that event attributes are not included, since they are not part of the payload |
139 | mValueL = KAEventFormatter(eventL, false); |
140 | mValueR = KAEventFormatter(eventR, false); |
141 | |
142 | reporter->setLeftPropertyValueTitle(i18nc("@title:column" , "Changed Alarm" )); |
143 | reporter->setRightPropertyValueTitle(i18nc("@title:column" , "Conflicting Alarm" )); |
144 | |
145 | reportDifference(reporter, KAEventFormatter::Id); |
146 | if (eventL.revision() != eventR.revision()) |
147 | reportDifference(reporter, KAEventFormatter::Revision); |
148 | if (eventL.actionSubType() != eventR.actionSubType()) |
149 | reportDifference(reporter, KAEventFormatter::AlarmType); |
150 | if (eventL.category() != eventR.category()) |
151 | reportDifference(reporter, KAEventFormatter::AlarmCategory); |
152 | if (eventL.templateName() != eventR.templateName()) |
153 | reportDifference(reporter, KAEventFormatter::TemplateName); |
154 | if (eventL.createdDateTime() != eventR.createdDateTime()) |
155 | reportDifference(reporter, KAEventFormatter::CreatedTime); |
156 | if (eventL.startDateTime() != eventR.startDateTime()) |
157 | reportDifference(reporter, KAEventFormatter::StartTime); |
158 | if (eventL.templateAfterTime() != eventR.templateAfterTime()) |
159 | reportDifference(reporter, KAEventFormatter::TemplateAfterTime); |
160 | if (*eventL.recurrence() != *eventR.recurrence()) |
161 | reportDifference(reporter, KAEventFormatter::Recurrence); |
162 | if (eventL.mainDateTime(true) != eventR.mainDateTime(true)) |
163 | reportDifference(reporter, KAEventFormatter::NextRecurrence); |
164 | if (eventL.repetition() != eventR.repetition()) |
165 | reportDifference(reporter, KAEventFormatter::SubRepetition); |
166 | if (eventL.repetition().interval() != eventR.repetition().interval()) |
167 | reportDifference(reporter, KAEventFormatter::RepeatInterval); |
168 | if (eventL.repetition().count() != eventR.repetition().count()) |
169 | reportDifference(reporter, KAEventFormatter::RepeatCount); |
170 | if (eventL.nextRepetition() != eventR.nextRepetition()) |
171 | reportDifference(reporter, KAEventFormatter::NextRepetition); |
172 | if (eventL.holidaysExcluded() != eventR.holidaysExcluded()) |
173 | reportDifference(reporter, KAEventFormatter::HolidaysExcluded); |
174 | if (eventL.workTimeOnly() != eventR.workTimeOnly()) |
175 | reportDifference(reporter, KAEventFormatter::WorkTimeOnly); |
176 | if (eventL.lateCancel() != eventR.lateCancel()) |
177 | reportDifference(reporter, KAEventFormatter::LateCancel); |
178 | if (eventL.autoClose() != eventR.autoClose()) |
179 | reportDifference(reporter, KAEventFormatter::AutoClose); |
180 | if (eventL.copyToKOrganizer() != eventR.copyToKOrganizer()) |
181 | reportDifference(reporter, KAEventFormatter::CopyKOrganizer); |
182 | if (eventL.enabled() != eventR.enabled()) |
183 | reportDifference(reporter, KAEventFormatter::Enabled); |
184 | if (eventL.isReadOnly() != eventR.isReadOnly()) |
185 | reportDifference(reporter, KAEventFormatter::ReadOnly); |
186 | if (eventL.toBeArchived() != eventR.toBeArchived()) |
187 | reportDifference(reporter, KAEventFormatter::Archive); |
188 | if (eventL.customProperties() != eventR.customProperties()) |
189 | reportDifference(reporter, KAEventFormatter::CustomProperties); |
190 | if (eventL.message() != eventR.message()) |
191 | reportDifference(reporter, KAEventFormatter::MessageText); |
192 | if (eventL.fileName() != eventR.fileName()) |
193 | reportDifference(reporter, KAEventFormatter::MessageFile); |
194 | if (eventL.fgColour() != eventR.fgColour()) |
195 | reportDifference(reporter, KAEventFormatter::FgColour); |
196 | if (eventL.bgColour() != eventR.bgColour()) |
197 | reportDifference(reporter, KAEventFormatter::BgColour); |
198 | if (eventL.font() != eventR.font()) |
199 | reportDifference(reporter, KAEventFormatter::Font); |
200 | if (eventL.preAction() != eventR.preAction()) |
201 | reportDifference(reporter, KAEventFormatter::PreAction); |
202 | if (eventL.cancelOnPreActionError() != eventR.cancelOnPreActionError()) |
203 | reportDifference(reporter, KAEventFormatter::PreActionCancel); |
204 | if (eventL.dontShowPreActionError() != eventR.dontShowPreActionError()) |
205 | reportDifference(reporter, KAEventFormatter::PreActionNoError); |
206 | if (eventL.postAction() != eventR.postAction()) |
207 | reportDifference(reporter, KAEventFormatter::PostAction); |
208 | if (eventL.confirmAck() != eventR.confirmAck()) |
209 | reportDifference(reporter, KAEventFormatter::ConfirmAck); |
210 | if (eventL.kmailSerialNumber() != eventR.kmailSerialNumber()) |
211 | reportDifference(reporter, KAEventFormatter::KMailSerial); |
212 | if (eventL.beep() != eventR.beep() |
213 | || eventL.speak() != eventR.speak() |
214 | || eventL.audioFile() != eventR.audioFile()) |
215 | reportDifference(reporter, KAEventFormatter::Sound); |
216 | if (eventL.repeatSound() != eventR.repeatSound()) |
217 | reportDifference(reporter, KAEventFormatter::SoundRepeat); |
218 | if (eventL.soundVolume() != eventR.soundVolume()) |
219 | reportDifference(reporter, KAEventFormatter::SoundVolume); |
220 | if (eventL.fadeVolume() != eventR.fadeVolume()) |
221 | reportDifference(reporter, KAEventFormatter::SoundFadeVolume); |
222 | if (eventL.fadeSeconds() != eventR.fadeSeconds()) |
223 | reportDifference(reporter, KAEventFormatter::SoundFadeTime); |
224 | if (eventL.reminderMinutes() != eventR.reminderMinutes()) |
225 | reportDifference(reporter, KAEventFormatter::Reminder); |
226 | if (eventL.reminderOnceOnly() != eventR.reminderOnceOnly()) |
227 | reportDifference(reporter, KAEventFormatter::ReminderOnce); |
228 | if (eventL.deferred() != eventR.deferred()) |
229 | reportDifference(reporter, KAEventFormatter::DeferralType); |
230 | if (eventL.deferDateTime() != eventR.deferDateTime()) |
231 | reportDifference(reporter, KAEventFormatter::DeferralTime); |
232 | if (eventL.deferDefaultMinutes() != eventR.deferDefaultMinutes()) |
233 | reportDifference(reporter, KAEventFormatter::DeferDefault); |
234 | if (eventL.deferDefaultDateOnly() != eventR.deferDefaultDateOnly()) |
235 | reportDifference(reporter, KAEventFormatter::DeferDefaultDate); |
236 | if (eventL.command() != eventR.command()) |
237 | reportDifference(reporter, KAEventFormatter::Command); |
238 | if (eventL.logFile() != eventR.logFile()) |
239 | reportDifference(reporter, KAEventFormatter::LogFile); |
240 | if (eventL.commandXterm() != eventR.commandXterm()) |
241 | reportDifference(reporter, KAEventFormatter::CommandXTerm); |
242 | if (eventL.emailSubject() != eventR.emailSubject()) |
243 | reportDifference(reporter, KAEventFormatter::EmailSubject); |
244 | if (eventL.emailFromId() != eventR.emailFromId()) |
245 | reportDifference(reporter, KAEventFormatter::EmailFromId); |
246 | if (eventL.emailAddresses() != eventR.emailAddresses()) |
247 | reportDifference(reporter, KAEventFormatter::EmailTo); |
248 | if (eventL.emailBcc() != eventR.emailBcc()) |
249 | reportDifference(reporter, KAEventFormatter::EmailBcc); |
250 | if (eventL.emailMessage() != eventR.emailMessage()) |
251 | reportDifference(reporter, KAEventFormatter::EmailBody); |
252 | if (eventL.emailAttachments() != eventR.emailAttachments()) |
253 | reportDifference(reporter, KAEventFormatter::EmailAttachments); |
254 | |
255 | KLocale* locale = KGlobal::locale(); |
256 | reporter->addProperty(AbstractDifferencesReporter::ConflictMode, i18nc("@label" , "Item revision" ), |
257 | locale->convertDigits(QString::number(left.revision()), locale->digitSet()), |
258 | locale->convertDigits(QString::number(right.revision()), locale->digitSet())); |
259 | } |
260 | |
261 | void SerializerPluginKAlarm::reportDifference(AbstractDifferencesReporter* reporter, KAEventFormatter::Parameter id) |
262 | { |
263 | if (mValueL.isApplicable(id) || mValueR.isApplicable(id)) |
264 | reporter->addProperty(AbstractDifferencesReporter::ConflictMode, KAEventFormatter::label(id), mValueL.value(id), mValueR.value(id)); |
265 | } |
266 | |
267 | QString SerializerPluginKAlarm::(const Item& item) const |
268 | { |
269 | return item.hasPayload<KAEvent>() ? item.payload<KAEvent>().id() : QString(); |
270 | } |
271 | |
272 | Q_EXPORT_PLUGIN2(akonadi_serializer_kalarm, SerializerPluginKAlarm) |
273 | |
274 | |
275 | // vim: et sw=4: |
276 | |