mirror of
https://gitee.com/ShopeX/OMS
synced 2026-03-22 10:25:35 +08:00
512 lines
18 KiB
PHP
512 lines
18 KiB
PHP
<?php
|
|
/**
|
|
* Copyright 2012-2026 ShopeX (https://www.shopex.cn)
|
|
*
|
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
* you may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
|
|
|
|
if(!defined('APP_DIR')){
|
|
define('APP_DIR',ROOT_DIR.'/app');
|
|
}
|
|
|
|
if(!defined('TRAIT_DIR')){
|
|
define('TRAIT_DIR',ROOT_DIR.'/trait');
|
|
}
|
|
|
|
if(!defined('ECAE_MODE') && defined('ECAE_SITE_ID') && ECAE_SITE_ID > 0){
|
|
define('ECAE_MODE', true);
|
|
}else{
|
|
define('ECAE_MODE', false);
|
|
}
|
|
|
|
error_reporting(E_ALL ^ E_NOTICE ^ E_DEPRECATED ^ E_WARNING);
|
|
|
|
require_once(dirname(__FILE__) . '/lib/ego/ego.php');
|
|
|
|
class kernel{
|
|
|
|
static $base_url = null;
|
|
static $url_app_map = array();
|
|
static $app_url_map = array();
|
|
static $console_output = false;
|
|
static private $__online = null;
|
|
static private $__router = null;
|
|
static private $__db_instance = null;
|
|
static private $__singleton_instance = array();
|
|
static private $__request_instance = null;
|
|
static private $__single_apps = array();
|
|
static private $__service_list = array();
|
|
static private $__base_url = array();
|
|
static private $__language = null;
|
|
|
|
static function cleanInstance() {
|
|
self::$__db_instance = null;
|
|
self::$__singleton_instance = [];
|
|
self::$__request_instance =null;
|
|
self::$__single_apps =[];
|
|
}
|
|
|
|
static function boot(){
|
|
set_error_handler(array('kernel', 'exception_error_handler'));
|
|
try{
|
|
// 如果已经安装直接引入CONFIG
|
|
if (self::is_online()) {
|
|
require ROOT_DIR . '/config/config.php';
|
|
@include APP_DIR . '/base/defined.php';
|
|
}
|
|
|
|
// 兼容PHP ERROR
|
|
if (defined('SENTRY_OPTIONS') && constant('SENTRY_OPTIONS') && is_array(constant('SENTRY_OPTIONS'))){
|
|
\Sentry\init(constant('SENTRY_OPTIONS'));
|
|
}
|
|
|
|
require(ROOT_DIR.'/config/mapper.php');
|
|
self::$url_app_map = $urlmap;
|
|
foreach(self::$url_app_map AS $flag=>$value){
|
|
self::$app_url_map[$value['app']] = $flag;
|
|
}
|
|
|
|
/*// xss 和 sql 注入问题
|
|
$before_request = json_encode($_REQUEST);
|
|
$after_request = json_encode(self::request_filter($_REQUEST));
|
|
if ($before_request != $after_request) {
|
|
header("HTTP/1.1 508 Not Found");
|
|
exit;
|
|
}*/
|
|
// if(!self::register_autoload()){
|
|
// require(dirname(__FILE__) . '/autoload.php');
|
|
// }
|
|
|
|
$pathinfo = self::request()->get_path_info();
|
|
$jump = false;
|
|
if(isset($pathinfo[1])){
|
|
if($p = strpos($pathinfo,'/',2)){
|
|
$part = substr($pathinfo,0,$p);
|
|
}else{
|
|
$part = $pathinfo;
|
|
$jump = true;
|
|
}
|
|
}else{
|
|
$part = '/';
|
|
}
|
|
|
|
if($part=='/api'){
|
|
cachemgr::init();
|
|
if(isset($_POST['method']) && (substr($_POST['method'],0,4) == 'wms.' ||substr($_POST['method'],0,6) == 'store.' || in_array($_POST['method'],['ome.order.deliverypriority']))){
|
|
#wms请求处理
|
|
//return kernel::single('rpc_service')->process($pathinfo);
|
|
return kernel::single('erpapi_rpc_service',1)->process($pathinfo);
|
|
}else{
|
|
return kernel::single('base_rpc_service',1)->process($pathinfo);
|
|
}
|
|
}elseif($part=='/callback'){
|
|
// RPC callback 功能已移除
|
|
// cachemgr::init();
|
|
// return kernel::single('rpc_service',1)->callback($pathinfo);
|
|
die('RPC callback function has been removed');
|
|
}elseif($part=='/openapi'){
|
|
cachemgr::init();
|
|
return kernel::single('base_rpc_service',1)->process($pathinfo);
|
|
}elseif($part=='/app-doc'){
|
|
cachemgr::init();
|
|
return kernel::single('base_misc_doc',1)->display($pathinfo);
|
|
}elseif($part=='/qimen'){
|
|
//qimen路由(birkenstock勃肯中间件使用)
|
|
cachemgr::init();
|
|
return kernel::single('qimen_rpc_service',1)->process($pathinfo);
|
|
}
|
|
|
|
if(isset(self::$url_app_map[$part])){
|
|
if($jump){
|
|
$request_uri = self::request()->get_request_uri();
|
|
$urlinfo = parse_url($request_uri);
|
|
$query = $urlinfo['query']?'?'.$urlinfo['query']:'';
|
|
header('Location: '.$urlinfo['path'].'/'.$query);
|
|
exit;
|
|
}else{
|
|
$app = self::$url_app_map[$part]['app'];
|
|
$prefix_len = strlen($part)+1;
|
|
// kernel::set_lang(self::$url_app_map[$part]['lang']);
|
|
}
|
|
}else{
|
|
if ($part !== '/index.php') {
|
|
header("HTTP/1.1 404 Not Found");exit;
|
|
}
|
|
|
|
$app = self::$url_app_map['/']['app'];
|
|
$prefix_len = 1;
|
|
// kernel::set_lang(self::$url_app_map['/']['lang']);
|
|
}
|
|
|
|
$lang = kernel::single('base_component_request', 1)->get_cookie('oms-language');
|
|
kernel::set_lang($lang ?: self::$url_app_map['/']['lang']);
|
|
|
|
if(!$app){
|
|
readfile(ROOT_DIR.'/app/base/readme.html');
|
|
exit;
|
|
}
|
|
|
|
if(!self::is_online()){
|
|
if(file_exists(APP_DIR.'/setup/app.xml')){
|
|
if($app!='setup'){
|
|
//todo:进入安装check
|
|
setcookie('LOCAL_SETUP_URL', app::get('setup')->base_url(1), 0, '/');
|
|
header('Location: '. kernel::base_url().'/app/setup/check.php');
|
|
exit;
|
|
}
|
|
}else{
|
|
echo '<h1>System is Offline, install please.</h1>';
|
|
exit;
|
|
}
|
|
}
|
|
|
|
date_default_timezone_set(
|
|
defined('DEFAULT_TIMEZONE') ? ('Etc/GMT'.(DEFAULT_TIMEZONE>=0?(DEFAULT_TIMEZONE*-1):'+'.(DEFAULT_TIMEZONE*-1))):'UTC'
|
|
);
|
|
|
|
if(isset($pathinfo[$prefix_len])){
|
|
$path = substr($pathinfo,$prefix_len);
|
|
}else{
|
|
$path = '';
|
|
}
|
|
|
|
//init cachemgr
|
|
if($app=='setup'){
|
|
cachemgr::init(false);
|
|
}else{
|
|
cachemgr::init();
|
|
}
|
|
|
|
//get app router
|
|
self::$__router = app::get($app)->router();
|
|
self::$__router->dispatch($path);
|
|
}catch(Exception $e){
|
|
// 异常上报
|
|
\Sentry\captureException($e);
|
|
|
|
base_errorpage::exception_handler($e);
|
|
}
|
|
}
|
|
|
|
static function request_filter($data){
|
|
if(is_array($data)){
|
|
foreach($data as $key=>$v){
|
|
$data[$key] = self::request_filter($data[$key]);
|
|
}
|
|
}else{
|
|
$length=strlen($data);
|
|
if($length){
|
|
if($length<3000){// 字符长度超过太长的跳过验证
|
|
$filter_rule=array(
|
|
'xss' =>"[\'\"\;\*\<\>]+.*\b(on)[a-zA-Z]{3,15}[\s\r\n\v\f]*\=|\b(expression)\(|<script[\s\\\\\/]*.*>|(<!\[cdata\[)|\b(eval|alert|prompt|msgbox)\s*\(|url\((\#|data|javascript)",
|
|
'sql' =>"([^{\s]{1}.+(select|update|insert((\/\*[\S\s]*?\*\/)|(\s)|(\+))+into).+?(from|set)((\/\*[\S\s]*?\*\/)|(\s)|(\+))+)|[^{\s]{1}.+(create|delete|drop|truncate|rename|desc)((\/\*[\S\s]*?\*\/)|(\s)|(\+))+(table|from|database)((\/\*[\S\s]*?\*\/)|(\s)|(\+))|(into((\/\*[\S\s]*?\*\/)|\s|\+)+(dump|out)file\b)|\bsleep\((\s*)(\d*)(\s*)\)|benchmark\(([^\,]*)\,([^\,]*)\)|\b(declare|set|select)\b.*@|union\b.*(select|all)\b|(select|update|insert|create|delete|drop|grant|truncate|rename|exec|desc|from|table|database|set|where)\b.*((charset|ascii|bin|char|uncompress|concat|concat_ws|conv|export_set|hex|instr|left|load_file|locate|mid|sub|substring|oct|reverse|right|unhex)\(|(master\.\.sysdatabases|msysaccessobjects|msysqueries|sysmodules|mysql\.db|sys\.database_name|information_schema\.|sysobjects|sp_makewebtask|xp_cmdshell|sp_oamethod|sp_addextendedproc|sp_oacreate|xp_regread|sys\.dbms_export_extension))",
|
|
);
|
|
foreach ($filter_rule as $key => $value) {
|
|
$data = preg_replace("/" . $value . "/si", "", $data);
|
|
}
|
|
}
|
|
} else {
|
|
$data = $data;
|
|
}
|
|
}
|
|
return $data;
|
|
}
|
|
|
|
static function exception_error_handler($errno, $errstr, $errfile, $errline )
|
|
{
|
|
switch ($errno) {
|
|
case E_ERROR:
|
|
case E_USER_ERROR:
|
|
throw new ErrorException($errstr, 0, $errno, $errfile, $errline);
|
|
break;
|
|
|
|
case E_STRICT:
|
|
case E_USER_WARNING:
|
|
case E_USER_NOTICE:
|
|
default:
|
|
//do nothing
|
|
break;
|
|
}
|
|
return true;
|
|
}//End Function
|
|
|
|
/**
|
|
* @return base_router
|
|
*/
|
|
static function router(){
|
|
return self::$__router;
|
|
}
|
|
|
|
static function openapi_url($openapi_service_name,$method='access',$params=null){
|
|
if(substr($openapi_service_name,0,8)!='openapi.'){
|
|
trigger_error('$openapi_service_name must start with: openapi.');
|
|
return false;
|
|
}
|
|
$arg = array();
|
|
foreach((array)$params as $k=>$v){
|
|
$arg[] = urlencode($k);
|
|
$arg[] = urlencode(str_replace('/','%2F',$v));
|
|
}
|
|
return kernel::base_url(1).kernel::url_prefix().'/openapi/'.substr($openapi_service_name,8).'/'.$method.'/'.implode('/',$arg);
|
|
}
|
|
|
|
static function request(){
|
|
if(!isset(self::$__request_instance)){
|
|
self::$__request_instance = kernel::single('base_request',1);
|
|
}
|
|
return self::$__request_instance;
|
|
}
|
|
|
|
static function url_prefix(){
|
|
return (defined('WITH_REWRITE') && WITH_REWRITE === true)?'':'/index.php';
|
|
}
|
|
|
|
static function this_url($full=false){
|
|
return self::base_url($full).self::url_prefix().self::request()->get_path_info();
|
|
}
|
|
|
|
static function log($message,$keepline=false){
|
|
if(self::$console_output){
|
|
if($keepline){
|
|
echo $message;
|
|
}else{
|
|
echo $message = $message."\n";
|
|
}
|
|
}else{
|
|
$kernel_log = app::get('ome')->getConf('ome.kernel.log');
|
|
if($kernel_log == 'true'){
|
|
//modify by edwin.lzh@gmail.com 2010/6/10
|
|
$message = sprintf("%s\t%s\n", date("Y-m-d H:i:s"), $message);
|
|
switch(LOG_TYPE)
|
|
{
|
|
case 3:
|
|
if(defined('LOG_FILE')){
|
|
$logfile = str_replace('{date}', date("Ymd"), LOG_FILE);
|
|
$ip = ($_SERVER['REMOTE_ADDR']) ? $_SERVER['REMOTE_ADDR'] : '127.0.0.1';
|
|
$ip = str_replace(array('.', ':'), array('_', '_'), $ip);
|
|
$logfile = str_replace('{ip}', $ip, $logfile);
|
|
}else{
|
|
$logfile = DATA_DIR . '/logs/all.php';
|
|
}
|
|
if(!file_exists($logfile)){
|
|
if(!is_dir(dirname($logfile))) utils::mkdir_p(dirname($logfile));
|
|
file_put_contents($logfile, (defined(LOG_HEAD_TEXT))?LOG_HEAD_TEXT:'<'.'?php exit()?'.">\n");
|
|
}
|
|
@error_log($message, 3, $logfile);
|
|
break;
|
|
// case 0:
|
|
// default:
|
|
// @error_log($message, 0);
|
|
}//End Switch
|
|
}
|
|
}
|
|
}
|
|
|
|
static function base_url($full=false){
|
|
$c = ($full) ? 'true' : 'false';
|
|
if(!isset(self::$__base_url[$c])){
|
|
if(defined('BASE_URL')){
|
|
if($full){
|
|
self::$__base_url[$c] = constant('BASE_URL');
|
|
}else{
|
|
$url = parse_url(constant('BASE_URL'));
|
|
if(isset($url['path'])){
|
|
self::$__base_url[$c] = $url['path'];
|
|
}else{
|
|
self::$__base_url[$c] = '';
|
|
}
|
|
}
|
|
}else{
|
|
if(!isset(self::$base_url)){
|
|
self::$base_url = self::request()->get_base_url();
|
|
}
|
|
|
|
if(self::$base_url == '/'){
|
|
self::$base_url = '';
|
|
}
|
|
|
|
if($full){
|
|
self::$__base_url[$c] = strtolower(self::request()->get_schema()).'://'.self::request()->get_host().self::$base_url;
|
|
}else{
|
|
self::$__base_url[$c] = self::$base_url;
|
|
}
|
|
}
|
|
}
|
|
return self::$__base_url[$c];
|
|
}
|
|
|
|
/**
|
|
* 获取当前网站的域名
|
|
* @param bool $full
|
|
*/
|
|
public static function domain_url($full = true)
|
|
{
|
|
$result = kernel::base_url($full);
|
|
if (empty(strpos($result, '://'))) {
|
|
return $result;
|
|
}
|
|
|
|
list($prefix, $domain) = explode('://', $result);
|
|
return $domain;
|
|
}
|
|
|
|
public static function get_host_url()
|
|
{
|
|
return strtolower(self::request()->get_schema()).'://'.self::request()->get_host();
|
|
}
|
|
|
|
static function set_online($mode){
|
|
self::$__online = $mode;
|
|
}
|
|
|
|
static function is_online(){
|
|
if(self::$__online===null){
|
|
self::$__online = file_exists(ROOT_DIR.'/config/config.php');
|
|
}
|
|
return self::$__online;
|
|
}
|
|
|
|
static function single($class_name,$arg=null){
|
|
if($arg===null){
|
|
$p = strpos($class_name,'_');
|
|
if($p){
|
|
$app_id = substr($class_name,0,$p);
|
|
if(!isset(self::$__single_apps[$app_id])){
|
|
self::$__single_apps[$app_id] = app::get($app_id);
|
|
}
|
|
$arg = self::$__single_apps[$app_id];
|
|
}
|
|
}
|
|
if(is_object($arg)){
|
|
$key = get_class($arg);
|
|
if($key==='app'){
|
|
$key .= '.' . $arg->app_id;
|
|
}
|
|
$key = '__class__' . $key;
|
|
}else{
|
|
$key = md5('__key__'.serialize($arg));
|
|
}
|
|
if(!isset(self::$__singleton_instance[$class_name][$key])){
|
|
self::$__singleton_instance[$class_name][$key] = new $class_name($arg);
|
|
}
|
|
return self::$__singleton_instance[$class_name][$key];
|
|
}
|
|
|
|
/** @return base_db_connections */
|
|
static function database(){
|
|
if(!isset(self::$__db_instance)){
|
|
$classname = defined('DATABASE_OBJECT') ? constant('DATABASE_OBJECT') : 'base_db_connections';
|
|
$obj = new $classname;
|
|
if($obj instanceof base_interface_db){
|
|
self::$__db_instance = $obj;
|
|
}else{
|
|
trigger_error(DATABASE_OBJECT.' must implements base_interface_db!', E_USER_ERROR);
|
|
exit;
|
|
}
|
|
}
|
|
return self::$__db_instance;
|
|
}
|
|
|
|
static function service($srv_name,$filter=null){
|
|
$defined_service = app::get('base')->getConf('server.'.$srv_name);
|
|
if($defined_service && $defined_service = kernel::single($defined_service)){
|
|
return $defined_service;
|
|
}
|
|
return self::servicelist($srv_name,$filter)->current();
|
|
}
|
|
|
|
static function servicelist($srv_name,$filter=null){
|
|
if(self::is_online()){
|
|
if(base_kvstore::instance('service')->fetch($srv_name,$service_define)){
|
|
return $service_define ? new service($service_define,$filter) : new ArrayIterator(array());
|
|
}
|
|
if(!(defined('WITHOUT_KVSTORE_PERSISTENT') && constant('WITHOUT_KVSTORE_PERSISTENT')) && get_class(base_kvstore::instance('service')->get_controller())!='base_kvstore_mysql'){
|
|
if(kernel::single('base_kvstore_mysql', 'service')->fetch($srv_name, $service_define)) {
|
|
base_kvstore::instance('service')->store($srv_name, $service_define);
|
|
return $service_define ? new service($service_define,$filter) : new ArrayIterator(array());
|
|
}
|
|
base_kvstore::instance('service')->store($srv_name, []);
|
|
}
|
|
}
|
|
return new ArrayIterator(array());
|
|
}
|
|
|
|
static function strip_magic_quotes(&$var){
|
|
foreach($var as $k=>$v){
|
|
if(is_array($v)){
|
|
self::strip_magic_quotes($var[$k]);
|
|
}else{
|
|
$var[$k] = stripcslashes($v);
|
|
}
|
|
}
|
|
}
|
|
|
|
static function register_autoload($load=array('kernel', 'autoload'))
|
|
{
|
|
if(function_exists('spl_autoload_register')){
|
|
return spl_autoload_register($load);
|
|
}else{
|
|
return false;
|
|
}
|
|
}
|
|
|
|
static function unregister_autoload($load=array('kernel', 'autoload'))
|
|
{
|
|
if(function_exists('spl_autoload_register')){
|
|
return spl_autoload_unregister($load);
|
|
}else{
|
|
return false;
|
|
}
|
|
}
|
|
|
|
static function autoload($class_name)
|
|
{
|
|
self::require_ego();
|
|
_eogo_auto_load($class_name);
|
|
}
|
|
|
|
/**
|
|
* 设置_lang
|
|
* @param mixed $language language
|
|
* @return mixed 返回操作结果
|
|
*/
|
|
static public function set_lang($language)
|
|
{
|
|
self::$__language = trim(strtolower($language));
|
|
}//End Function
|
|
|
|
/**
|
|
* 获取_lang
|
|
* @return mixed 返回结果
|
|
*/
|
|
static public function get_lang()
|
|
{
|
|
return self::$__language ? self::$__language : ((defined('LANG')&&constant('LANG')) ? LANG : 'zh-cn');
|
|
}//End Function
|
|
|
|
/**
|
|
* require_ego
|
|
* @return mixed 返回值
|
|
*/
|
|
static public function require_ego() {
|
|
|
|
require_once(dirname(__FILE__) . '/lib/ego/ego.php');
|
|
|
|
}
|
|
}
|
|
|
|
function __($str){
|
|
return $str;
|
|
}
|