/** * @test */ public function getRandom() { // いかなる状態であっても // 値が得られなければならない $r = Ethna_Util::getRandom(); $this->assertEquals(64, strlen($r)); }
function testGetRandom() { // いかなる状態であっても // 値が得られなければならない $r = Ethna_Util::getRandom(); $this->assertNotNULL($r); $this->assertEqual(64, strlen($r)); }
/** * smarty function:ユニークIDを生成する(double postチェック用) * * sample: * <code> * {uniqid} * </code> * <code> * <input type="hidden" name="uniqid" value="a0f24f75e...e48864d3e"> * </code> * * @param string $type 表示タイプ("get" or "post"−デフォルト="post") * @see isDuplicatePost */ function smarty_function_uniqid($params, &$smarty) { $uniqid = Ethna_Util::getRandom(); if (isset($params['type']) && $params['type'] == 'get') { return "uniqid={$uniqid}"; } else { return "<input type=\"hidden\" name=\"uniqid\" value=\"{$uniqid}\" />\n"; } }
/** * preprocess before forwarding. * * @access public */ function preforward() { parent::preforward(); $cookie_path = str_replace(rtrim($_SERVER['DOCUMENT_ROOT'], '/'), '', $this->af->get('xoops_root_path')); !$cookie_path and $cookie_path = '/'; $xoops_url = sprintf('http://%s%s', $_SERVER['SERVER_NAME'], $cookie_path); $this->af->setApp('xoops_cookie_path', $cookie_path); $this->af->setApp('xoops_url', $xoops_url); $this->af->setApp('prefix', Ethna_Util::getRandom(6)); $this->af->setApp('salt', Ethna_Util::getRandom(8)); }
function perform() { if (!is_writable($this->config->get('data_dir'))) { $this->ae->add('error', $this->config->get('data_dir') . 'に書き込み権限がありません'); return 'error'; } $fl =& $this->backend->getManager('FileList'); $file_list =& $fl->scandir($this->config->get('data_dir')); $files = count($file_list); if ($files === 0) { $id = 1; } else { if ($files >= $this->config->get('project_limit')) { $this->ae->add('error', 'これ以上フォームを追加できません'); return 'project'; } list($id) = sscanf($file_list[0], '%03d.cgi'); ++$id; } $data_file = sprintf('%03d.cgi', $id); $data_file_path = $this->config->get('data_dir') . $data_file; $name = $this->af->get('name'); $file = $this->af->get('file'); if ($file === '') { $file = Ethna_Util::getRandom(6); } if ($file !== basename($file, $this->config->get('mobile_suffix'))) { $this->ae->add('error', $this->config->get('mobile_suffix') . 'は予約語につき変更して下さい'); return 'project'; } $file_p = $this->config->get('publish_dir') . $file . '.php'; $file_m = $this->config->get('publish_dir') . $file . $this->config->get('mobile_suffix') . '.php'; if (is_file($file_p) || is_file($file_m)) { $this->ae->add('error', $file . 'は使用中につき変更して下さい'); return 'project'; } $data =& $this->backend->getManager('Data'); $data->load($data_file_path); $data->set('file', $file); $data->set('name', $name); $data->set('mailto', ''); $data->set('body', '先にテンプレートを作成して下さい。'); $data->set('receipt', '先にテンプレートを作成して下さい。'); $data->set('attr', array()); if (!$data->write()) { $this->ae->add('error', $data_file_path . 'に書き込めませんでした'); return 'error'; } array_unshift($file_list, $data_file); $this->af->clearFormVars(); return 'project'; }
/** * CRCFIDの初期化と設定を行う。セッション開始されてなければならない * * @access public * @access public * @return bool true:成功 false:失敗 */ function setCSRF() { $c =& Ethna_Controller::getInstance(); $session = $c->getSession(); if (!$session->isStart(true)) { return false; } if (is_Null($session->get('__CSRF__'))) { $session->set('__CSRF__', Ethna_Util::getRandom()); } $csrfid = $session->get('__CSRF__'); $form = $c->getActionForm(); $form->setApp('csrfid', $csrfid); return true; }
public function start($lifetime = 0, $anonymous = false) { if ($this->session_start) { // we need this? $_SESSION['REMOTE_ADDR'] = $_SERVER['REMOTE_ADDR']; $_SESSION['__anonymous__'] = $anonymous; return true; } if (is_null($lifetime)) { ini_set('session.use_cookies', 0); } else { ini_set('session.use_cookies', 1); } session_set_cookie_params($lifetime); session_id(Ethna_Util::getRandom()); // do not start test as cli test //session_start(); $_SESSION['REMOTE_ADDR'] = isset($_SERVER['REMOTE_ADDR']) ? $_SERVER['REMOTE_ADDR'] : false; $_SESSION['__anonymous__'] = $anonymous; $this->anonymous = $anonymous; $this->session_start = true; $this->logger->log(LOG_INFO, 'Session started.'); return true; }
/** * preprocess Index action. * * @access public * @return string Forward name (null if no errors.) */ function prepare() { if ($this->af->validate() == 0) { $username = $this->af->get('ftp_username'); $password = $this->af->get('ftp_password'); $xoops_root_path = $this->af->get('root_path'); var_dump($username, $password, $xoops_root_path); if ($conn_id = ftp_connect('localhost')) { $this->af->setApp($i++, $i++); if (ftp_login($conn_id, $username, $password)) { $ftp_root = $this->seekFTPRoot($conn_id); if ($ftp_root !== false) { $install_dir = str_replace($ftp_root, '', $xoops_root_path) . '/install'; $install_dir_dest = $install_dir . '_' . Ethna_Util::getRandom(16); ftp_rename($conn_id, $install_dir, $install_dir_dest); $mainfile = str_replace($ftp_root, '', $xoops_root_path) . '/mainfile.php'; ftp_chmod($conn_id, 0644, $mainfile); return null; } } } } return 'json_error'; }
/** * メールを送信する * * $attach の指定方法: * - 既存のファイルを添付するとき * <code> * array('filename' => '/tmp/hoge.xls', 'content-type' => 'application/vnd.ms-excel') * </code> * - 文字列に名前を付けて添付するとき * <code> * array('name' => 'foo.txt', 'content' => 'this is foo.') * </code> * 'content-type' 省略時は 'application/octet-stream' となる。 * 複数添付するときは上の配列を添字0から始まるふつうの配列に入れる。 * * @access public * @param string $to メール送信先アドレス (nullのときは送信せずに内容を return する) * @param string $template メールテンプレート名 or タイプ * @param array $macro テンプレートマクロ or $templateがMAILSENDER_TYPE_DIRECTのときはメール送信内容) * @param array $attach 添付ファイル */ function send($to, $template, $macro, $attach = null) { // メール内容を作成 if ($template === MAILSENDER_TYPE_DIRECT) { $mail = $macro; } else { $renderer = $this->getTemplateEngine(); // 基本情報設定 $env_datetime = _et('%Y/%m/%d %H:%M:%S'); $renderer->setProp("env_datetime", strftime($env_datetime)); $renderer->setProp("env_useragent", $_SERVER["HTTP_USER_AGENT"]); $renderer->setProp("env_remoteaddr", $_SERVER["REMOTE_ADDR"]); // デフォルトマクロ設定 $macro = $this->_setDefaultMacro($macro); // ユーザ定義情報設定 if (is_array($macro)) { foreach ($macro as $key => $value) { $renderer->setProp($key, $value); } } if (isset($this->def[$template])) { $template = $this->def[$template]; } $mail = $renderer->perform(sprintf('%s/%s', $this->mail_dir, $template), true); if (Ethna::isError($mail)) { return $mail; } } if ($to === null) { return $mail; } // メール内容をヘッダと本文に分離 $mail = str_replace("\r\n", "\n", $mail); list($header, $body) = $this->_parse($mail); // 添付ファイル (multipart) if ($attach !== null) { $attach = isset($attach[0]) ? $attach : array($attach); $boundary = Ethna_Util::getRandom(); $body = "This is a multi-part message in MIME format.\n\n" . "--{$boundary}\n" . "Content-Type: text/plain; charset=utf-8\n" . "Content-Transfer-Encoding: 8bit\n\n" . "{$body}\n"; foreach ($attach as $part) { if (isset($part['content']) === false && isset($part['filename']) && is_readable($part['filename'])) { $part['content'] = file_get_contents($part['filename']); $part['filename'] = basename($part['filename']); } if (isset($part['content']) === false) { continue; } if (isset($part['content-type']) === false) { $part['content-type'] = 'application/octet-stream'; } if (isset($part['name']) === false) { $part['name'] = $part['filename']; } if (isset($part['filename']) === false) { $part['filename'] = $part['name']; } $part['name'] = preg_replace_callback('/([^\\x00-\\x7f]+)/', function ($matches) { return Ethna_Util::encode_MIME($matches[1]); }, $part['name']); // XXX: rfc2231 $part['filename'] = preg_replace_callback('/([^\\x00-\\x7f]+)/', function ($matches) { return Ethna_Util::encode_MIME($matches[1]); }, $part['filename']); $body .= "--{$boundary}\n" . "Content-Type: " . $part['content-type'] . ";\n" . "\tname=\"" . $part['name'] . "\"\n" . "Content-Transfer-Encoding: base64\n" . "Content-Disposition: attachment;\n" . "\tfilename=\"" . $part['filename'] . "\"\n\n"; $body .= chunk_split(base64_encode($part['content'])); } $body .= "--{$boundary}--"; } // ヘッダ if (isset($header['mime-version']) === false) { $header['mime-version'] = array('Mime-Version', '1.0'); } if (isset($header['subject']) === false) { $header['subject'] = array('Subject', 'no subject in original'); } if (isset($header['content-type']) === false) { $header['content-type'] = array('Content-Type', $attach === null ? 'text/plain; charset=utf-8' : "multipart/mixed; \n\tboundary=\"{$boundary}\""); } if (isset($header['content-transfer-encoding']) === false) { $header['Content-Transfer-Encoding'] = ['Content-Transfer-Encoding', '8bit']; } $header_line = ""; foreach ($header as $key => $value) { if ($key == 'subject') { // should be added by mail() continue; } if ($header_line != "") { $header_line .= "\n"; } $header_line .= $value[0] . ": " . $value[1]; } // 改行コードを CRLF に if (strtoupper(substr(PHP_OS, 0, 3)) == 'WIN') { $body = str_replace("\n", "\r\n", $body); } $wa_config = 'mail_func_workaround'; if ($this->config->get($wa_config) == false && isset($this->options[$wa_config]) == false) { $header_line = str_replace("\n", "\r\n", $header_line); } // 送信 foreach (to_array($to) as $rcpt) { if (is_string($this->option)) { mail($rcpt, $header['subject'][1], $body, $header_line, $this->option); } else { mail($rcpt, $header['subject'][1], $body, $header_line); } } }
/** * セッションを開始する * * @access public * @param int $lifetime セッション有効期間(秒単位, 0ならセッションクッキー) * @return bool true:正常終了 false:エラー */ function start($lifetime = 0, $anonymous = false) { if ($this->session_start) { // we need this? $_SESSION['REMOTE_ADDR'] = $_SERVER['REMOTE_ADDR']; $_SESSION['__anonymous__'] = $anonymous; return true; } if (is_null($lifetime)) { ini_set('session.use_cookies', 0); } else { ini_set('session.use_cookies', 1); } session_set_cookie_params($lifetime); session_id(Ethna_Util::getRandom()); session_start(); $_SESSION['REMOTE_ADDR'] = $_SERVER['REMOTE_ADDR']; $_SESSION['__anonymous__'] = $anonymous; $this->session_start = true; return true; }
/** * キーを生成する * * @access public * @return string keyname */ function _generateKey() { return Ethna_Util::getRandom(32); }
/** * smarty function:ユニークIDを生成する(double postチェック用) * * sample: * <code> * {uniqid} * </code> * <code> * <input type="hidden" name="uniqid" value="a0f24f75e...e48864d3e"> * </code> * * @param string $type 表示タイプ("get" or "post"−デフォルト="post") * @see isDuplicatePost */ function smarty_function_uniqid($params, &$smarty) { extract($params); $uniqid = Ethna_Util::getRandom(); if (isset($type) && $type == 'get') { print "uniqid={$uniqid}"; } else { print "<input type=\"hidden\" name=\"uniqid\" value=\"{$uniqid}\" />\n"; } }
function setConfirmVars($form_id) { // 送信内容をhiddenで復元 $c =& Ethna_Controller::getInstance(); $this->vars['CONFIRM'] = true; $hidden =& $this->vars['hidden']; $hidden = $this->getHidden('_send', 'true'); $hidden = $this->getHidden('id', $form_id); $hidden = $this->getHidden('uniqid', Ethna_Util::getRandom(20)); $attr_list = $this->attr_list; foreach ($attr_list as $attr) { $id = $attr['id']; $t = $attr['type_name'][0]; $value = $this->af->get($id); $this->vars[$id . '_c'] = ''; $display =& $this->vars[$id . '_c']; if ($t == 'f') { if (!empty($value['size'])) { $file_name = $display = basename($value['name']); $dst_name = $id . md5($_SERVER['REQUEST_TIME'] . $_SERVER['REMOTE_ADDR']); $dst_name = substr($dst_name, 0, 20); $dst_name = preg_replace('/^.+(?=\\.)/', $dst_name, $file_name); $src = $value['tmp_name']; $dst = sprintf('%s/upload_%s', $c->getDirectory('tmp'), $dst_name); if (!move_uploaded_file($src, $dst)) { $this->vars['ERROR'] = 'アップロードに失敗しました'; return null; } $hidden = $this->getHidden($id . '_type', $value['type']); $hidden = $this->getHidden($id, sprintf('%s_%s', $file_name, $dst_name)); } } else { if ($t == 'c') { if (is_array($value)) { foreach ($value as $v) { $hidden = $this->getHidden($id . '[]', $v); } $display = implode(', ', $value); } } else { $hidden = $this->getHidden($id, $value); $display = $value; } } $this->changeBlankText($display, $t); $display = $this->escape($display, true); } $hidden .= "\n"; }
/** * メールを送信する * * @access public * @param string $to メール送信先アドレス * @param string $type メールテンプレートタイプ * @param array $macro テンプレートマクロ($typeがMAILSENDER_TYPE_DIRECTの場合はメール送信内容) * @param array $attach 添付ファイル(array('content-type' => ..., 'content' => ...)) * @return string $toがnullの場合テンプレートマクロ適用後のメール内容 */ function send($to, $type, $macro, $attach = null) { // コンテンツ作成 if ($type !== MAILSENDER_TYPE_DIRECT) { $smarty =& $this->getTemplateEngine(); // 基本情報設定 $smarty->assign("env_datetime", strftime('%Y年%m月%d日 %H時%M分%S秒')); $smarty->assign("env_useragent", $_SERVER["HTTP_USER_AGENT"]); $smarty->assign("env_remoteaddr", $_SERVER["REMOTE_ADDR"]); // デフォルトマクロ設定 $macro = $this->_setDefaultMacro($macro); // ユーザ定義情報設定 if (is_array($macro)) { foreach ($macro as $key => $value) { $smarty->assign($key, $value); } } $mail = $smarty->fetch(sprintf('%s/%s', $this->mail_dir, $type)); } else { $mail = $macro; } if (is_null($to)) { return $mail; } // 送信 foreach (to_array($to) as $rcpt) { list($header, $body) = $this->_parse($mail); // multipart対応 if ($attach != null) { $boundary = Ethna_Util::getRandom(); $body = "This is a multi-part message in MIME format.\n\n" . "--{$boundary}\n" . "Content-Type: text/plain; charset=ISO-2022-JP\n\n" . "{$body}\n" . "--{$boundary}\n" . "Content-Type: " . $attach['content-type'] . "; name=\"" . $attach['name'] . "\"\n" . "Content-Transfer-Encoding: base64\n" . "Content-Disposition: attachment; filename=\"" . $attach['name'] . "\"\n\n"; $body .= chunk_split(base64_encode($attach['content'])); $body .= "--{$boundary}--"; } $body = str_replace("\r\n", "\n", $body); // 最低限必要なヘッダを追加 if (array_key_exists('mime-version', $header) == false) { $header['mime-version'] = array('Mime-Version', '1.0'); } if (array_key_exists('subject', $header) == false) { $header['subject'] = array('Subject', 'no subject in original'); } if (array_key_exists('content-type', $header) == false) { if ($attach == null) { $header['content-type'] = array('Content-Type', 'text/plain; charset=ISO-2022-JP'); } else { $header['content-type'] = array('Content-Type', "multipart/mixed; boundary=\"{$boundary}\""); } } switch ($this->config->get('use_email')) { case 'mail': return $this->mail($rcpt, $header, $body, $this->option); break; case 'popbeforesmtp': return $this->popbeforesmtp($rcpt, $header, $body, $this->option); break; default: break; } } }