From b5745656c10f00e8fe6b9b7fdd9017e3107fbc55 Mon Sep 17 00:00:00 2001 From: dave Date: Mon, 20 Apr 2009 05:02:23 +0000 Subject: [PATCH] - Add user/pass support to the fair info - Add a generic fair stats uploader, can't do YSF stats yet, but it will soon (and when it does it can replace the YSF specific stats uploader) - Add better authentication to the incoming xml transport. --- admin/fair_stats.php | 382 +++++++++++++++++++++++++++++++++++++++++++ fair_info.php | 14 +- xmltransport.php | 5 + 3 files changed, 399 insertions(+), 2 deletions(-) create mode 100644 admin/fair_stats.php diff --git a/admin/fair_stats.php b/admin/fair_stats.php new file mode 100644 index 0000000..7bb2b03 --- /dev/null +++ b/admin/fair_stats.php @@ -0,0 +1,382 @@ + + Copyright (C) 2009 David Grant + + This program 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, version 2. + + This program 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 this program; see the file COPYING. If not, write to + the Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +?> + 'committee_main.php', + 'Administration' => 'admin/index.php'), + "one-click_ysf_affiliation_stats" + ); + echo "
"; + + /* SFIAB config options server side */ + $server_config = array(); + $server_config['fair_stats_participation'] = 'no'; + $server_config['fair_stats_schools_ext'] = 'no'; + $server_config['fair_stats_minorities'] = 'no'; + $server_config['fair_stats_guests'] = 'no'; + + function curl_query($fair, $xml) + { + switch($fair['type']) { + case 'sfiab': + $url = $fair['url'].'/xmltransport.php'; + break; + case 'ysf': + $url = "https://secure.ysf-fsj.ca/registration/xmlaffiliation.php"; + break; + } + + $ch = curl_init(); /// initialize a cURL session + curl_setopt ($ch, CURLOPT_URL, $url); + curl_setopt ($ch, CURLOPT_HEADER, 0); /// Header control + curl_setopt ($ch, CURLOPT_POST, 1); /// tell it to make a POST, not a GET + curl_setopt ($ch, CURLOPT_POSTFIELDS, "xml=".urlencode($xml)); /// put the query string here starting with "?" + curl_setopt ($ch, CURLOPT_RETURNTRANSFER, 1); /// This allows the output to be set into a variable $datastream + curl_setopt ($ch, CURLOPT_POSTFIELDSIZE, 0); + curl_setopt ($ch, CURLOPT_TIMEOUT, 360); + curl_setopt ($ch, CURLOPT_SSLVERSION, 3); + curl_setopt ($ch, CURLOPT_SSL_VERIFYPEER, false); + $datastream = curl_exec ($ch); /// execute the curl session and return the output to a variable $datastream + $datastream = str_replace(" standalone=\"yes\"","",$datastream); + curl_close ($ch); /// close the curl session + + switch($fair['type']) { + case 'sfiab': + $d=xml_parsexml(urldecode($datastream)); + $datastream = $d['sfiab'][0]; + break; + case 'ysf': + break; + } + return $datastream; + } + + if($_GET['year']) $year=intval($_GET['year']); + else $year=$config['FAIRYEAR']; + + if($_GET['id']) $fairs_id=intval($_GET['id']); + else if($_POST['id']) $fairs_id=intval($_POST['id']); + else $fairs_id = -1; + + if($fairs_id != -1) { + $q = mysql_query("SELECT * FROM fairs WHERE id='$fairs_id'"); + $fair = mysql_fetch_assoc($q); + } + + + if($_POST['action']=="sendstats" && $_POST['xml']) { + if(function_exists('curl_init')) { + $r = curl_query($fair, $_POST['xml']); + if($r['error'][0] == 0) + echo happy(i18n("The %1 Server said:", array($fair['name'])).' '.$r['message'][0]); + else + echo error(i18n("The %1 Server said:", array($fair['name'])).' '.$r['message'][0]); + $fairs_id = -1; + $year = $config['FAIRYEAR']; + } else { + echo error("CURL Support Missing"); + echo i18n("Your PHP installation does not support CURL. You will need to login to the YSF system as the regional coodinator and upload the XML data manually"); + send_footer(); + exit; + } + } + + + echo "
"; + $q=mysql_query("SELECT * FROM fairs WHERE `type`='sfiab' OR `type`='ysf'"); + echo ""; + echo "\n"; + while($r=mysql_fetch_object($q)) { + if($year==$r->year) $sel="selected=\"selected\""; else $sel=""; + echo "\n"; + } + echo "\n"; + echo ""; + echo "
"; + echo "
"; + echo "
"; + + if($fairs_id == -1) { + echo i18n('Statistics will be shown below this line before being sent. Please select a fair and year first.'); + /* Wait for them to select somethign before generating stats */ + send_footer(); + exit; + } + + /* Query the server to see what stats we need */ + $xmldata=array("sfiab"=>array( + "username"=>$fair['username'], + "password"=>$fair['password'], + "getstats"=>array('year'=>$year))); + + $output=""; + xmlCreateRecurse($xmldata); + $xml=$output; + + $data = curl_query($fair, $xml); + + if($data['error'][0] != 0) { + echo error("Server said: {$data['message'][0]}
"); + send_footer(); + exit; + } + + foreach($server_config as $k=>$v) { + $server_config[$k] = $data['statconfig'][0][$k][0]; + } + + /* Gather all stats, then we'll decide what to send */ + $stats = array(); + $stats['year'] = $year; + + /* Now, overwrite all the stats with what we pulled down from the server */ + if(is_array($data['stats'][0])) { + foreach($data['stats'][0] as $k=>$v) { + $stats[$k] = $v[0]; + } + } + + /* And now, overwrite all the stuff we pulled down with stats we can compute */ + + //number of schools + $q=mysql_query("SELECT COUNT(id) AS num FROM schools WHERE year='$year'"); + $r=mysql_fetch_object($q); + $stats['schools_total']=$r->num; + + //number of schools participating + $q=mysql_query("SELECT DISTINCT(students.schools_id) AS sid, schools.* + FROM students + LEFT JOIN registrations ON students.registrations_id=registrations.id + LEFT JOIN schools ON students.schools_id=schools.id + WHERE students.year='$year' + AND registrations.year='$year' + AND (registrations.status='complete' OR registrations.status='paymentpending')"); + $stats['schools_active']=mysql_num_rows($q); + $stats['students_public'] = 0; + $stats['students_private'] = 0; + $stats['schools_atrisk'] = 0; + while($si=mysql_fetch_assoc($q)) { + if($si['designate'] == 'public') + $stats['students_public']++; + if($si['designate'] == 'independent') + $stats['students_private']++; + if($si['atrisk'] == 'yes') + $stats['schools_atrisk']++; + } + + //numbers of students: + $q=mysql_query("SELECT students.*,schools.* + FROM students + LEFT JOIN registrations ON students.registrations_id=registrations.id + LEFT JOIN schools on students.schools_id=schools.id + WHERE students.year='$year' + AND registrations.year='$year' + AND (registrations.status='complete' OR registrations.status='paymentpending')"); + echo mysql_error(); + $stats['students_total'] = mysql_num_rows($q); + $stats['students_public'] = 0; + $stats['students_private'] = 0; + $stats['students_atrisk'] = 0; + $grademap = array(1=>1, 2=>1, 3=>1, 4=>4, 5=>4, 6=>4, 7=>7, 8=>7, + 9=>9, 10=>9, 11=>11, 12=>11, 13=>11); + foreach($grademap as $k=>$g) { + $stats["male_$g"] = 0; + $stats["female_$g"] = 0; + $stats["projects_$g"] = 0; + } + $unknown = array(); + while($s=mysql_fetch_assoc($q)) { + if(!in_array($s['sex'], array('male','female'))) + $unknown[$grademap[$s['grade']]]++; + else + $stats["{$s['sex']}_{$grademap[$s['grade']]}"]++; + + if($s['designate'] == 'public') + $stats['students_public']++; + if($s['designate'] == 'independent') + $stats['students_private']++; + if($s['atrisk'] == 'yes') + $stats['students_atrisk']++; + } + + foreach($unknown as $g=>$a) { + $m = round($a/2); + $f = $a - $m; + $stats["male_$g"] += $m; + $stats["female_$g"] += $f; + } + + //projects + $q=mysql_query("SELECT MAX(students.grade) AS grade FROM students + LEFT JOIN registrations ON students.registrations_id=registrations.id + LEFT JOIN projects ON projects.registrations_id=registrations.id + WHERE students.year='$year' + AND registrations.year='$year' + AND projects.year='$year' + AND (registrations.status='complete' OR registrations.status='paymentpending') + GROUP BY projects.id"); + echo mysql_error(); + while($r=mysql_fetch_assoc($q)) { + $stats["projects_{$grademap[$r['grade']]}"]++; + } + + + $q=mysql_query("SELECT COUNT(id) AS num FROM users + LEFT JOIN users_committee ON users_committee.users_id=users.id + WHERE types LIKE '%committee%' + AND year='$year' + AND users_committee.committee_active='yes' + AND deleted='no'"); + $r = mysql_fetch_object($q); + $stats['committee_members'] = $r->num; + + $q=mysql_query("SELECT COUNT(id) AS num FROM users LEFT JOIN users_judge ON users_judge.users_id=users.id + WHERE users.year='$year' + AND users.types LIKE '%judge%' + AND users.deleted='no' + AND users_judge.judge_complete='yes' + AND users_judge.judge_active='yes'"); + $r=mysql_fetch_object($q); + $stats['judges'] = $r->num; + + + /* Print all blocks the server requests */ + + if($server_config['fair_stats_participation'] == 'yes') { + $rangemap = array(1=>'1-3', 4=>'4-6', 7=>'7-8', 9=>'9-10', 11=>'11-12'); + echo ''.i18n('Fair participation').'
'; + echo '
'; + echo i18n("Number of students: %1", array($stats['students_total'])); + echo ''; + echo ''; + foreach($rangemap as $k=>$v) echo ""; + echo ''; + echo ''; + foreach($rangemap as $k=>$v) echo ""; + echo ''; + echo ''; + foreach($rangemap as $k=>$v) echo ""; + echo ''; + echo ''; + foreach($rangemap as $k=>$v) echo ""; + echo ''; + echo '
'.i18n('Grade').'
$v
'.i18n('Male').'{$stats["male_$k"]}
'.i18n('Female').'{$stats["female_$k"]}
'.i18n('Projects').'{$stats["projects_$k"]}
'; + echo '
'; + echo i18n("Number of schools: %1",array($stats['schools_total'])); + echo '
'; + echo i18n("Number of active schools: %1",array($stats['schools_active'])); + echo '
'; + echo '
'; + echo i18n("Number of committee members: %1 (note: this is number of committee members who logged in to SFIAB for the year, anyone who was active but didn't log in to SFIAB will NOT be counted)",array($stats['committee_members'])); + echo '
'; + echo i18n("Number of judges: %1",array($stats['judges'])); + echo '
'; + echo '
'; + echo '
'; + } + + if($server_config['fair_stats_schools_ext'] == 'yes') { + echo ''.i18n('Extended School/Participant data').'
'; + echo '
'; + echo i18n('Public schools: %1 (%2 students).',array( + $stats['schools_public'], $stats['students_public'])); + echo '
'; + echo i18n('Private/Independent schools: %1 (%2 students).',array( + $stats['schools_private'], $stats['students_private'])); + echo '
'; + echo i18n('At-risk/inner city schools: %1 (%2 students).',array( + $stats['schools_atrisk'], $stats['students_atrisk'])); + echo '
'; + echo '
'; + echo '
'; + } + if($server_config['fair_stats_minorities'] != '') { + echo ''.i18n('Data on minority groups').'
'; + echo '
'; + echo '
'; + echo '
'; + } + if($server_config['fair_stats_guests'] == 'yes' ) { + echo ''.i18n('Guests visiting the fair').'
'; + echo '
'; + echo '
'; + echo '
'; + } + + echo "
"; + + echo "
"; + + /* Format XML output, and print it, last chance for the user to edit it */ + + if($fair['type'] == 'ysf') { + /* Map data into YSF tags */ + } else { + $xmldata=array("sfiab"=>array( + "username"=>$fair['username'], + "password"=>$fair['password'], + "stats"=>$stats)); + } + + $output=""; + xmlCreateRecurse($xmldata); + $xml=$output; + + echo "

