PageRenderTime 52ms CodeModel.GetById 17ms RepoModel.GetById 0ms app.codeStats 1ms

/blog/wp-content/plugins/shopp/core/model/Customer.php

https://github.com/kennethreitz-archive/wordpress-skeleton
PHP | 725 lines | 612 code | 90 blank | 23 comment | 147 complexity | 3baf997268ae628e9625358dbd1610bf MD5 | raw file
  1. <?php
  2. /**
  3. * Customer class
  4. * Customer contact information
  5. *
  6. * @author Jonathan Davis
  7. * @version 1.0
  8. * @copyright Ingenesis Limited, 28 March, 2008
  9. * @package shopp
  10. **/
  11. class Customer extends DatabaseObject {
  12. static $table = "customer";
  13. var $login;
  14. var $looping = false;
  15. var $management = array(
  16. "account" => "account",
  17. "downloads" => "downloads",
  18. "history" => "history",
  19. "status" => "status",
  20. "logout" => "logout",
  21. );
  22. function Customer ($id=false,$key=false) {
  23. $this->init(self::$table);
  24. if ($this->load($id,$key)) return true;
  25. else return false;
  26. }
  27. function management () {
  28. global $Shopp;
  29. if (isset($_GET['acct'])) {
  30. switch ($_GET['acct']) {
  31. case "receipt": break;
  32. case "history": $this->load_orders(); break;
  33. case "downloads": $this->load_downloads(); break;
  34. // case "logout": $Shopp->Cart->logout(); break;
  35. }
  36. }
  37. if (!empty($_POST['vieworder']) && !empty($_POST['purchaseid'])) {
  38. $Purchase = new Purchase($_POST['purchaseid']);
  39. if ($Purchase->email == $_POST['email']) {
  40. $Shopp->Cart->data->Purchase = $Purchase;
  41. $Purchase->load_purchased();
  42. ob_start();
  43. include(SHOPP_TEMPLATES."/receipt.php");
  44. $content = ob_get_contents();
  45. ob_end_clean();
  46. return '<div id="shopp">'.$content.'</div>';
  47. }
  48. }
  49. if (!empty($_GET['acct']) && !empty($_GET['id'])) {
  50. $Purchase = new Purchase($_GET['id']);
  51. if ($Purchase->customer != $this->id) {
  52. new ShoppError(sprintf(__('Order number %s could not be found in your order history.','Shopp'),$Purchase->id),'customer_order_history',SHOPP_AUTH_ERR);
  53. unset($_GET['acct']);
  54. return false;
  55. } else {
  56. $Shopp->Cart->data->Purchase = $Purchase;
  57. $Purchase->load_purchased();
  58. ob_start();
  59. include(SHOPP_TEMPLATES."/receipt.php");
  60. $content = ob_get_contents();
  61. ob_end_clean();
  62. }
  63. $management = apply_filters('shopp_account_management_url',
  64. '<p><a href="'.$this->tag('url').'">&laquo; Return to Account Management</a></p>');
  65. echo '<div id="shopp">'.$management.$content.$management.'</div>';
  66. return false;
  67. }
  68. if (!empty($_POST['customer'])) {
  69. $this->updates($_POST);
  70. if ($_POST['password'] == $_POST['confirm-password'])
  71. $this->password = wp_hash_password($_POST['password']);
  72. $this->save();
  73. }
  74. }
  75. function recovery () {
  76. global $Shopp;
  77. $authentication = $Shopp->Settings->get('account_system');
  78. $errors = array();
  79. // Check email or login supplied
  80. if (empty($_POST['account-login'])) {
  81. if ($authentication == "wordpress") $errors[] = new ShoppError(__('Enter an email address or login name','Shopp'));
  82. else $errors[] = new ShoppError(__('Enter an email address','Shopp'));
  83. } else {
  84. // Check that the account exists
  85. if (strpos($_POST['account-login'],'@') !== false) {
  86. $RecoveryCustomer = new Customer($_POST['account-login'],'email');
  87. if (!$RecoveryCustomer->id)
  88. $errors[] = new ShoppError(__('There is no user registered with that email address.','Shopp'),'password_recover_noaccount',SHOPP_AUTH_ERR);
  89. } else {
  90. $user_data = get_userdatabylogin($_POST['account-login']);
  91. $RecoveryCustomer = new Customer($user_data->ID,'wpuser');
  92. if (empty($RecoveryCustomer->id))
  93. $errors[] = new ShoppError(__('There is no user registered with that login name.','Shopp'),'password_recover_noaccount',SHOPP_AUTH_ERR);
  94. }
  95. }
  96. // return errors
  97. if (!empty($errors)) return;
  98. // Generate new key
  99. $RecoveryCustomer->activation = wp_generate_password(20, false);
  100. do_action_ref_array('shopp_generate_password_key', array(&$RecoveryCustomer));
  101. $RecoveryCustomer->save();
  102. $subject = apply_filters('shopp_recover_password_subject', sprintf(__('[%s] Password Recovery Request','Shopp'),get_option('blogname')));
  103. $_ = array();
  104. $_[] = 'From: "'.get_option('blogname').'" <'.$Shopp->Settings->get('merchant_email').'>';
  105. $_[] = 'To: '.$RecoveryCustomer->email;
  106. $_[] = 'Subject: '.$subject;
  107. $_[] = '';
  108. $_[] = __('A request has beem made to reset the password for the following site and account:','Shopp');
  109. $_[] = get_option('siteurl');
  110. $_[] = '';
  111. if (isset($_POST['email-login']))
  112. $_[] = sprintf(__('Email: %s','Shopp'), $RecoveryCustomer->email);
  113. if (isset($_POST['loginname-login']))
  114. $_[] = sprintf(__('Login name: %s','Shopp'), $user_data->user_login);
  115. $_[] = '';
  116. $_[] = __('To reset your password visit the following address, otherwise just ignore this email and nothing will happen.');
  117. $_[] = '';
  118. $_[] = add_query_arg(array('acct'=>'rp','key'=>$RecoveryCustomer->activation),$Shopp->link('account'));
  119. $message = apply_filters('shopp_recover_password_message',join("\r\n",$_));
  120. if (!shopp_email($message)) {
  121. new ShoppError(__('The e-mail could not be sent.'),'password_recovery_email',SHOPP_ERR);
  122. shopp_redirect(add_query_arg('acct','recover',$Shopp->link('account')));
  123. } else {
  124. new ShoppError(__('Check your email address for instructions on resetting the password for your account.','Shopp'),'password_recovery_email',SHOPP_ERR);
  125. }
  126. }
  127. function reset_password ($activation) {
  128. global $Shopp;
  129. $authentication = $Shopp->Settings->get('account_system');
  130. $user_data = false;
  131. $activation = preg_replace('/[^a-z0-9]/i', '', $activation);
  132. $errors = array();
  133. if (empty($activation) || !is_string($activation))
  134. $errors[] = new ShoppError(__('Invalid key'));
  135. $RecoveryCustomer = new Customer($activation,'activation');
  136. if (empty($RecoveryCustomer->id))
  137. $errors[] = new ShoppError(__('Invalid key'));
  138. if (!empty($errors)) return false;
  139. // Generate a new random password
  140. $password = wp_generate_password();
  141. do_action_ref_array('password_reset', array(&$RecoveryCustomer,$password));
  142. $RecoveryCustomer->password = wp_hash_password($password);
  143. if ($authentication == "wordpress") {
  144. $user_data = get_userdata($RecoveryCustomer->wpuser);
  145. wp_set_password($password, $user_data->ID);
  146. }
  147. $RecoveryCustomer->activation = '';
  148. $RecoveryCustomer->save();
  149. $subject = apply_filters('shopp_reset_password_subject', sprintf(__('[%s] New Password','Shopp'),get_option('blogname')));
  150. $_ = array();
  151. $_[] = 'From: "'.get_option('blogname').'" <'.$Shopp->Settings->get('merchant_email').'>';
  152. $_[] = 'To: '.$RecoveryCustomer->email;
  153. $_[] = 'Subject: '.$subject;
  154. $_[] = '';
  155. $_[] = sprintf(__('Your new password for %s:','Shopp'),get_option('siteurl'));
  156. $_[] = '';
  157. if ($user_data)
  158. $_[] = sprintf(__('Login name: %s','Shopp'), $user_data->user_login);
  159. $_[] = sprintf(__('Password: %s'), $password) . "\r\n";
  160. $_[] = '';
  161. $_[] = __('Click here to login:').' '.$Shopp->link('account');
  162. $message = apply_filters('shopp_reset_password_message',join("\r\n",$_));
  163. if (!shopp_email($message)) {
  164. new ShoppError(__('The e-mail could not be sent.'),'password_reset_email',SHOPP_ERR);
  165. shopp_redirect(add_query_arg('acct','recover',$Shopp->link('account')));
  166. } else {
  167. new ShoppError(__('Check your email address for your new password.','Shopp'),'password_reset_email',SHOPP_ERR);
  168. }
  169. unset($_GET['acct']);
  170. }
  171. function load_downloads () {
  172. if (empty($this->id)) return false;
  173. $db =& DB::get();
  174. $orders = DatabaseObject::tablename(Purchase::$table);
  175. $purchases = DatabaseObject::tablename(Purchased::$table);
  176. $pricing = DatabaseObject::tablename(Price::$table);
  177. $asset = DatabaseObject::tablename(Asset::$table);
  178. $query = "SELECT p.*,f.name as filename,f.size,f.properties FROM $purchases AS p LEFT JOIN $orders AS o ON o.id=p.purchase LEFT JOIN $asset AS f ON f.parent=p.price WHERE o.customer=$this->id AND f.size > 0";
  179. $this->downloads = $db->query($query,AS_ARRAY);
  180. }
  181. function load_orders ($filters=array()) {
  182. if (empty($this->id)) return false;
  183. global $Shopp;
  184. $db =& DB::get();
  185. $where = '';
  186. if (isset($filters['where'])) $where = " AND {$filters['where']}";
  187. $orders = DatabaseObject::tablename(Purchase::$table);
  188. $purchases = DatabaseObject::tablename(Purchased::$table);
  189. $query = "SELECT o.* FROM $orders AS o LEFT JOIN $purchases AS p ON p.purchase=o.id WHERE o.customer=$this->id $where ORDER BY created DESC";
  190. $Shopp->purchases = $db->query($query,AS_ARRAY);
  191. foreach($Shopp->purchases as &$p) {
  192. $Purchase = new Purchase();
  193. $Purchase->updates($p);
  194. $p = $Purchase;
  195. }
  196. }
  197. function new_wpuser () {
  198. global $Shopp;
  199. require_once(ABSPATH."/wp-includes/registration.php");
  200. if (empty($this->login)) return false;
  201. if (username_exists($this->login)){
  202. new ShoppError(__('The login name you provided is already in use. Please choose another login name.','Shopp'),'login_exists',SHOPP_ERR);
  203. return false;
  204. }
  205. if (empty($this->password)) $this->password = wp_generate_password(12,true);
  206. // Create the WordPress account
  207. $wpuser = wp_insert_user(array(
  208. 'user_login' => $this->login,
  209. 'user_pass' => $this->password,
  210. 'user_email' => $this->email,
  211. 'display_name' => $this->firstname.' '.$this->Customer->lastname,
  212. 'nickname' => $handle,
  213. 'first_name' => $this->firstname,
  214. 'last_name' => $this->lastname
  215. ));
  216. if (!$wpuser) return false;
  217. // Link the WP user ID to this customer record
  218. $this->wpuser = $wpuser;
  219. // Send email notification of the new account
  220. wp_new_user_notification( $wpuser, $this->password );
  221. $this->password = "";
  222. if (SHOPP_DEBUG) new ShoppError('Successfully created the WordPress user for the Shopp account.',false,SHOPP_DEBUG_ERR);
  223. return true;
  224. }
  225. function exportcolumns () {
  226. $prefix = "c.";
  227. return array(
  228. $prefix.'firstname' => __('Customer\'s First Name','Shopp'),
  229. $prefix.'lastname' => __('Customer\'s Last Name','Shopp'),
  230. $prefix.'email' => __('Customer\'s Email Address','Shopp'),
  231. $prefix.'phone' => __('Customer\'s Phone Number','Shopp'),
  232. $prefix.'company' => __('Customer\'s Company','Shopp'),
  233. $prefix.'info' => __('Customer\'s Custom Information','Shopp'),
  234. $prefix.'created' => __('Customer Created Date','Shopp'),
  235. $prefix.'modified' => __('Customer Last Updated Date','Shopp'),
  236. );
  237. }
  238. function tag ($property,$options=array()) {
  239. global $Shopp;
  240. $menus = array(
  241. "account" => __("My Account","Shopp"),
  242. "downloads" => __("Downloads","Shopp"),
  243. "history" => __("Order History","Shopp"),
  244. "status" => __("Order Status","Shopp"),
  245. "logout" => __("Logout","Shopp")
  246. );
  247. // Return strings with no options
  248. switch ($property) {
  249. case "url": return $Shopp->link('account');
  250. case "recover-url": return add_query_arg('acct','recover',$Shopp->link('account'));
  251. case "process":
  252. if (isset($_GET['acct'])) return $_GET['acct'];
  253. return false;
  254. case "loggedin": return $Shopp->Cart->data->login; break;
  255. case "notloggedin": return (!$Shopp->Cart->data->login && $Shopp->Settings->get('account_system') != "none"); break;
  256. case "login-label":
  257. $accounts = $Shopp->Settings->get('account_system');
  258. $label = __('Email Address','Shopp');
  259. if ($accounts == "wordpress") $label = __('Login Name','Shopp');
  260. if (isset($options['label'])) $label = $options['label'];
  261. return $label;
  262. break;
  263. case "email-login":
  264. case "loginname-login":
  265. case "account-login":
  266. if (!empty($_POST['account-login']))
  267. $options['value'] = $_POST['account-login'];
  268. return '<input type="text" name="account-login" id="account-login"'.inputattrs($options).' />';
  269. break;
  270. case "password-login":
  271. if (!empty($_POST['password-login']))
  272. $options['value'] = $_POST['password-login'];
  273. return '<input type="password" name="password-login" id="password-login"'.inputattrs($options).' />';
  274. break;
  275. case "recover-button":
  276. if (!isset($options['value'])) $options['value'] = __('Get New Password','Shopp');
  277. return '<input type="submit" name="recover-login" id="recover-button"'.inputattrs($options).' />';
  278. break;
  279. case "submit-login": // Deprecating
  280. case "login-button":
  281. if (!isset($options['value'])) $options['value'] = __('Login','Shopp');
  282. if (is_shopp_page('account'))
  283. $string = '<input type="hidden" name="process-login" id="process-login" value="true" />';
  284. else $string = '<input type="hidden" name="process-login" id="process-login" value="false" />';
  285. $string .= '<input type="submit" name="submit-login" id="submit-login"'.inputattrs($options).' />';
  286. return $string;
  287. break;
  288. case "errors-exist":
  289. $Errors =& ShoppErrors();
  290. return ($Errors->exist(SHOPP_AUTH_ERR));
  291. break;
  292. case "login-errors":
  293. $Errors =& ShoppErrors();
  294. $result = "";
  295. if (!$Errors->exist(SHOPP_AUTH_ERR)) return false;
  296. $errors = $Errors->get(SHOPP_AUTH_ERR);
  297. foreach ((array)$errors as $error)
  298. if (!empty($error)) $result .= '<p class="error">'.$error->message().'</p>';
  299. $Errors->reset();
  300. return $result;
  301. break;
  302. case "menu":
  303. if (!$this->looping) {
  304. reset($this->management);
  305. $this->looping = true;
  306. } else next($this->management);
  307. if (current($this->management)) return true;
  308. else {
  309. $this->looping = false;
  310. reset($this->management);
  311. return false;
  312. }
  313. break;
  314. case "management":
  315. if (array_key_exists('url',$options)) return add_query_arg('acct',key($this->management),$Shopp->link('account'));
  316. if (array_key_exists('action',$options)) return key($this->management);
  317. return $menus[key($this->management)];
  318. case "accounts": return $Shopp->Settings->get('account_system'); break;
  319. case "order-lookup":
  320. $auth = $Shopp->Settings->get('account_system');
  321. if ($auth != "none") return true;
  322. if (!empty($_POST['vieworder']) && !empty($_POST['purchaseid'])) {
  323. require_once("Purchase.php");
  324. $Purchase = new Purchase($_POST['purchaseid']);
  325. if ($Purchase->email == $_POST['email']) {
  326. $Shopp->Cart->data->Purchase = $Purchase;
  327. $Purchase->load_purchased();
  328. ob_start();
  329. include(SHOPP_TEMPLATES."/receipt.php");
  330. $content = ob_get_contents();
  331. ob_end_clean();
  332. return '<div id="shopp">'.$content.'</div>';
  333. }
  334. }
  335. ob_start();
  336. include(SHOPP_ADMINPATH."/orders/account.php");
  337. $content = ob_get_contents();
  338. ob_end_clean();
  339. return '<div id="shopp">'.$content.'</div>';
  340. break;
  341. case "firstname":
  342. if ($options['mode'] == "value") return $this->firstname;
  343. if (!empty($this->firstname))
  344. $options['value'] = $this->firstname;
  345. return '<input type="text" name="firstname" id="firstname"'.inputattrs($options).' />';
  346. break;
  347. case "lastname":
  348. if ($options['mode'] == "value") return $this->lastname;
  349. if (!empty($this->lastname))
  350. $options['value'] = $this->lastname;
  351. return '<input type="text" name="lastname" id="lastname"'.inputattrs($options).' />';
  352. break;
  353. case "company":
  354. if ($options['mode'] == "value") return $this->company;
  355. if (!empty($this->company))
  356. $options['value'] = $this->company;
  357. return '<input type="text" name="company" id="company"'.inputattrs($options).' />';
  358. break;
  359. case "email":
  360. if ($options['mode'] == "value") return $this->email;
  361. if (!empty($this->email))
  362. $options['value'] = $this->email;
  363. return '<input type="text" name="email" id="email"'.inputattrs($options).' />';
  364. break;
  365. case "loginname":
  366. if ($options['mode'] == "value") return $this->loginname;
  367. if (!empty($this->login))
  368. $options['value'] = $this->login;
  369. return '<input type="text" name="login" id="login"'.inputattrs($options).' />';
  370. break;
  371. case "password":
  372. if ($options['mode'] == "value")
  373. return strlen($this->password) == 34?str_pad('&bull;',8):$this->password;
  374. if (!empty($this->password))
  375. $options['value'] = $this->password;
  376. return '<input type="password" name="password" id="password"'.inputattrs($options).' />';
  377. break;
  378. case "confirm-password":
  379. if (!empty($this->confirm_password))
  380. $options['value'] = $this->confirm_password;
  381. return '<input type="password" name="confirm-password" id="confirm-password"'.inputattrs($options).' />';
  382. break;
  383. case "phone":
  384. if ($options['mode'] == "value") return $this->phone;
  385. if (!empty($this->phone))
  386. $options['value'] = $this->phone;
  387. return '<input type="text" name="phone" id="phone"'.inputattrs($options).' />';
  388. break;
  389. case "hasinfo":
  390. case "has-info":
  391. if (empty($this->info)) return false;
  392. if (!$this->looping) {
  393. reset($this->info);
  394. $this->looping = true;
  395. } else next($this->info);
  396. if (current($this->info)) return true;
  397. else {
  398. $this->looping = false;
  399. reset($this->info);
  400. return false;
  401. }
  402. break;
  403. case "info":
  404. $info = current($this->info);
  405. $name = key($this->info);
  406. $allowed_types = array("text","password","hidden","checkbox","radio");
  407. if (empty($options['type'])) $options['type'] = "hidden";
  408. if (in_array($options['type'],$allowed_types)) {
  409. if ($options['mode'] == "name") return $name;
  410. if ($options['mode'] == "value") return $info;
  411. $options['value'] = $info;
  412. return '<input type="text" name="info['.$name.']" id="customer-info-'.$name.'"'.inputattrs($options).' />';
  413. }
  414. break;
  415. case "save-button":
  416. if (!isset($options['label'])) $options['label'] = __('Save','Shopp');
  417. $result = '<input type="hidden" name="customer" value="true" />';
  418. $result .= '<input type="submit" name="save" id="save-button"'.inputattrs($options).' />';
  419. return $result;
  420. break;
  421. // Downloads UI tags
  422. case "hasdownloads":
  423. case "has-downloads": return (!empty($this->downloads)); break;
  424. case "downloads":
  425. if (empty($this->downloads)) return false;
  426. if (!$this->looping) {
  427. reset($this->downloads);
  428. $this->looping = true;
  429. } else next($this->downloads);
  430. if (current($this->downloads)) return true;
  431. else {
  432. $this->looping = false;
  433. reset($this->downloads);
  434. return false;
  435. }
  436. break;
  437. case "download":
  438. $download = current($this->downloads);
  439. $df = get_option('date_format');
  440. $properties = unserialize($download->properties);
  441. $string = '';
  442. if (array_key_exists('id',$options)) $string .= $download->download;
  443. if (array_key_exists('purchase',$options)) $string .= $download->purchase;
  444. if (array_key_exists('name',$options)) $string .= $download->name;
  445. if (array_key_exists('variation',$options)) $string .= $download->optionlabel;
  446. if (array_key_exists('downloads',$options)) $string .= $download->downloads;
  447. if (array_key_exists('key',$options)) $string .= $download->dkey;
  448. if (array_key_exists('created',$options)) $string .= $download->created;
  449. if (array_key_exists('total',$options)) $string .= money($download->total);
  450. if (array_key_exists('filetype',$options)) $string .= $properties['mimetype'];
  451. if (array_key_exists('size',$options)) $string .= readableFileSize($download->size);
  452. if (array_key_exists('date',$options)) $string .= _d($df,mktimestamp($download->created));
  453. if (array_key_exists('url',$options)) $string .= (SHOPP_PERMALINKS) ?
  454. $Shopp->shopuri."download/".$download->dkey :
  455. add_query_arg('shopp_download',$download->dkey,$Shopp->link('account'));
  456. return $string;
  457. break;
  458. // Downloads UI tags
  459. case "haspurchases":
  460. case "has-purchases":
  461. $filters = array();
  462. if (isset($options['daysago']))
  463. $filters['where'] = "UNIX_TIMESTAMP(o.created) > UNIX_TIMESTAMP()-".($options['daysago']*86400);
  464. if (empty($Shopp->purchases)) $this->load_orders($filters);
  465. return (!empty($Shopp->purchases));
  466. break;
  467. case "purchases":
  468. if (!$this->looping) {
  469. reset($Shopp->purchases);
  470. $Shopp->Cart->data->Purchase = current($Shopp->purchases);
  471. $this->looping = true;
  472. } else {
  473. $Shopp->Cart->data->Purchase = next($Shopp->purchases);
  474. }
  475. if (current($Shopp->purchases)) {
  476. $Shopp->Cart->data->Purchase = current($Shopp->purchases);
  477. return true;
  478. }
  479. else {
  480. $this->looping = false;
  481. return false;
  482. }
  483. break;
  484. case "receipt":
  485. return add_query_arg(
  486. array(
  487. 'acct'=>'receipt',
  488. 'id'=>$Shopp->Cart->data->Purchase->id),
  489. $Shopp->link('account'));
  490. }
  491. }
  492. } // end Customer class
  493. class CustomersExport {
  494. var $sitename = "";
  495. var $headings = false;
  496. var $data = false;
  497. var $defined = array();
  498. var $customer_cols = array();
  499. var $billing_cols = array();
  500. var $shipping_cols = array();
  501. var $selected = array();
  502. var $recordstart = true;
  503. var $content_type = "text/plain";
  504. var $extension = "txt";
  505. function CustomersExport () {
  506. global $Shopp;
  507. $this->customer_cols = Customer::exportcolumns();
  508. $this->billing_cols = Billing::exportcolumns();
  509. $this->shipping_cols = Shipping::exportcolumns();
  510. $this->defined = array_merge($this->customer_cols,$this->billing_cols,$this->shipping_cols);
  511. $this->sitename = get_bloginfo('name');
  512. $this->headings = ($Shopp->Settings->get('customerexport_headers') == "on");
  513. $this->selected = $Shopp->Settings->get('customerexport_columns');
  514. $Shopp->Settings->save('customerexport_lastexport',mktime());
  515. }
  516. function query ($request=array()) {
  517. $db =& DB::get();
  518. if (empty($request)) $request = $_GET;
  519. if (!empty($request['start'])) {
  520. list($month,$day,$year) = explode("/",$request['start']);
  521. $starts = mktime(0,0,0,$month,$day,$year);
  522. }
  523. if (!empty($request['end'])) {
  524. list($month,$day,$year) = explode("/",$request['end']);
  525. $ends = mktime(0,0,0,$month,$day,$year);
  526. }
  527. $where = "WHERE c.id IS NOT NULL ";
  528. if (isset($request['s']) && !empty($request['s'])) $where .= " AND (id='{$request['s']}' OR firstname LIKE '%{$request['s']}%' OR lastname LIKE '%{$request['s']}%' OR CONCAT(firstname,' ',lastname) LIKE '%{$request['s']}%' OR transactionid LIKE '%{$request['s']}%')";
  529. if (!empty($request['start']) && !empty($request['end'])) $where .= " AND (UNIX_TIMESTAMP(c.created) >= $starts AND UNIX_TIMESTAMP(c.created) <= $ends)";
  530. $customer_table = DatabaseObject::tablename(Customer::$table);
  531. $billing_table = DatabaseObject::tablename(Billing::$table);
  532. $shipping_table = DatabaseObject::tablename(Shipping::$table);
  533. $c = 0; $columns = array();
  534. foreach ($this->selected as $column) $columns[] = "$column AS col".$c++;
  535. $query = "SELECT ".join(",",$columns)." FROM $customer_table AS c LEFT JOIN $billing_table AS b ON c.id=b.customer LEFT JOIN $shipping_table AS s ON c.id=s.customer $where ORDER BY c.created ASC";
  536. $this->data = $db->query($query,AS_ARRAY);
  537. }
  538. // Implement for exporting all the data
  539. function output () {
  540. if (!$this->data) $this->query();
  541. if (!$this->data) return false;
  542. header("Content-type: $this->content_type; charset=UTF-8");
  543. header("Content-Disposition: attachment; filename=\"$this->sitename Customer Export.$this->extension\"");
  544. header("Content-Description: Delivered by WordPress/Shopp ".SHOPP_VERSION);
  545. header("Cache-Control: maxage=1");
  546. header("Pragma: public");
  547. $this->begin();
  548. if ($this->headings) $this->heading();
  549. $this->records();
  550. $this->end();
  551. }
  552. function begin() {}
  553. function heading () {
  554. foreach ($this->selected as $name)
  555. $this->export($this->defined[$name]);
  556. $this->record();
  557. }
  558. function records () {
  559. foreach ($this->data as $key => $record) {
  560. foreach(get_object_vars($record) as $column)
  561. $this->export($this->parse($column));
  562. $this->record();
  563. }
  564. }
  565. function parse ($column) {
  566. if (preg_match("/^[sibNaO](?:\:.+?\{.*\}$|\:.+;$|;$)/",$column)) {
  567. $list = unserialize($column);
  568. $column = "";
  569. foreach ($list as $name => $value)
  570. $column .= (empty($column)?"":";")."$name:$value";
  571. }
  572. return $column;
  573. }
  574. function end() {}
  575. // Implement for exporting a single value
  576. function export ($value) {
  577. echo ($this->recordstart?"":"\t").$value;
  578. $this->recordstart = false;
  579. }
  580. function record () {
  581. echo "\n";
  582. $this->recordstart = true;
  583. }
  584. }
  585. class CustomersTabExport extends CustomersExport {
  586. function CustomersTabExport () {
  587. parent::CustomersExport();
  588. $this->output();
  589. }
  590. }
  591. class CustomersCSVExport extends CustomersExport {
  592. function CustomersCSVExport () {
  593. parent::CustomersExport();
  594. $this->content_type = "text/csv";
  595. $this->extension = "csv";
  596. $this->output();
  597. }
  598. function export ($value) {
  599. $value = str_replace('"','""',$value);
  600. if (preg_match('/^\s|[,"\n\r]|\s$/',$value)) $value = '"'.$value.'"';
  601. echo ($this->recordstart?"":",").$value;
  602. $this->recordstart = false;
  603. }
  604. }
  605. class CustomersXLSExport extends CustomersExport {
  606. function CustomersXLSExport () {
  607. parent::CustomersExport();
  608. $this->content_type = "application/vnd.ms-excel";
  609. $this->extension = "xls";
  610. $this->c = 0; $this->r = 0;
  611. $this->output();
  612. }
  613. function begin () {
  614. echo pack("ssssss", 0x809, 0x8, 0x0, 0x10, 0x0, 0x0);
  615. }
  616. function end () {
  617. echo pack("ss", 0x0A, 0x00);
  618. }
  619. function export ($value) {
  620. if (preg_match('/^[\d\.]+$/',$value)) {
  621. echo pack("sssss", 0x203, 14, $this->r, $this->c, 0x0);
  622. echo pack("d", $value);
  623. } else {
  624. $l = strlen($value);
  625. echo pack("ssssss", 0x204, 8+$l, $this->r, $this->c, 0x0, $l);
  626. echo $value;
  627. }
  628. $this->c++;
  629. }
  630. function record () {
  631. $this->c = 0;
  632. $this->r++;
  633. }
  634. }
  635. ?>