mirror of
https://github.com/acanas/swad-core.git
synced 2024-06-18 06:25:42 +02:00
Version 16.15.1
This commit is contained in:
parent
a175012444
commit
80881e24a2
|
@ -1326,7 +1326,7 @@ CREATE TABLE IF NOT EXISTS usr_nicknames (
|
|||
CREATE TABLE IF NOT EXISTS usr_report (
|
||||
RepCod INT NOT NULL AUTO_INCREMENT,
|
||||
UsrCod INT NOT NULL,
|
||||
ReportTime DATETIME NOT NULL,
|
||||
ReportTimeUTC DATETIME NOT NULL,
|
||||
UniqueDirL CHAR(2) NOT NULL,
|
||||
UniqueDirR CHAR(41) NOT NULL,
|
||||
Filename VARCHAR(255) NOT NULL,
|
||||
|
|
|
@ -146,13 +146,14 @@
|
|||
/****************************** Public constants *****************************/
|
||||
/*****************************************************************************/
|
||||
|
||||
#define Log_PLATFORM_VERSION "SWAD 16.15 (2016-10-06)"
|
||||
#define Log_PLATFORM_VERSION "SWAD 16.15.1 (2016-10-06)"
|
||||
#define CSS_FILE "swad15.229.css"
|
||||
#define JS_FILE "swad15.238.1.js"
|
||||
|
||||
// Number of lines (includes comments but not blank lines) has been got with the following command:
|
||||
// nl swad*.c swad*.h css/swad*.css py/swad*.py js/swad*.js soap/swad*.h sql/swad*.sql | tail -1
|
||||
/*
|
||||
Version 16.15.1: Oct 06, 2016 User's usage reports are stored into database. (205950 lines)
|
||||
Version 16.15: Oct 06, 2016 New database table to store user's usage reports. (205896 lines)
|
||||
Version 16.14: Oct 06, 2016 By default, teachers see (do not edit) documents. Now they must click on small edit icon to edit. (205875 lines)
|
||||
Version 16.13.2: Oct 05, 2016 User's usage report is open to any logged user. (205907 lines)
|
||||
|
|
|
@ -2801,7 +2801,7 @@ mysql> DESCRIBE usr_report;
|
|||
DB_CreateTable ("CREATE TABLE IF NOT EXISTS usr_report ("
|
||||
"RepCod INT NOT NULL AUTO_INCREMENT,"
|
||||
"UsrCod INT NOT NULL,"
|
||||
"ReportTime DATETIME NOT NULL,"
|
||||
"ReportTimeUTC DATETIME NOT NULL,"
|
||||
"UniqueDirL CHAR(2) NOT NULL," // 2 leftmost chars from a unique 43 chars base64url codified from a unique SHA-256 string
|
||||
"UniqueDirR CHAR(41) NOT NULL," // 41 rightmost chars from a unique 43 chars base64url codified from a unique SHA-256 string
|
||||
"Filename VARCHAR(255) NOT NULL," // Report filename
|
||||
|
|
178
swad_report.c
178
swad_report.c
|
@ -93,40 +93,44 @@ static void Req_TitleReport (struct CurrentTimeUTC *CurrentTimeUTC);
|
|||
|
||||
static void Rep_GetCurrentDateTimeUTC (struct CurrentTimeUTC *CurrentTimeUTC);
|
||||
|
||||
static void Rep_WriteHeader (struct CurrentTimeUTC *CurrentTimeUTC,
|
||||
static void Rep_CreateNewReportFile (const struct CurrentTimeUTC *CurrentTimeUTC,
|
||||
char *FilenameReport,char *Permalink);
|
||||
static void Rep_CreateNewReportEntryIntoDB (const char *FilenameReport,
|
||||
const char *Permalink);
|
||||
static void Rep_WriteHeader (const struct CurrentTimeUTC *CurrentTimeUTC,
|
||||
const char *Permalink);
|
||||
static void Rep_WriteSectionPlatform (void);
|
||||
static void Rep_WriteSectionUsrInfo (void);
|
||||
static void Rep_WriteSectionUsrFigures (struct UsrFigures *UsrFigures,
|
||||
struct tm *tm_FirstClickTime,
|
||||
struct CurrentTimeUTC *CurrentTimeUTC);
|
||||
static void Rep_WriteSectionGlobalHits (struct UsrFigures *UsrFigures,
|
||||
struct tm *tm_FirstClickTime);
|
||||
static void Rep_WriteSectionCurrentCourses (struct UsrFigures *UsrFigures,
|
||||
struct tm *tm_FirstClickTime,
|
||||
struct CurrentTimeUTC *CurrentTimeUTC,
|
||||
static void Rep_WriteSectionUsrFigures (const struct UsrFigures *UsrFigures,
|
||||
const struct tm *tm_FirstClickTime,
|
||||
const struct CurrentTimeUTC *CurrentTimeUTC);
|
||||
static void Rep_WriteSectionGlobalHits (const struct UsrFigures *UsrFigures,
|
||||
const struct tm *tm_FirstClickTime);
|
||||
static void Rep_WriteSectionCurrentCourses (const struct UsrFigures *UsrFigures,
|
||||
const struct tm *tm_FirstClickTime,
|
||||
const struct CurrentTimeUTC *CurrentTimeUTC,
|
||||
unsigned long MaxHitsPerYear);
|
||||
static void Rep_WriteSectionHistoricCourses (struct UsrFigures *UsrFigures,
|
||||
struct tm *tm_FirstClickTime,
|
||||
static void Rep_WriteSectionHistoricCourses (const struct UsrFigures *UsrFigures,
|
||||
const struct tm *tm_FirstClickTime,
|
||||
unsigned long MaxHitsPerYear);
|
||||
|
||||
static unsigned long Rep_GetMaxHitsPerYear (time_t FirstClickTimeUTC);
|
||||
static void Rep_GetAndWriteCurrentCrssOfAUsr (const struct UsrData *UsrDat,Rol_Role_t Role,
|
||||
time_t FirstClickTimeUTC,
|
||||
struct tm *tm_FirstClickTime,
|
||||
const struct tm *tm_FirstClickTime,
|
||||
unsigned long MaxHitsPerYear);
|
||||
static void Rep_GetAndWriteHistoricCrssOfAUsr (const struct UsrData *UsrDat,Rol_Role_t Role,
|
||||
time_t FirstClickTimeUTC,
|
||||
struct tm *tm_FirstClickTime,
|
||||
const struct tm *tm_FirstClickTime,
|
||||
unsigned long MaxHitsPerYear);
|
||||
static void Rep_WriteRowCrsData (long CrsCod,Rol_Role_t Role,
|
||||
time_t FirstClickTimeUTC,
|
||||
struct tm *tm_FirstClickTime,
|
||||
const struct tm *tm_FirstClickTime,
|
||||
unsigned long MaxHitsPerYear);
|
||||
|
||||
static void Rep_ShowMyHitsPerYear (bool AnyCourse,long CrsCod,Rol_Role_t Role,
|
||||
time_t FirstClickTimeUTC,
|
||||
struct tm *tm_FirstClickTime,
|
||||
const struct tm *tm_FirstClickTime,
|
||||
unsigned long MaxHitsPerYear);
|
||||
static void Rep_DrawBarNumHits (float HitsNum,float HitsMax,
|
||||
unsigned MaxBarWidth);
|
||||
|
@ -188,9 +192,6 @@ static void Rep_CreateMyUsageReport (struct CurrentTimeUTC *CurrentTimeUTC,
|
|||
{
|
||||
extern const char *Txt_Report_of_use_of_PLATFORM;
|
||||
struct UsrFigures UsrFigures;
|
||||
char PathReports[PATH_MAX+1];
|
||||
char PathDirReport[PATH_MAX+1];
|
||||
char PathFileReport[PATH_MAX+1];
|
||||
struct tm tm_FirstClickTime;
|
||||
bool GetUsrFiguresAgain;
|
||||
unsigned long MaxHitsPerYear;
|
||||
|
@ -198,40 +199,11 @@ static void Rep_CreateMyUsageReport (struct CurrentTimeUTC *CurrentTimeUTC,
|
|||
/***** Get current date-time *****/
|
||||
Rep_GetCurrentDateTimeUTC (CurrentTimeUTC);
|
||||
|
||||
/***** Path for reports *****/
|
||||
sprintf (PathReports,"%s/%s",
|
||||
Cfg_PATH_SWAD_PUBLIC,Cfg_FOLDER_REP);
|
||||
Fil_CreateDirIfNotExists (PathReports);
|
||||
/***** Create a new report file *****/
|
||||
Rep_CreateNewReportFile (CurrentTimeUTC,FilenameReport,Permalink);
|
||||
|
||||
/***** Create a new report directory *****/
|
||||
/* Path of the public directory for the file with the report */
|
||||
sprintf (PathReports,"%s/%s/%c%c",
|
||||
Cfg_PATH_SWAD_PUBLIC,Cfg_FOLDER_REP,
|
||||
Gbl.UniqueNameEncrypted[0],
|
||||
Gbl.UniqueNameEncrypted[1]);
|
||||
Fil_CreateDirIfNotExists (PathReports);
|
||||
sprintf (PathDirReport,"%s/%s",
|
||||
PathReports,
|
||||
&Gbl.UniqueNameEncrypted[2]);
|
||||
if (mkdir (PathDirReport,(mode_t) 0xFFF))
|
||||
Lay_ShowErrorAndExit ("Can not create directory for report.");
|
||||
|
||||
/* Path of the public file with the report */
|
||||
sprintf (FilenameReport,"%s_%06u_%06u.html",
|
||||
Rep_FILENAME_ROOT,CurrentTimeUTC->Date,CurrentTimeUTC->Time);
|
||||
sprintf (PathFileReport,"%s/%s",
|
||||
PathDirReport,FilenameReport);
|
||||
if ((Gbl.F.Rep = fopen (PathFileReport,"wb")) == NULL)
|
||||
Lay_ShowErrorAndExit ("Can not create report file.");
|
||||
|
||||
/* Permalink */
|
||||
sprintf (Permalink,"%s/%s/%c%c/%s/%s",
|
||||
Cfg_URL_SWAD_PUBLIC,
|
||||
Cfg_FOLDER_REP,
|
||||
Gbl.UniqueNameEncrypted[0],
|
||||
Gbl.UniqueNameEncrypted[1],
|
||||
&Gbl.UniqueNameEncrypted[2],
|
||||
FilenameReport);
|
||||
/***** Store report entry into database *****/
|
||||
Rep_CreateNewReportEntryIntoDB (FilenameReport,Permalink);
|
||||
|
||||
/***** Start file *****/
|
||||
Lay_StartHTMLFile (Gbl.F.Rep,FilenameReport);
|
||||
|
@ -378,11 +350,83 @@ static void Rep_GetCurrentDateTimeUTC (struct CurrentTimeUTC *CurrentTimeUTC)
|
|||
}
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
/*************** Create a new file for user's usage report *******************/
|
||||
/*****************************************************************************/
|
||||
|
||||
static void Rep_CreateNewReportFile (const struct CurrentTimeUTC *CurrentTimeUTC,
|
||||
char *FilenameReport,char *Permalink)
|
||||
{
|
||||
char PathReports[PATH_MAX+1];
|
||||
char PathUniqueDirL[PATH_MAX+1];
|
||||
char PathUniqueDirR[PATH_MAX+1];
|
||||
char PathFileReport[PATH_MAX+1];
|
||||
|
||||
/***** Path for reports *****/
|
||||
sprintf (PathReports,"%s/%s",
|
||||
Cfg_PATH_SWAD_PUBLIC,Cfg_FOLDER_REP);
|
||||
Fil_CreateDirIfNotExists (PathReports);
|
||||
|
||||
/***** Unique directory for the file with the report *****/
|
||||
/* 1. Create a directory using the leftmost 2 chars of a unique name */
|
||||
sprintf (PathUniqueDirL,"%s/%s/%c%c",
|
||||
Cfg_PATH_SWAD_PUBLIC,Cfg_FOLDER_REP,
|
||||
Gbl.UniqueNameEncrypted[0],
|
||||
Gbl.UniqueNameEncrypted[1]);
|
||||
Fil_CreateDirIfNotExists (PathUniqueDirL);
|
||||
|
||||
/* 2. Create a directory using the rightmost 41 chars of a unique name */
|
||||
sprintf (PathUniqueDirR,"%s/%s",
|
||||
PathUniqueDirL,
|
||||
&Gbl.UniqueNameEncrypted[2]);
|
||||
if (mkdir (PathUniqueDirR,(mode_t) 0xFFF))
|
||||
Lay_ShowErrorAndExit ("Can not create directory for report.");
|
||||
|
||||
/***** Path of the public file with the report */
|
||||
sprintf (FilenameReport,"%s_%06u_%06u.html",
|
||||
Rep_FILENAME_ROOT,CurrentTimeUTC->Date,CurrentTimeUTC->Time);
|
||||
sprintf (PathFileReport,"%s/%s",
|
||||
PathUniqueDirR,FilenameReport);
|
||||
if ((Gbl.F.Rep = fopen (PathFileReport,"wb")) == NULL)
|
||||
Lay_ShowErrorAndExit ("Can not create report file.");
|
||||
|
||||
/***** Permalink *****/
|
||||
sprintf (Permalink,"%s/%s/%c%c/%s/%s",
|
||||
Cfg_URL_SWAD_PUBLIC,
|
||||
Cfg_FOLDER_REP,
|
||||
Gbl.UniqueNameEncrypted[0],
|
||||
Gbl.UniqueNameEncrypted[1],
|
||||
&Gbl.UniqueNameEncrypted[2],
|
||||
FilenameReport);
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
/************** Insert a new user's usage report into database ***************/
|
||||
/*****************************************************************************/
|
||||
|
||||
static void Rep_CreateNewReportEntryIntoDB (const char *FilenameReport,
|
||||
const char *Permalink)
|
||||
{
|
||||
char Query[1024+PATH_MAX*2];
|
||||
|
||||
/***** Insert a new user's usage report into database *****/
|
||||
sprintf (Query,"INSERT INTO usr_report"
|
||||
" (UsrCod,ReportTimeUTC,UniqueDirL,UniqueDirR,Filename,Permalink)"
|
||||
" VALUES"
|
||||
" ('%ld',UTC_TIMESTAMP(),'%c%c','%s','%s','%s')",
|
||||
Gbl.Usrs.Me.UsrDat.UsrCod,
|
||||
Gbl.UniqueNameEncrypted[0], // 2 leftmost chars from a unique 43 chars base64url codified from a unique SHA-256 string
|
||||
Gbl.UniqueNameEncrypted[1],
|
||||
&Gbl.UniqueNameEncrypted[2], // 41 rightmost chars from a unique 43 chars base64url codified from a unique SHA-256 string
|
||||
FilenameReport,Permalink);
|
||||
DB_QueryINSERT (Query,"can not create new report");
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
/******************** Write header of user's usage report ********************/
|
||||
/*****************************************************************************/
|
||||
|
||||
static void Rep_WriteHeader (struct CurrentTimeUTC *CurrentTimeUTC,
|
||||
static void Rep_WriteHeader (const struct CurrentTimeUTC *CurrentTimeUTC,
|
||||
const char *Permalink)
|
||||
{
|
||||
extern const char *Txt_Report_of_use_of_PLATFORM;
|
||||
|
@ -411,7 +455,6 @@ static void Rep_WriteHeader (struct CurrentTimeUTC *CurrentTimeUTC,
|
|||
CurrentTimeUTC->StrTime);
|
||||
|
||||
/***** Permalink *****/
|
||||
/*
|
||||
fprintf (Gbl.F.Rep,"<li>%s: "
|
||||
"<a href=\"%s\" target=\"_blank\""
|
||||
" style=\"text-decoration:none;\">"
|
||||
|
@ -420,7 +463,6 @@ static void Rep_WriteHeader (struct CurrentTimeUTC *CurrentTimeUTC,
|
|||
"</li>",
|
||||
Txt_Permalink,
|
||||
Permalink,Permalink);
|
||||
*/
|
||||
|
||||
/***** End of header *****/
|
||||
fprintf (Gbl.F.Rep,"</ul>"
|
||||
|
@ -515,9 +557,9 @@ static void Rep_WriteSectionUsrInfo (void)
|
|||
/********* Write section for user's figures in user's usage report ***********/
|
||||
/*****************************************************************************/
|
||||
|
||||
static void Rep_WriteSectionUsrFigures (struct UsrFigures *UsrFigures,
|
||||
struct tm *tm_FirstClickTime,
|
||||
struct CurrentTimeUTC *CurrentTimeUTC)
|
||||
static void Rep_WriteSectionUsrFigures (const struct UsrFigures *UsrFigures,
|
||||
const struct tm *tm_FirstClickTime,
|
||||
const struct CurrentTimeUTC *CurrentTimeUTC)
|
||||
{
|
||||
extern const char *Txt_Figures;
|
||||
extern const char *Txt_TIME_Since;
|
||||
|
@ -686,8 +728,8 @@ static void Rep_WriteSectionUsrFigures (struct UsrFigures *UsrFigures,
|
|||
/******** Write section for user's global hits in user's usage report ********/
|
||||
/*****************************************************************************/
|
||||
|
||||
static void Rep_WriteSectionGlobalHits (struct UsrFigures *UsrFigures,
|
||||
struct tm *tm_FirstClickTime)
|
||||
static void Rep_WriteSectionGlobalHits (const struct UsrFigures *UsrFigures,
|
||||
const struct tm *tm_FirstClickTime)
|
||||
{
|
||||
extern const char *Txt_Hits;
|
||||
|
||||
|
@ -711,9 +753,9 @@ static void Rep_WriteSectionGlobalHits (struct UsrFigures *UsrFigures,
|
|||
/****** Write section for user's current courses in user's usage report ******/
|
||||
/*****************************************************************************/
|
||||
|
||||
static void Rep_WriteSectionCurrentCourses (struct UsrFigures *UsrFigures,
|
||||
struct tm *tm_FirstClickTime,
|
||||
struct CurrentTimeUTC *CurrentTimeUTC,
|
||||
static void Rep_WriteSectionCurrentCourses (const struct UsrFigures *UsrFigures,
|
||||
const struct tm *tm_FirstClickTime,
|
||||
const struct CurrentTimeUTC *CurrentTimeUTC,
|
||||
unsigned long MaxHitsPerYear)
|
||||
{
|
||||
extern const char *Txt_Courses;
|
||||
|
@ -746,8 +788,8 @@ static void Rep_WriteSectionCurrentCourses (struct UsrFigures *UsrFigures,
|
|||
/***** Write section for user's historic courses in user's usage report ******/
|
||||
/*****************************************************************************/
|
||||
|
||||
static void Rep_WriteSectionHistoricCourses (struct UsrFigures *UsrFigures,
|
||||
struct tm *tm_FirstClickTime,
|
||||
static void Rep_WriteSectionHistoricCourses (const struct UsrFigures *UsrFigures,
|
||||
const struct tm *tm_FirstClickTime,
|
||||
unsigned long MaxHitsPerYear)
|
||||
{
|
||||
extern const char *Txt_Courses;
|
||||
|
@ -820,7 +862,7 @@ static unsigned long Rep_GetMaxHitsPerYear (time_t FirstClickTimeUTC)
|
|||
|
||||
static void Rep_GetAndWriteCurrentCrssOfAUsr (const struct UsrData *UsrDat,Rol_Role_t Role,
|
||||
time_t FirstClickTimeUTC,
|
||||
struct tm *tm_FirstClickTime,
|
||||
const struct tm *tm_FirstClickTime,
|
||||
unsigned long MaxHitsPerYear)
|
||||
{
|
||||
extern const char *Txt_USER_in_COURSE;
|
||||
|
@ -901,7 +943,7 @@ static void Rep_GetAndWriteCurrentCrssOfAUsr (const struct UsrData *UsrDat,Rol_R
|
|||
|
||||
static void Rep_GetAndWriteHistoricCrssOfAUsr (const struct UsrData *UsrDat,Rol_Role_t Role,
|
||||
time_t FirstClickTimeUTC,
|
||||
struct tm *tm_FirstClickTime,
|
||||
const struct tm *tm_FirstClickTime,
|
||||
unsigned long MaxHitsPerYear)
|
||||
{
|
||||
extern const char *Txt_Hits_as_a_USER;
|
||||
|
@ -965,7 +1007,7 @@ static void Rep_GetAndWriteHistoricCrssOfAUsr (const struct UsrData *UsrDat,Rol_
|
|||
|
||||
static void Rep_WriteRowCrsData (long CrsCod,Rol_Role_t Role,
|
||||
time_t FirstClickTimeUTC,
|
||||
struct tm *tm_FirstClickTime,
|
||||
const struct tm *tm_FirstClickTime,
|
||||
unsigned long MaxHitsPerYear)
|
||||
{
|
||||
extern const char *Txt_YEAR_OF_DEGREE[1+Deg_MAX_YEARS_PER_DEGREE];
|
||||
|
@ -1027,7 +1069,7 @@ static void Rep_WriteRowCrsData (long CrsCod,Rol_Role_t Role,
|
|||
|
||||
static void Rep_ShowMyHitsPerYear (bool AnyCourse,long CrsCod,Rol_Role_t Role,
|
||||
time_t FirstClickTimeUTC,
|
||||
struct tm *tm_FirstClickTime,
|
||||
const struct tm *tm_FirstClickTime,
|
||||
unsigned long MaxHitsPerYear)
|
||||
{
|
||||
char Query[512];
|
||||
|
|
Loading…
Reference in New Issue
Block a user