コード例 #1
0
ファイル: RouteTrait.php プロジェクト: Tanklong/openvj
 /**
  * @throws NotFoundException
  */
 public static function route()
 {
     $dispatcher = Application::get('dispatcher');
     $request = Application::get('request');
     $response = Application::get('response');
     Application::emit('route.dispatch.before');
     //判断Event是否已经发送过响应
     if (headers_sent()) {
         return;
     }
     $urlParts = parse_url($request->getRequestUri());
     $route = $dispatcher->dispatch($request->getMethod(), $urlParts['path']);
     //[0]: Dispatch Status, [1]: handler, [2]: vars
     Application::emit('route.dispatch', $route);
     //同上
     if (headers_sent()) {
         return;
     }
     switch ($route[0]) {
         case Dispatcher::NOT_FOUND:
         case Dispatcher::METHOD_NOT_ALLOWED:
             throw new NotFoundException();
             break;
         case Dispatcher::FOUND:
             list(, $handler, $vars) = $route;
             $controller = new $handler['className']($request, $response);
             $ret = call_user_func([$controller, $handler['actionName']], $vars);
             if (headers_sent() || $ret === null) {
                 return;
             }
             if ($ret instanceof Response && $ret !== $response) {
                 // overwrite response
                 $response = $ret;
             } else {
                 if (is_string($ret)) {
                     $response->setContent($ret);
                 }
                 if ($response->headers->get('content-type') === null) {
                     $response->headers->set('content-type', 'text/html');
                 }
                 $response->setCharset('UTF-8');
             }
             $response->prepare($request);
             $response->send();
             break;
     }
 }
コード例 #2
0
ファイル: VijosImporter.php プロジェクト: Tanklong/openvj
 /**
  * 导入 Vijos 数据库用户表
  *
  * @param callable $progress
  * @param callable $done
  * @return bool
  * @throws UserException
  */
 public function import(callable $progress = null)
 {
     if (Application::coll('User')->count() > 0) {
         throw new UserException('User.Importer.VijosImporter.userCollectionNotEmpty');
     }
     $MAX_USER_ID = 1;
     $cursor = $this->source->selectCollection('User')->find()->sort(['_id' => 1]);
     foreach ($cursor as $user) {
         $_id = new \MongoId();
         $uid = (int) $user['_id'];
         if ($uid > $MAX_USER_ID) {
             $MAX_USER_ID = $uid;
         }
         // vijos 中,username 被 escape 过
         $user['user'] = htmlspecialchars_decode($user['user']);
         if (is_callable($progress)) {
             $progress($uid, $user['user']);
         }
         $doc = ['_id' => $_id, 'uid' => $uid, 'user' => $user['user'], 'luser' => UserUtil::canonicalizeUsername($user['user']), 'g' => $user['g'], 'gender' => (int) $user['sex'] + 1, 'regat' => (int) $user['treg'], 'regip' => $user['ipreg'], 'loginat' => (int) $user['tlogin'], 'loginip' => '255.255.255.255'];
         // 检查是否有 Email 重叠
         $count = $this->source->selectCollection('User')->find(['lmail' => mb_strtolower($user['mail'], 'UTF-8')])->count();
         if ($count > 1) {
             $doc['mail'] = Application::get('random')->generateString(20, VJ::RANDOM_CHARS) . '@openvj';
             $doc['lmail'] = mb_strtolower($doc['mail'], 'UTF-8');
             $doc['omail'] = $user['mail'];
         } else {
             $doc['mail'] = $user['mail'];
             $doc['lmail'] = UserUtil::canonicalizeEmail($doc['mail']);
             $doc['salt'] = $user['salt'];
             $doc['hash'] = 'vj2|' . base64_encode(mb_strtolower($user['user'], 'UTF-8')) . '|' . $user['pass'];
         }
         try {
             Application::coll('User')->insert($doc);
             Application::emit('user.created', [$uid]);
         } catch (\MongoCursorException $e) {
             // TODO: Duplicate user
         }
     }
     // Update UID counter
     Application::coll('System')->update(['_id' => 'UserCounter'], ['$set' => ['count' => $MAX_USER_ID + 1]], ['upsert' => true]);
     return true;
 }
