[Fusionforge-commits] r8694 - in trunk: gforge gforge/www/pm gforge/www/pm/include tests/func/Tasks

Alain Peyrat aljeux at libremir.placard.fr.eu.org
Wed Jan 27 20:54:13 CET 2010


Author: aljeux
Date: 2010-01-27 20:54:13 +0100 (Wed, 27 Jan 2010)
New Revision: 8694

Added:
   trunk/gforge/www/pm/csv.php
   trunk/gforge/www/pm/format_csv.php
   trunk/tests/func/Tasks/createTask.php
Removed:
   trunk/tests/func/Tasks/csv.php
Modified:
   trunk/gforge/CHANGES
   trunk/gforge/www/pm/downloadcsv.php
   trunk/gforge/www/pm/include/ProjectGroupHTML.class.php
   trunk/gforge/www/pm/postuploadcsv.php
   trunk/gforge/www/pm/task.php
   trunk/tests/func/Tasks/AllTests.php
Log:
Tasks: CSV Improved import/export

Modified: trunk/gforge/CHANGES
===================================================================
--- trunk/gforge/CHANGES	2010-01-27 16:44:22 UTC (rev 8693)
+++ trunk/gforge/CHANGES	2010-01-27 19:54:13 UTC (rev 8694)
@@ -36,6 +36,7 @@
 * Mediawiki plugin: mostly rewritten.  Now creates independent wikis
   for projects, allowing different sets of permissions.
 * Forums: New 'move' option to move a thread from one forum to another (Alcatel-Lucent).
+* Tasks: Improved CSV import/export (Alcatel-Lucent)
 
 FusionForge-4.8.2:
 * Maintenance release, security and bugfixes.

Added: trunk/gforge/www/pm/csv.php
===================================================================
--- trunk/gforge/www/pm/csv.php	                        (rev 0)
+++ trunk/gforge/www/pm/csv.php	2010-01-27 19:54:13 UTC (rev 8694)
@@ -0,0 +1,131 @@
+<?php
+/*
+ * Copyright (C) 2009 Alain Peyrat, Alcatel-Lucent
+ *
+ * This file is part of FusionForge.
+ *
+ * FusionForge is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published
+ * by the Free Software Foundation; either version 2 of the License,
+ * or (at your option) any later version.
+ *
+ * FusionForge is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with FusionForge; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+ * USA
+ */
+
+/*
+ * Standard Alcatel-Lucent disclaimer for contributing to open source
+ *
+ * "The provided file ("Contribution") has not been tested and/or
+ * validated for release as or in products, combinations with products or
+ * other commercial use. Any use of the Contribution is entirely made at
+ * the user's own responsibility and the user can not rely on any features,
+ * functionalities or performances Alcatel-Lucent has attributed to the
+ * Contribution.
+ *
+ * THE CONTRIBUTION BY ALCATEL-LUCENT IS PROVIDED AS IS, WITHOUT WARRANTY
+ * OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+ * WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, COMPLIANCE,
+ * NON-INTERFERENCE AND/OR INTERWORKING WITH THE SOFTWARE TO WHICH THE
+ * CONTRIBUTION HAS BEEN MADE, TITLE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * ALCATEL-LUCENT BE LIABLE FOR ANY DAMAGES OR OTHER LIABLITY, WHETHER IN
+ * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * CONTRIBUTION OR THE USE OR OTHER DEALINGS IN THE CONTRIBUTION, WHETHER
+ * TOGETHER WITH THE SOFTWARE TO WHICH THE CONTRIBUTION RELATES OR ON A STAND
+ * ALONE BASIS."
+ */
+
+//
+//	This page contains a form with a file-upload button
+//	so a user can choose a file to upload a .csv file and store it in task mgr
+//
+
+
+pm_header(array('title'=>_('Upload data into the task manager.'),'group_project_id'=>$group_project_id));
+
+$headers = getIntFromRequest('headers', 1);
+$full = getIntFromRequest('full', 1);
+$sep = getStringFromRequest('sep', ',');
+
+$url_set_format = '/pm/task.php?group_id='.$group_id.'&amp;group_project_id='.$group_project_id.'&amp;func=format_csv&amp;sep='.urlencode($sep).'&amp;full='.$full.'&amp;headers='.$headers;
+
+$url_export = '/pm/task.php?group_id='.$group_id.'&amp;group_project_id='.$group_project_id.'&amp;func=downloadcsv&amp;sep='.urlencode($sep).'&amp;full='.$full.'&amp;headers='.$headers;
+
+$format = $full ? "Full CSV" : "Normal CSV";
+$format .= $headers ? ' with headers' : ' without headers';
+$format .= " using '$sep' as separator.";
+?>
+<p><?php echo _('This page allows you to export or import all the tasks using a CSV (<a href="http://en.wikipedia.org/wiki/Comma-separated_values">Comma Separated Values</a>) File. This format can be used to view tasks using MS Excel.'); ?></p>
+<h2><?php echo _('Export tasks as a CSV file'); ?></h2>
+
+<strong><?php echo _('Selected CSV Format :'); ?></strong> <?php echo $format ?> <a href="<?php echo $url_set_format ?>">(Change)</a>
+
+<p><a href="<?php echo $url_export ?>"><?php echo _('Export CSV file'); ?></a></p>
+
+<h2><?php echo _('Import tasks using a CSV file'); ?></h2>
+<form enctype="multipart/form-data" method="post" action="<?php echo getStringFromServer('PHP_SELF')?>?group_project_id=<? echo $group_project_id ?>&amp;group_id=<? echo $group_id ?>&amp;func=postuploadcsv">
+<p><?php echo _('Choose a file in the proper .csv format for uploading.'); ?></p>
+<input type="file" name="userfile"  size="30" />
+<input type="submit" name="submit" value="submit" />
+</form>
+
+<p><strong>Notes:</strong></p>
+<div>
+<ul>
+<li>Be careful, when importing a CSV file, all the tasks will be replaced by the ones present in the file.</li>
+<li>If project_task_id is empty, then a new task will be created.</li>
+<li>If project_task_id is present, then the corresponding task will be updated.</li>
+</ul>
+</div>
+
+<h2>Record Layout</h2>
+
+<table align="center" border="1" cellspacing="0" cellpadding="3">
+<tr><td><strong>Field Name</strong></td><td><strong>Description</strong></td></tr>
+<tr><td>project_task_id</td><td>this is the ID in gforge database</td></tr>
+<tr><td>external_task_id</td><td>optional, the equivalent of project_task_id but determined by
+external application, such as MS Project. Primarily preserved for sorting purposes only.</td></tr>
+<tr><td>parent_id</td><td>the project_task_id of the parent task, if any</td></tr>
+<tr><td>external_parent_id</td><td>the equivalent of parent project_task_id but
+        determined by external application, such as MS Project. Primarily preserved for matching purposes only.</td></tr>
+<tr><td>title</td><td>The summary or brief description</td></tr>
+<tr><td>category</td><td>The category name (must be defined, only available in full export)</td></tr>
+<tr><td>duration</td><td>Duration in days</td></tr>
+<tr><td>work</td><td>Number of hours required to complete</td></tr>
+<tr><td>start_date</td><td>The start date in MM-DD-YYYY HH:MM:SS format</td></tr>
+<tr><td>end_date</td><td>The end date in MM-DD-YYYY HH:MM:SS format</td></tr>
+<tr><td>percent_complete</td><td>Percentage of completion</td></tr>
+<tr><td>priority</td><td>integers 1 to 5</td></tr>
+<tr><td>notes</td><td>optional, the details of the task or a comment to add to a task</td></tr>
+<tr><td>resource1_unixname</td><td>optional, the unixname or precisely-matched realname of the assignee </td></tr>
+<tr><td>resource2_unixname</td><td>optional, same as above</td></tr>
+<tr><td>resource3_unixname</td><td>optional, same as above</td></tr>
+<tr><td>resource4_unixname</td><td>optional, same as above</td></tr>
+<tr><td>resource5_unixname</td><td>optional, same as above</td></tr>
+<tr><td>dependenton1_project_task_id</td><td>optional, the GForge task_id of a task to be dependent on</td></tr>
+<tr><td>dependenton1_external_task_id</td><td>optional, the ID used by the external application</td></tr>
+<tr><td>dependenton1_linktype</td><td>SS, SF, FS, FF, - The same types as MS Project</td></tr>
+<tr><td>dependenton2_project_task_id</td><td>repetition of dependenton1</td></tr>
+<tr><td>dependenton2_external_task_id</td><td>repetition of dependenton1</td></tr>
+<tr><td>dependenton2_linktype</td><td>repetition of dependenton1</td></tr>
+<tr><td>dependenton3_project_task_id</td><td>repetition of dependenton1</td></tr>
+<tr><td>dependenton3_external_task_id</td><td>repetition of dependenton1</td></tr>
+<tr><td>dependenton3_linktype</td><td>repetition of dependenton1</td></tr>
+<tr><td>dependenton4_project_task_id</td><td>repetition of dependenton1</td></tr>
+<tr><td>dependenton4_external_task_id</td><td>repetition of dependenton1</td></tr>
+<tr><td>dependenton4_linktype</td><td>repetition of dependenton1</td></tr>
+<tr><td>dependenton5_project_task_id</td><td>repetition of dependenton1</td></tr>
+<tr><td>dependenton5_external_task_id</td><td>repetition of dependenton1</td></tr>
+<tr><td>dependenton5_linktype</td><td>repetition of dependenton1</td></tr>
+</table>
+<p />
+<?php
+pm_footer(array());
+?>

