From 93a33d4148d06122184faf9e094515cfaa253551 Mon Sep 17 00:00:00 2001 From: acanas Date: Wed, 15 Sep 2021 20:21:02 +0200 Subject: [PATCH] Version 21.5.1: Sep 15, 2021 Queries moved to module swad_forum_database. --- swad_account.c | 4 +- swad_center.c | 4 +- swad_changelog.h | 3 +- swad_course.c | 4 +- swad_degree.c | 4 +- swad_error.c | 5 + swad_error.h | 1 + swad_figure.c | 3 +- swad_forum.c | 1398 +---------------------------------------- swad_forum.h | 25 - swad_forum_database.c | 1387 +++++++++++++++++++++++++++++++++++++++- swad_forum_database.h | 62 +- swad_indicator.c | 4 +- swad_institution.c | 4 +- swad_profile.c | 2 +- 15 files changed, 1455 insertions(+), 1455 deletions(-) diff --git a/swad_account.c b/swad_account.c index 302cf431..b71c667c 100644 --- a/swad_account.c +++ b/swad_account.c @@ -44,7 +44,7 @@ #include "swad_exam_database.h" #include "swad_follow.h" #include "swad_form.h" -#include "swad_forum.h" +#include "swad_forum_database.h" #include "swad_global.h" #include "swad_HTML.h" #include "swad_ID.h" @@ -1005,7 +1005,7 @@ void Acc_CompletelyEliminateAccount (struct UsrData *UsrDat, UsrDat->FullName); /***** Remove user's clipboard in forums *****/ - For_DB_RemoveUsrFromThrClipboard (UsrDat->UsrCod); + For_DB_RemoveUsrFromClipboard (UsrDat->UsrCod); /***** Remove some files of the user's from database *****/ Brw_DB_RemoveUsrFiles (UsrDat->UsrCod); diff --git a/swad_center.c b/swad_center.c index 8d6a957b..048ac051 100644 --- a/swad_center.c +++ b/swad_center.c @@ -41,7 +41,7 @@ #include "swad_figure.h" #include "swad_figure_cache.h" #include "swad_form.h" -#include "swad_forum.h" +#include "swad_forum_database.h" #include "swad_global.h" #include "swad_hierarchy.h" #include "swad_hierarchy_level.h" @@ -1080,7 +1080,7 @@ void Ctr_RemoveCenter (void) else // Center has no degrees or users ==> remove it { /***** Remove all the threads and posts in forums of the center *****/ - For_RemoveForums (HieLvl_CTR,Ctr_EditingCtr->CtrCod); + For_DB_RemoveForums (HieLvl_CTR,Ctr_EditingCtr->CtrCod); /***** Remove surveys of the center *****/ Svy_RemoveSurveys (HieLvl_CTR,Ctr_EditingCtr->CtrCod); diff --git a/swad_changelog.h b/swad_changelog.h index 93387637..78b774d6 100644 --- a/swad_changelog.h +++ b/swad_changelog.h @@ -602,13 +602,14 @@ TODO: FIX BUG, URGENT! En las fechas como par TODO: En las encuestas, que los estudiantes no puedan ver los resultados hasta que no finalice el plazo. */ -#define Log_PLATFORM_VERSION "SWAD 21.5 (2021-09-15)" +#define Log_PLATFORM_VERSION "SWAD 21.5.1 (2021-09-15)" #define CSS_FILE "swad20.45.css" #define JS_FILE "swad20.69.1.js" /* TODO: Rename CENTRE to CENTER in help wiki. TODO: Rename ASSESSMENT.Announcements to ASSESSMENT.Calls_for_exams + Version 21.5.1: Sep 15, 2021 Queries moved to module swad_forum_database. (315348 lines) Version 21.5: Sep 15, 2021 New module swad_forum_database for database queries related to forums. (315354 lines) Version 21.4: Sep 15, 2021 New module swad_firewall_database for database queries related to firewall. (315286 lines) Version 21.3.1: Sep 15, 2021 Queries moved to module swad_browser_database. (315201 lines) diff --git a/swad_course.c b/swad_course.c index c07b26ff..56e9b9e9 100644 --- a/swad_course.c +++ b/swad_course.c @@ -43,7 +43,7 @@ #include "swad_figure.h" #include "swad_figure_cache.h" #include "swad_form.h" -#include "swad_forum.h" +#include "swad_forum_database.h" #include "swad_game.h" #include "swad_global.h" #include "swad_help.h" @@ -1823,7 +1823,7 @@ static void Crs_EmptyCourseCompletely (long CrsCod) Not_DB_RemoveCrsNotices (CrsCod); /***** Remove all the threads and posts in forums of the course *****/ - For_RemoveForums (HieLvl_CRS,CrsCod); + For_DB_RemoveForums (HieLvl_CRS,CrsCod); /***** Remove all surveys in the course *****/ Svy_RemoveSurveys (HieLvl_CRS,CrsCod); diff --git a/swad_degree.c b/swad_degree.c index 795fd1d9..e72a19d5 100644 --- a/swad_degree.c +++ b/swad_degree.c @@ -42,7 +42,7 @@ #include "swad_figure.h" #include "swad_figure_cache.h" #include "swad_form.h" -#include "swad_forum.h" +#include "swad_forum_database.h" #include "swad_global.h" #include "swad_hierarchy.h" #include "swad_HTML.h" @@ -1350,7 +1350,7 @@ void Deg_RemoveDegreeCompletely (long DegCod) DB_FreeMySQLResult (&mysql_res); /***** Remove all the threads and posts in forums of the degree *****/ - For_RemoveForums (HieLvl_DEG,DegCod); + For_DB_RemoveForums (HieLvl_DEG,DegCod); /***** Remove surveys of the degree *****/ Svy_RemoveSurveys (HieLvl_DEG,DegCod); diff --git a/swad_error.c b/swad_error.c index a7908de9..f9388802 100644 --- a/swad_error.c +++ b/swad_error.c @@ -468,6 +468,11 @@ void Err_WrongForumExit (void) Err_ShowErrorAndExit ("Wrong forum."); } +void Err_WrongThreadExit (void) + { + Err_ShowErrorAndExit ("Wrong thread."); + } + void Err_WrongPostExit (void) { Err_ShowErrorAndExit ("Wrong post."); diff --git a/swad_error.h b/swad_error.h index 6db628a9..56f79bb9 100644 --- a/swad_error.h +++ b/swad_error.h @@ -90,6 +90,7 @@ void Err_WrongEventExit (void); void Err_WrongAnnouncementExit (void); void Err_WrongNoticeExit (void); void Err_WrongForumExit (void); +void Err_WrongThreadExit (void); void Err_WrongPostExit (void); void Err_WrongMessageExit (void); void Err_WrongMailDomainExit (void); diff --git a/swad_figure.c b/swad_figure.c index 0c627ca5..ea798bd1 100644 --- a/swad_figure.c +++ b/swad_figure.c @@ -44,6 +44,7 @@ #include "swad_follow_database.h" #include "swad_form.h" #include "swad_forum.h" +#include "swad_forum_database.h" #include "swad_global.h" #include "swad_hierarchy.h" #include "swad_hierarchy_level.h" @@ -2670,7 +2671,7 @@ static void Fig_WriteForumTitleAndStats (For_ForumType_t ForumType, /***** Compute number of forums, number of threads and number of posts *****/ NumForums = For_DB_GetNumTotalForumsOfType (ForumType,CtyCod,InsCod,CtrCod,DegCod,CrsCod); NumThreads = For_DB_GetNumTotalThrsInForumsOfType (ForumType,CtyCod,InsCod,CtrCod,DegCod,CrsCod); - NumPosts = For_GetNumTotalPstsInForumsOfType (ForumType,CtyCod,InsCod,CtrCod,DegCod,CrsCod,&NumUsrsToBeNotifiedByEMail); + NumPosts = For_DB_GetNumTotalPstsInForumsOfType (ForumType,CtyCod,InsCod,CtrCod,DegCod,CrsCod,&NumUsrsToBeNotifiedByEMail); /***** Compute number of threads per forum, number of posts per forum and number of posts per thread *****/ NumThrsPerForum = (NumForums ? (double) NumThreads / (double) NumForums : diff --git a/swad_forum.c b/swad_forum.c index 4bebd8d3..e8677f7e 100644 --- a/swad_forum.c +++ b/swad_forum.c @@ -308,18 +308,7 @@ static unsigned For_NumPstsInThrWithPstCod (long PstCod,long *ThrCod); static void For_RemoveThreadOnly (long ThrCod); static void For_RemoveThreadAndItsPsts (long ThrCod); -static void For_DB_UpdateThrFirstAndLastPst (long ThrCod,long FirstPstCod,long LastPstCod); -static void For_DB_UpdateThrLastPst (long ThrCod,long LastPstCod); -static long For_GetLastPstCod (long ThrCod); - -static void For_DB_UpdateThrReadTime (long ThrCod, - time_t CreatTimeUTCOfTheMostRecentPostRead); -static unsigned For_DB_GetNumOfReadersOfThr (long ThrCod); -static unsigned For_DB_GetNumOfWritersInThr (long ThrCod); -static unsigned For_DB_GetNumPstsInThr (long ThrCod); -static unsigned For_DB_GetNumMyPstInThr (long ThrCod); static time_t For_GetThrReadTime (long ThrCod); -static void For_DB_RemoveThrFromReadThrs (long ThrCod); static void For_ShowPostsOfAThread (struct For_Forums *Forums, Ale_AlertType_t AlertType,const char *Message); static void For_PutIconNewPost (void *Forums); @@ -370,17 +359,13 @@ static void For_WriteLinkToForum (const struct For_Forums *Forums, bool IsLastItemInLevel[1 + For_FORUM_MAX_LEVELS]); static unsigned For_GetNumThrsWithNewPstsInForum (const struct For_Forum *Forum, unsigned NumThreads); -static unsigned For_GetNumOfThreadsInForumNewerThan (const struct For_Forum *Forum, - const char *Time); static unsigned For_GetNumOfUnreadPostsInThr (long ThrCod,unsigned NumPostsInThr); -static unsigned For_DB_GetNumOfPostsInThrNewerThan (long ThrCod,const char *Time); static void For_WriteNumberOfThrs (unsigned NumThrs); static void For_ShowForumThreadsHighlightingOneThread (struct For_Forums *Forums, Ale_AlertType_t AlertType,const char *Message); static void For_PutIconNewThread (void *Forums); static void For_PutAllHiddenParamsNewThread (void *Forums); -static unsigned For_GetNumThrsInForum (const struct For_Forum *Forum); static void For_ListForumThrs (struct For_Forums *Forums, long ThrCods[Pag_ITEMS_PER_PAGE], long ThrCodHighlighted, @@ -394,18 +379,10 @@ static void For_RestrictAccess (const struct For_Forums *Forums); static void For_WriteFormForumPst (struct For_Forums *Forums, bool IsReply,const char *Subject); -static void For_DB_UpdateNumUsrsNotifiedByEMailAboutPost (long PstCod, - unsigned NumUsrsToBeNotifiedByEMail); - static void For_PutAllHiddenParamsRemThread (void *Forums); static bool For_CheckIfICanMoveThreads (void); -static long For_DB_GetThrInMyClipboard (void); -static bool For_DB_CheckIfThrBelongsToForum (long ThrCod,const struct For_Forum *Forum); -static void For_DB_MoveThrToCurrentForum (const struct For_Forums *Forums); static void For_InsertThrInClipboard (long ThrCod); -static void For_DB_RemoveExpiredThrsClipboards (void); -static void For_DB_RemoveThrCodFromThrClipboard (long ThrCod); /*****************************************************************************/ /********************************** Reset forum ******************************/ @@ -530,7 +507,7 @@ static bool For_RemoveForumPst (long PstCod,long MedCod) /***** Update the last post of the thread *****/ if (!ThreadDeleted) - For_DB_UpdateThrLastPst (ThrCod,For_GetLastPstCod (ThrCod)); + For_DB_UpdateThrLastPst (ThrCod,For_DB_GetThrLastPst (ThrCod)); return ThreadDeleted; } @@ -581,7 +558,7 @@ static void For_RemoveThreadOnly (long ThrCod) For_DB_RemoveThrFromReadThrs (ThrCod); /***** Remove thread code from thread clipboard *****/ - For_DB_RemoveThrCodFromThrClipboard (ThrCod); + For_DB_RemoveThrFromClipboard (ThrCod); /***** Delete thread from forum thread table *****/ For_DB_RemoveThread (ThrCod); @@ -644,160 +621,6 @@ void For_GetForumTypeAndLocationOfAPost (long PstCod,struct For_Forum *Forum) DB_FreeMySQLResult (&mysql_res); } -/*****************************************************************************/ -/********* Modify the codes of the first and last posts of a thread **********/ -/*****************************************************************************/ - -static void For_DB_UpdateThrFirstAndLastPst (long ThrCod,long FirstPstCod,long LastPstCod) - { - /***** Update the code of the first and last posts of a thread *****/ - DB_QueryUPDATE ("can not update a thread of a forum", - "UPDATE for_threads" - " SET FirstPstCod=%ld," - "LastPstCod=%ld" - " WHERE ThrCod=%ld", - FirstPstCod, - LastPstCod, - ThrCod); - } - -/*****************************************************************************/ -/************** Modify the code of the last post of a thread *****************/ -/*****************************************************************************/ - -static void For_DB_UpdateThrLastPst (long ThrCod,long LastPstCod) - { - /***** Update the code of the last post of a thread *****/ - DB_QueryUPDATE ("can not update a thread of a forum", - "UPDATE for_threads" - " SET LastPstCod=%ld" - " WHERE ThrCod=%ld", - LastPstCod, - ThrCod); - } - -/*****************************************************************************/ -/**************** Get the code of the last post of a thread ******************/ -/*****************************************************************************/ - -static long For_GetLastPstCod (long ThrCod) - { - long LastPstCod; - - /***** Get the code of the last post of a thread from database *****/ - LastPstCod = DB_QuerySELECTCode ("can not get the most recent post" - " of a thread of a forum", - "SELECT PstCod" - " FROM for_posts" - " WHERE ThrCod=%ld" - " ORDER BY CreatTime DESC" - " LIMIT 1", - ThrCod); - if (LastPstCod <= 0) - Err_ShowErrorAndExit ("Error when getting the most recent post of a thread of a forum."); - - return LastPstCod; - } - -/*****************************************************************************/ -/************* Update read date of a thread for the current user *************/ -/*****************************************************************************/ -// Update for_read table indicating that this thread page and previous ones -// have been read and have no new posts for the current user -// (even if any previous pages have been no read actually) -// Note that database is not updated with the current time, -// but with the creation time of the most recent post in this thread read by me. - -static void For_DB_UpdateThrReadTime (long ThrCod, - time_t CreatTimeUTCOfTheMostRecentPostRead) - { - /***** Insert or replace pair ThrCod-UsrCod in for_read *****/ - DB_QueryREPLACE ("can not update the status of reading" - " of a thread of a forum", - "REPLACE INTO for_read" - " (ThrCod,UsrCod,ReadTime)" - " VALUES" - " (%ld,%ld,FROM_UNIXTIME(%ld))", - ThrCod, - Gbl.Usrs.Me.UsrDat.UsrCod, - (long) CreatTimeUTCOfTheMostRecentPostRead); - } - -/*****************************************************************************/ -/**************** Get number of users that have read a thread ****************/ -/*****************************************************************************/ - -static unsigned For_DB_GetNumOfReadersOfThr (long ThrCod) - { - /***** Get number of distinct readers of a thread from database *****/ - return (unsigned) - DB_QueryCOUNT ("can not get the number of readers of a thread of a forum", - "SELECT COUNT(*)" - " FROM for_read" - " WHERE ThrCod=%ld", - ThrCod); - } - -/*****************************************************************************/ -/********** Get number of users that have write posts in a thread ************/ -/*****************************************************************************/ - -static unsigned For_DB_GetNumOfWritersInThr (long ThrCod) - { - /***** Get number of distinct writers in a thread from database *****/ - return DB_QueryCOUNT ("can not get the number of writers in a thread of a forum", - "SELECT COUNT(DISTINCT UsrCod)" - " FROM for_posts" - " WHERE ThrCod=%ld", - ThrCod); - } - -/*****************************************************************************/ -/********************** Get number of posts in a thread **********************/ -/*****************************************************************************/ - -static unsigned For_DB_GetNumPstsInThr (long ThrCod) - { - /***** Get number of posts in a thread from database *****/ - return (unsigned) - DB_QueryCOUNT ("can not get the number of posts in a thread of a forum", - "SELECT COUNT(*)" - " FROM for_posts" - " WHERE ThrCod=%ld", - ThrCod); - } - -/*****************************************************************************/ -/************** Get whether there are posts of mine in a thread **************/ -/*****************************************************************************/ - -static unsigned For_DB_GetNumMyPstInThr (long ThrCod) - { - /***** Get if I have write posts in a thread from database *****/ - return (unsigned) - DB_QueryCOUNT ("can not check if you have written posts in a thead of a forum", - "SELECT COUNT(*)" - " FROM for_posts" - " WHERE ThrCod=%ld" - " AND UsrCod=%ld", - ThrCod, - Gbl.Usrs.Me.UsrDat.UsrCod); - } - -/*****************************************************************************/ -/*********************** Get number of posts from a user *********************/ -/*****************************************************************************/ - -unsigned For_DB_GetNumPostsUsr (long UsrCod) - { - /***** Get number of posts from a user from database *****/ - return DB_QueryCOUNT ("can not get number of forum posts from a user", - "SELECT COUNT(*)" - " FROM for_posts" - " WHERE UsrCod=%ld", - UsrCod); - } - /*****************************************************************************/ /****************** Get thread read time for the current user ****************/ /*****************************************************************************/ @@ -831,33 +654,6 @@ static time_t For_GetThrReadTime (long ThrCod) return ReadTimeUTC; } -/*****************************************************************************/ -/********************* Remove thread read status for a thread ****************/ -/*****************************************************************************/ - -static void For_DB_RemoveThrFromReadThrs (long ThrCod) - { - /***** Remove pairs ThrCod-UsrCod in for_read for a thread *****/ - DB_QueryDELETE ("can not remove the status of reading" - " of a thread of a forum", - "DELETE FROM for_read" - " WHERE ThrCod=%ld", - ThrCod); - } - -/*****************************************************************************/ -/********************** Remove thread read status for a user *****************/ -/*****************************************************************************/ - -void For_DB_RemoveUsrFromReadThrs (long UsrCod) - { - DB_QueryDELETE ("can not remove the status of reading by a user" - " of all the threads of a forum", - "DELETE FROM for_read" - " WHERE UsrCod=%ld", - UsrCod); - } - /*****************************************************************************/ /************************ Show posts in a thread *****************************/ /*****************************************************************************/ @@ -1933,7 +1729,7 @@ static void For_WriteLinkToForum (const struct For_Forums *Forums, char ForumName[For_MAX_BYTES_FORUM_NAME + 1]; /***** Get number of threads and number of posts *****/ - NumThrs = For_GetNumThrsInForum (Forum); + NumThrs = For_DB_GetNumThrsInForum (Forum); NumThrsWithNewPosts = For_GetNumThrsWithNewPstsInForum (Forum,NumThrs); Class = (NumThrsWithNewPosts ? The_ClassFormLinkInBoxBold[Gbl.Prefs.Theme] : The_ClassFormLinkInBox[Gbl.Prefs.Theme]); @@ -2164,7 +1960,7 @@ static unsigned For_GetNumThrsWithNewPstsInForum (const struct For_Forum *Forum, { /***** Get number of threads with a last message modify time > newest read time (row[0]) *****/ row = mysql_fetch_row (mysql_res); - NumThrsWithNewPosts = For_GetNumOfThreadsInForumNewerThan (Forum,row[0]); + NumThrsWithNewPosts = For_DB_GetNumOfThreadsInForumNewerThan (Forum,row[0]); } /***** Free structure that stores the query result *****/ @@ -2173,35 +1969,6 @@ static unsigned For_GetNumThrsWithNewPstsInForum (const struct For_Forum *Forum, return NumThrsWithNewPosts; } -/*****************************************************************************/ -/**** Get number of threads in forum with a modify time > a specified time ***/ -/*****************************************************************************/ - -static unsigned For_GetNumOfThreadsInForumNewerThan (const struct For_Forum *Forum, - const char *Time) - { - char SubQuery[256]; - - /***** Get number of threads with a last message modify time - > specified time from database *****/ - if (Forum->Location > 0) - sprintf (SubQuery," AND for_threads.Location=%ld",Forum->Location); - else - SubQuery[0] = '\0'; - return (unsigned) - DB_QueryCOUNT ("can not check if there are new posts in a forum", - "SELECT COUNT(*)" - " FROM for_threads," - "for_posts" - " WHERE for_threads.ForumType=%u" - "%s" - " AND for_threads.LastPstCod=for_posts.PstCod" - " AND for_posts.ModifTime>'%s'", - (unsigned) Forum->Type, - SubQuery, - Time); - } - /*****************************************************************************/ /** Get number of unread posts in a thread since my last read of that thread */ /*****************************************************************************/ @@ -2223,7 +1990,7 @@ static unsigned For_GetNumOfUnreadPostsInThr (long ThrCod,unsigned NumPostsInThr { /***** Get the number of posts in thread with a modify time > newest read time for me (row[0]) *****/ row = mysql_fetch_row (mysql_res); - NumUnreadPosts = For_DB_GetNumOfPostsInThrNewerThan (ThrCod,row[0]); + NumUnreadPosts = For_DB_GetNumPstsInThrNewerThan (ThrCod,row[0]); } /***** Free structure that stores the query result *****/ @@ -2232,23 +1999,6 @@ static unsigned For_GetNumOfUnreadPostsInThr (long ThrCod,unsigned NumPostsInThr return NumUnreadPosts; } -/*****************************************************************************/ -/**** Get number of posts in thread with a modify time > a specified time ****/ -/*****************************************************************************/ - -static unsigned For_DB_GetNumOfPostsInThrNewerThan (long ThrCod,const char *Time) - { - /***** Get the number of posts in thread with a modify time > a specified time from database *****/ - return (unsigned) - DB_QueryCOUNT ("can not check if there are new posts in a thread of a forum", - "SELECT COUNT(*)" - " FROM for_posts" - " WHERE ThrCod=%ld" - " AND ModifTime>'%s'", - ThrCod, - Time); - } - /*****************************************************************************/ /************** Get and write total number of threads and posts **************/ /*****************************************************************************/ @@ -2483,861 +2233,6 @@ static void For_PutAllHiddenParamsNewThread (void *Forums) -1L); } -/*****************************************************************************/ -/********************** Get number of forums of a type ***********************/ -/*****************************************************************************/ - -unsigned For_DB_GetNumTotalForumsOfType (For_ForumType_t ForumType, - long CtyCod, - long InsCod, - long CtrCod, - long DegCod, - long CrsCod) - { - /***** Get number of forums of a type from database *****/ - switch (ForumType) - { - case For_FORUM_GLOBAL_USRS: - case For_FORUM_GLOBAL_TCHS: - case For_FORUM__SWAD__USRS: - case For_FORUM__SWAD__TCHS: - return 1; // Only one forum - case For_FORUM_INSTIT_USRS: - case For_FORUM_INSTIT_TCHS: - if (InsCod > 0) - // InsCod > 0 ==> 0 <= number of institutions forums for an institution <= 1 - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT Location)" - " FROM for_threads" - " WHERE ForumType=%u" - " AND Location=%ld", - (unsigned) ForumType, - InsCod); - - if (CtyCod > 0) - // InsCod <= 0 && CtyCod > 0 ==> Number of institution forums for a country - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT for_threads.Location)" - " FROM for_threads," - "ins_instits" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=ins_instits.InsCod" - " AND ins_instits.CtyCod=%ld", - (unsigned) ForumType, - CtyCod); - - // CtyCod <= 0 ==> Number of institutions forums for the whole platform - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT Location)" - " FROM for_threads" - " WHERE ForumType=%u", - (unsigned) ForumType); - case For_FORUM_CENTER_USRS: - case For_FORUM_CENTER_TCHS: - if (CtrCod > 0) - // CtrCod > 0 ==> 0 <= number of center forums for a center <= 1 - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT Location)" - " FROM for_threads" - " WHERE ForumType=%u" - " AND Location=%ld", - (unsigned) ForumType, - CtrCod); - - if (InsCod > 0) - // CtrCod <= 0 && InsCod > 0 ==> Number of center forums for an institution - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT for_threads.Location)" - " FROM for_threads," - "ctr_centers" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=%ld", - (unsigned) ForumType, - InsCod); - - if (CtyCod > 0) - // InsCod <= 0 && CtyCod > 0 ==> Number of center forums for a country - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT for_threads.Location)" - " FROM for_threads," - "ctr_centers," - "ins_instits" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=ins_instits.InsCod" - " AND ins_instits.CtyCod=%ld", - (unsigned) ForumType, - CtyCod); - - // InsCod <= 0 ==> Number of center forums for the whole platform - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT Location)" - " FROM for_threads" - " WHERE ForumType=%u", - (unsigned) ForumType); - case For_FORUM_DEGREE_USRS: - case For_FORUM_DEGREE_TCHS: - if (DegCod > 0) - // DegCod > 0 ==> 0 <= number of degree forums for a degree <= 1 - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT Location)" - " FROM for_threads" - " WHERE ForumType=%u" - " AND Location=%ld", - (unsigned) ForumType, - DegCod); - - if (CtrCod > 0) - // DegCod <= 0 && CtrCod > 0 ==> Number of degree forums for a center - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT for_threads.Location)" - " FROM for_threads," - "deg_degrees" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=%ld", - (unsigned) ForumType, - CtrCod); - - if (InsCod > 0) - // CtrCod <= 0 && InsCod > 0 ==> Number of degree forums for an institution - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT for_threads.Location)" - " FROM for_threads," - "deg_degrees," - "ctr_centers" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=%ld", - (unsigned) ForumType, - InsCod); - - if (CtyCod > 0) - // InsCod <= 0 && CtyCod > 0 ==> Number of degree forums for a country - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT for_threads.Location)" - " FROM for_threads," - "deg_degrees," - "ctr_centers," - "ins_instits" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=ins_instits.InsCod" - " AND ins_instits.CtyCod=%ld", - (unsigned) ForumType, - CtyCod); - - // InsCod <= 0 ==> Number of degree forums for the whole platform - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT Location)" - " FROM for_threads" - " WHERE ForumType=%u", - (unsigned) ForumType); - case For_FORUM_COURSE_USRS: - case For_FORUM_COURSE_TCHS: - if (CrsCod > 0) - // CrsCod > 0 ==> 0 <= number of course forums for a course <= 1 - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT Location)" - " FROM for_threads" - " WHERE ForumType=%u" - " AND Location=%ld", - (unsigned) ForumType, - CrsCod); - - if (DegCod > 0) - // CrsCod <= 0 && DegCod > 0 ==> Number of course forums for a degree - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT for_threads.Location)" - " FROM for_threads," - "crs_courses" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=crs_courses.CrsCod" - " AND crs_courses.DegCod=%ld", - (unsigned) ForumType, - DegCod); - - if (CtrCod > 0) - // DegCod <= 0 && CtrCod > 0 ==> Number of course forums for a center - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT for_threads.Location)" - " FROM for_threads," - "crs_courses," - "deg_degrees" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=crs_courses.CrsCod" - " AND crs_courses.DegCod=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=%ld", - (unsigned) ForumType, - CtrCod); - - if (InsCod > 0) - // CtrCod <= 0 && InsCod > 0 ==> Number of course forums for an institution - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT for_threads.Location)" - " FROM for_threads," - "crs_courses," - "deg_degrees," - "ctr_centers" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=crs_courses.CrsCod" - " AND crs_courses.DegCod=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=%ld", - (unsigned) ForumType, - InsCod); - - if (CtyCod > 0) - // InsCod <= 0 && CtyCod > 0 ==> Number of course forums for a country - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT for_threads.Location)" - " FROM for_threads," - "crs_courses," - "deg_degrees," - "ctr_centers," - "ins_instits" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=crs_courses.CrsCod" - " AND crs_courses.DegCod=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=ins_instits.InsCod" - " AND ins_instits.CtyCod=%ld", - (unsigned) ForumType, - CtyCod); - - // InsCod <= 0 ==> Number of course forums for the whole platform - return (unsigned) - DB_QueryCOUNT ("can not get number of forums of a type", - "SELECT COUNT(DISTINCT Location)" - " FROM for_threads" - " WHERE ForumType=%u", - (unsigned) ForumType); - default: - return 0; - } - } - -/*****************************************************************************/ -/*********** Get total number of threads in forums of this type **************/ -/*****************************************************************************/ - -unsigned For_DB_GetNumTotalThrsInForumsOfType (For_ForumType_t ForumType, - long CtyCod, - long InsCod, - long CtrCod, - long DegCod, - long CrsCod) - { - /***** Get total number of threads in forums of this type from database *****/ - switch (ForumType) - { - case For_FORUM_GLOBAL_USRS: - case For_FORUM_GLOBAL_TCHS: - case For_FORUM__SWAD__USRS: - case For_FORUM__SWAD__TCHS: - // Total number of threads in forums of this type - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads" - " WHERE ForumType=%u", - (unsigned) ForumType); - case For_FORUM_INSTIT_USRS: - case For_FORUM_INSTIT_TCHS: - if (InsCod > 0) - // InsCod > 0 ==> Number of threads in institution forums for an institution - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads" - " WHERE ForumType=%u" - " AND Location=%ld", - (unsigned) ForumType, - InsCod); - - if (CtyCod > 0) - // InsCod <= 0 && CtyCod > 0 ==> Number of threads in institution forums for a country - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads," - "ins_instits" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=ins_instits.InsCod" - " AND ins_instits.CtyCod=%ld", - (unsigned) ForumType, - CtyCod); - - // InsCod <= 0 ==> Number of threads in institution forums for the whole platform - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads" - " WHERE ForumType=%u", - (unsigned) ForumType); - case For_FORUM_CENTER_USRS: - case For_FORUM_CENTER_TCHS: - if (CtrCod > 0) - // CtrCod > 0 ==> 0 <= Number of threads in center forums for a center <= 1 - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads" - " WHERE ForumType=%u" - " AND Location=%ld", - (unsigned) ForumType, - CtrCod); - - if (InsCod > 0) - // CtrCod <= 0 && InsCod > 0 ==> Number of threads in center forums for an institution - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads," - "ctr_centers" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=%ld", - (unsigned) ForumType, - InsCod); - - if (CtyCod > 0) - // InsCod <= 0 && CtyCod > 0 ==> Number of threads in center forums for a country - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads," - "ctr_centers," - "ins_instits" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=ins_instits.InsCod" - " AND ins_instits.CtyCod=%ld", - (unsigned) ForumType, - CtyCod); - - // InsCod <= 0 ==> Number of threads in center forums for the whole platform - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads" - " WHERE ForumType=%u", - (unsigned) ForumType); - case For_FORUM_DEGREE_USRS: - case For_FORUM_DEGREE_TCHS: - if (DegCod > 0) - // DegCod > 0 ==> Number of threads in degree forums for a degree - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads" - " WHERE ForumType=%u" - " AND Location=%ld", - (unsigned) ForumType, - DegCod); - - if (CtrCod > 0) - // DegCod <= 0 && CtrCod > 0 ==> Number of threads in degree forums for a center - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads," - "deg_degrees" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=%ld", - (unsigned) ForumType, - CtrCod); - - if (InsCod > 0) - // CtrCod <= 0 && InsCod > 0 ==> Number of threads in degree forums for an institution - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads," - "deg_degrees," - "ctr_centers" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=%ld", - (unsigned) ForumType, - InsCod); - - if (CtyCod > 0) // InsCod <= 0 && CtyCod > 0 ==> Number of threads in degree forums for a country - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads," - "deg_degrees," - "ctr_centers," - "ins_instits" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=ins_instits.InsCod" - " AND ins_instits.CtyCod=%ld", - (unsigned) ForumType, - CtyCod); - - // InsCod <= 0 ==> Number of threads in degree forums for the whole platform - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads" - " WHERE ForumType=%u", - (unsigned) ForumType); - case For_FORUM_COURSE_USRS: - case For_FORUM_COURSE_TCHS: - if (CrsCod > 0) - // CrsCod > 0 ==> 0 <= Number of threads in course forums for a course - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads" - " WHERE ForumType=%u" - " AND Location=%ld", - (unsigned) ForumType, - CrsCod); - - if (DegCod > 0) - // CrsCod <= 0 && DegCod > 0 ==> Number of threads in course forums for a degree - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads," - "crs_courses" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=crs_courses.CrsCod" - " AND crs_courses.DegCod=%ld", - (unsigned) ForumType, - DegCod); - - if (CtrCod > 0) - // DegCod <= 0 && CtrCod > 0 ==> Number of threads in course forums for a center - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads," - "crs_courses," - "deg_degrees" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=crs_courses.CrsCod" - " AND crs_courses.DegCod=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=%ld", - (unsigned) ForumType, - CtrCod); - - if (InsCod > 0) - // CtrCod <= 0 && InsCod > 0 ==> Number of threads in course forums for an institution - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads," - "crs_courses," - "deg_degrees," - "ctr_centers" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=crs_courses.CrsCod" - " AND crs_courses.DegCod=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=%ld", - (unsigned) ForumType, - InsCod); - - if (CtyCod > 0) - // InsCod <= 0 && CtyCod > 0 ==> Number of threads in course forums for a country - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads," - "crs_courses," - "deg_degrees," - "ctr_centers," - "ins_instits" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=crs_courses.CrsCod" - " AND crs_courses.DegCod=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=ins_instits.InsCod" - " AND ins_instits.CtyCod=%ld", - (unsigned) ForumType, - CtyCod); - - // InsCod <= 0 ==> Number of threads in course forums for the whole platform - return (unsigned) - DB_QueryCOUNT ("can not get the number of threads in forums of a type", - "SELECT COUNT(*)" - " FROM for_threads" - " WHERE ForumType=%u", - (unsigned) ForumType); - default: - return 0; - } - } - -/*****************************************************************************/ -/******************* Get number of threads in a forum ************************/ -/*****************************************************************************/ - -static unsigned For_GetNumThrsInForum (const struct For_Forum *Forum) - { - char SubQuery[256]; - - /***** Get number of threads in a forum from database *****/ - if (Forum->Location > 0) - sprintf (SubQuery," AND Location=%ld",Forum->Location); - else - SubQuery[0] = '\0'; - return (unsigned) - DB_QueryCOUNT ("can not get number of threads in a forum", - "SELECT COUNT(*)" - " FROM for_threads" - " WHERE ForumType=%u" - "%s", - (unsigned) Forum->Type, - SubQuery); - } - -/*****************************************************************************/ -/************** Get total number of posts in forums of a type ****************/ -/*****************************************************************************/ - -unsigned For_GetNumTotalPstsInForumsOfType (For_ForumType_t ForumType, - long CtyCod, - long InsCod, - long CtrCod, - long DegCod, - long CrsCod, - unsigned *NumUsrsToBeNotifiedByEMail) - { - MYSQL_RES *mysql_res; - MYSQL_ROW row; - unsigned NumPosts; - - /***** Get total number of posts in forums of this type from database *****/ - switch (ForumType) - { - case For_FORUM_GLOBAL_USRS: - case For_FORUM_GLOBAL_TCHS: - case For_FORUM__SWAD__USRS: - case For_FORUM__SWAD__TCHS: - // Total number of posts in forums of this type - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "for_posts " - " WHERE for_threads.ForumType=%u" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType); - break; - case For_FORUM_INSTIT_USRS: case For_FORUM_INSTIT_TCHS: - if (InsCod > 0) // InsCod > 0 ==> Number of posts in institutions forums for an institution - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "for_posts" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=%ld" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType, - InsCod); - else if (CtyCod > 0) // InsCod <= 0 && CtyCod > 0 ==> Number of posts in institutions forums for a country - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "ins_instits," - "for_posts" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=ins_instits.InsCod" - " AND ins_instits.CtyCod=%ld" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType, - CtyCod); - else // InsCod <= 0 ==> Number of posts in institution forums for the whole platform - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "for_posts " - " WHERE for_threads.ForumType=%u" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType); - break; - case For_FORUM_CENTER_USRS: - case For_FORUM_CENTER_TCHS: - if (CtrCod > 0) // CtrCod > 0 ==> Number of posts in center forums for a center - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "for_posts" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=%ld" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType, - CtrCod); - else if (InsCod > 0) // CtrCod <= 0 && InsCod > 0 ==> Number of posts in center forums for an institution - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "ctr_centers," - "for_posts" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=%ld" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType, - InsCod); - else if (CtyCod > 0) // InsCod <= 0 && CtyCod > 0 ==> Number of posts in center forums for a country - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "ctr_centers," - "ins_instits," - "for_posts" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=ins_instits.InsCod" - " AND ins_instits.CtyCod=%ld" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType, - CtyCod); - else // InsCod <= 0 ==> Number of posts in center forums for the whole platform - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "for_posts" - " WHERE for_threads.ForumType=%u" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType); - break; - case For_FORUM_DEGREE_USRS: - case For_FORUM_DEGREE_TCHS: - if (DegCod > 0) // DegCod > 0 ==> Number of posts in degree forums for a degree - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "for_posts" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=%ld" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType, - DegCod); - else if (CtrCod > 0) // DegCod <= 0 && CtrCod > 0 ==> Number of posts in degree forums for a center - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "deg_degrees," - "for_posts" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=%ld" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType, - CtrCod); - else if (InsCod > 0) // CtrCod <= 0 && InsCod > 0 ==> Number of posts in degree forums for an institution - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "deg_degrees," - "ctr_centers," - "for_posts" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=%ld" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType, - InsCod); - else if (CtyCod > 0) // InsCod <= 0 && CtyCod > 0 ==> Number of posts in degree forums for a country - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "deg_degrees," - "ctr_centers," - "ins_instits," - "for_posts" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=ins_instits.InsCod" - " AND ins_instits.CtyCod=%ld" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType, - CtyCod); - else // InsCod <= 0 ==> Number of posts in degree forums for the whole platform - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "for_posts " - " WHERE for_threads.ForumType=%u" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType); - break; - case For_FORUM_COURSE_USRS: - case For_FORUM_COURSE_TCHS: - if (CrsCod > 0) // CrsCod > 0 ==> 0 <= number of posts in course forums for a course - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "for_posts " - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=%ld" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType, - CrsCod); - else if (DegCod > 0) // CrsCod <= 0 && DegCod > 0 ==> Number of posts in course forums for a degree - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "crs_courses," - "for_posts " - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=crs_courses.CrsCod" - " AND crs_courses.DegCod=%ld" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType, - DegCod); - else if (CtrCod > 0) // DegCod <= 0 && CtrCod > 0 ==> Number of posts in course forums for a center - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "crs_courses," - "deg_degrees," - "for_posts " - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=crs_courses.CrsCod" - " AND crs_courses.DegCod=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=%ld" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType, - CtrCod); - else if (InsCod > 0) // CtrCod <= 0 && InsCod > 0 ==> Number of posts in course forums for an institution - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "crs_courses," - "deg_degrees," - "ctr_centers," - "for_posts" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=crs_courses.CrsCod" - " AND crs_courses.DegCod=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=%ld" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType, - InsCod); - else if (CtyCod > 0) // InsCod <= 0 && CtyCod > 0 ==> Number of posts in course forums for a country - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "crs_courses," - "deg_degrees," - "ctr_centers," - "ins_instits," - "for_posts" - " WHERE for_threads.ForumType=%u" - " AND for_threads.Location=crs_courses.CrsCod" - " AND crs_courses.DegCod=deg_degrees.DegCod" - " AND deg_degrees.CtrCod=ctr_centers.CtrCod" - " AND ctr_centers.InsCod=ins_instits.InsCod" - " AND ins_instits.CtyCod=%ld" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType, - CtyCod); - else // CrsCod <= 0 && DegCod <= 0 && CtrCod <= 0 ==> Number of posts in course forums for the whole platform - DB_QuerySELECT (&mysql_res,"can not get the total number" - " of forums of a type", - "SELECT COUNT(*)," // row[0] - "SUM(for_posts.NumNotif)" // row[1] - " FROM for_threads," - "for_posts " - " WHERE for_threads.ForumType=%u" - " AND for_threads.ThrCod=for_posts.ThrCod", - (unsigned) ForumType); - break; - default: - return 0; - } - - /* Get row with number of posts */ - row = mysql_fetch_row (mysql_res); - - /* Get number of posts (row[0]) */ - if (sscanf (row[0],"%u",&NumPosts) != 1) - Err_ShowErrorAndExit ("Error when getting the total number of forums of a type."); - - /* Get number of users notified (row[1]) */ - if (row[1]) - { - if (sscanf (row[1],"%u",NumUsrsToBeNotifiedByEMail) != 1) - Err_ShowErrorAndExit ("Error when getting the total number of forums of a type."); - } - else - *NumUsrsToBeNotifiedByEMail = 0; - - /***** Free structure that stores the query result *****/ - DB_FreeMySQLResult (&mysql_res); - - return NumPosts; - } - /*****************************************************************************/ /************************ List the threads of a forum ************************/ /*****************************************************************************/ @@ -3531,29 +2426,14 @@ static void For_GetThreadData (struct For_Thread *Thr) Dat_StartEndTime_t Order; /***** Get data of a thread from database *****/ - if (DB_QuerySELECT (&mysql_res,"can not get data of a thread of a forum", - "SELECT m0.PstCod," // row[0] - "m1.PstCod," // row[1] - "m0.UsrCod," // row[2] - "m1.UsrCod," // row[3] - "UNIX_TIMESTAMP(m0.CreatTime)," // row[4] - "UNIX_TIMESTAMP(m1.CreatTime)," // row[5] - "m0.Subject" - " FROM for_threads," - "for_posts AS m0," - "for_posts AS m1" - " WHERE for_threads.ThrCod=%ld" - " AND for_threads.FirstPstCod=m0.PstCod" - " AND for_threads.LastPstCod=m1.PstCod", - Thr->ThrCod) != 1) - Err_ShowErrorAndExit ("Error when getting data of a thread of a forum."); + if (For_DB_GetThreadData (&mysql_res,Thr->ThrCod) != 1) + Err_WrongThreadExit (); row = mysql_fetch_row (mysql_res); - /***** Get the code of the first post in this thread (row[0]) *****/ + /***** Get the codes of the first (row[0]) + and the last post (row[1]) in this thread *****/ Thr->PstCod[Dat_START_TIME] = Str_ConvertStrCodToLongCod (row[0]); - - /***** Get the code of the last post in this thread (row[1]) *****/ - Thr->PstCod[Dat_END_TIME ] = Str_ConvertStrCodToLongCod (row[1]); + Thr->PstCod[Dat_END_TIME ] = Str_ConvertStrCodToLongCod (row[1]); /***** Get the code of the first message (row[0]) and the last message (row[1]) in this thread *****/ @@ -3596,13 +2476,13 @@ static void For_GetThreadData (struct For_Thread *Thr) Thr->NumUnreadPosts = For_GetNumOfUnreadPostsInThr (Thr->ThrCod,Thr->NumPosts); /***** Get number of posts that I have written in this thread *****/ - Thr->NumMyPosts = For_DB_GetNumMyPstInThr (Thr->ThrCod); + Thr->NumMyPosts = For_DB_GetNumMyPstsInThr (Thr->ThrCod); /***** Get number of users who have write posts in this thread *****/ Thr->NumWriters = For_DB_GetNumOfWritersInThr (Thr->ThrCod); /***** Get number of users who have read this thread *****/ - Thr->NumReaders = For_DB_GetNumOfReadersOfThr (Thr->ThrCod); + Thr->NumReaders = For_DB_GetNumReadersOfThr (Thr->ThrCod); } /*****************************************************************************/ @@ -4087,21 +2967,6 @@ void For_ReceiveForumPost (void) For_ShowPostsOfAThread (&Forums,Ale_SUCCESS,Txt_FORUM_Post_sent); } -/*****************************************************************************/ -/********* Update number of users notified in table of forum posts **********/ -/*****************************************************************************/ - -static void For_DB_UpdateNumUsrsNotifiedByEMailAboutPost (long PstCod, - unsigned NumUsrsToBeNotifiedByEMail) - { - DB_QueryUPDATE ("can not update the number of notifications of a post", - "UPDATE for_posts" - " SET NumNotif=NumNotif+%u" - " WHERE PstCod=%ld", - NumUsrsToBeNotifiedByEMail, - PstCod); - } - /*****************************************************************************/ /***************************** Delete a forum post ***************************/ /*****************************************************************************/ @@ -4143,7 +3008,7 @@ void For_RemovePost (void) Err_NoPermissionExit (); /* Check if the message is the last message in the thread */ - if (Forums.PstCod != For_GetLastPstCod (Forums.Thread.Current)) + if (Forums.PstCod != For_DB_GetThrLastPst (Forums.Thread.Current)) Err_NoPermissionExit (); /***** Remove the post *****/ @@ -4390,116 +3255,6 @@ static bool For_CheckIfICanMoveThreads (void) return (Gbl.Usrs.Me.Role.Logged == Rol_SYS_ADM); // If I have permission to move threads... } -/*****************************************************************************/ -/**************** Get if there is a thread ready to be moved *****************/ -/*****************************************************************************/ - -static long For_DB_GetThrInMyClipboard (void) - { - return DB_QuerySELECTCode ("can not check if there is" - " any thread ready to be moved", - "SELECT ThrCod" - " FROM for_clipboards" - " WHERE UsrCod=%ld", - Gbl.Usrs.Me.UsrDat.UsrCod); - } - -/*****************************************************************************/ -/***************** Get if a thread belongs to current forum ******************/ -/*****************************************************************************/ - -static bool For_DB_CheckIfThrBelongsToForum (long ThrCod,const struct For_Forum *Forum) - { - char SubQuery[256]; - - /***** Get if a thread belong to current forum from database *****/ - if (Forum->Location > 0) - sprintf (SubQuery," AND for_threads.Location=%ld",Forum->Location); - else - SubQuery[0] = '\0'; - - return (DB_QueryCOUNT ("can not get if a thread belong to current forum", - "SELECT COUNT(*)" - " FROM for_threads" - " WHERE ThrCod=%ld" - " AND ForumType=%u" - "%s", - ThrCod, - (unsigned) Forum->Type, - SubQuery) != 0); - } - -/*****************************************************************************/ -/************************ Move a thread to current forum *********************/ -/*****************************************************************************/ - -static void For_DB_MoveThrToCurrentForum (const struct For_Forums *Forums) - { - /***** Move a thread to current forum *****/ - switch (Forums->Forum.Type) - { - case For_FORUM_GLOBAL_USRS: - case For_FORUM_GLOBAL_TCHS: - case For_FORUM__SWAD__USRS: - case For_FORUM__SWAD__TCHS: - DB_QueryUPDATE ("can not move a thread to current forum", - "UPDATE for_threads" - " SET ForumType=%u," - "Location=-1" - " WHERE ThrCod=%ld", - (unsigned) Forums->Forum.Type, - Forums->Thread.Current); - break; - case For_FORUM_INSTIT_USRS: - case For_FORUM_INSTIT_TCHS: - DB_QueryUPDATE ("can not move a thread to current forum", - "UPDATE for_threads" - " SET ForumType=%u," - "Location=%ld" - " WHERE ThrCod=%ld", - (unsigned) Forums->Forum.Type, - Forums->Forum.Location, - Forums->Thread.Current); - break; - case For_FORUM_CENTER_USRS: - case For_FORUM_CENTER_TCHS: - DB_QueryUPDATE ("can not move a thread to current forum", - "UPDATE for_threads" - " SET ForumType=%u," - "Location=%ld" - " WHERE ThrCod=%ld", - (unsigned) Forums->Forum.Type, - Forums->Forum.Location, - Forums->Thread.Current); - break; - case For_FORUM_DEGREE_USRS: - case For_FORUM_DEGREE_TCHS: - DB_QueryUPDATE ("can not move a thread to current forum", - "UPDATE for_threads" - " SET ForumType=%u," - "Location=%ld" - " WHERE ThrCod=%ld", - (unsigned) Forums->Forum.Type, - Forums->Forum.Location, - Forums->Thread.Current); - break; - case For_FORUM_COURSE_USRS: - case For_FORUM_COURSE_TCHS: - DB_QueryUPDATE ("can not move a thread to current forum", - "UPDATE for_threads" - " SET ForumType=%u," - "Location=%ld" - " WHERE ThrCod=%ld", - (unsigned) Forums->Forum.Type, - Forums->Forum.Location, - Forums->Thread.Current); - break; - default: - Err_WrongForumExit (); - break; - } - } - /*****************************************************************************/ /********************* Insert thread in thread clipboard ********************/ /*****************************************************************************/ @@ -4507,131 +3262,8 @@ static void For_DB_MoveThrToCurrentForum (const struct For_Forums *Forums) static void For_InsertThrInClipboard (long ThrCod) { /***** Remove expired thread clipboards *****/ - For_DB_RemoveExpiredThrsClipboards (); + For_DB_RemoveExpiredClipboards (); /***** Add thread to my clipboard *****/ - DB_QueryREPLACE ("can not add thread to clipboard", - "REPLACE INTO for_clipboards" - " (ThrCod,UsrCod)" - " VALUES" - " (%ld,%ld)", - ThrCod, - Gbl.Usrs.Me.UsrDat.UsrCod); - } - -/*****************************************************************************/ -/************* Remove expired thread clipboards (from all users) *************/ -/*****************************************************************************/ - -static void For_DB_RemoveExpiredThrsClipboards (void) - { - DB_QueryDELETE ("can not remove old threads from clipboards", - "DELETE LOW_PRIORITY FROM for_clipboards" - " WHERE TimeInsert // For boolean type -// #include // For malloc -// #include // To access MySQL databases -// #include // For NULL -// #include // For asprintf -// #include -// #include // For time_t -// #include "swad_action.h" -// #include "swad_box.h" -// #include "swad_config.h" #include "swad_database.h" -// #include "swad_error.h" -// #include "swad_figure.h" -// #include "swad_form.h" +#include "swad_error.h" #include "swad_forum.h" #include "swad_forum_database.h" #include "swad_global.h" -// #include "swad_hierarchy.h" -// #include "swad_HTML.h" -// #include "swad_layout.h" -// #include "swad_logo.h" -// #include "swad_message.h" -// #include "swad_notification.h" -// #include "swad_pagination.h" -// #include "swad_parameter.h" -// #include "swad_profile.h" -// #include "swad_role.h" -// #include "swad_timeline.h" -// #include "swad_timeline_database.h" /*****************************************************************************/ /************** External global variables from others modules ****************/ @@ -75,6 +51,141 @@ extern struct Globals Gbl; /***************************** Private prototypes ****************************/ /*****************************************************************************/ +/*****************************************************************************/ +/******************* Get number of threads in a forum ************************/ +/*****************************************************************************/ + +unsigned For_DB_GetNumThrsInForum (const struct For_Forum *Forum) + { + char SubQuery[256]; + + /***** Get number of threads in a forum from database *****/ + if (Forum->Location > 0) + sprintf (SubQuery," AND Location=%ld",Forum->Location); + else + SubQuery[0] = '\0'; + + return (unsigned) + DB_QueryCOUNT ("can not get number of threads in a forum", + "SELECT COUNT(*)" + " FROM for_threads" + " WHERE ForumType=%u" + "%s", + (unsigned) Forum->Type, + SubQuery); + } + +/*****************************************************************************/ +/**** Get number of threads in forum with a modify time > a specified time ***/ +/*****************************************************************************/ + +unsigned For_DB_GetNumOfThreadsInForumNewerThan (const struct For_Forum *Forum, + const char *Time) + { + char SubQuery[256]; + + /***** Get number of threads with a last message modify time + > specified time from database *****/ + if (Forum->Location > 0) + sprintf (SubQuery," AND for_threads.Location=%ld",Forum->Location); + else + SubQuery[0] = '\0'; + + return (unsigned) + DB_QueryCOUNT ("can not check if there are new posts in a forum", + "SELECT COUNT(*)" + " FROM for_threads," + "for_posts" + " WHERE for_threads.ForumType=%u" + "%s" + " AND for_threads.LastPstCod=for_posts.PstCod" + " AND for_posts.ModifTime>'%s'", + (unsigned) Forum->Type, + SubQuery, + Time); + } + +/*****************************************************************************/ +/*********** Remove all the threads and posts in forums of a scope ***********/ +/*****************************************************************************/ + +void For_DB_RemoveForums (HieLvl_Level_t Scope,long ForumLocation) + { + static const struct + { + For_ForumType_t Usrs; + For_ForumType_t Tchs; + } ForumType[HieLvl_NUM_LEVELS] = + { + [HieLvl_UNK] = {For_FORUM_GLOBAL_USRS,For_FORUM_GLOBAL_TCHS}, // No forums for this scope + [HieLvl_SYS] = {For_FORUM_GLOBAL_USRS,For_FORUM_GLOBAL_TCHS}, // Not removable + [HieLvl_CTY] = {For_FORUM_GLOBAL_USRS,For_FORUM_GLOBAL_TCHS}, // No forums for this scope + [HieLvl_INS] = {For_FORUM_INSTIT_USRS,For_FORUM_INSTIT_TCHS}, + [HieLvl_CTR] = {For_FORUM_CENTER_USRS,For_FORUM_CENTER_TCHS}, + [HieLvl_DEG] = {For_FORUM_DEGREE_USRS,For_FORUM_DEGREE_TCHS}, + [HieLvl_CRS] = {For_FORUM_COURSE_USRS,For_FORUM_COURSE_TCHS}, + }; + + /***** Remove disabled posts *****/ + DB_QueryDELETE ("can not remove the disabled posts in forums", + "DELETE FROM for_disabled" + " USING for_threads," + "for_posts," + "for_disabled" + " WHERE" + " (for_threads.ForumType=%u" + " OR" + " for_threads.ForumType=%u)" + " AND for_threads.Location=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod" + " AND for_posts.PstCod=for_disabled.PstCod", + ForumType[Scope].Usrs, + ForumType[Scope].Tchs, + ForumLocation); + + /***** Remove posts *****/ + DB_QueryDELETE ("can not remove posts in forums", + "DELETE FROM for_posts" + " USING for_threads," + "for_posts" + " WHERE" + " (for_threads.ForumType=%u" + " OR" + " for_threads.ForumType=%u)" + " AND for_threads.Location=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + ForumType[Scope].Usrs, + ForumType[Scope].Tchs, + ForumLocation); + + /***** Remove threads read *****/ + DB_QueryDELETE ("can not remove read threads in forums", + "DELETE FROM for_read" + " USING for_threads," + "for_read" + " WHERE" + " (for_threads.ForumType=%u" + " OR" + " for_threads.ForumType=%u)" + " AND for_threads.Location=%ld" + " AND for_threads.ThrCod=for_read.ThrCod", + ForumType[Scope].Usrs, + ForumType[Scope].Tchs, + ForumLocation); + + /***** Remove threads *****/ + DB_QueryDELETE ("can not remove threads in forums", + "DELETE FROM for_threads" + " WHERE" + " (for_threads.ForumType=%u" + " OR" + " for_threads.ForumType=%u)" + " AND Location=%ld", + ForumType[Scope].Usrs, + ForumType[Scope].Tchs, + ForumLocation); + } + /*****************************************************************************/ /**************** Insert new post in the table of forum posts ****************/ /*****************************************************************************/ @@ -98,6 +209,21 @@ long For_DB_InsertForumPst (long ThrCod,long UsrCod, MedCod); } +/*****************************************************************************/ +/********* Update number of users notified in table of forum posts **********/ +/*****************************************************************************/ + +void For_DB_UpdateNumUsrsNotifiedByEMailAboutPost (long PstCod, + unsigned NumUsrsToBeNotifiedByEMail) + { + DB_QueryUPDATE ("can not update the number of notifications of a post", + "UPDATE for_posts" + " SET NumNotif=NumNotif+%u" + " WHERE PstCod=%ld", + NumUsrsToBeNotifiedByEMail, + PstCod); + } + /*****************************************************************************/ /******************** Get if a forum post exists in database *****************/ /*****************************************************************************/ @@ -111,6 +237,19 @@ bool For_DB_GetIfForumPstExists (long PstCod) PstCod) != 0); // Post exists if it appears in table of forum posts } +/*****************************************************************************/ +/*********************** Get number of posts from a user *********************/ +/*****************************************************************************/ + +unsigned For_DB_GetNumPostsUsr (long UsrCod) + { + return DB_QueryCOUNT ("can not get number of forum posts from a user", + "SELECT COUNT(*)" + " FROM for_posts" + " WHERE UsrCod=%ld", + UsrCod); + } + /*****************************************************************************/ /*********** Get the number of posts in the thread than holds a post *********/ /*****************************************************************************/ @@ -174,6 +313,109 @@ long For_DB_InsertForumThread (const struct For_Forums *Forums, FirstPstCod); } +/*****************************************************************************/ +/********* Modify the codes of the first and last posts of a thread **********/ +/*****************************************************************************/ + +void For_DB_UpdateThrFirstAndLastPst (long ThrCod,long FirstPstCod,long LastPstCod) + { + DB_QueryUPDATE ("can not update a thread of a forum", + "UPDATE for_threads" + " SET FirstPstCod=%ld," + "LastPstCod=%ld" + " WHERE ThrCod=%ld", + FirstPstCod, + LastPstCod, + ThrCod); + } + +/*****************************************************************************/ +/************** Modify the code of the last post of a thread *****************/ +/*****************************************************************************/ + +void For_DB_UpdateThrLastPst (long ThrCod,long LastPstCod) + { + /***** Update the code of the last post of a thread *****/ + DB_QueryUPDATE ("can not update a thread of a forum", + "UPDATE for_threads" + " SET LastPstCod=%ld" + " WHERE ThrCod=%ld", + LastPstCod, + ThrCod); + } + +/*****************************************************************************/ +/***************************** Get data of a thread **************************/ +/*****************************************************************************/ + +unsigned For_DB_GetThreadData (MYSQL_RES **mysql_res,long ThrCod) + { + return (unsigned) + DB_QuerySELECT (mysql_res,"can not get data of a thread of a forum", + "SELECT m0.PstCod," // row[0] + "m1.PstCod," // row[1] + "m0.UsrCod," // row[2] + "m1.UsrCod," // row[3] + "UNIX_TIMESTAMP(m0.CreatTime)," // row[4] + "UNIX_TIMESTAMP(m1.CreatTime)," // row[5] + "m0.Subject" + " FROM for_threads," + "for_posts AS m0," + "for_posts AS m1" + " WHERE for_threads.ThrCod=%ld" + " AND for_threads.FirstPstCod=m0.PstCod" + " AND for_threads.LastPstCod=m1.PstCod", + ThrCod); + } + +/*****************************************************************************/ +/***************** Get if a thread belongs to current forum ******************/ +/*****************************************************************************/ + +bool For_DB_CheckIfThrBelongsToForum (long ThrCod,const struct For_Forum *Forum) + { + char SubQuery[256]; + + /***** Get if a thread belong to current forum from database *****/ + if (Forum->Location > 0) + sprintf (SubQuery," AND for_threads.Location=%ld",Forum->Location); + else + SubQuery[0] = '\0'; + + return (DB_QueryCOUNT ("can not get if a thread belong to current forum", + "SELECT COUNT(*)" + " FROM for_threads" + " WHERE ThrCod=%ld" + " AND ForumType=%u" + "%s", + ThrCod, + (unsigned) Forum->Type, + SubQuery) != 0); + } + +/*****************************************************************************/ +/**************** Get the code of the last post of a thread ******************/ +/*****************************************************************************/ + +long For_DB_GetThrLastPst (long ThrCod) + { + long LastPstCod; + + /***** Get the code of the last post of a thread from database *****/ + LastPstCod = DB_QuerySELECTCode ("can not get the most recent post" + " of a thread of a forum", + "SELECT PstCod" + " FROM for_posts" + " WHERE ThrCod=%ld" + " ORDER BY CreatTime DESC" + " LIMIT 1", + ThrCod); + if (LastPstCod <= 0) + Err_ShowErrorAndExit ("Error when getting the most recent post of a thread of a forum."); + + return LastPstCod; + } + /*****************************************************************************/ /********************* Get the thread subject from a thread ******************/ /*****************************************************************************/ @@ -190,6 +432,68 @@ void For_DB_GetThrSubject (long ThrCod,char Subject[Cns_MAX_BYTES_SUBJECT + 1]) ThrCod); } +/*****************************************************************************/ +/********** Get number of users that have write posts in a thread ************/ +/*****************************************************************************/ + +unsigned For_DB_GetNumOfWritersInThr (long ThrCod) + { + /***** Get number of distinct writers in a thread from database *****/ + return DB_QueryCOUNT ("can not get the number of writers in a thread of a forum", + "SELECT COUNT(DISTINCT UsrCod)" + " FROM for_posts" + " WHERE ThrCod=%ld", + ThrCod); + } + +/*****************************************************************************/ +/********************** Get number of posts in a thread **********************/ +/*****************************************************************************/ + +unsigned For_DB_GetNumPstsInThr (long ThrCod) + { + /***** Get number of posts in a thread from database *****/ + return (unsigned) + DB_QueryCOUNT ("can not get the number of posts in a thread of a forum", + "SELECT COUNT(*)" + " FROM for_posts" + " WHERE ThrCod=%ld", + ThrCod); + } + +/*****************************************************************************/ +/************** Get whether there are posts of mine in a thread **************/ +/*****************************************************************************/ + +unsigned For_DB_GetNumMyPstsInThr (long ThrCod) + { + /***** Get if I have write posts in a thread from database *****/ + return (unsigned) + DB_QueryCOUNT ("can not check if you have written posts in a thead of a forum", + "SELECT COUNT(*)" + " FROM for_posts" + " WHERE ThrCod=%ld" + " AND UsrCod=%ld", + ThrCod, + Gbl.Usrs.Me.UsrDat.UsrCod); + } + +/*****************************************************************************/ +/**** Get number of posts in thread with a modify time > a specified time ****/ +/*****************************************************************************/ + +unsigned For_DB_GetNumPstsInThrNewerThan (long ThrCod,const char *Time) + { + return (unsigned) + DB_QueryCOUNT ("can not check if there are new posts in a thread of a forum", + "SELECT COUNT(*)" + " FROM for_posts" + " WHERE ThrCod=%ld" + " AND ModifTime>'%s'", + ThrCod, + Time); + } + /*****************************************************************************/ /*************** Delete a thread from the forum thread table *****************/ /*****************************************************************************/ @@ -202,6 +506,207 @@ void For_DB_RemoveThread (long ThrCod) ThrCod); } +/*****************************************************************************/ +/************* Update read date of a thread for the current user *************/ +/*****************************************************************************/ +// Update for_read table indicating that this thread page and previous ones +// have been read and have no new posts for the current user +// (even if any previous pages have been no read actually) +// Note that database is not updated with the current time, +// but with the creation time of the most recent post in this thread read by me. + +void For_DB_UpdateThrReadTime (long ThrCod, + time_t CreatTimeUTCOfTheMostRecentPostRead) + { + /***** Insert or replace pair ThrCod-UsrCod in for_read *****/ + DB_QueryREPLACE ("can not update the status of reading" + " of a thread of a forum", + "REPLACE INTO for_read" + " (ThrCod,UsrCod,ReadTime)" + " VALUES" + " (%ld,%ld,FROM_UNIXTIME(%ld))", + ThrCod, + Gbl.Usrs.Me.UsrDat.UsrCod, + (long) CreatTimeUTCOfTheMostRecentPostRead); + } + +/*****************************************************************************/ +/**************** Get number of users that have read a thread ****************/ +/*****************************************************************************/ + +unsigned For_DB_GetNumReadersOfThr (long ThrCod) + { + /***** Get number of distinct readers of a thread from database *****/ + return (unsigned) + DB_QueryCOUNT ("can not get the number of readers of a thread of a forum", + "SELECT COUNT(*)" + " FROM for_read" + " WHERE ThrCod=%ld", + ThrCod); + } + +/*****************************************************************************/ +/********************* Remove thread read status for a thread ****************/ +/*****************************************************************************/ + +void For_DB_RemoveThrFromReadThrs (long ThrCod) + { + DB_QueryDELETE ("can not remove the status of reading" + " of a thread of a forum", + "DELETE FROM for_read" + " WHERE ThrCod=%ld", + ThrCod); + } + +/*****************************************************************************/ +/********************** Remove thread read status for a user *****************/ +/*****************************************************************************/ + +void For_DB_RemoveUsrFromReadThrs (long UsrCod) + { + DB_QueryDELETE ("can not remove the status of reading by a user" + " of all the threads of a forum", + "DELETE FROM for_read" + " WHERE UsrCod=%ld", + UsrCod); + } + +/*****************************************************************************/ +/*********************** Insert thread in my clipboard ***********************/ +/*****************************************************************************/ + +void For_DB_InsertThrInMyClipboard (long ThrCod) + { + DB_QueryREPLACE ("can not add thread to clipboard", + "REPLACE INTO for_clipboards" + " (ThrCod,UsrCod)" + " VALUES" + " (%ld,%ld)", + ThrCod, + Gbl.Usrs.Me.UsrDat.UsrCod); + } + +/*****************************************************************************/ +/************************ Move a thread to current forum *********************/ +/*****************************************************************************/ + +void For_DB_MoveThrToCurrentForum (const struct For_Forums *Forums) + { + /***** Move a thread to current forum *****/ + switch (Forums->Forum.Type) + { + case For_FORUM_GLOBAL_USRS: + case For_FORUM_GLOBAL_TCHS: + case For_FORUM__SWAD__USRS: + case For_FORUM__SWAD__TCHS: + DB_QueryUPDATE ("can not move a thread to current forum", + "UPDATE for_threads" + " SET ForumType=%u," + "Location=-1" + " WHERE ThrCod=%ld", + (unsigned) Forums->Forum.Type, + Forums->Thread.Current); + break; + case For_FORUM_INSTIT_USRS: + case For_FORUM_INSTIT_TCHS: + DB_QueryUPDATE ("can not move a thread to current forum", + "UPDATE for_threads" + " SET ForumType=%u," + "Location=%ld" + " WHERE ThrCod=%ld", + (unsigned) Forums->Forum.Type, + Forums->Forum.Location, + Forums->Thread.Current); + break; + case For_FORUM_CENTER_USRS: + case For_FORUM_CENTER_TCHS: + DB_QueryUPDATE ("can not move a thread to current forum", + "UPDATE for_threads" + " SET ForumType=%u," + "Location=%ld" + " WHERE ThrCod=%ld", + (unsigned) Forums->Forum.Type, + Forums->Forum.Location, + Forums->Thread.Current); + break; + case For_FORUM_DEGREE_USRS: + case For_FORUM_DEGREE_TCHS: + DB_QueryUPDATE ("can not move a thread to current forum", + "UPDATE for_threads" + " SET ForumType=%u," + "Location=%ld" + " WHERE ThrCod=%ld", + (unsigned) Forums->Forum.Type, + Forums->Forum.Location, + Forums->Thread.Current); + break; + case For_FORUM_COURSE_USRS: + case For_FORUM_COURSE_TCHS: + DB_QueryUPDATE ("can not move a thread to current forum", + "UPDATE for_threads" + " SET ForumType=%u," + "Location=%ld" + " WHERE ThrCod=%ld", + (unsigned) Forums->Forum.Type, + Forums->Forum.Location, + Forums->Thread.Current); + break; + default: + Err_WrongForumExit (); + break; + } + } + +/*****************************************************************************/ +/**************** Get if there is a thread ready to be moved *****************/ +/*****************************************************************************/ + +long For_DB_GetThrInMyClipboard (void) + { + return DB_QuerySELECTCode ("can not check if there is" + " any thread ready to be moved", + "SELECT ThrCod" + " FROM for_clipboards" + " WHERE UsrCod=%ld", + Gbl.Usrs.Me.UsrDat.UsrCod); + } + +/*****************************************************************************/ +/**************** Remove thread code from thread clipboard *******************/ +/*****************************************************************************/ + +void For_DB_RemoveThrFromClipboard (long ThrCod) + { + DB_QueryDELETE ("can not remove a thread from clipboard", + "DELETE FROM for_clipboards" + " WHERE ThrCod=%ld", + ThrCod); + } + +/*****************************************************************************/ +/********************* Remove thread clipboard of a user *********************/ +/*****************************************************************************/ + +void For_DB_RemoveUsrFromClipboard (long UsrCod) + { + DB_QueryDELETE ("can not remove a thread from the clipboard of a user", + "DELETE FROM for_clipboards" + " WHERE UsrCod=%ld", + UsrCod); + } + +/*****************************************************************************/ +/************* Remove expired thread clipboards (from all users) *************/ +/*****************************************************************************/ + +void For_DB_RemoveExpiredClipboards (void) + { + DB_QueryDELETE ("can not remove old threads from clipboards", + "DELETE LOW_PRIORITY FROM for_clipboards" + " WHERE TimeInsert 0) + // InsCod > 0 ==> 0 <= number of institutions forums for an institution <= 1 + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT Location)" + " FROM for_threads" + " WHERE ForumType=%u" + " AND Location=%ld", + (unsigned) ForumType, + InsCod); + + if (CtyCod > 0) + // InsCod <= 0 && CtyCod > 0 ==> Number of institution forums for a country + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT for_threads.Location)" + " FROM for_threads," + "ins_instits" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=ins_instits.InsCod" + " AND ins_instits.CtyCod=%ld", + (unsigned) ForumType, + CtyCod); + + // CtyCod <= 0 ==> Number of institutions forums for the whole platform + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT Location)" + " FROM for_threads" + " WHERE ForumType=%u", + (unsigned) ForumType); + case For_FORUM_CENTER_USRS: + case For_FORUM_CENTER_TCHS: + if (CtrCod > 0) + // CtrCod > 0 ==> 0 <= number of center forums for a center <= 1 + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT Location)" + " FROM for_threads" + " WHERE ForumType=%u" + " AND Location=%ld", + (unsigned) ForumType, + CtrCod); + + if (InsCod > 0) + // CtrCod <= 0 && InsCod > 0 ==> Number of center forums for an institution + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT for_threads.Location)" + " FROM for_threads," + "ctr_centers" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=%ld", + (unsigned) ForumType, + InsCod); + + if (CtyCod > 0) + // InsCod <= 0 && CtyCod > 0 ==> Number of center forums for a country + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT for_threads.Location)" + " FROM for_threads," + "ctr_centers," + "ins_instits" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=ins_instits.InsCod" + " AND ins_instits.CtyCod=%ld", + (unsigned) ForumType, + CtyCod); + + // InsCod <= 0 ==> Number of center forums for the whole platform + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT Location)" + " FROM for_threads" + " WHERE ForumType=%u", + (unsigned) ForumType); + case For_FORUM_DEGREE_USRS: + case For_FORUM_DEGREE_TCHS: + if (DegCod > 0) + // DegCod > 0 ==> 0 <= number of degree forums for a degree <= 1 + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT Location)" + " FROM for_threads" + " WHERE ForumType=%u" + " AND Location=%ld", + (unsigned) ForumType, + DegCod); + + if (CtrCod > 0) + // DegCod <= 0 && CtrCod > 0 ==> Number of degree forums for a center + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT for_threads.Location)" + " FROM for_threads," + "deg_degrees" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=%ld", + (unsigned) ForumType, + CtrCod); + + if (InsCod > 0) + // CtrCod <= 0 && InsCod > 0 ==> Number of degree forums for an institution + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT for_threads.Location)" + " FROM for_threads," + "deg_degrees," + "ctr_centers" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=%ld", + (unsigned) ForumType, + InsCod); + + if (CtyCod > 0) + // InsCod <= 0 && CtyCod > 0 ==> Number of degree forums for a country + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT for_threads.Location)" + " FROM for_threads," + "deg_degrees," + "ctr_centers," + "ins_instits" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=ins_instits.InsCod" + " AND ins_instits.CtyCod=%ld", + (unsigned) ForumType, + CtyCod); + + // InsCod <= 0 ==> Number of degree forums for the whole platform + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT Location)" + " FROM for_threads" + " WHERE ForumType=%u", + (unsigned) ForumType); + case For_FORUM_COURSE_USRS: + case For_FORUM_COURSE_TCHS: + if (CrsCod > 0) + // CrsCod > 0 ==> 0 <= number of course forums for a course <= 1 + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT Location)" + " FROM for_threads" + " WHERE ForumType=%u" + " AND Location=%ld", + (unsigned) ForumType, + CrsCod); + + if (DegCod > 0) + // CrsCod <= 0 && DegCod > 0 ==> Number of course forums for a degree + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT for_threads.Location)" + " FROM for_threads," + "crs_courses" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=crs_courses.CrsCod" + " AND crs_courses.DegCod=%ld", + (unsigned) ForumType, + DegCod); + + if (CtrCod > 0) + // DegCod <= 0 && CtrCod > 0 ==> Number of course forums for a center + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT for_threads.Location)" + " FROM for_threads," + "crs_courses," + "deg_degrees" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=crs_courses.CrsCod" + " AND crs_courses.DegCod=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=%ld", + (unsigned) ForumType, + CtrCod); + + if (InsCod > 0) + // CtrCod <= 0 && InsCod > 0 ==> Number of course forums for an institution + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT for_threads.Location)" + " FROM for_threads," + "crs_courses," + "deg_degrees," + "ctr_centers" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=crs_courses.CrsCod" + " AND crs_courses.DegCod=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=%ld", + (unsigned) ForumType, + InsCod); + + if (CtyCod > 0) + // InsCod <= 0 && CtyCod > 0 ==> Number of course forums for a country + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT for_threads.Location)" + " FROM for_threads," + "crs_courses," + "deg_degrees," + "ctr_centers," + "ins_instits" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=crs_courses.CrsCod" + " AND crs_courses.DegCod=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=ins_instits.InsCod" + " AND ins_instits.CtyCod=%ld", + (unsigned) ForumType, + CtyCod); + + // InsCod <= 0 ==> Number of course forums for the whole platform + return (unsigned) + DB_QueryCOUNT ("can not get number of forums of a type", + "SELECT COUNT(DISTINCT Location)" + " FROM for_threads" + " WHERE ForumType=%u", + (unsigned) ForumType); + default: + return 0; + } + } + +/*****************************************************************************/ +/*********** Get total number of threads in forums of this type **************/ +/*****************************************************************************/ + +unsigned For_DB_GetNumTotalThrsInForumsOfType (For_ForumType_t ForumType, + long CtyCod, + long InsCod, + long CtrCod, + long DegCod, + long CrsCod) + { + /***** Get total number of threads in forums of this type from database *****/ + switch (ForumType) + { + case For_FORUM_GLOBAL_USRS: + case For_FORUM_GLOBAL_TCHS: + case For_FORUM__SWAD__USRS: + case For_FORUM__SWAD__TCHS: + // Total number of threads in forums of this type + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads" + " WHERE ForumType=%u", + (unsigned) ForumType); + case For_FORUM_INSTIT_USRS: + case For_FORUM_INSTIT_TCHS: + if (InsCod > 0) + // InsCod > 0 ==> Number of threads in institution forums for an institution + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads" + " WHERE ForumType=%u" + " AND Location=%ld", + (unsigned) ForumType, + InsCod); + + if (CtyCod > 0) + // InsCod <= 0 && CtyCod > 0 ==> Number of threads in institution forums for a country + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads," + "ins_instits" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=ins_instits.InsCod" + " AND ins_instits.CtyCod=%ld", + (unsigned) ForumType, + CtyCod); + + // InsCod <= 0 ==> Number of threads in institution forums for the whole platform + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads" + " WHERE ForumType=%u", + (unsigned) ForumType); + case For_FORUM_CENTER_USRS: + case For_FORUM_CENTER_TCHS: + if (CtrCod > 0) + // CtrCod > 0 ==> 0 <= Number of threads in center forums for a center <= 1 + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads" + " WHERE ForumType=%u" + " AND Location=%ld", + (unsigned) ForumType, + CtrCod); + + if (InsCod > 0) + // CtrCod <= 0 && InsCod > 0 ==> Number of threads in center forums for an institution + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads," + "ctr_centers" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=%ld", + (unsigned) ForumType, + InsCod); + + if (CtyCod > 0) + // InsCod <= 0 && CtyCod > 0 ==> Number of threads in center forums for a country + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads," + "ctr_centers," + "ins_instits" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=ins_instits.InsCod" + " AND ins_instits.CtyCod=%ld", + (unsigned) ForumType, + CtyCod); + + // InsCod <= 0 ==> Number of threads in center forums for the whole platform + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads" + " WHERE ForumType=%u", + (unsigned) ForumType); + case For_FORUM_DEGREE_USRS: + case For_FORUM_DEGREE_TCHS: + if (DegCod > 0) + // DegCod > 0 ==> Number of threads in degree forums for a degree + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads" + " WHERE ForumType=%u" + " AND Location=%ld", + (unsigned) ForumType, + DegCod); + + if (CtrCod > 0) + // DegCod <= 0 && CtrCod > 0 ==> Number of threads in degree forums for a center + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads," + "deg_degrees" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=%ld", + (unsigned) ForumType, + CtrCod); + + if (InsCod > 0) + // CtrCod <= 0 && InsCod > 0 ==> Number of threads in degree forums for an institution + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads," + "deg_degrees," + "ctr_centers" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=%ld", + (unsigned) ForumType, + InsCod); + + if (CtyCod > 0) // InsCod <= 0 && CtyCod > 0 ==> Number of threads in degree forums for a country + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads," + "deg_degrees," + "ctr_centers," + "ins_instits" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=ins_instits.InsCod" + " AND ins_instits.CtyCod=%ld", + (unsigned) ForumType, + CtyCod); + + // InsCod <= 0 ==> Number of threads in degree forums for the whole platform + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads" + " WHERE ForumType=%u", + (unsigned) ForumType); + case For_FORUM_COURSE_USRS: + case For_FORUM_COURSE_TCHS: + if (CrsCod > 0) + // CrsCod > 0 ==> 0 <= Number of threads in course forums for a course + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads" + " WHERE ForumType=%u" + " AND Location=%ld", + (unsigned) ForumType, + CrsCod); + + if (DegCod > 0) + // CrsCod <= 0 && DegCod > 0 ==> Number of threads in course forums for a degree + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads," + "crs_courses" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=crs_courses.CrsCod" + " AND crs_courses.DegCod=%ld", + (unsigned) ForumType, + DegCod); + + if (CtrCod > 0) + // DegCod <= 0 && CtrCod > 0 ==> Number of threads in course forums for a center + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads," + "crs_courses," + "deg_degrees" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=crs_courses.CrsCod" + " AND crs_courses.DegCod=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=%ld", + (unsigned) ForumType, + CtrCod); + + if (InsCod > 0) + // CtrCod <= 0 && InsCod > 0 ==> Number of threads in course forums for an institution + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads," + "crs_courses," + "deg_degrees," + "ctr_centers" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=crs_courses.CrsCod" + " AND crs_courses.DegCod=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=%ld", + (unsigned) ForumType, + InsCod); + + if (CtyCod > 0) + // InsCod <= 0 && CtyCod > 0 ==> Number of threads in course forums for a country + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads," + "crs_courses," + "deg_degrees," + "ctr_centers," + "ins_instits" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=crs_courses.CrsCod" + " AND crs_courses.DegCod=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=ins_instits.InsCod" + " AND ins_instits.CtyCod=%ld", + (unsigned) ForumType, + CtyCod); + + // InsCod <= 0 ==> Number of threads in course forums for the whole platform + return (unsigned) + DB_QueryCOUNT ("can not get the number of threads in forums of a type", + "SELECT COUNT(*)" + " FROM for_threads" + " WHERE ForumType=%u", + (unsigned) ForumType); + default: + return 0; + } + } + +/*****************************************************************************/ +/************** Get total number of posts in forums of a type ****************/ +/*****************************************************************************/ + +unsigned For_DB_GetNumTotalPstsInForumsOfType (For_ForumType_t ForumType, + long CtyCod, + long InsCod, + long CtrCod, + long DegCod, + long CrsCod, + unsigned *NumUsrsToBeNotifiedByEMail) + { + MYSQL_RES *mysql_res; + MYSQL_ROW row; + unsigned NumPosts; + + /***** Get total number of posts in forums of this type from database *****/ + switch (ForumType) + { + case For_FORUM_GLOBAL_USRS: + case For_FORUM_GLOBAL_TCHS: + case For_FORUM__SWAD__USRS: + case For_FORUM__SWAD__TCHS: + // Total number of posts in forums of this type + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "for_posts " + " WHERE for_threads.ForumType=%u" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType); + break; + case For_FORUM_INSTIT_USRS: case For_FORUM_INSTIT_TCHS: + if (InsCod > 0) // InsCod > 0 ==> Number of posts in institutions forums for an institution + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "for_posts" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType, + InsCod); + else if (CtyCod > 0) // InsCod <= 0 && CtyCod > 0 ==> Number of posts in institutions forums for a country + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "ins_instits," + "for_posts" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=ins_instits.InsCod" + " AND ins_instits.CtyCod=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType, + CtyCod); + else // InsCod <= 0 ==> Number of posts in institution forums for the whole platform + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "for_posts " + " WHERE for_threads.ForumType=%u" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType); + break; + case For_FORUM_CENTER_USRS: + case For_FORUM_CENTER_TCHS: + if (CtrCod > 0) // CtrCod > 0 ==> Number of posts in center forums for a center + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "for_posts" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType, + CtrCod); + else if (InsCod > 0) // CtrCod <= 0 && InsCod > 0 ==> Number of posts in center forums for an institution + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "ctr_centers," + "for_posts" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType, + InsCod); + else if (CtyCod > 0) // InsCod <= 0 && CtyCod > 0 ==> Number of posts in center forums for a country + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "ctr_centers," + "ins_instits," + "for_posts" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=ins_instits.InsCod" + " AND ins_instits.CtyCod=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType, + CtyCod); + else // InsCod <= 0 ==> Number of posts in center forums for the whole platform + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "for_posts" + " WHERE for_threads.ForumType=%u" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType); + break; + case For_FORUM_DEGREE_USRS: + case For_FORUM_DEGREE_TCHS: + if (DegCod > 0) // DegCod > 0 ==> Number of posts in degree forums for a degree + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "for_posts" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType, + DegCod); + else if (CtrCod > 0) // DegCod <= 0 && CtrCod > 0 ==> Number of posts in degree forums for a center + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "deg_degrees," + "for_posts" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType, + CtrCod); + else if (InsCod > 0) // CtrCod <= 0 && InsCod > 0 ==> Number of posts in degree forums for an institution + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "deg_degrees," + "ctr_centers," + "for_posts" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType, + InsCod); + else if (CtyCod > 0) // InsCod <= 0 && CtyCod > 0 ==> Number of posts in degree forums for a country + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "deg_degrees," + "ctr_centers," + "ins_instits," + "for_posts" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=ins_instits.InsCod" + " AND ins_instits.CtyCod=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType, + CtyCod); + else // InsCod <= 0 ==> Number of posts in degree forums for the whole platform + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "for_posts " + " WHERE for_threads.ForumType=%u" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType); + break; + case For_FORUM_COURSE_USRS: + case For_FORUM_COURSE_TCHS: + if (CrsCod > 0) // CrsCod > 0 ==> 0 <= number of posts in course forums for a course + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "for_posts " + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType, + CrsCod); + else if (DegCod > 0) // CrsCod <= 0 && DegCod > 0 ==> Number of posts in course forums for a degree + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "crs_courses," + "for_posts " + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=crs_courses.CrsCod" + " AND crs_courses.DegCod=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType, + DegCod); + else if (CtrCod > 0) // DegCod <= 0 && CtrCod > 0 ==> Number of posts in course forums for a center + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "crs_courses," + "deg_degrees," + "for_posts " + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=crs_courses.CrsCod" + " AND crs_courses.DegCod=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType, + CtrCod); + else if (InsCod > 0) // CtrCod <= 0 && InsCod > 0 ==> Number of posts in course forums for an institution + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "crs_courses," + "deg_degrees," + "ctr_centers," + "for_posts" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=crs_courses.CrsCod" + " AND crs_courses.DegCod=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType, + InsCod); + else if (CtyCod > 0) // InsCod <= 0 && CtyCod > 0 ==> Number of posts in course forums for a country + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "crs_courses," + "deg_degrees," + "ctr_centers," + "ins_instits," + "for_posts" + " WHERE for_threads.ForumType=%u" + " AND for_threads.Location=crs_courses.CrsCod" + " AND crs_courses.DegCod=deg_degrees.DegCod" + " AND deg_degrees.CtrCod=ctr_centers.CtrCod" + " AND ctr_centers.InsCod=ins_instits.InsCod" + " AND ins_instits.CtyCod=%ld" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType, + CtyCod); + else // CrsCod <= 0 && DegCod <= 0 && CtrCod <= 0 ==> Number of posts in course forums for the whole platform + DB_QuerySELECT (&mysql_res,"can not get the total number" + " of forums of a type", + "SELECT COUNT(*)," // row[0] + "SUM(for_posts.NumNotif)" // row[1] + " FROM for_threads," + "for_posts " + " WHERE for_threads.ForumType=%u" + " AND for_threads.ThrCod=for_posts.ThrCod", + (unsigned) ForumType); + break; + default: + return 0; + } + + /* Get row with number of posts */ + row = mysql_fetch_row (mysql_res); + + /* Get number of posts (row[0]) */ + if (sscanf (row[0],"%u",&NumPosts) != 1) + Err_ShowErrorAndExit ("Error when getting the total number of forums of a type."); + + /* Get number of users notified (row[1]) */ + if (row[1]) + { + if (sscanf (row[1],"%u",NumUsrsToBeNotifiedByEMail) != 1) + Err_ShowErrorAndExit ("Error when getting the total number of forums of a type."); + } + else + *NumUsrsToBeNotifiedByEMail = 0; + + /***** Free structure that stores the query result *****/ + DB_FreeMySQLResult (&mysql_res); + + return NumPosts; + } diff --git a/swad_forum_database.h b/swad_forum_database.h index 6ae69b7b..2e3a7d40 100644 --- a/swad_forum_database.h +++ b/swad_forum_database.h @@ -27,13 +27,7 @@ /********************************* Headers ***********************************/ /*****************************************************************************/ -// #include "swad_center.h" -// #include "swad_degree.h" -// #include "swad_institution.h" -// #include "swad_notification.h" -// #include "swad_pagination.h" -// #include "swad_scope.h" -// #include "swad_string.h" +#include "swad_forum.h" /*****************************************************************************/ /************************ Public constants and types *************************/ @@ -43,11 +37,20 @@ /***************************** Public prototypes *****************************/ /*****************************************************************************/ +//------------------------------- Forums -------------------------------------- +unsigned For_DB_GetNumThrsInForum (const struct For_Forum *Forum); +unsigned For_DB_GetNumOfThreadsInForumNewerThan (const struct For_Forum *Forum, + const char *Time); +void For_DB_RemoveForums (HieLvl_Level_t Scope,long ForumLocation); + //------------------------------- Posts --------------------------------------- long For_DB_InsertForumPst (long ThrCod,long UsrCod, const char *Subject,const char *Content, long MedCod); +void For_DB_UpdateNumUsrsNotifiedByEMailAboutPost (long PstCod, + unsigned NumUsrsToBeNotifiedByEMail); bool For_DB_GetIfForumPstExists (long PstCod); +unsigned For_DB_GetNumPostsUsr (long UsrCod); unsigned For_DB_GetThreadAndNumPostsGivenPstCod (MYSQL_RES **mysql_res,long PstCod); void For_DB_RemovePst (long PstCod); void For_DB_RemoveThreadPsts (long ThrCod); @@ -55,13 +58,58 @@ void For_DB_RemoveThreadPsts (long ThrCod); //------------------------------ Threads -------------------------------------- long For_DB_InsertForumThread (const struct For_Forums *Forums, long FirstPstCod); +void For_DB_UpdateThrFirstAndLastPst (long ThrCod,long FirstPstCod,long LastPstCod); +void For_DB_UpdateThrLastPst (long ThrCod,long LastPstCod); +unsigned For_DB_GetThreadData (MYSQL_RES **mysql_res,long ThrCod); +bool For_DB_CheckIfThrBelongsToForum (long ThrCod,const struct For_Forum *Forum); +long For_DB_GetThrLastPst (long ThrCod); void For_DB_GetThrSubject (long ThrCod,char Subject[Cns_MAX_BYTES_SUBJECT + 1]); +unsigned For_DB_GetNumOfWritersInThr (long ThrCod); +unsigned For_DB_GetNumPstsInThr (long ThrCod); +unsigned For_DB_GetNumMyPstsInThr (long ThrCod); +unsigned For_DB_GetNumPstsInThrNewerThan (long ThrCod,const char *Time); void For_DB_RemoveThread (long ThrCod); +//----------------------------- Thread read ----------------------------------- +void For_DB_UpdateThrReadTime (long ThrCod, + time_t CreatTimeUTCOfTheMostRecentPostRead); +unsigned For_DB_GetNumReadersOfThr (long ThrCod); +void For_DB_RemoveThrFromReadThrs (long ThrCod); +void For_DB_RemoveUsrFromReadThrs (long UsrCod); + +//-------------------------- Thread clipboard --------------------------------- +void For_DB_InsertThrInMyClipboard (long ThrCod); +void For_DB_MoveThrToCurrentForum (const struct For_Forums *Forums); +long For_DB_GetThrInMyClipboard (void); +void For_DB_RemoveThrFromClipboard (long ThrCod); +void For_DB_RemoveUsrFromClipboard (long UsrCod); +void For_DB_RemoveExpiredClipboards (void); + //--------------------------- Disabled posts ---------------------------------- void For_DB_InsertPstIntoDisabled (long PstCod); bool For_DB_GetIfPstIsEnabled (long PstCod); void For_DB_RemovePstFromDisabled (long PstCod); void For_DB_RemoveDisabledPstsInThread (long ThrCod); +//----------------------------- Statistics ------------------------------------ +unsigned For_DB_GetNumTotalForumsOfType (For_ForumType_t ForumType, + long CtyCod, + long InsCod, + long CtrCod, + long DegCod, + long CrsCod); +unsigned For_DB_GetNumTotalThrsInForumsOfType (For_ForumType_t ForumType, + long CtyCod, + long InsCod, + long CtrCod, + long DegCod, + long CrsCod); +unsigned For_DB_GetNumTotalPstsInForumsOfType (For_ForumType_t ForumType, + long CtyCod, + long InsCod, + long CtrCod, + long DegCod, + long CrsCod, + unsigned *NumUsrsToBeNotifiedByEMail); + #endif diff --git a/swad_indicator.c b/swad_indicator.c index 9e52f68c..0d857c92 100644 --- a/swad_indicator.c +++ b/swad_indicator.c @@ -35,7 +35,7 @@ #include "swad_department.h" #include "swad_error.h" #include "swad_form.h" -#include "swad_forum.h" +#include "swad_forum_database.h" #include "swad_global.h" #include "swad_hierarchy_level.h" #include "swad_HTML.h" @@ -1452,7 +1452,7 @@ void Ind_ComputeAndStoreIndicatorsCrs (long CrsCod,int NumIndicatorsFromDB, /***** Indicator #3: information about online tutoring *****/ IndicatorsCrs->NumThreads = For_DB_GetNumTotalThrsInForumsOfType (For_FORUM_COURSE_USRS,-1L,-1L,-1L,-1L,CrsCod); - IndicatorsCrs->NumPosts = For_GetNumTotalPstsInForumsOfType (For_FORUM_COURSE_USRS,-1L,-1L,-1L,-1L,CrsCod,&(IndicatorsCrs->NumUsrsToBeNotifiedByEMail)); + IndicatorsCrs->NumPosts = For_DB_GetNumTotalPstsInForumsOfType (For_FORUM_COURSE_USRS,-1L,-1L,-1L,-1L,CrsCod,&(IndicatorsCrs->NumUsrsToBeNotifiedByEMail)); IndicatorsCrs->NumMsgsSentByTchs = Msg_DB_GetNumMsgsSentByTchsCrs (CrsCod); IndicatorsCrs->ThereIsOnlineTutoring = (IndicatorsCrs->NumThreads != 0) || (IndicatorsCrs->NumPosts != 0) || diff --git a/swad_institution.c b/swad_institution.c index 18f0d0eb..4f477e72 100644 --- a/swad_institution.c +++ b/swad_institution.c @@ -39,7 +39,7 @@ #include "swad_figure.h" #include "swad_figure_cache.h" #include "swad_form.h" -#include "swad_forum.h" +#include "swad_forum_database.h" #include "swad_global.h" #include "swad_hierarchy.h" #include "swad_hierarchy_level.h" @@ -1243,7 +1243,7 @@ void Ins_RemoveInstitution (void) else // Institution has no users ==> remove it { /***** Remove all the threads and posts in forums of the institution *****/ - For_RemoveForums (HieLvl_INS,Ins_EditingIns->InsCod); + For_DB_RemoveForums (HieLvl_INS,Ins_EditingIns->InsCod); /***** Remove surveys of the institution *****/ Svy_RemoveSurveys (HieLvl_INS,Ins_EditingIns->InsCod); diff --git a/swad_profile.c b/swad_profile.c index 2e3a1e0b..84fe3379 100644 --- a/swad_profile.c +++ b/swad_profile.c @@ -39,7 +39,7 @@ #include "swad_figure.h" #include "swad_follow_database.h" #include "swad_form.h" -#include "swad_forum.h" +#include "swad_forum_database.h" #include "swad_global.h" #include "swad_hierarchy_level.h" #include "swad_HTML.h"