コード例 #3
0
ファイル: UserManager.php プロジェクト: Tanklong/openvj
 /**
  * 创建用户
  *
  * @param string $username
  * @param string $password
  * @param string $email
  * @return int UID
  * @throws InvalidArgumentException
  * @throws UserException
  */
 public function createUser($username, $password, $email)
 {
     if (!is_string($username)) {
         throw new InvalidArgumentException('username', 'type_invalid');
     }
     if (!is_string($password)) {
         throw new InvalidArgumentException('password', 'type_invalid');
     }
     if (!is_string($email)) {
         throw new InvalidArgumentException('email', 'type_invalid');
     }
     // 检查用户名
     if (!mb_check_encoding($username, 'UTF-8')) {
         throw new InvalidArgumentException('username', 'encoding_invalid');
     }
     $username = trim($username);
     if (!Validator::regex('/^\\S*$/')->length(3, 16)->validate($username)) {
         throw new InvalidArgumentException('username', 'format_invalid');
     }
     // 检查关键字
     $keyword = KeywordFilter::isContainGeneric($username);
     if ($keyword === false) {
         $keyword = KeywordFilter::isContainName($username);
     }
     if ($keyword !== false) {
         throw new UserException('UserManager.name_forbid', ['keyword' => $keyword]);
     }
     // 检查密码
     if (!Validator::length(0, 50)->validate($password)) {
         throw new InvalidArgumentException('password', 'format_invalid');
     }
     // 检查 email
     if (!Validator::email()->validate($email)) {
         throw new InvalidArgumentException('password', 'format_invalid');
     }
     // 处理用户名
     $username = VJ::removeEmoji($username);
     // 检查用户名和 Email 是否唯一
     if (UserUtil::getUserObjectByUsername($username) !== null) {
         throw new UserException('UserManager.createUser.user_exists');
     }
     if (UserUtil::getUserObjectByEmail($email) !== null) {
         throw new UserException('UserManager.createUser.email_exists');
     }
     // 生成 hash & salt
     $hashSaltPair = $this->user_credential->password_encoder->generateHash($password);
     // 插入记录
     try {
         $_id = new \MongoId();
         $doc = ['_id' => $_id, 'uid' => $_id, 'user' => $username, 'luser' => UserUtil::canonicalizeUsername($username), 'mail' => $email, 'lmail' => UserUtil::canonicalizeEmail($email), 'salt' => $hashSaltPair['salt'], 'hash' => $hashSaltPair['hash'], 'g' => $email, 'gender' => VJ::USER_GENDER_UNKNOWN, 'regat' => new \MongoDate(), 'regip' => $this->request->getClientIp()];
         Application::coll('User')->insert($doc);
     } catch (\MongoCursorException $e) {
         // 插入失败
         throw new UserException('UserManager.createUser.user_or_email_exists');
     }
     // 插入成功:更新 uid
     // 获取递增 uid
     $counterRec = Application::coll('System')->findAndModify(['_id' => 'UserCounter'], ['$inc' => ['count' => 1]], [], ['new' => true, 'upsert' => true]);
     $uid = (int) $counterRec['count'];
     try {
         // 修改 uid
         Application::coll('User')->update(['_id' => $_id], ['$set' => ['uid' => $uid]]);
     } catch (\MongoCursorException $e) {
         // 修改 uid 失败(uid 重复),则删除用户记录
         Application::critical('createUser.uidDuplicate', ['uid' => $uid]);
         Application::coll('User')->remove(['_id' => $_id], ['justOne' => true]);
         throw new UserException('UserManager.createUser.internal');
     }
     Application::emit('user.created', [$uid]);
     return $uid;
 }