Modified: trunk/gforge/www/pm/downloadcsv.php
===================================================================
--- trunk/gforge/www/pm/downloadcsv.php	2010-01-27 16:44:22 UTC (rev 8693)
+++ trunk/gforge/www/pm/downloadcsv.php	2010-01-27 19:54:13 UTC (rev 8694)
@@ -1,5 +1,48 @@
 <?php
 /*
+ * Copyright (C) 2009 Alain Peyrat, Alcatel-Lucent
+ *
+ * This file is part of FusionForge.
+ *
+ * FusionForge is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published
+ * by the Free Software Foundation; either version 2 of the License,
+ * or (at your option) any later version.
+ *
+ * FusionForge is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with FusionForge; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+ * USA
+ */
+
+/*
+ * Standard Alcatel-Lucent disclaimer for contributing to open source
+ *
+ * "The provided file ("Contribution") has not been tested and/or
+ * validated for release as or in products, combinations with products or
+ * other commercial use. Any use of the Contribution is entirely made at
+ * the user's own responsibility and the user can not rely on any features,
+ * functionalities or performances Alcatel-Lucent has attributed to the
+ * Contribution.
+ *
+ * THE CONTRIBUTION BY ALCATEL-LUCENT IS PROVIDED AS IS, WITHOUT WARRANTY
+ * OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+ * WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, COMPLIANCE,
+ * NON-INTERFERENCE AND/OR INTERWORKING WITH THE SOFTWARE TO WHICH THE
+ * CONTRIBUTION HAS BEEN MADE, TITLE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * ALCATEL-LUCENT BE LIABLE FOR ANY DAMAGES OR OTHER LIABLITY, WHETHER IN
+ * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * CONTRIBUTION OR THE USE OR OTHER DEALINGS IN THE CONTRIBUTION, WHETHER
+ * TOGETHER WITH THE SOFTWARE TO WHICH THE CONTRIBUTION RELATES OR ON A STAND
+ * ALONE BASIS."
+ */
+
+/*
 Record description for .csv file format
 
 project_task_id					This is the ID in gforge database
@@ -41,10 +84,15 @@
 require_once $gfcommon.'include/User.class.php';
 require_once $gfcommon.'pm/ProjectTaskFactory.class.php';
 
-header('Content-type: text/comma-separated-values');
-list($year,$month) = explode('-', date('Y-m'));
-header('Content-disposition: filename="task_report-'.$year.'-'.month.'.csv"');
+$headers = getIntFromRequest('headers');
+$full = getIntFromRequest('full');
+$sep = getStringFromRequest('sep', ',');
 
+$date = date('Y-m-d');
+
+header('Content-type: text/csv');
+header('Content-disposition: filename="tasks-'.$date.'.csv"');
+
 $ptf = new ProjectTaskFactory($pg);
 if (!$ptf || !is_object($ptf)) {
     exit_error('Error','Could Not Get ProjectTaskFactory');
@@ -61,22 +109,100 @@
 //	Iterate the array of tasks and dump them out to a comma-separated file
 //
 
-$arrRemove = array("\r\n", "\n", ',');
+$arrRemove = array("\r\n", "\n", $sep);
 
+$header = array(
+	'project_task_id',
+	'external_task_id',
+	'parent_id',
+	'external_parent_id',
+	'title',
+	'duration',
+	'work',
+	'start_date',
+	'end_date',
+	'percent_complete',
+	'priority',
+	'notes',
+	'resource1_unixname',
+	'resource2_unixname',
+	'resource3_unixname',
+	'resource4_unixname',
+	'resource5_unixname',
+	'dependenton1_project_task_id',
+	'dependenton1_external_task_id',
+	'dependenton1_linktype',
+	'dependenton2_project_task_id',
+	'dependenton2_external_task_id',
+	'dependenton2_linktype',
+	'dependenton3_project_task_id',
+	'dependenton3_external_task_id',
+	'dependenton3_linktype',
+	'dependenton4_project_task_id',
+	'dependenton4_external_task_id',
+	'dependenton4_linktype',
+	'dependenton5_project_task_id',
+	'dependenton5_external_task_id',
+	'dependenton5_linktype');
+
+if ($full) {
+$header = array(
+	'project_task_id',
+	'external_task_id',
+	'parent_id',
+	'external_parent_id',
+	'title',
+	'category',
+	'duration',
+	'work',
+	'start_date',
+	'end_date',
+	'percent_complete',
+	'priority',
+	'notes',
+	'resource1_unixname',
+	'resource2_unixname',
+	'resource3_unixname',
+	'resource4_unixname',
+	'resource5_unixname',
+	'dependenton1_project_task_id',
+	'dependenton1_external_task_id',
+	'dependenton1_linktype',
+	'dependenton2_project_task_id',
+	'dependenton2_external_task_id',
+	'dependenton2_linktype',
+	'dependenton3_project_task_id',
+	'dependenton3_external_task_id',
+	'dependenton3_linktype',
+	'dependenton4_project_task_id',
+	'dependenton4_external_task_id',
+	'dependenton4_linktype',
+	'dependenton5_project_task_id',
+	'dependenton5_external_task_id',
+	'dependenton5_linktype');
+}
+
+if ($headers) {
+	echo join($sep, $header)."\n";
+}
+
 for ($i=0; $i<count($pt_arr); $i++) {
 
-	echo $pt_arr[$i]->getID().','.
-		$pt_arr[$i]->getExternalID().','.
-		$pt_arr[$i]->getParentID().','.
-		','.
-		str_replace($arrRemove, ' ', $pt_arr[$i]->getSummary()).','.
-		$pt_arr[$i]->getDuration().','.
-		$pt_arr[$i]->getHours().','.
-		date('Y-m-d H:i:s',$pt_arr[$i]->getStartDate()).','.
-		date('Y-m-d H:i:s',$pt_arr[$i]->getEndDate()).','.
-		$pt_arr[$i]->getPercentComplete().','.
-		$pt_arr[$i]->getPriority().','.
-		str_replace($arrRemove, ' ', $pt_arr[$i]->getDetails()).',';
+	echo $pt_arr[$i]->getID().$sep.
+		$pt_arr[$i]->getExternalID().$sep.
+		$pt_arr[$i]->getParentID().$sep.
+		$sep.
+		str_replace($arrRemove, ' ', $pt_arr[$i]->getSummary()).$sep;
+	if ($full) {
+		echo $pt_arr[$i]->getCategoryName().$sep;
+	}
+	echo $pt_arr[$i]->getDuration().$sep.
+		$pt_arr[$i]->getHours().$sep.
+		date('Y-m-d H:i:s',$pt_arr[$i]->getStartDate()).$sep.
+		date('Y-m-d H:i:s',$pt_arr[$i]->getEndDate()).$sep.
+		$pt_arr[$i]->getPercentComplete().$sep.
+		$pt_arr[$i]->getPriority().$sep.
+		str_replace($arrRemove, ' ', $pt_arr[$i]->getDetails()).$sep;
 
 		$users =& user_get_objects($pt_arr[$i]->getAssignedTo());
 		for ($j=0; $j<5; $j++) {
@@ -85,19 +211,19 @@
 					echo $users[$j]->getUnixName();
 				}
 			}
-			echo ',';
+			echo $sep;
 		}
 
 		$dependentOn =& $pt_arr[$i]->getDependentOn();
 		$keys=array_keys($dependentOn);
 		for ($j=0; $j<5; $j++) {
 			if ($j < count($keys)) {
-				echo $keys[$j].',,'.$dependentOn[$keys[$j]];
+				echo $keys[$j].$sep.$sep.$dependentOn[$keys[$j]];
 			} else {
-				echo ',,';
+				echo $sep.$sep;
 			}
 			if ($j<4) {
-				echo ',';
+				echo $sep;
 			}
 		}
 	echo "\n";

Added: trunk/gforge/www/pm/format_csv.php
===================================================================
--- trunk/gforge/www/pm/format_csv.php	                        (rev 0)
+++ trunk/gforge/www/pm/format_csv.php	2010-01-27 19:54:13 UTC (rev 8694)
@@ -0,0 +1,103 @@
+<?php
+/*
+ * Copyright (C) 2009 Alain Peyrat, Alcatel-Lucent
+ *
+ * This file is part of FusionForge.
+ *
+ * FusionForge is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published
+ * by the Free Software Foundation; either version 2 of the License,
+ * or (at your option) any later version.
+ * 
+ * FusionForge is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with FusionForge; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+ * USA
+ */
+
+/*
+ * Standard Alcatel-Lucent disclaimer for contributing to open source
+ *
+ * "The provided file ("Contribution") has not been tested and/or
+ * validated for release as or in products, combinations with products or
+ * other commercial use. Any use of the Contribution is entirely made at
+ * the user's own responsibility and the user can not rely on any features,
+ * functionalities or performances Alcatel-Lucent has attributed to the
+ * Contribution.
+ *
+ * THE CONTRIBUTION BY ALCATEL-LUCENT IS PROVIDED AS IS, WITHOUT WARRANTY
+ * OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+ * WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, COMPLIANCE,
+ * NON-INTERFERENCE AND/OR INTERWORKING WITH THE SOFTWARE TO WHICH THE
+ * CONTRIBUTION HAS BEEN MADE, TITLE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * ALCATEL-LUCENT BE LIABLE FOR ANY DAMAGES OR OTHER LIABLITY, WHETHER IN
+ * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * CONTRIBUTION OR THE USE OR OTHER DEALINGS IN THE CONTRIBUTION, WHETHER
+ * TOGETHER WITH THE SOFTWARE TO WHICH THE CONTRIBUTION RELATES OR ON A STAND
+ * ALONE BASIS."
+ */
+
+//
+//	This page contains a form with a file-upload button
+//	so a user can choose a file to upload a .csv file and store it in task mgr
+//
+
+
+pm_header(array('title'=>_('Upload data into the task manager.'),'group_project_id'=>$group_project_id));
+
+$headers = getIntFromRequest('headers', 1);
+$full = getIntFromRequest('full', 1);
+$sep = getStringFromRequest('sep', ',');
+
+?>
+<center>
+<table>
+	<tr>
+		<td>
+		<fieldset><legend><b>CSV Format</b></legend>
+		<form action="/pm/task.php" method="get"><input type="hidden"
+			name="group_id" value="<?php echo $group_id ?>" /> <input
+			type="hidden" name="group_project_id"
+			value="<?php echo $group_project_id ?>" /> <input type="hidden"
+			name="func" value="csv" />
+		<table>
+			<tr>
+				<td valign="top"><b>Content :</b></td>
+				<td><input type="radio" name="full" value="1"<?php if ($full) echo ' checked="checked"' ?>/>Full<br />
+				<input type="radio" name="full" value="0"<?php if (!$full) echo ' checked="checked"' ?> />Normal</td>
+			</tr>
+			<tr><td colspan="2">&nbsp;</td></tr>
+			<tr>
+				<td valign="top"><b>Separator :</b></td>
+				<td><input type="radio" name="sep" value=","<?php if ($sep==',') echo ' checked="checked"' ?>/>Comma (char: ',')<br />
+				<input type="radio" name="sep" value=";"<?php if ($sep==';') echo ' checked="checked"' ?>/>Semi-colon (char: ';')</td>
+			</tr>
+			<tr><td colspan="2">&nbsp;</td></tr>
+			<tr>
+				<td valign="top"><b>Header :</b></td>
+				<td><input type="radio" name="headers" value="1"<?php if ($headers) echo ' checked="checked"' ?>/>Included<br />
+				<input type="radio" name="headers" value="0"<?php if (!$headers) echo ' checked="checked"' ?>/>None</td>
+			</tr>
+		</table>
+		<input type="submit" name="Submit" /></form>
+		</fieldset>
+		</td>
+	</tr>
+</table>
+</center>
+<p><strong>Notes:</strong></p>
+<div>
+<ul>
+<li><strong>Full/Normal :</strong> In Full, the category is also exported.</li>
+<li><strong>Comma/Semi-colon :</strong> Some international version of MS Excel uses ';' instead of ','.</li>
+<li><strong>Headers Included or not :</strong> Add a line with the name of the fields at the fist line.</li>
+</ul>
+</div>
+<?php
+pm_footer(array());
+?>

