tce_functions_install.php 15.1 KB
Newer Older
nick's avatar
nick committed
1
<?php
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
2
3
4
//============================================================+
// File name   : tce_functions_install.php
// Begin       : 2002-05-13
tecnickcom's avatar
tecnickcom committed
5
// Last Update : 2013-10-23
nick's avatar
nick committed
6
//
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
7
8
9
10
11
12
// Description : Installation functions for TCExam.
//
// Author: Nicola Asuni
//
// (c) Copyright:
//               Nicola Asuni
Nick's avatar
Nick committed
13
//               Tecnick.com LTD
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
14
15
16
//               www.tecnick.com
//               info@tecnick.com
//
nick's avatar
nick committed
17
// License:
tecnickcom's avatar
tecnickcom committed
18
//    Copyright (C) 2004-2013  Nicola Asuni - Tecnick.com LTD
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
19
20
21
22
23
//    See LICENSE.TXT file for more information.
//============================================================+

/**
 * Install TCExam database.
tecnickcom's avatar
tecnickcom committed
24
25
26
27
28
29
30
31
32
33
 * @param string $db_type database type (MySQL)
 * @param string $db_host database host
 * @param string $db_port database port number
 * @param string $db_user database user
 * @param string $db_password database password
 * @param string $database_name database name
 * @param string $table_prefix prefix for tables
 * @param boolean $drop_database if true drop existing database
 * @param boolean $create_new if true creates new database
 * @param string $progress_log log file name
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
34
35
36
37
38
39
40
 * @return boolean True in case of success, False otherwise.
 */
function F_install_database($db_type, $db_host, $db_port, $db_user, $db_password, $database_name, $table_prefix, $drop_database, $create_new, $progress_log) {
	ini_set('memory_limit', '256M');
	define ('K_DATABASE_TYPE', $db_type); // database type (for Database Abstraction Layer)
	// Load the Database Abstraction Layer for selected DATABASE type
	switch (K_DATABASE_TYPE) {
nick's avatar
nick committed
41
		case 'ORACLE': {
nicolaasuni's avatar
9.0.029    
nicolaasuni committed
42
43
44
			require_once('../shared/code/tce_db_dal_oracle.php');
			break;
		}
nick's avatar
nick committed
45
		case 'POSTGRESQL': {
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
46
47
48
			require_once('../shared/code/tce_db_dal_postgresql.php');
			break;
		}
nick's avatar
nick committed
49
		case 'MYSQL': {
tecnickcom's avatar
tecnickcom committed
50
51
52
53
			require_once('../shared/code/tce_db_dal_mysqli.php');
			break;
		}
		case 'MYSQLDEPRECATED': {
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
54
55
			require_once('../shared/code/tce_db_dal_mysql.php');
			break;
nick's avatar
nick committed
56
57
58
		}
		default: {
			return false;
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
59
60
		}
	}
nick's avatar
nick committed
61
62
	echo "\n".'<li>create or replace database and get connection........';
	error_log('  create or replace database and get connection'."\n", 3, $progress_log); //log info
nicolaasuni's avatar
9.0.029    
nicolaasuni committed
63
	if ($db = F_create_database(K_DATABASE_TYPE, $db_host, $db_port, $db_user, $db_password, $database_name, $table_prefix, $drop_database, $create_new)) { //create database if not exist
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
64
65
66
67
		echo '<span style="color:#008000">[OK]</span></li>';
		echo "\n".'<li>create database tables..........';
		error_log('  [START] create database tables'."\n", 3, $progress_log); //log info
		// process structure sql file
nick's avatar
nick committed
68
		if (F_execute_sql_queries($db, strtolower(K_DATABASE_TYPE).'_db_structure.sql', 'tce_', $table_prefix, $progress_log)) {
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
69
			echo '<span style="color:#008000">[OK]</span></li>';
nick's avatar
nick committed
70
			error_log('  [END:OK] create database tables'."\n", 3, $progress_log); //log info
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
71
72
			echo "\n".'<li>fill tables with default data...';
			error_log('  [START] fill tables with default data'."\n", 3, $progress_log); //log info
nick's avatar
nick committed
73
74
			// process data sql file
			if (F_execute_sql_queries($db, 'db_data.sql', 'tce_', $table_prefix, $progress_log)) {
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
75
76
77
				echo '<span style="color:#008000">[OK]</span></li>';
				error_log('  [END:OK] fill tables with default data'."\n", 3, $progress_log); //log info
			} else {
tecnickcom's avatar
tecnickcom committed
78
79
				echo '<span style="color:#CC0000">[ERROR '.F_db_error($db).']</span></li>';
				error_log('  [END:ERROR] fill tables with default data: '.F_db_error($db)."\n", 3, $progress_log); //log info
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
80
81
82
				return false;
			}
		} else {
tecnickcom's avatar
tecnickcom committed
83
84
			echo '<span style="color:#CC0000">[ERROR '.F_db_error($db).']</span></li>';
			error_log('  [END:ERROR] create database tables: '.F_db_error($db)."\n", 3, $progress_log); //log info
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
85
86
87
			return false;
		}
	} else {
tecnickcom's avatar
tecnickcom committed
88
89
		echo '<span style="color:#CC0000">[ERROR: '.F_db_error($db).']</span></li>';
		error_log('  [END:ERROR] could not connect to database: '.F_db_error($db)."\n", 3, $progress_log); //log info
nick's avatar
nick committed
90
		return false;
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
91
92
93
94
95
96
97
98
	}
	flush();
	return true;
}