".i18n("The following data will be sent to")." {$fair['name']}

"; + echo "
"; + echo ""; + echo ""; + echo ""; + echo "
"; + echo "
"; + echo ""; + echo "
"; + + + echo "
";
+ print_r($fair);
+ print_r($server_config);
+ print_r($stats);
+ echo "
"; + + + + + send_footer(); +?> diff --git a/fair_info.php b/fair_info.php index 29d635a..9c1efc1 100644 --- a/fair_info.php +++ b/fair_info.php @@ -51,10 +51,14 @@ $abbrv = mysql_escape_string(stripslashes($_POST['abbrv'])); $url = mysql_escape_string($_POST['url']); $type = array_key_exists($_POST['type'], $fair_type) ? $_POST['type'] : ''; + $username = mysql_escape_string(stripslashes($_POST['username'])); + $password = mysql_escape_string(stripslashes($_POST['password'])); $q = mysql_query("UPDATE fairs SET `name`='$name', `abbrv`='$abbrv', `url`='$url', - `type`='$type' WHERE id=$id"); + `type`='$type' , `username`='$username', + `password`='$password' + WHERE id=$id"); $u['fairs_id'] = $id; user_save($u); @@ -111,7 +115,13 @@ if($_SESSION['embed'] == true) { echo ''.i18n('URL').''; if($f['url'] == '') $f['url'] = 'http://'; echo ""; - echo ''; + echo ''; + echo ''.i18n('Username').''; + echo ""; + echo ''; + echo ''.i18n('Password').''; + echo ""; + echo ''; echo ""; echo "
"; diff --git a/xmltransport.php b/xmltransport.php index 293d60e..be8a2a0 100644 --- a/xmltransport.php +++ b/xmltransport.php @@ -42,6 +42,11 @@ } $i = mysql_fetch_assoc($q); $u = user_load_by_uid($i['uid']); + if(!is_array($u) || $u['password'] == '') { + echo "1authentication failed"; + exit; + } + if($u['password'] != $password) { echo "1authentication failed"; exit;