コード例 #4
0
ファイル: UserCredential.php プロジェクト: Tanklong/openvj
 /**
  * 检查 记住我 token 是否正确
  *
  * @param string $clientToken
  * @param bool $secretly
  * @return array
  * @throws UserException
  */
 public function checkRememberMeTokenCredential($token, $secretly = false)
 {
     try {
         $tokenRec = Application::get('token_manager')->find('rememberme', $token);
         if ($tokenRec === null) {
             throw new UserException('UserCredential.checkRememberMeTokenCredential.invalid_rememberme_token');
         }
         //是否需要检查 user-agent 和 ip 地址呢
         $user = UserUtil::getUserObjectByUid($tokenRec['data']['uid']);
         if (!UserUtil::isUserObjectValid($user)) {
             throw new UserException('UserCredential.checkRememberMeTokenCredential.user_not_valid');
         }
         if (!$secretly) {
             Application::emit('user.login.succeeded', [VJ::LOGIN_TYPE_TOKEN, $user]);
             Application::info('credential.login.ok', ['uid' => $user['uid']]);
         }
         return $user;
     } catch (InvalidArgumentException $e) {
         throw new UserException('UserCredential.checkRememberMeTokenCredential.invalid_rememberme_token');
     }
 }
コード例 #5
0
ファイル: DiscussionUtil.php プロジェクト: Tanklong/openvj
 /**
  * 修改主题
  *
  * @param \MongoId $discussionId
  * @param string $markdown
  * @return array|null
  * @throws InvalidArgumentException
  * @throws UserException
  */
 public static function modifyDiscussion(\MongoId $discussionId, $markdown)
 {
     if (!is_string($markdown)) {
         throw new InvalidArgumentException('markdown', 'type_invalid');
     }
     if (!mb_check_encoding($markdown, 'UTF-8')) {
         throw new InvalidArgumentException('markdown', 'encoding_invalid');
     }
     //if (!Validator::length(VJ::COMMENT_MIN, VJ::COMMENT_MAX)) {
     //throw new UserException('CommentUtil.content_invalid_length');
     //}
     self::initParser();
     $html = self::$parser->parse($markdown);
     $keyword = KeywordFilter::isContainGeneric(strip_tags($html));
     if ($keyword !== false) {
         throw new UserException('CommentUtil.content_forbid', ['keyword' => $keyword]);
     }
     $result = Application::coll('Discussion')->update(['_id' => $discussionId], ['$set' => ['raw' => $markdown, 'html' => $html]]);
     if ($result['n'] === 1) {
         Application::emit('discussion.modify.succeeded', [$discussionId]);
         return ['_id' => $discussionId, 'html' => $html];
     } else {
         return null;
     }
 }
コード例 #6
0
ファイル: CommentUtil.php プロジェクト: Tanklong/openvj
 /**
  * 删除回复
  *
  * @param \MongoId $commentId
  * @param string $ref
  * @param \MongoId $replyId
  * @return bool
  * @throws InvalidArgumentException
  */
 public static function deleteReply(\MongoId $commentId, $ref, \MongoId $replyId)
 {
     if (!is_string($ref)) {
         throw new InvalidArgumentException('ref', 'type_invalid');
     }
     if (!mb_check_encoding($ref, 'UTF-8')) {
         throw new InvalidArgumentException('ref', 'encoding_invalid');
     }
     $result = Application::coll('Comment')->update(['_id' => $commentId, 'ref' => $ref, 'deleted' => false, 'replies' => ['$elemMatch' => ['_id' => $replyId, 'deleted' => false]]], ['$set' => ['replies.$.deleted' => true]]);
     $success = $result['n'] === 1;
     if ($success) {
         Application::emit('comment.reply.delete.succeeded', [$ref, $commentId, $replyId]);
     }
     return $success;
 }