Version 15.166

This commit is contained in:
Antonio Cañas Vargas 2016-03-30 01:28:58 +02:00
parent 8d5441fe73
commit dce912d16f
6 changed files with 83 additions and 24 deletions

View File

@ -2065,7 +2065,7 @@ struct Act_Actions Act_Actions[Act_NUM_ACTIONS] =
/* ActReqImpTstQst */{1007,-1,TabAss,ActReqTst ,0x110,0x100,0x000,Act_CONTENT_NORM,Act_MAIN_WINDOW,NULL ,TsI_ShowFormImportQstsFromXML ,NULL}, /* ActReqImpTstQst */{1007,-1,TabAss,ActReqTst ,0x110,0x100,0x000,Act_CONTENT_NORM,Act_MAIN_WINDOW,NULL ,TsI_ShowFormImportQstsFromXML ,NULL},
/* ActImpTstQst */{1008,-1,TabAss,ActReqTst ,0x110,0x100,0x000,Act_CONTENT_DATA,Act_MAIN_WINDOW,NULL ,TsI_ImportQstsFromXML ,NULL}, /* ActImpTstQst */{1008,-1,TabAss,ActReqTst ,0x110,0x100,0x000,Act_CONTENT_DATA,Act_MAIN_WINDOW,NULL ,TsI_ImportQstsFromXML ,NULL},
/* ActLstTstQst */{ 132,-1,TabAss,ActReqTst ,0x110,0x100,0x000,Act_CONTENT_NORM,Act_MAIN_WINDOW,NULL ,Tst_ListQuestionsToEdit ,NULL}, /* ActLstTstQst */{ 132,-1,TabAss,ActReqTst ,0x110,0x100,0x000,Act_CONTENT_NORM,Act_MAIN_WINDOW,NULL ,Tst_ListQuestionsToEdit ,NULL},
/* ActRcvTstQst */{ 126,-1,TabAss,ActReqTst ,0x110,0x100,0x000,Act_CONTENT_NORM,Act_MAIN_WINDOW,NULL ,Tst_ReceiveQst ,NULL}, /* ActRcvTstQst */{ 126,-1,TabAss,ActReqTst ,0x110,0x100,0x000,Act_CONTENT_DATA,Act_MAIN_WINDOW,NULL ,Tst_ReceiveQst ,NULL},
/* ActRemTstQst */{ 133,-1,TabAss,ActReqTst ,0x110,0x100,0x000,Act_CONTENT_NORM,Act_MAIN_WINDOW,NULL ,Tst_RemoveQst ,NULL}, /* ActRemTstQst */{ 133,-1,TabAss,ActReqTst ,0x110,0x100,0x000,Act_CONTENT_NORM,Act_MAIN_WINDOW,NULL ,Tst_RemoveQst ,NULL},
/* ActShfTstQst */{ 455,-1,TabAss,ActReqTst ,0x110,0x100,0x000,Act_CONTENT_NORM,Act_MAIN_WINDOW,NULL ,Tst_ChangeShuffleQst ,NULL}, /* ActShfTstQst */{ 455,-1,TabAss,ActReqTst ,0x110,0x100,0x000,Act_CONTENT_NORM,Act_MAIN_WINDOW,NULL ,Tst_ChangeShuffleQst ,NULL},

View File