Modified: trunk/gforge/www/pm/include/ProjectGroupHTML.class.php
===================================================================
--- trunk/gforge/www/pm/include/ProjectGroupHTML.class.php	2010-01-27 16:44:22 UTC (rev 8693)
+++ trunk/gforge/www/pm/include/ProjectGroupHTML.class.php	2010-01-27 19:54:13 UTC (rev 8694)
@@ -62,10 +62,14 @@
 			. '\', \'' . $gantt_winopt . '\'); return false;';
 		}
 		//upload/download as CSV files
-		$labels[] = _('Download as CSV');
-		$links[]  = '/pm/task.php?group_id='.$group_id.'&amp;group_project_id='.$group_project_id.'&amp;func=downloadcsv';
-		$labels[] = _('Upload CSV');
-		$links[]  = '/pm/task.php?group_id='.$group_id.'&amp;group_project_id='.$group_project_id.'&amp;func=uploadcsv';
+//		$labels[] = _('Download as CSV');
+//		$links[]  = '/pm/task.php?group_id='.$group_id.'&amp;group_project_id='.$group_project_id.'&amp;func=downloadcsv';
+//		$labels[] = _('Upload CSV');
+//		$links[]  = '/pm/task.php?group_id='.$group_id.'&amp;group_project_id='.$group_project_id.'&amp;func=uploadcsv';
+
+		// Import/Export using CSV files.
+		$labels[] = _('Import/Export CSV');
+		$links[]  = '/pm/task.php?group_id='.$group_id.'&amp;group_project_id='.$group_project_id.'&amp;func=csv';
 	}
 	if ($pg && is_object($pg) && $pg->userIsAdmin()) {
 		$labels[] = _('Reporting');

Modified: trunk/gforge/www/pm/postuploadcsv.php
===================================================================
--- trunk/gforge/www/pm/postuploadcsv.php	2010-01-27 16:44:22 UTC (rev 8693)
+++ trunk/gforge/www/pm/postuploadcsv.php	2010-01-27 19:54:13 UTC (rev 8694)
@@ -1,53 +1,120 @@
 <?php
+/*
+ * Copyright (C) 2009 Alain Peyrat, Alcatel-Lucent
+ *
+ * This file is part of FusionForge.
+ *
+ * FusionForge is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published
+ * by the Free Software Foundation; either version 2 of the License,
+ * or (at your option) any later version.
+ *
+ * FusionForge is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with FusionForge; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+ * USA
+ */
+
+/*
+ * Standard Alcatel-Lucent disclaimer for contributing to open source
+ *
+ * "The provided file ("Contribution") has not been tested and/or
+ * validated for release as or in products, combinations with products or
+ * other commercial use. Any use of the Contribution is entirely made at
+ * the user's own responsibility and the user can not rely on any features,
+ * functionalities or performances Alcatel-Lucent has attributed to the
+ * Contribution.
+ *
+ * THE CONTRIBUTION BY ALCATEL-LUCENT IS PROVIDED AS IS, WITHOUT WARRANTY
+ * OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+ * WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, COMPLIANCE,
+ * NON-INTERFERENCE AND/OR INTERWORKING WITH THE SOFTWARE TO WHICH THE
+ * CONTRIBUTION HAS BEEN MADE, TITLE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * ALCATEL-LUCENT BE LIABLE FOR ANY DAMAGES OR OTHER LIABLITY, WHETHER IN
+ * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * CONTRIBUTION OR THE USE OR OTHER DEALINGS IN THE CONTRIBUTION, WHETHER
+ * TOGETHER WITH THE SOFTWARE TO WHICH THE CONTRIBUTION RELATES OR ON A STAND
+ * ALONE BASIS."
+ */
+
 require_once $gfcommon.'pm/import_utils.php';
 
 $input_file = getUploadedFile('userfile');
 if (is_uploaded_file($input_file['tmp_name'])) {
-	$size =	$input_file['size'];
 	$handle = fopen($input_file['tmp_name'], 'r');
 	$tasks = array();
 	
-	while (($cols = fgetcsv($handle, 4096, ",")) !== FALSE) {
+	// Detect separator & if headers are present or not.
+	$sep = ',';
+	$values = fgetcsv($handle, 4096, $sep);
+	if (count($values) == 1) {
+		$sep = ';';
+		fseek($handle, 0);
+		$values = fgetcsv($handle, 4096, $sep);
+	}
+	$headers = (in_array('project_task_id', $values) && in_array('title', $values));
 
-		$resources = array();
-		for ($i=12;$i<17;$i++) {
-			if (trim($cols[$i]) != '') {
-				$resources[] = array('user_name'=>$cols[$i]);
+	// Rewind the file.
+	fseek($handle, 0);
+	
+	if ($headers) {
+		// Headers are given in the file (first line).
+		$headers = array_flip(fgetcsv($handle, 4096, $sep));
+		while (($values = fgetcsv($handle, 4096, $sep)) !== false) {
+			$task = array();
+			foreach($headers as $name => $id) {
+				if ($name == 'project_task_id') $name = 'id';
+				if ($name == 'title') $name = 'name';
+				$task[$name] = $values[$id];
 			}
+			$tasks[] = $task;
 		}
-
-		$dependentOn = array();
-
-		for ($i=17;$i<30;$i=$i+3) {
-			if (trim($cols[$i]) != '') {
-				$dependentOn[] = array('task_id'=>$cols[$i], 'msproj_id'=>$cols[$i+1], 'task_name'=>'', 'link_type'=>$cols[$i+2]);
+	} else {
+		// Original code (default format, no headers)
+		while (($cols = fgetcsv($handle, 4096, $sep)) !== false) {
+	
+			$resources = array();
+			for ($i=12;$i<17;$i++) {
+				if (trim($cols[$i]) != '') {
+					$resources[] = array('user_name'=>$cols[$i]);
+				}
 			}
+	
+			$dependentOn = array();
+	
+			for ($i=17;$i<30;$i=$i+3) {
+				if (trim($cols[$i]) != '') {
+					$dependentOn[] = array('task_id'=>$cols[$i], 'msproj_id'=>$cols[$i+1], 'task_name'=>'', 'link_type'=>$cols[$i+2]);
+				}
+			}
+	
+			$tasks[] = array('id'=>$cols[0],
+					'msproj_id'=>$cols[1],
+					'parent_id'=>$cols[2],
+					'parent_msproj_id'=>$cols[3],
+					'name'=>$cols[4],
+					'duration'=>$cols[5],
+					'work'=>$cols[6],
+					'start_date'=>$cols[7],
+					'end_date'=>$cols[8],
+					'percent_complete'=>$cols[9],	
+					'priority'=>$cols[10],
+					'resources'=>$resources,
+					'dependenton'=>$dependentOn,
+					'notes'=>$cols[11]);
 		}
-
-		$tasks[] = array('id'=>$cols[0],
-				'msproj_id'=>$cols[1],
-				'parent_id'=>$cols[2],
-				'parent_msproj_id'=>$cols[3],
-				'name'=>$cols[4],
-				'duration'=>$cols[5],
-				'work'=>$cols[6],
-				'start_date'=>$cols[7],
-				'end_date'=>$cols[8],
-				'percent_complete'=>$cols[9],	
-				'priority'=>$cols[10],
-				'resources'=>$resources,
-				'dependenton'=>$dependentOn,
-				'notes'=>$cols[11]);
 	}
+	$res=&pm_import_tasks($group_project_id, $tasks);
 	
+	if ($res['success']) {
+		$feedback .= 'Import Was Successful';
+	} else {
+		$feedback .= $res['errormessage'];
+	}
 }
-
-$res=&pm_import_tasks($group_project_id, $tasks);
-
-if ($res['success']) {
-	$feedback .= 'Import Was Successful';
-} else {
-	$feedback .= $res['errormessage'];
-}
-
 ?>

Modified: trunk/gforge/www/pm/task.php
===================================================================
--- trunk/gforge/www/pm/task.php	2010-01-27 16:44:22 UTC (rev 8693)
+++ trunk/gforge/www/pm/task.php	2010-01-27 19:54:13 UTC (rev 8694)
@@ -185,6 +185,16 @@
 		break;
 	}
 
+	case 'csv': {
+		include $gfwww.'pm/csv.php';
+		exit;
+	}
+
+	case 'format_csv': {
+		include $gfwww.'pm/format_csv.php';
+		exit;
+	}
+
 	case 'downloadcsv': {
 
 		if ($pg->userIsAdmin()) {
@@ -209,8 +219,9 @@
 
 	case 'postuploadcsv': {
 
-		if ($pg->userIsAdmin()) {			
+		if ($pg->userIsAdmin()) {
 			include $gfwww.'pm/postuploadcsv.php';
+			include $gfwww.'pm/browse_task.php';
 		} else {
 			exit_permission_denied();
 		}

Modified: trunk/tests/func/Tasks/AllTests.php
===================================================================
--- trunk/tests/func/Tasks/AllTests.php	2010-01-27 16:44:22 UTC (rev 8693)
+++ trunk/tests/func/Tasks/AllTests.php	2010-01-27 19:54:13 UTC (rev 8694)
@@ -44,32 +44,32 @@
  */
 
 if (!defined('PHPUnit_MAIN_METHOD')) {
-    define('PHPUnit_MAIN_METHOD', 'Tasks_AllTests::main');
+	define('PHPUnit_MAIN_METHOD', 'Tasks_AllTests::main');
 }
- 
+
 require_once 'PHPUnit/Framework.php';
 require_once 'PHPUnit/TextUI/TestRunner.php';
- 
-require_once dirname(__FILE__).'/csv.php';
- 
+
+require_once dirname(__FILE__).'/createTask.php';
+
 class Tasks_AllTests
 {
-    public static function main()
-    {
-        PHPUnit_TextUI_TestRunner::run(self::suite());
-    }
- 
-    public static function suite()
-    {
-        $suite = new PHPUnit_Framework_TestSuite('PHPUnit Framework');
- 
-        $suite->addTestSuite('ExportCSV');
- 
-        return $suite;
-    }
+	public static function main()
+	{
+		PHPUnit_TextUI_TestRunner::run(self::suite());
+	}
+
+	public static function suite()
+	{
+		$suite = new PHPUnit_Framework_TestSuite('PHPUnit Framework');
+
+		$suite->addTestSuite('CreateTask');
+
+		return $suite;
+	}
 }
- 
+
 if (PHPUnit_MAIN_METHOD == 'Tasks_AllTests::main') {
-    Framework_AllTests::main();
+	Framework_AllTests::main();
 }
 ?>

Added: trunk/tests/func/Tasks/createTask.php
===================================================================
--- trunk/tests/func/Tasks/createTask.php	                        (rev 0)
+++ trunk/tests/func/Tasks/createTask.php	2010-01-27 19:54:13 UTC (rev 8694)
@@ -0,0 +1,471 @@
+<?php
+/*
+ * Copyright (C) 2010 Alain Peyrat, Alcatel-Lucent
+ *
+ * This file is part of FusionForge.
+ *
+ * FusionForge is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published
+ * by the Free Software Foundation; either version 2 of the License,
+ * or (at your option) any later version.
+ *
+ * FusionForge is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with FusionForge; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+ * USA
+ */
+
+/*
+ * Standard Alcatel-Lucent disclaimer for contributing to open source
+ *
+ * "The test suite ("Contribution") has not been tested and/or
+ * validated for release as or in products, combinations with products or
+ * other commercial use. Any use of the Contribution is entirely made at
+ * the user's own responsibility and the user can not rely on any features,
+ * functionalities or performances Alcatel-Lucent has attributed to the
+ * Contribution.
+ *
+ * THE CONTRIBUTION BY ALCATEL-LUCENT IS PROVIDED AS IS, WITHOUT WARRANTY
+ * OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+ * WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, COMPLIANCE,
+ * NON-INTERFERENCE AND/OR INTERWORKING WITH THE SOFTWARE TO WHICH THE
+ * CONTRIBUTION HAS BEEN MADE, TITLE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * ALCATEL-LUCENT BE LIABLE FOR ANY DAMAGES OR OTHER LIABLITY, WHETHER IN
+ * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * CONTRIBUTION OR THE USE OR OTHER DEALINGS IN THE CONTRIBUTION, WHETHER
+ * TOGETHER WITH THE SOFTWARE TO WHICH THE CONTRIBUTION RELATES OR ON A STAND
+ * ALONE BASIS."
+ */
+require_once 'func/Testing/SeleniumGforge.php';
+
+class CreateTask extends FForge_SeleniumTestCase
+{
+    function testcreateTask()
+    {
+        $this->setUpTasks();
+        $this->createSomeTasks();
+        // $this->browseTasks();
+        $this->setTaskPriority();
+        $this->completeTask();
+        $this->closeTask();
+        $this->deleteTask();
+        // $this->assignTask();
+        $this->orderTask();
+        $this->registerEmailAddressForNotification();
+        // $this->createSubproject();
+        // $this->createPrivateSubproject();
+        $this->displayGANTT();
+        //$this->displayActivityReportByDeveloper();
+        //$this->displayActivityReportBySubproject();
+        $this->exportCSV();
+    }
+
+    function setUpTasks()
+    {
+        $this->init();
+
+        // Initialize "rep_time_tracking" table
+        $this->click("link=Reporting");
+        $this->waitForPageToLoad("30000");
+
+        $this->click("link=Initialize / Rebuild Reporting Tables");
+        $this->waitForPageToLoad("30000");
+        $this->click("im_sure");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+
+//        $this->switchUser('uadmin');
+        $this->open( ROOT );
+        $this->waitForPageToLoad("30000");
+        $this->click("link=ProjectA");
+        $this->waitForPageToLoad("30000");
+
+        $this->click("link=Task Manager");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("To Do"));
+        $this->assertTrue($this->isTextPresent("Next Release"));
+        $this->click("link=To Do");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("No Matching Tasks found"));
+    }
+
+    function createSomeTasks()
+    {
+        // Create a first task
+        $this->click("link=Add task");
+        $this->waitForPageToLoad("30000");
+        $this->type("summary", "Task1: Hello Paris");
+        $this->type("details", "Details: Hello Paris");
+        $this->type("hours", "10");
+        $this->click("//td[@id='main']/form/table/tbody/tr[9]/td/input");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task Created Successfully"));
+
+        // Create a second task
+        $this->click("link=Add task");
+        $this->waitForPageToLoad("30000");
+        $this->type("summary", "Task2: Hello France");
+        $this->type("details", "Details: Hello France");
+        $this->type("hours", "15");
+        $this->click("//td[@id='main']/form/table/tbody/tr[9]/td/input");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task Created Successfully"));
+
+        // Create a third task
+        $this->click("link=Add task");
+        $this->waitForPageToLoad("30000");
+        $this->type("summary", "Task3: Hello World");
+        $this->type("details", "Details: Hello World");
+        $this->type("hours", "20");
+        $this->click("//td[@id='main']/form/table/tbody/tr[9]/td/input");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task Created Successfully"));
+    }
+
+    function browseTasks()
+    {
+        // Let us check that the 3 tasks appear on the list of tasks
+        $this->click("link=Tasks");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=To Do");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task1: Hello Paris"));
+        $this->assertTrue($this->isTextPresent("Task2: Hello France"));
+        $this->assertTrue($this->isTextPresent("Task3: Hello World"));
+
+        // Let us assign tasks to users so that we can filter by assignee
+        $this->click("link=exact:Task1: Hello Paris");
+        $this->waitForPageToLoad("30000");
+        $this->removeSelection("assigned_to[]", "label=None");
+        $this->addSelection("assigned_to[]", "label=ucoredev Lastname");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=exact:Task2: Hello France");
+        $this->waitForPageToLoad("30000");
+        $this->removeSelection("assigned_to[]", "label=None");
+        $this->addSelection("assigned_to[]", "label=ucontrib Lastname");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=exact:Task3: Hello World");
+        $this->waitForPageToLoad("30000");
+        $this->removeSelection("assigned_to[]", "label=None");
+        $this->addSelection("assigned_to[]", "label=ucontrib Lastname");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+
+        // There should not be unassigned tasks
+        $this->select("_assigned_to", "label=Unassigned");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("No Matching Tasks found"));
+
+        // Tasks 2 and 3 should be assigned to ucontrib
+        $this->select("_assigned_to", "label=ucontrib Lastname");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task2:"));
+        $this->assertTrue($this->isTextPresent("Task3:"));
+
+        // Task 1 should be assigned to ucoredev
+        $this->select("_assigned_to", "label=ucoredev Lastname");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task1:"));
+
+        // "Any" should show the 3 tasks
+        $this->select("_assigned_to", "label=Any");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task1:"));
+        $this->assertTrue($this->isTextPresent("Task2:"));
+        $this->assertTrue($this->isTextPresent("Task3:"));
+
+        // Let use close a task to sort by status
+        $this->click("link=exact:Task1: Hello Paris");
+        $this->waitForPageToLoad("30000");
+        $this->click("status_id");
+        $this->select("status_id", "label=Closed");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+
+        // Select open tasks
+        $this->select("_status", "label=Open");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task2:"));
+        $this->assertTrue($this->isTextPresent("Task3:"));
+
+        // Select closed tasks
+        $this->select("_status", "label=Closed");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task1:"));
+
+        // Select "Any" status
+        $this->select("_status", "label=Any");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task1:"));
+        $this->assertTrue($this->isTextPresent("Task2:"));
+        $this->assertTrue($this->isTextPresent("Task3:"));
+
+        // Let us add categories to sort by category
+        $this->click("link=Admin");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=Add/Edit Categories");
+        $this->waitForPageToLoad("30000");
+        $this->type("name", "mycategory");
+        $this->click("post_changes");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Category Inserted"));
+        $this->type("name", "yourcategory");
+        $this->click("post_changes");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Category Inserted"));
+        $this->assertTrue($this->isTextPresent("mycategory"));
+        $this->assertTrue($this->isTextPresent("yourcategory"));
+
+        // Set Task1 to mycategory
+        $this->click("link=To Do: Browse tasks");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=exact:Task1: Hello Paris");
+        $this->waitForPageToLoad("30000");
+        $this->select("category_id", "label=mycategory");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+
+        // Set Task2 to yourcategory
+        $this->click("link=To Do: Browse tasks");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=exact:Task2: Hello France");
+        $this->waitForPageToLoad("30000");
+        $this->select("category_id", "label=yourcategory");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+
+        // Select "Any" category
+        $this->select("_category_id", "label=Any");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->select("_order", "label=Task Summary");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task1:"));
+        $this->assertTrue($this->isTextPresent("Task2:"));
+        $this->assertTrue($this->isTextPresent("Task3:"));
+
+        // Select "mycategory" category
+        $this->select("_category_id", "label=mycategory");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task1:"));
+        $this->assertFalse($this->isTextPresent("Task2:"));
+        $this->assertFalse($this->isTextPresent("Task3:"));
+
+        // Select "yourcategory" category
+        $this->select("_category_id", "label=yourcategory");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertFalse($this->isTextPresent("Task1:"));
+        $this->assertTrue($this->isTextPresent("Task2:"));
+        $this->assertFalse($this->isTextPresent("Task3:"));
+
+        // Set Detail view to Detailed
+        $this->click("link=To Do: Browse tasks");
+        $this->waitForPageToLoad("30000");
+        $this->select("_category_id", "label=Any");
+        $this->select("_view", "label=Detailed");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Details: Hello Paris"));
+        $this->assertTrue($this->isTextPresent("Details: Hello France"));
+        $this->assertTrue($this->isTextPresent("Details: Hello World"));
+
+        // Set Detail view to Summary
+        $this->select("_view", "label=Summary");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertFalse($this->isTextPresent("Details: Hello"));
+
+    }
+
+    function setTaskPriority()
+    {
+        // Set the priority of a task
+        $this->click("link=exact:Task2: Hello France");
+        $this->waitForPageToLoad("30000");
+        $this->select("priority", "label=5 - Highest");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+
+        // Check the priority is OK
+        $this->click("link=exact:Task2: Hello France");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Highest"));
+    }
+
+    function completeTask()
+    {
+        // Set the completing value of a task
+        $this->select("percent_complete", "label=45%");
+        $this->click("//option[@value='45']");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task Updated Successfully"));
+
+        // Check the percentage is OK
+        $this->click("link=exact:Task2: Hello France");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("45%"));
+    }
+
+    function closeTask()
+    {
+        // Done in browseTasks()
+    }
+
+    function deleteTask()
+    {
+        // Delete a task
+        $this->click("link=To Do: Browse tasks");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=exact:Task3: Hello World");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=Delete this task");
+        $this->waitForPageToLoad("30000");
+        $this->click("confirm_delete");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task Successfully Deleted"));
+
+        // Let us check that Task3 no longer appears on the list of tasks
+        $this->click("link=Tasks");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=To Do");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Task1: Hello Paris"));
+        $this->assertTrue($this->isTextPresent("Task2: Hello France"));
+        $this->assertFalse($this->isTextPresent("Task3: Hello World"));
+    }
+
+    function assignTask()
+    {
+        $this->open("/pm/task.php?group_id=6&group_project_id=2");
+        $this->click("link=exact:Task1: Hello Paris");
+        $this->waitForPageToLoad("30000");
+        $this->addSelection("assigned_to[]", "label=ucontrib Lastname");
+        $this->removeSelection("assigned_to[]", "label=ucoredev Lastname");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+
+        $this->switchUser('ucontrib');
+        $this->open( ROOT );
+        $this->waitForPageToLoad("30000");
+        $this->click("link=ProjectA");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=My Page");
+        $this->waitForPageToLoad("30000");
+        // You cannot click on "Assigned Tasks" tabs,
+        // but the text is present in the page anyway.
+        // $this->click("link=Assigned Tasks");
+        $this->assertTrue($this->isTextPresent("Task2: Hello France"));
+        $this->switchUser('uadmin');
+        $this->open( ROOT );
+        $this->waitForPageToLoad("30000");
+    }
+
+    function orderTask()
+    {
+    }
+
+    function registerEmailAddressForNotification()
+    {
+    }
+
+    function createSubproject()
+    {
+        $this->open("/pm/task.php?group_id=6");
+        $this->click("link=Project Admin");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=Tools");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=Task Manager Admin");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=Add a Subproject");
+        $this->waitForPageToLoad("30000");
+        $this->type("project_name", "public");
+        $this->type("description", "This is a public subproject");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Subproject Inserted"));
+        $this->click("link=Task Manager");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("This is a public subproject"));
+    }
+
+    function createPrivateSubproject()
+    {
+        $this->open("/pm/task.php?group_id=6");
+        $this->click("link=Project Admin");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=Tools");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=Task Manager Admin");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=Add a Subproject");
+        $this->waitForPageToLoad("30000");
+        $this->click("//input[@name='is_public' and @value='0']");
+        $this->type("project_name", "private");
+        $this->type("description", "This is a private subproject");
+        $this->click("submit");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Subproject Inserted"));
+        $this->click("link=Task Manager");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("This is a private subproject"));
+    }
+
+    function displayGANTT()
+    {
+        // Display GANTT diagram
+        $this->click("link=Tasks");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=To Do");
+        $this->waitForPageToLoad("30000");
+        $this->click("link=Gantt Chart");
+        $this->waitForPopUp("Gantt_Chart", "30000");
+    }
+
+    function displayActivityReportByDeveloper()
+    {
+        // Display activity report by developer
+        $this->click("link=Reporting");
+        $this->waitForPageToLoad("30000");
+        $this->select("what", "label=Report by Assignee");
+        $this->click("//input[@value='Show']");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Tasks By Assignee"));
+        $this->assertTrue($this->isTextPresent("ucontrib"));
+        $this->assertFalse($this->isTextPresent("ucoredev"));
+    }
+
+    function displayActivityReportBySubproject()
+    {
+        // Display activity report by subproject
+        $this->select("what", "label=Report by Subproject");
+        $this->click("//input[@value='Show']");
+        $this->waitForPageToLoad("30000");
+        $this->assertTrue($this->isTextPresent("Tasks By Category"));
+        $this->assertTrue($this->isTextPresent("To Do"));
+    }
+
+    function exportCSV()
+    {
+    }
+}
+?>

