+
+
+void DeleteRoomReference(long QRnumber)
+{
+ HashPos *At;
+ long HKLen;
+ const char *HK;
+ void *vData = NULL;
+ rss_room_counter *pRoomC;
+
+ At = GetNewHashPos(RSSQueueRooms, 0);
+
+ if (GetHashPosFromKey(RSSQueueRooms, LKEY(QRnumber), At))
+ {
+ GetHashPos(RSSQueueRooms, At, &HKLen, &HK, &vData);
+ if (vData != NULL)
+ {
+ pRoomC = (rss_room_counter *) vData;
+ pRoomC->count --;
+ if (pRoomC->count == 0)
+ DeleteEntryFromHash(RSSQueueRooms, At);
+ }
+ }
+ DeleteHashPos(&At);
+}
+
+void UnlinkRooms(rss_aggregator *Cfg)
+{
+ DeleteRoomReference(Cfg->QRnumber);
+ if (Cfg->OtherQRnumbers != NULL)
+ {
+ long HKLen;
+ const char *HK;
+ HashPos *At;
+ void *vData;
+
+ At = GetNewHashPos(Cfg->OtherQRnumbers, 0);
+ while (! server_shutting_down &&
+ GetNextHashPos(Cfg->OtherQRnumbers,
+ At,
+ &HKLen, &HK,
+ &vData) &&
+ (vData != NULL))
+ {
+ long *lData = (long*) vData;
+ DeleteRoomReference(*lData);
+ }
+
+ DeleteHashPos(&At);
+ }
+}
+
+void UnlinkRSSAggregator(rss_aggregator *Cfg)
+{
+ HashPos *At;
+
+ UnlinkRooms(Cfg);
+
+ At = GetNewHashPos(RSSFetchUrls, 0);
+ if (GetHashPosFromKey(RSSFetchUrls, SKEY(Cfg->Url), At))
+ {
+ DeleteEntryFromHash(RSSFetchUrls, At);
+ }
+ DeleteHashPos(&At);
+ last_run = time(NULL);
+}
+
+void FreeNetworkSaveMessage (void *vMsg)
+{
+ networker_save_message *Msg = (networker_save_message *) vMsg;
+
+ CtdlFreeMessageContents(&Msg->Msg);
+ FreeStrBuf(&Msg->Message);
+ FreeStrBuf(&Msg->MsgGUID);
+ free(Msg);
+}
+
+eNextState AbortNetworkSaveMessage (AsyncIO *IO)
+{
+ return eAbort; ///TODO
+}
+
+eNextState RSSSaveMessage(AsyncIO *IO)
+{
+ long len;
+ const char *Key;
+ rss_aggregator *Ctx = (rss_aggregator *) IO->Data;
+
+ Ctx->ThisMsg->Msg.cm_fields['M'] = SmashStrBuf(&Ctx->ThisMsg->Message);
+
+ CtdlSubmitMsg(&Ctx->ThisMsg->Msg, &Ctx->recp, NULL, 0);
+
+ /* write the uidl to the use table so we don't store this item again */
+ cdb_store(CDB_USETABLE,
+ SKEY(Ctx->ThisMsg->MsgGUID),
+ &Ctx->ThisMsg->ut,
+ sizeof(struct UseTable) );
+
+ if (GetNextHashPos(Ctx->Messages,
+ Ctx->Pos,
+ &len, &Key,
+ (void**) &Ctx->ThisMsg))
+ return NextDBOperation(IO, RSS_FetchNetworkUsetableEntry);
+ else
+ return eAbort;
+}
+
+eNextState RSS_FetchNetworkUsetableEntry(AsyncIO *IO)
+{
+ const char *Key;
+ long len;
+ struct cdbdata *cdbut;
+ rss_aggregator *Ctx = (rss_aggregator *) IO->Data;
+
+ /* Find out if we've already seen this item */
+ strcpy(Ctx->ThisMsg->ut.ut_msgid,
+ ChrPtr(Ctx->ThisMsg->MsgGUID)); /// TODO
+ Ctx->ThisMsg->ut.ut_timestamp = time(NULL);
+
+ cdbut = cdb_fetch(CDB_USETABLE, SKEY(Ctx->ThisMsg->MsgGUID));
+#ifndef DEBUG_RSS
+ if (cdbut != NULL) {
+ /* Item has already been seen */
+ EV_syslog(LOG_DEBUG,
+ "%s has already been seen\n",
+ ChrPtr(Ctx->ThisMsg->MsgGUID));
+ cdb_free(cdbut);
+
+ /* rewrite the record anyway, to update the timestamp */
+ cdb_store(CDB_USETABLE,
+ SKEY(Ctx->ThisMsg->MsgGUID),
+ &Ctx->ThisMsg->ut, sizeof(struct UseTable) );
+
+ if (GetNextHashPos(Ctx->Messages,
+ Ctx->Pos,
+ &len, &Key,
+ (void**) &Ctx->ThisMsg))
+ return NextDBOperation(
+ IO,
+ RSS_FetchNetworkUsetableEntry);
+ else
+ return eAbort;
+ }
+ else
+#endif
+ {
+ NextDBOperation(IO, RSSSaveMessage);
+ return eSendMore;
+ }
+}
+