@ -135,13 +135,15 @@
/****************************** Public constants *****************************/ /****************************** Public constants *****************************/
/*****************************************************************************/ /*****************************************************************************/
#define Log_PLATFORM_VERSION "SWAD 15.165.8 (2016-03-29)" #define Log_PLATFORM_VERSION "SWAD 15.166 (2016-03-29)"
#define CSS_FILE "swad15.165.5.css" #define CSS_FILE "swad15.165.5.css"
#define JS_FILE "swad15.131.3.js" #define JS_FILE "swad15.131.3.js"
// Number of lines (includes comments but not blank lines) has been got with the following command: // 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 // nl swad*.c swad*.h css/swad*.css py/swad*.py js/swad*.js soap/swad*.h sql/swad*.sql | tail -1
/* /*
Version 15.166: Mar 30, 2016 Changes in form to edit a test question.
Fixed bug while reading a parameter. (196943 lines)
Version 15.165.8: Mar 30, 2016 Changes related to image in test questions. (196896 lines) Version 15.165.8: Mar 30, 2016 Changes related to image in test questions. (196896 lines)
Version 15.165.7: Mar 29, 2016 New field for image in database table of test questions. (196879 lines) Version 15.165.7: Mar 29, 2016 New field for image in database table of test questions. (196879 lines)
1 change necessary in database: 1 change necessary in database:

View File

@ -163,6 +163,21 @@ bool Fil_ReadStdinIntoTmpFile (void)
} }
rewind (Gbl.F.Tmp); rewind (Gbl.F.Tmp);
/* For debug
FILE *FileTgt;
***** Open destination file *****
if ((FileTgt = fopen ("/tmp/borrame.txt","wb")) == NULL)
Lay_ShowErrorAndExit ("Can not open target file.");
***** Copy source file into destination file *****
Fil_FastCopyOfOpenFiles (Gbl.F.Tmp,FileTgt);
***** Close the files *****
rewind (Gbl.F.Tmp);
fclose (FileTgt);
*/
return true; return true;
} }
@ -460,7 +475,8 @@ void Fil_RemoveOldTmpFiles (const char *Path,time_t TimeToRemove,bool RemoveDire
void Fil_FastCopyOfFiles (const char *PathSrc,const char *PathTgt) void Fil_FastCopyOfFiles (const char *PathSrc,const char *PathTgt)
{ {
FILE *FileSrc,*FileTgt; FILE *FileSrc;
FILE *FileTgt;
/***** Open source file *****/ /***** Open source file *****/
if ((FileSrc = fopen (PathSrc,"rb")) == NULL) if ((FileSrc = fopen (PathSrc,"rb")) == NULL)

View File

@ -642,6 +642,7 @@ struct Globals
char *Text; char *Text;
size_t Length; size_t Length;
} Stem, Feedback; } Stem, Feedback;
char Image[Cry_LENGTH_ENCRYPTED_STR_SHA256_BASE64+1];
bool Shuffle; bool Shuffle;
struct struct
{ {

View File

@ -59,6 +59,8 @@ extern struct Globals Gbl;
/***************************** Private prototypes ****************************/ /***************************** Private prototypes ****************************/
/*****************************************************************************/ /*****************************************************************************/
static void Par_ShowErrorReadingParam (const char *ParamName,const char *ExpectedChar,int Ch);
/*****************************************************************************/ /*****************************************************************************/
/*** Read all parameters passed to this CGI and store for later processing ***/ /*** Read all parameters passed to this CGI and store for later processing ***/
/*****************************************************************************/ /*****************************************************************************/
@ -420,6 +422,7 @@ unsigned Par_GetParameter (tParamType ParamType,const char *ParamName,
size_t BytesToCopy; size_t BytesToCopy;
size_t BytesAlreadyCopied = 0; size_t BytesAlreadyCopied = 0;
int Ch; int Ch;
unsigned i;
char *PtrSrc; char *PtrSrc;
char *PtrDst; char *PtrDst;
char *PtrStartOfParam; char *PtrStartOfParam;
@ -511,6 +514,7 @@ unsigned Par_GetParameter (tParamType ParamType,const char *ParamName,
break; break;
case Act_CONTENT_DATA: case Act_CONTENT_DATA:
rewind (Gbl.F.Tmp); rewind (Gbl.F.Tmp);
while (ContinueSearching) while (ContinueSearching)
{ {
Result = Str_ReceiveFileUntilDelimitStr (Gbl.F.Tmp,NULL,StrAux,Gbl.DelimiterString,(unsigned long long) Par_MAX_BYTES_STR_AUX); Result = Str_ReceiveFileUntilDelimitStr (Gbl.F.Tmp,NULL,StrAux,Gbl.DelimiterString,(unsigned long long) Par_MAX_BYTES_STR_AUX);
@ -531,24 +535,26 @@ unsigned Par_GetParameter (tParamType ParamType,const char *ParamName,
if (!strcasecmp (Str_GetNextStrFromFileConvertingToLower (Gbl.F.Tmp,StrAux,Par_LENGTH_OF_STR_BEFORE_PARAM-1),StringBeforeParam+1)) // Start of a parameter if (!strcasecmp (Str_GetNextStrFromFileConvertingToLower (Gbl.F.Tmp,StrAux,Par_LENGTH_OF_STR_BEFORE_PARAM-1),StringBeforeParam+1)) // Start of a parameter
if (!strcasecmp (Str_GetNextStrFromFileConvertingToLower (Gbl.F.Tmp,StrAux,ParamNameLength),ParamName)) // Parameter found if (!strcasecmp (Str_GetNextStrFromFileConvertingToLower (Gbl.F.Tmp,StrAux,ParamNameLength),ParamName)) // Parameter found
{ {
/* Skip "'" symbol after parameter name */ /* Skip quote after parameter name */
Ch = fgetc (Gbl.F.Tmp); Ch = fgetc (Gbl.F.Tmp);
if (Ch != (int) '\"') if (Ch != (int) '\"')
{ Par_ShowErrorReadingParam (ParamName,""",Ch);
sprintf (Gbl.Message,"Error reading parameter <strong>%s</strong>."
" A <strong>&quot;</strong> character was expected, but a <strong>%c</strong> (ASCII code %d) has been found.",
ParamName,(char) Ch,Ch);
Lay_ShowErrorAndExit (Gbl.Message);
}
/* Skip carriage returns, spaces, etc. */ /* Skip two CR-LF (0x0D 0x0A) */
do for (i = 0;
Ch = fgetc (Gbl.F.Tmp); i < 2;
while (isspace (Ch) && Ch != EOF); i++)
{
Ch = fgetc (Gbl.F.Tmp);
if (Ch != 0x0D) // '\r'
Par_ShowErrorReadingParam (ParamName,"0x0D",Ch);
Ch = fgetc (Gbl.F.Tmp);
if (Ch != 0x0A) // '\n'
Par_ShowErrorReadingParam (ParamName,"0x0A",Ch);
}
/* Get the parameter */ /* Get the parameter */
ParamValue[0] = Ch; Result = Str_ReceiveFileUntilDelimitStr (Gbl.F.Tmp,(FILE *) NULL,ParamValue,Gbl.DelimiterStringIncludingInitialRet,(unsigned long long) MaxBytes);
Result = Str_ReceiveFileUntilDelimitStr (Gbl.F.Tmp,(FILE *) NULL,&ParamValue[1],Gbl.DelimiterStringIncludingInitialRet,(unsigned long long) MaxBytes);
/* Depending on the result... */ /* Depending on the result... */
switch (Result) switch (Result)
@ -579,6 +585,19 @@ unsigned Par_GetParameter (tParamType ParamType,const char *ParamName,
return NumTimes; return NumTimes;
} }
/*****************************************************************************/
/********************** Write error reading parameter ************************/
/*****************************************************************************/
static void Par_ShowErrorReadingParam (const char *ParamName,const char *ExpectedChar,int Ch)
{
sprintf (Gbl.Message,"Error reading parameter <strong>%s</strong>."
" A <strong>%s</strong> character was expected,"
" but a character with code %X has been found.",
ParamName,ExpectedChar,Ch);
Lay_ShowErrorAndExit (Gbl.Message);
}
/*****************************************************************************/ /*****************************************************************************/
/***** Search in the string StrSrc the next string until find separator ******/ /***** Search in the string StrSrc the next string until find separator ******/
/*****************************************************************************/ /*****************************************************************************/

View File

@ -146,6 +146,7 @@ static void Tst_ShowTstResultAfterAssess (long TstCod,unsigned *NumQstsNotBlank,
static void Tst_WriteQstAndAnsExam (unsigned NumQst,long QstCod,MYSQL_ROW row, static void Tst_WriteQstAndAnsExam (unsigned NumQst,long QstCod,MYSQL_ROW row,
double *ScoreThisQst,bool *AnswerIsNotBlank); double *ScoreThisQst,bool *AnswerIsNotBlank);
static void Tst_WriteQstImage (const char *Image); static void Tst_WriteQstImage (const char *Image);
static void Tst_PutFormToUploadNewQstImage (void);
static void Tst_UpdateScoreQst (long QstCod,float ScoreThisQst,bool AnswerIsNotBlank); static void Tst_UpdateScoreQst (long QstCod,float ScoreThisQst,bool AnswerIsNotBlank);
static void Tst_UpdateMyNumAccessTst (unsigned NumAccessesTst); static void Tst_UpdateMyNumAccessTst (unsigned NumAccessesTst);
static void Tst_UpdateLastAccTst (void); static void Tst_UpdateLastAccTst (void);
@ -1023,6 +1024,17 @@ static void Tst_WriteQstImage (const char *Image)
Image); Image);
} }
/*****************************************************************************/
/************* Put form to upload a new image for a test question ************/
/*****************************************************************************/
static void Tst_PutFormToUploadNewQstImage (void)
{
fprintf (Gbl.F.Out,"<input type=\"file\" name=\"%s\""
" size=\"40\" maxlength=\"100\" value=\"\" />",
Fil_NAME_OF_PARAM_FILENAME_ORG);
}
/*****************************************************************************/ /*****************************************************************************/
/******************* Write the feedback of a test question *******************/ /******************* Write the feedback of a test question *******************/
/*****************************************************************************/ /*****************************************************************************/
@ -4174,7 +4186,7 @@ static void Tst_PutFormEditOneQst (char *Stem,char *Feedback)
{ {
/***** Get the type of answer and the stem from the database *****/ /***** Get the type of answer and the stem from the database *****/
/* Get the question from database */ /* Get the question from database */
sprintf (Query,"SELECT AnsType,Shuffle,Stem,Feedback" sprintf (Query,"SELECT AnsType,Shuffle,Stem,Image,Feedback"
" FROM tst_questions" " FROM tst_questions"
" WHERE QstCod='%ld' AND CrsCod='%ld'", " WHERE QstCod='%ld' AND CrsCod='%ld'",
Gbl.Test.QstCod, Gbl.Test.QstCod,
@ -4193,12 +4205,16 @@ static void Tst_PutFormEditOneQst (char *Stem,char *Feedback)
strncpy (Stem,row[2],Cns_MAX_BYTES_TEXT); strncpy (Stem,row[2],Cns_MAX_BYTES_TEXT);
Stem[Cns_MAX_BYTES_TEXT] = '\0'; Stem[Cns_MAX_BYTES_TEXT] = '\0';
/* Get the feedback of the question from the database (row[3]) */ /* Get the image of the question from the database (row[3]) */
strncpy (Gbl.Test.Image,row[3],Cry_LENGTH_ENCRYPTED_STR_SHA256_BASE64);
Gbl.Test.Image[Cry_LENGTH_ENCRYPTED_STR_SHA256_BASE64] = '\0';
/* Get the feedback of the question from the database (row[4]) */
Feedback[0] = '\0'; Feedback[0] = '\0';
if (row[3]) if (row[4])
if (row[3][0]) if (row[4][0])
{ {
strncpy (Feedback,row[3],Cns_MAX_BYTES_TEXT); strncpy (Feedback,row[4],Cns_MAX_BYTES_TEXT);
Feedback[Cns_MAX_BYTES_TEXT] = '\0'; Feedback[Cns_MAX_BYTES_TEXT] = '\0';
} }
@ -4378,17 +4394,21 @@ static void Tst_PutFormEditOneQst (char *Stem,char *Feedback)
/***** Image *****/ /***** Image *****/
if (Gbl.Usrs.Me.LoggedRole == Rol_SYS_ADM) if (Gbl.Usrs.Me.LoggedRole == Rol_SYS_ADM)
{
fprintf (Gbl.F.Out,"<tr>" fprintf (Gbl.F.Out,"<tr>"
"<td class=\"RIGHT_TOP\">" "<td class=\"RIGHT_TOP\">"
"<label class=\"%s\">" "<label class=\"%s\">"
"%s:" "%s:"
"</label>" "</label>"
"</td>" "</td>"
"<td class=\"LEFT_TOP\">" "<td class=\"LEFT_TOP\">",
"</td>"
"</tr>",
The_ClassForm[Gbl.Prefs.Theme], The_ClassForm[Gbl.Prefs.Theme],
Txt_Image); Txt_Image);
Tst_WriteQstImage (Gbl.Test.Image);
Tst_PutFormToUploadNewQstImage ();
fprintf (Gbl.F.Out,"</td>"
"</tr>");
}
/***** Feedback *****/ /***** Feedback *****/
fprintf (Gbl.F.Out,"<tr>" fprintf (Gbl.F.Out,"<tr>"
@ -4735,6 +4755,7 @@ static void Tst_GetQstFromForm (char *Stem,char *Feedback)
{ {
sprintf (TagStr,"TagTxt%u",NumTag); sprintf (TagStr,"TagTxt%u",NumTag);
Par_GetParToText (TagStr,Gbl.Test.TagText[NumTag],Tst_MAX_BYTES_TAG); Par_GetParToText (TagStr,Gbl.Test.TagText[NumTag],Tst_MAX_BYTES_TAG);
if (Gbl.Test.TagText[NumTag][0]) if (Gbl.Test.TagText[NumTag][0])
{ {
Str_ChangeFormat (Str_FROM_FORM,Str_TO_TEXT, Str_ChangeFormat (Str_FROM_FORM,Str_TO_TEXT,