Deleted: trunk/tests/func/Tasks/csv.php
===================================================================
--- trunk/tests/func/Tasks/csv.php	2010-01-27 16:44:22 UTC (rev 8693)
+++ trunk/tests/func/Tasks/csv.php	2010-01-27 19:54:13 UTC (rev 8694)
@@ -1,94 +0,0 @@
-<?php
-/*
- * Copyright (C) 2008 Alain Peyrat <aljeux at free.fr>
- * Copyright (C) 2009 Alain Peyrat, Alcatel-Lucent
- *
- * This file is part of FusionForge.
- *
- * FusionForge is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published
- * by the Free Software Foundation; either version 2 of the License,
- * or (at your option) any later version.
- *
- * FusionForge is distributed in the hope that it will be useful, but
- * WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with FusionForge; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
- * USA
- */
-
-/*
- * Standard Alcatel-Lucent disclaimer for contributing to open source
- *
- * "The test suite ("Contribution") has not been tested and/or
- * validated for release as or in products, combinations with products or
- * other commercial use. Any use of the Contribution is entirely made at
- * the user's own responsibility and the user can not rely on any features,
- * functionalities or performances Alcatel-Lucent has attributed to the
- * Contribution.
- *
- * THE CONTRIBUTION BY ALCATEL-LUCENT IS PROVIDED AS IS, WITHOUT WARRANTY
- * OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
- * WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, COMPLIANCE,
- * NON-INTERFERENCE AND/OR INTERWORKING WITH THE SOFTWARE TO WHICH THE
- * CONTRIBUTION HAS BEEN MADE, TITLE AND NON-INFRINGEMENT. IN NO EVENT SHALL
- * ALCATEL-LUCENT BE LIABLE FOR ANY DAMAGES OR OTHER LIABLITY, WHETHER IN
- * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
- * CONTRIBUTION OR THE USE OR OTHER DEALINGS IN THE CONTRIBUTION, WHETHER
- * TOGETHER WITH THE SOFTWARE TO WHICH THE CONTRIBUTION RELATES OR ON A STAND
- * ALONE BASIS."
- */
-
-require_once 'func/Testing/SeleniumGforge.php';
-
-class ExportCSV extends FForge_SeleniumTestCase
-{
-	function testexportCSV()
-	{
-		$this->createProject('ProjectA');
-
-		// Test: Create a simple bug report (Message1/Text1).
-		$this->open( BASE );
-		$this->click("link=ProjectA");
-		$this->waitForPageToLoad("30000");
-		$this->click("link=Task Manager");
-		$this->waitForPageToLoad("30000");
-		$this->assertTrue($this->isTextPresent("To Do"));
-		$this->assertTrue($this->isTextPresent("Next Release"));
-		$this->click("link=To Do");
-		$this->waitForPageToLoad("30000");
-		$this->assertTrue($this->isTextPresent("No Matching Tasks found"));
-
-		$this->click("link=Add task");
-		$this->waitForPageToLoad("30000");
-		$this->type("summary", "Task1: Hello Paris");
-		$this->type("details", "Hello Paris");
-		$this->type("hours", "10");
-		$this->click("submit");
-		$this->waitForPageToLoad("30000");
-		$this->assertTrue($this->isTextPresent("Task Created Successfully"));
-
-		$this->click("link=Add task");
-		$this->waitForPageToLoad("30000");
-		$this->type("summary", "Task2: Hello France");
-		$this->type("details", "Hello France");
-		$this->type("hours", "15");
-		$this->click("submit");
-		$this->waitForPageToLoad("30000");
-		$this->assertTrue($this->isTextPresent("Task Created Successfully"));
-
-		$this->click("link=Add task");
-		$this->waitForPageToLoad("30000");
-		$this->type("summary", "Task3: Hello World");
-		$this->type("details", "Hello World");
-		$this->type("hours", "20");
-		$this->click("submit");
-		$this->waitForPageToLoad("30000");
-		$this->assertTrue($this->isTextPresent("Task Created Successfully"));
-	}
-}
-?>




More information about the Fusionforge-commits mailing list