/**
 * Parses an SQL file and execute queries.
tecnickcom's avatar
tecnickcom committed
99
100
101
102
103
 * @param string $db database connector
 * @param string $sql_file file to parse
 * @param string $search string to replace
 * @param string $replace replace string
 * @param string $progress_log log file name
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
104
105
106
107
 * @return boolean true in case of success, false otherwise.
 */
function F_execute_sql_queries($db, $sql_file, $search, $replace, $progress_log) {
	ini_set('memory_limit', -1); // remove memory limit
nick's avatar
nick committed
108

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
	$sql_data = @fread(@fopen($sql_file, 'r'), @filesize($sql_file)); //open and read file
	if ($search) {
		$sql_data = str_replace($search, $replace, $sql_data); // execute search and replace for the given parameters
	}
	$sql_data = str_replace("\r", '', $sql_data); // remove CR
	$sql_data = "\n".$sql_data; //prepare string for replacements
	$sql_data = preg_replace("/\/\*([^\*]*)\*\//si", ' ', $sql_data); // remove comments (/* ... */)
	$sql_data = preg_replace("/\n([\s]*)\#([^\n]*)/si", '', $sql_data); // remove comments (lines starting with '#' (MySQL))
	$sql_data = preg_replace("/\n([\s]*)\-\-([^\n]*)/si", '', $sql_data); // remove comments (lines starting with '--' (PostgreSQL))
	$sql_data = preg_replace("/;([\s]*)\n/si", ";\r", $sql_data); // mark valid new lines
	$sql_data = str_replace("\n", " ", $sql_data); // remove carriage returns
	$sql_data = preg_replace("/(;\r)$/si", '', $sql_data); // remove last ";\r"
	$sql_query = explode(";\r", trim($sql_data)); // split sql string into SQL statements
	//execute queries
	while(list($key, $sql) = each($sql_query)) { //for query on sql file
		error_log('    [SQL] '.$key."\n", 3, $progress_log); //create progress log file
		echo ' '; //print something to keep browser live
		if (($key % 300) == 0) { //force flush output every 300 processed queries
			echo '<!-- '.$key.' -->'."\n"; flush(); //force flush output to browser
		}
		if(!$r = F_db_query($sql, $db)) {
			return FALSE;
		}
nick's avatar
nick committed
132
	}
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
133
134
135
136
137
	return TRUE;
}

