rhymix/classes/mobile/Mobile.class.php
Min-Soo Kim 30fd0c428c Improve cookie security; Secure flag
SSL 항상 사용 옵션인 경우 쿠키도 이에 맞추어 SSL 인 경우에만 사용되도록 secure flag 를 추가합니다.
선택적 SSL 인 경우 SSL 이 적용되지 않은 구간에서도 쿠키를 읽을 수 있어야 하므로, 적용하지 않습니다.

이 PR 로 변경되는 내용

- Context 클래스에 checkSslEnforce 메소드 추가
- SSL 항상 사용 옵션일 경우, 가능한 secure 플래그를 달아서 쿠기 굽기
- SSO 쿠키의 경우 javascript 접근이 필요 없을 것으로 예상 ( https://github.com/rhymix/rhymix/pull/1034 ) 되어서 `httpOnly` 플래그도 추가.

안드로이드 웹뷰의 경우 StackOverFlow 의 Reading secure cookies in android WebView 라는 글을 참고하면, 읽어오는 것이 가능하다고 합니다. 주소에 프로토콜을 적지 않을 경우 secure flag 가 달린 쿠키는 정상적으로 읽어오지 않는 듯 하니 안드로이드 웹뷰를 사용하시는 분들은 대응이 필요할 것으로 보입니다.

https: //github.com/rhymix/rhymix/pull/1034 를 실수로 merge 하여서 다시 올립니다.
Co-Authored-By: Kijin Sung <kijin@kijinsung.com>
2018-07-29 12:15:24 +09:00

138 lines
2.7 KiB
PHP

<?php
/* Copyright (C) NAVER <http://www.navercorp.com> */
/**
* Mobile class
*
* @author NAVER (developers@xpressengine.com)
*/
class Mobile
{
/**
* Whether mobile or not mobile mode
* @var bool
*/
protected static $_ismobile = null;
/**
* Get instance of Mobile class
*
* @return Mobile
*/
public function getInstance()
{
return new self();
}
/**
* Get current mobile mode
*
* @return bool
*/
public static function isFromMobilePhone()
{
// Return cached result.
if (self::$_ismobile !== null)
{
return self::$_ismobile;
}
// Not mobile if disabled explicitly.
if (!self::isMobileEnabled() || Context::get('full_browse') || $_COOKIE["FullBrowse"])
{
return self::$_ismobile = false;
}
// Try to detect from URL arguments and cookies, and finally fall back to user-agent detection.
$m = Context::get('m');
$cookie = isset($_COOKIE['rx_uatype']) ? $_COOKIE['rx_uatype'] : null;
$uahash = base64_encode_urlsafe(md5($_SERVER['HTTP_USER_AGENT'], true));
if (strncmp($cookie, $uahash . ':', strlen($uahash) + 1) !== 0)
{
$cookie = null;
}
elseif ($m === null)
{
$m = substr($cookie, -1);
}
if ($m === '1')
{
self::$_ismobile = TRUE;
}
elseif ($m === '0')
{
self::$_ismobile = FALSE;
}
else
{
self::$_ismobile = Rhymix\Framework\UA::isMobile() && (config('mobile.tablets') || !Rhymix\Framework\UA::isTablet());
}
// Set cookie to prevent recalculation.
$uatype = $uahash . ':' . (self::$_ismobile ? '1' : '0');
if ($cookie !== $uatype)
{
setcookie('rx_uatype', $uatype, 0, null, null, Context::isAlwaysSSL());
$_COOKIE['rx_uatype'] = $uatype;
}
return self::$_ismobile;
}
/**
* Get current mobile mode
*
* @return bool
*/
public static function _isFromMobilePhone()
{
return self::isFromMobilePhone();
}
/**
* Detect mobile device by user agent
*
* @return bool Returns true on mobile device or false.
*/
public static function isMobileCheckByAgent()
{
return Rhymix\Framework\UA::isMobile();
}
/**
* Check if user-agent is a tablet PC as iPad or Andoid tablet.
*
* @return bool TRUE for tablet, and FALSE for else.
*/
public static function isMobilePadCheckByAgent()
{
return Rhymix\Framework\UA::isTablet();
}
/**
* Set mobile mode
*
* @param bool $ismobile
* @return void
*/
public static function setMobile($ismobile)
{
self::$_ismobile = (bool)$ismobile;
}
/**
* Check if mobile view is enabled
*
* @raturn bool
*/
public static function isMobileEnabled()
{
$mobile_enabled = config('mobile.enabled');
if ($mobile_enabled === null)
{
$mobile_enabled = config('use_mobile_view') ? true : false;
}
return $mobile_enabled;
}
}