Files
booking/booking.import_data.inc

318 lines
12 KiB
PHP

<?php
/**
* @file
* Provide functionality to upload csv for bulk update of payment data
*/
function booking_import_data_admin()
{
global $event;
$prefix = t("<p>Upload csv file containing data to import. Minimum fields present should be <strong>nid</strong>, " .
" along with user-specified fields of <strong>!config</strong>. CSV Column names should match exactly (case sensitive).</p>",
array('!config' => variable_get('booking_import_include_fields', '')));
$prefix .= "<p>Note that only registration specific data like phone numbers, barcodes, etc can be updated, as well as study group membership and roles. Other data like room allocations cannot be uploaded at this time.</p>";
$form = array();
$form['file'] = array(
'#type' => 'file',
'#title' => t('CSV data'),
'#description' => t('Upload CSV data to be processed'),
);
$form['submit'] = array (
'#type' => 'submit',
'#value' => t('Submit'),
);
return array (
'first_para' => array (
'#type' => 'markup',
'#markup' => $prefix,
),
'form' => $form,
);
}
function booking_import_data_admin_validate($form, &$form_state) {
$file = file_save_upload('file', array(
'file_validate_extensions' => array('txt csv'), // Validate extensions.
));
// If the file passed validation:
if ($file) {
// Move the file, into the Drupal file system
if ($file = file_move($file, 'public://', FILE_EXISTS_REPLACE )) {
// Save the file for use in the submit handler.
$form_state['storage']['file'] = $file;
}
else {
form_set_error('file', t('Failed to write the uploaded file to the site\'s file folder.'));
}
}
else {
form_set_error('file', t('No file was uploaded.'));
}
}
function booking_import_data_admin_submit($form, &$form_state)
{
global $event;
$array = array();
//$expected_fields = array('nid', 'booking_amount_paid', 'booking_total_pay_reqd', 'booking_status');
$error = false;
$update_counter = 0;
$delimiter = ",";
$result_array = array();
$update_messages = array();
$datetime_fields = array('booking_outflight_origin_ts', 'booking_outflight_destination_ts', 'booking_rtrnflight_origin_ts',
'booking_rtrnflight_destination_ts','booking_dob', 'booking_passport_expiry_date');
$builtin_fields_to_import = array('nid');
$custom_fields_to_import = explode(";", variable_get('booking_import_include_fields', ''));
$fields_to_import = array_merge($builtin_fields_to_import, $custom_fields_to_import);
//get the file name from temporary storage field
$file = $form_state['storage']['file'];
// We are done with the file, remove it from storage.
unset($form_state['storage']['file']);
drupal_set_message(t('Input file uploaded successfully, filename: "@filename"', array('@filename' => $file->filename)));
$filename = drupal_realpath($file->uri);
//as per http://stackoverflow.com/questions/4541749/fgetcsv-fails-to-read-line-ending-in-mac-formatted-csv-file-any-better-solution
ini_set("auto_detect_line_endings", "1");
//convert csv to associative array
//based on http://stackoverflow.com/questions/4801895/csv-to-associative-array
if( ($handle = fopen( $filename, "r")) !== FALSE) {
$rowCounter = 0;
while (($rowData = fgetcsv($handle, 0, $delimiter)) !== FALSE) {
if( 0 === $rowCounter) {
$headerRecord = $rowData;
} else {
foreach( $rowData as $key => $value) {
$array[$rowCounter - 1][ $headerRecord[$key] ] = $value;
}
}
$rowCounter++;
}
fclose($handle);
}
else //unable to open file
{
drupal_set_message("Error: Unable to open input file " . $filename, 'error', FALSE);
return;
}
//watchdog('booking', "<pre>Import data:\n@info</pre>", array('@info' => print_r( $array, true)));
//process the input data
foreach ($array as $record)
{
$rows = 0;
//watchdog('booking', "<pre>Processing row data:\n@info</pre>", array('@info' => print_r( $record, true)));
$update_counter++;
$update_text = "";
$update_array = array();
$studygroups_update_array = array();
$studygroup_roles_update_array = array();
//do some error checking
foreach($fields_to_import as $field)
{
/*
if (! isset($record[$field]))
watchdog('booking', 'Non-set field !field: !info', array ('!field' => $field, '!info' => var_export($record, TRUE)));
if ($record[$field] == '')
watchdog('booking', 'Blank field !field: !info', array ('!field' => $field, '!info' => var_export($record, TRUE)));
*/
//make sure to skip the nid field since we can't update that
if ($field == 'nid')
{
//do nothing
}
//convert the booking status to the number used internally
elseif ($field == 'booking_status')
{
$update_text .= " set booking status to '" . $record[$field] . "'; ";
$update_array[$field] = _booking_status_lookup($record[$field]);
}
//check for fields that need to be converted to a timestamp from text
elseif (in_array($field, $datetime_fields))
{
$update_array[$field] = _datetime_to_ts_nonstrict($record[$field]);
$update_text .= " set '" . $field . "' to '" . $update_array[$field] . "'; ";
}
elseif ( (! isset($record[$field])) || $record[$field] == '' )
{
//drupal_set_message("Error: Unable to locate expected field '$field' in input file for record number $update_counter.", 'error', FALSE);
//watchdog('booking', 'Processing user record: @info', array ('@info' => $record['nid']));
//$error = true;
//skip to the next record
//continue 2;
}
elseif (preg_match('/session(\d{1,2})_role/i', $field, $matches))
{
$session_id = $matches[1];
//drupal_set_message(t('Setting session id !field role to value: !info', array ('!field' => $session_id, '!info' => var_export($record[$field], TRUE))));
$studygroup_roles_update_array[$session_id] = $record[$field];
}
elseif (preg_match('/session(\d{1,2})$/i', $field, $matches))
{
$session_id = $matches[1];
//drupal_set_message(t('Setting session id !field group to value: !info', array ('!field' => $session_id, '!info' => var_export($record[$field], TRUE))));
$studygroups_update_array[$session_id] = $record[$field];
}
else
{
$update_text .= " set '" . $field . "' to '" . $record[$field] . "'; ";
$update_array[$field] = $record[$field];
}
}
if (count($update_array) > 0)
{
$query = db_update('booking_person')
->fields($update_array)
->condition('nid', $record['nid']);
$rows = $query->execute();
$update_messages[] = t("Update Query:<br />@info<br />Condition: @nid<br />Rows affected: @rows<br />Values: <br /><pre>@values</pre>", array('@info' => (string) $query, '@nid' => $record['nid'], '@rows' => $rows, '@values' => print_r( $update_array, true) ));
}
//handle study group processing
$update_text .= _booking_import_studygroup_info($record['nid'], $studygroups_update_array, $studygroup_roles_update_array);
drupal_set_message(t("Updating record !nid as follows: !update", array('!nid' => $record['nid'], '!update' => $update_text)));
//$args = $query->getArguments();
/*
watchdog('booking', "Update Query:<br />@info<br />Condition: @nid<br />Rows affected: @rows<br />Values: <br /><pre>@values</pre>",
array('@info' => (string) $query, '@nid' => $record['nid'], '@rows' => $rows, '@values' => print_r( $update_array, true) ));
*/
/*
$result_array[] = t('Setting payment for id !nid to $!price of total required $!total and status to !status',
array('!nid' => $record['nid'],
'!price' => $record['booking_amount_paid'],
'!total' => $record['booking_total_pay_reqd'],
'!status' => _booking_status_lookup($record['booking_status'])
)
);
*/
/*
//TODO: output this from $result_array
drupal_set_message(t('Setting payment for id !nid to $!price of total required $!total and status to !status',
array('!nid' => $record['nid'],
'!price' => $record['booking_amount_paid'],
'!total' => $record['booking_total_pay_reqd'],
'!status' => _booking_status_lookup($record['booking_status']))
));
*/
// watchdog('booking', 'Setting payment for regn id !nid to $!price and status to !status',
// array('!nid' => $record['nid'], '!price' => $record['booking_amount_paid'], '!status' => _booking_status_lookup($record['booking_status'])));
/*
db_update('booking_person')
->fields(array(
'booking_amount_paid' => $record['booking_amount_paid'],
'booking_total_pay_reqd' => $record['booking_total_pay_reqd'],
'booking_status' => _booking_status_lookup($record['booking_status']),
))
->condition('nid', $record['nid'])
->execute();
*/
} //end processing input data
//output our results to watchdog
//watchdog('booking', '<pre>@print_r</pre>', array('@print_r', print_r( $result_array, TRUE)));
//delete the uploaded file
file_delete($file);
//let the user know we finished
drupal_set_message(t("Finished processing @count records from input file \"@filename\"",
array('@count' => $update_counter, '@filename' => $file->filename)));
watchdog('booking', "<pre>Data Import concluded:\n" . implode("\n", $update_messages) . "</pre>");
/*
// Make the storage of the file permanent
$file->status = FILE_STATUS_PERMANENT;
// Save file status.
file_save($file);
// Set a response to the user.
drupal_set_message(t('The form has been submitted and the image has been saved, filename: @filename.', array('@filename' => $file->filename)));
*/
}
/**
* Function for processing CSV import data for study groups
*/
function _booking_import_studygroup_info($nid, $studygroups_update_array, $studygroup_roles_update_array)
{
global $event;
$update_text = "";
$studygroup_roles = _booking_studygroup_role_lookup();
//update the study group mapping info if imported
foreach ($studygroup_roles_update_array as $key => $value)
{
//turn leader/helper/reserve text into the number used internally in the database
if (!is_numeric($value))
{
$role = array_search($value, $studygroup_roles);
}
else
{
$role = $value;
}
//confirm that the data is valid
if (is_numeric($key) && is_numeric($studygroups_update_array[$key]))
{
//check whether there is already a record to be updated or if it is a new record
$record_check = db_query("SELECT * FROM {booking_studygroup_mapping} WHERE booking_eventid = :eid and booking_node_id = :nid and booking_studygroup_id = :sid",
array(':eid' => $event->eid, ':nid' => $nid, ':sid' => $studygroups_update_array[$key]))->fetchObject();
//no existing record, so run a db_insert
if (! $record_check) {
$update_text .= t('Running DB insert for nid !nid, studygroup session id !id, for study group with ID !sid, for role !role;',
array ('!nid' => $nid, '!id' => $key, '!sid' => $studygroups_update_array[$key], '!role' => $role));
db_insert('booking_studygroup_mapping')
->fields(array(
'booking_eventid' => $event->eid,
'booking_node_id' => $nid,
'booking_studygroup_id' => $key,
'booking_session_id' => $studygroups_update_array[$key],
'booking_studygroup_role' => $role,
))
->execute();
}
//we found an existing record so just update it
else
{
$update_text .= t('Running DB update for nid !nid, studygroup session id !id, for study group with ID !sid, for role !role;',
array ('!nid' => $nid, '!id' => $key, '!sid' => $studygroups_update_array[$key], '!role' => $role));
db_update('booking_studygroup_mapping')
->fields(array (
'booking_session_id' => $studygroups_update_array[$key],
'booking_studygroup_role' => $role,
))
->condition('booking_node_id', $nid)
->condition('booking_studygroup_id', $key)
->execute();
}
}
}
return $update_text;
}