/**
 * Create new database. Existing database will be dropped.
nicolaasuni's avatar
9.0.029    
nicolaasuni committed
138
 * Oracle databases must be created manually (create the tcexam user and set the database name equal to user name)
tecnickcom's avatar
tecnickcom committed
139
140
141
142
143
144
145
146
147
148
 * @param string $host Database server path. It can also include a port number. e.g. "hostname:port" or a path to a local socket e.g. ":/path/to/socket" for the localhost. Note: Whenever you specify "localhost" or "localhost:port" as server, the MySQL client library will override this and try to connect to a local socket (named pipe on Windows). If you want to use TCP/IP, use "127.0.0.1" instead of "localhost". If the MySQL client library tries to connect to the wrong local socket, you should set the correct path as mysql.default_host in your PHP configuration and leave the server field blank.
 * @param string $dbtype database type ('MYSQL' or 'POSTGREQL')
 * @param string $host database host
 * @param string $port database port
 * @param string $user Name of the user that owns the server process.
 * @param string $password Password of the user that owns the server process.
 * @param string $database Database name.
 * @param string $table_prefix prefix for tables
 * @param boolean $drop if true drop existing database
 * @param boolean $create if true creates new database
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
149
150
 * @return database link identifier on success, FALSE otherwise.
 */
nicolaasuni's avatar
9.0.029    
nicolaasuni committed
151
function F_create_database($dbtype, $host, $port, $user, $password, $database, $table_prefix, $drop, $create) {
nick's avatar
nick committed
152
153
	// open default connection
	if ($drop OR $create) {
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
154
		if ($db = @F_db_connect($host, $port, $user, $password)) {
nicolaasuni's avatar
9.0.029    
nicolaasuni committed
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
			if ($dbtype == 'ORACLE') {
				if ($drop) {
					$table_prefix = strtoupper($table_prefix);
					// DROP sequences
					$sql = 'select \'DROP SEQUENCE \'||sequence_name||\'\' from user_sequences where sequence_name like \''.$table_prefix.'%\'';
					if($r = @F_db_query($sql, $db)) {
						while($m = @F_db_fetch_array($r)) {
							@F_db_query($m[0], $db);
						}
					}
					// DROP triggers
					$sql = 'select \'DROP TRIGGER \'||trigger_name||\'\' from user_triggers where trigger_name like \''.$table_prefix.'%\'';
					if($r = @F_db_query($sql, $db)) {
						while($m = @F_db_fetch_array($r)) {
							@F_db_query($m[0], $db);
						}
					}
					// DROP tables
					$sql = 'select \'DROP TABLE \'||table_name||\' CASCADE CONSTRAINTS\' from user_tables where table_name like \''.$table_prefix.'%\'';
					if($r = @F_db_query($sql, $db)) {
						while($m = @F_db_fetch_array($r)) {
							@F_db_query($m[0], $db);
						}
					}
nick's avatar
nick committed
179
				} else {
nicolaasuni's avatar
9.0.029    
nicolaasuni committed
180
					echo '<span style="color:#000080">[SKIP DROP]</span> ';
nick's avatar
nick committed
181
				}
nick's avatar
nick committed
182
				// Note: Oracle Database automatically creates a schema when you create a user,
nicolaasuni's avatar
9.0.029    
nicolaasuni committed
183
				//       so you have to create a tcexam user before calling this.
nick's avatar
nick committed
184
			} else {
nicolaasuni's avatar
9.0.029    
nicolaasuni committed
185
186
187
				if ($drop) {
					// DROP existing database (if exist)
					@F_db_query('DROP DATABASE '.$database.'', $db);
nick's avatar
nick committed
188
				} else {
nicolaasuni's avatar
9.0.029    
nicolaasuni committed
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
					echo '<span style="color:#000080">[SKIP DROP]</span> ';
				}
				if($create) {
					// create database
					$sql = 'CREATE DATABASE '.$database.'';
					if ($dbtype == 'MYSQL') {
						$sql .= ' CHARACTER SET utf8 COLLATE utf8_unicode_ci';
					} elseif ($dbtype == 'POSTGRESQL') {
						$sql .= ' ENCODING=\'UNICODE\'';
					}
					if(!$r = @F_db_query($sql, $db)) {
						return FALSE;
					}
				} else {
					echo '<span style="color:#000080">[SKIP CREATE]</span> ';
				}
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
205
206
207
208
			}
			@F_db_close($db);
		} else {
			return FALSE;
nick's avatar
nick committed
209
210
211
212
213
214
215
216
		}
	} else {
		echo '<span style="color:#000080">[SKIP DROP AND CREATE]</span> ';
	}
	if ($db = @F_db_connect($host, $port, $user, $password, $database)) {
		return $db;
	} else {
		return FALSE;
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
217
218
219
220
221
	}
}

/**
 * Update some configuration files.
tecnickcom's avatar
tecnickcom committed
222
223
224
225
226
227
228
229
230
231
232
233
 * @param string $db_type database type (MySQL)
 * @param string $db_host database host
 * @param string $db_port database port number
 * @param string $db_user database user
 * @param string $db_password database password
 * @param string $database_name database name
 * @param string $table_prefix table prefix
 * @param string $path_host host URL
 * @param string $path_tcexam relative URL where this program is installed
 * @param string $path_main real full server path where this program is installed
 * @param string $standard_port standard http web port
 * @param string $progress_log log file name
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
234
235
236
 * @return boolean true in case of success, false otherwise
 */
function F_update_config_files($db_type, $db_host, $db_port, $db_user, $db_password, $database_name, $table_prefix, $path_host, $path_tcexam, $path_main, $standard_port, $progress_log) {
nick's avatar
nick committed
237

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
238
239
	if(!defined('PHP_VERSION_ID')) {
		$version = PHP_VERSION;
tecnickcom's avatar
tecnickcom committed
240
		define('PHP_VERSION_ID', (($version[0] * 10000) + ($version[2] * 100) + $version[4]));
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
241
242
243
244
	}
	if (PHP_VERSION_ID < 50300) {
		@set_magic_quotes_runtime(0);
	}
nick's avatar
nick committed
245

tecnickcom's avatar
tecnickcom committed
246
247
248
249
250
251
	// initialize configuration directories with default values
	
	rename('../shared/config.default', '../shared/config');
	rename('../admin/config.default', '../admin/config');
	rename('../public/config.default', '../public/config');

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
252
	$config_file = array(); // configuration files
nick's avatar
nick committed
253

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
254
255
	$config_file[0] = '../shared/config/tce_db_config.php';
	$config_file[1] = '../shared/config/tce_paths.php';
nick's avatar
nick committed
256

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
257
	// file parameters to change as regular expressions (0=>search, 1=>replace)
nick's avatar
nick committed
258
259
	$parameter = array();

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
260
	$parameter[0] = array(
nick's avatar
nick committed
261

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
262
263
264
265
266
267
268
269
		'0'  => array ('0' => "K_DATABASE_TYPE', '([^\']*)'", '1' => "K_DATABASE_TYPE', '".$db_type."'"),
		'1'  => array ('0' => "K_DATABASE_HOST', '([^\']*)'", '1' => "K_DATABASE_HOST', '".$db_host."'"),
		'2'  => array ('0' => "K_DATABASE_PORT', '([^\']*)'", '1' => "K_DATABASE_PORT', '".$db_port."'"),
		'3'  => array ('0' => "K_DATABASE_NAME', '([^\']*)'", '1' => "K_DATABASE_NAME', '".$database_name."'"),
		'4'  => array ('0' => "K_DATABASE_USER_NAME', '([^\']*)'", '1' => "K_DATABASE_USER_NAME', '".$db_user."'"),
		'5'  => array ('0' => "K_DATABASE_USER_PASSWORD', '([^\']*)'", '1' => "K_DATABASE_USER_PASSWORD', '".$db_password."'"),
		'6'  => array ('0' => "K_TABLE_PREFIX', '([^\']*)'", '1' => "K_TABLE_PREFIX', '".$table_prefix."'")
	);
nick's avatar
nick committed
270

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
271
272
273
274
275
276
	$parameter[1] = array(
		'0'  => array ('0' => "K_PATH_HOST', '([^\']*)'", '1' => "K_PATH_HOST', '".$path_host."'"),
		'1'  => array ('0' => "K_PATH_TCEXAM', '([^\']*)'", '1' => "K_PATH_TCEXAM', '".$path_tcexam."'"),
		'2'  => array ('0' => "K_PATH_MAIN', '([^\']*)'", '1' => "K_PATH_MAIN', '".$path_main."'"),
		'3'  => array ('0' => "K_STANDARD_PORT', ([^\)]*)", '1' => "K_STANDARD_PORT', ".$standard_port."")
	);
nick's avatar
nick committed
277

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
278
	while(list($key, $file_name) = each($config_file)) { //for each configuration file
nick's avatar
nick committed
279

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
280
281
282
283
284
		error_log('  [START] process file: '.basename($file_name)."\n", 3, $progress_log); //log info
		echo "\n".'<li>start process <i>'.basename($file_name).'</i> file:';
		echo "\n".'<ul>';
		//try to change file permissions (unix-like only)
		//chmod($file_name, 0777);
nick's avatar
nick committed
285

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
286
287
288
289
290
291
292
293
294
		echo "\n".'<li>open file.................';
		error_log('    open file', 3, $progress_log); //log info
		$fp = fopen($file_name, 'r+');
		if (!$fp) {
			echo '<span style="color:#CC0000">[ERROR]</span></li>';
			error_log(' [ERROR]'."\n", 3, $progress_log); //log info
		} else { // the file has been opened
			echo '<span style="color:#008000">[OK]</span></li>';
			error_log(' [OK]'."\n", 3, $progress_log); //log info
nick's avatar
nick committed
295

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
296
297
298
299
300
301
302
			//read the file
			echo "\n".'<li>read file.................';
			error_log('    read file', 3, $progress_log); //log info
			$file_data = fread($fp, filesize($file_name));
			if (!$file_data){
				echo '<span style="color:#CC0000">[ERROR]</span></li>';
				error_log(' [ERROR]'."\n", 3, $progress_log); //log info
nick's avatar
nick committed
303
			} else {
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
304
305
				echo '<span style="color:#008000">[OK]</span></li>';
				error_log(' [OK]'."\n", 3, $progress_log); //log info
nick's avatar
nick committed
306

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
307
308
309
310
				//change cfg file values
				while(list($pkey, $pval) = each($parameter[$key])) { //for each file parameter
					echo "\n".'<li>update value '.$pkey.' ...........';
					error_log('      update value '.$pkey.'', 3, $progress_log); //log info
nicolaasuni's avatar
9.0.027    
nicolaasuni committed
311
					$file_data = preg_replace('#'.$pval[0].'#', $pval[1], $file_data); //update cfg parameters
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
312
313
314
315
					echo '<span style="color:#008000">[OK]</span></li>';
					error_log(' [OK]'."\n", 3, $progress_log); //log info
				}
			}
nick's avatar
nick committed
316

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
317
318
319
320
321
322
323
			//write the file
			echo "\n".'<li>write file................';
			error_log('    write file', 3, $progress_log); //log info
			rewind ($fp);
			if (!fwrite ($fp, $file_data)) {
				echo '<span style="color:#CC0000">[ERROR]</span></li>';
				error_log(' [ERROR]'."\n", 3, $progress_log); //log info
nick's avatar
nick committed
324
			} else {
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
325
326
327
				echo '<span style="color:#008000">[OK]</span></li>';
				error_log(' [OK]'."\n", 3, $progress_log); //log info
			}
nick's avatar
nick committed
328

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
329
330
331
			if (strlen($file_data) < filesize($file_name)) {
				ftruncate ($fp, strlen($file_data)); //truncate file
			}
nick's avatar
nick committed
332

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
333
334
335
336
337
338
339
340
341
342
			echo "\n".'<li>close file................';
			error_log('    close file', 3, $progress_log); //log info
			if (fclose($fp)) {
				echo '<span style="color:#008000">[OK]</span></li>';
				error_log(' [OK]'."\n", 3, $progress_log); //log info
			} else {
				echo '<span style="color:#CC0000">[ERROR]</span></li>';
				error_log(' [ERROR]'."\n", 3, $progress_log); //log info
			}
		}
nick's avatar
nick committed
343

nicolaasuni's avatar
9.0.026    
nicolaasuni committed
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
		//try to set file permissions to read only (unix-like only)
		//chmod($file_name, 0644);
		echo "\n".'</ul>';
		echo "\n".'</li>';
		echo "\n".'<li>end process <i>'.basename($file_name).'</i> file</li>';
		error_log('  [END] process file: '.basename($file_name)."\n", 3, $progress_log); //log info
	}
	if (PHP_VERSION_ID < 50300) {
		set_magic_quotes_runtime(get_magic_quotes_gpc()); //restore magic quotes settings
	}
	flush(); // force browser output
	return TRUE;
}

//============================================================+
nick's avatar
nick committed
359
// END OF FILE
nicolaasuni's avatar
9.0.026    
nicolaasuni committed
360
//============================================================+