合并分支 'akun' 到 'master'
Akun 查看合并请求 !729
正在显示
1 个修改的文件
包含
73 行增加
和
205 行删除
| @@ -11,6 +11,7 @@ namespace App\Console\Commands\Domain; | @@ -11,6 +11,7 @@ namespace App\Console\Commands\Domain; | ||
| 11 | 11 | ||
| 12 | use App\Models\Devops\ServerConfig; | 12 | use App\Models\Devops\ServerConfig; |
| 13 | use App\Models\Devops\ServersIp; | 13 | use App\Models\Devops\ServersIp; |
| 14 | +use App\Models\Domain\DomainCreateTask; | ||
| 14 | use App\Models\Project\CountryCustom; | 15 | use App\Models\Project\CountryCustom; |
| 15 | use App\Models\Project\Project; | 16 | use App\Models\Project\Project; |
| 16 | use Illuminate\Console\Command; | 17 | use Illuminate\Console\Command; |
| @@ -42,9 +43,6 @@ class DomainInfo extends Command | @@ -42,9 +43,6 @@ class DomainInfo extends Command | ||
| 42 | */ | 43 | */ |
| 43 | public function handle() | 44 | public function handle() |
| 44 | { | 45 | { |
| 45 | - //更新主站域名有效时间 | ||
| 46 | - $this->startUpdateDomain(); | ||
| 47 | - | ||
| 48 | //主站证书到期更新 | 46 | //主站证书到期更新 |
| 49 | $this->startUpdateCert(); | 47 | $this->startUpdateCert(); |
| 50 | 48 | ||
| @@ -58,27 +56,6 @@ class DomainInfo extends Command | @@ -58,27 +56,6 @@ class DomainInfo extends Command | ||
| 58 | } | 56 | } |
| 59 | 57 | ||
| 60 | /** | 58 | /** |
| 61 | - * 更新域名到期时间 | ||
| 62 | - * @author Akun | ||
| 63 | - * @date 2024/02/26 10:26 | ||
| 64 | - */ | ||
| 65 | - public function startUpdateDomain() | ||
| 66 | - { | ||
| 67 | - $domainModel = new DomainInfoModel(); | ||
| 68 | - $list = $domainModel->where('status', '=', 1)->where(function ($query) { | ||
| 69 | - $query->whereNull('domain_end_time')->orWhere('domain_end_time', '<', date('Y-m-d H:i:s')); | ||
| 70 | - })->get()->toArray(); | ||
| 71 | - foreach ($list as $v) { | ||
| 72 | - $time = $this->updateDomain($v['domain']); | ||
| 73 | - $data = [ | ||
| 74 | - 'domain_start_time' => $time['start'], | ||
| 75 | - 'domain_end_time' => $time['end'] | ||
| 76 | - ]; | ||
| 77 | - $domainModel->edit($data, ['id' => $v['id']]); | ||
| 78 | - } | ||
| 79 | - } | ||
| 80 | - | ||
| 81 | - /** | ||
| 82 | * 主站证书到期更新 | 59 | * 主站证书到期更新 |
| 83 | * @author Akun | 60 | * @author Akun |
| 84 | * @date 2024/02/26 10:26 | 61 | * @date 2024/02/26 10:26 |
| @@ -88,33 +65,42 @@ class DomainInfo extends Command | @@ -88,33 +65,42 @@ class DomainInfo extends Command | ||
| 88 | $domainModel = new DomainInfoModel(); | 65 | $domainModel = new DomainInfoModel(); |
| 89 | $projectModel = new Project(); | 66 | $projectModel = new Project(); |
| 90 | $serverIpModel = new ServersIp(); | 67 | $serverIpModel = new ServersIp(); |
| 68 | + $domainCreateTaskModel = new DomainCreateTask(); | ||
| 91 | $end_day = date('Y-m-d H:i:s', time() + 3 * 24 * 3600);//3天后到期 | 69 | $end_day = date('Y-m-d H:i:s', time() + 3 * 24 * 3600);//3天后到期 |
| 92 | - $list = $domainModel->where('status', '=', 1)->where(function ($query) use ($end_day) { | 70 | + $list = $domainModel->where('status', '=', 1)->where('type', 1)->where(function ($query) use ($end_day) { |
| 93 | $query->whereNull('certificate_end_time')->orWhere('certificate_end_time', '<', $end_day); | 71 | $query->whereNull('certificate_end_time')->orWhere('certificate_end_time', '<', $end_day); |
| 94 | })->get()->toArray(); | 72 | })->get()->toArray(); |
| 95 | foreach ($list as $v) { | 73 | foreach ($list as $v) { |
| 96 | - //更新证书到期时间 | ||
| 97 | - $data = []; | ||
| 98 | - | ||
| 99 | - $ssl = $this->updateDomainSsl($v['domain']); | ||
| 100 | - $ssl['from'] && $data['certificate_start_time'] = $ssl['from']; | ||
| 101 | - $ssl['to'] && $data['certificate_end_time'] = $ssl['to']; | ||
| 102 | - | ||
| 103 | $project_info = $projectModel->read(['id' => $v['project_id']], ['serve_id']); | 74 | $project_info = $projectModel->read(['id' => $v['project_id']], ['serve_id']); |
| 104 | - if ($v['type'] == 1 && $ssl['to'] < $end_day && $project_info) { | 75 | + if (!$project_info) { |
| 76 | + continue; | ||
| 77 | + } | ||
| 78 | + | ||
| 105 | $servers_ip_info = $serverIpModel->read(['id' => $project_info['serve_id']], ['servers_id', 'ip', 'domain']); | 79 | $servers_ip_info = $serverIpModel->read(['id' => $project_info['serve_id']], ['servers_id', 'ip', 'domain']); |
| 106 | - if ($servers_ip_info && $servers_ip_info['servers_id'] != ServerConfig::SELF_SITE_ID && $this->check_cname($v['domain'], $servers_ip_info)) { | ||
| 107 | - //非自建站项目,申请免费证书 | ||
| 108 | - $this->updatePrivate($v); | 80 | + if (!$servers_ip_info) { |
| 81 | + continue; | ||
| 82 | + } | ||
| 109 | 83 | ||
| 110 | - $ssl_new = $this->updateDomainSsl($v['domain']); | ||
| 111 | - $ssl_new['from'] && $data['certificate_start_time'] = $ssl_new['from']; | ||
| 112 | - $ssl_new['to'] && $data['certificate_end_time'] = $ssl_new['to']; | 84 | + //过滤自建站项目域名 |
| 85 | + if ($servers_ip_info['servers_id'] == ServerConfig::SELF_SITE_ID) { | ||
| 86 | + continue; | ||
| 113 | } | 87 | } |
| 114 | 88 | ||
| 89 | + //过滤已解析到别的ip的域名 | ||
| 90 | + if (!$this->check_cname($v['domain'], $servers_ip_info)) { | ||
| 91 | + continue; | ||
| 115 | } | 92 | } |
| 116 | 93 | ||
| 117 | - $domainModel->edit($data, ['id' => $v['id']]); | 94 | + //创建更新站点证书任务 |
| 95 | + $task_info = $domainCreateTaskModel->read(['type' => DomainCreateTask::TYPE_MAIN, 'domain_id' => $v['id'], 'status' => ['<', DomainCreateTask::STATUS_SUC]]); | ||
| 96 | + if (!$task_info) { | ||
| 97 | + $domainCreateTaskModel->add([ | ||
| 98 | + 'server_id' => $servers_ip_info['servers_id'], | ||
| 99 | + 'project_id' => $v['project_id'], | ||
| 100 | + 'domain_id' => $v['id'], | ||
| 101 | + 'type' => DomainCreateTask::TYPE_MAIN | ||
| 102 | + ]); | ||
| 103 | + } | ||
| 118 | } | 104 | } |
| 119 | } | 105 | } |
| 120 | 106 | ||
| @@ -128,12 +114,12 @@ class DomainInfo extends Command | @@ -128,12 +114,12 @@ class DomainInfo extends Command | ||
| 128 | $domainModel = new DomainInfoModel(); | 114 | $domainModel = new DomainInfoModel(); |
| 129 | $projectModel = new Project(); | 115 | $projectModel = new Project(); |
| 130 | $serverIpModel = new ServersIp(); | 116 | $serverIpModel = new ServersIp(); |
| 117 | + $domainCreateTaskModel = new DomainCreateTask(); | ||
| 131 | $end_day = date('Y-m-d H:i:s', time() + 3 * 24 * 3600);//3天后到期 | 118 | $end_day = date('Y-m-d H:i:s', time() + 3 * 24 * 3600);//3天后到期 |
| 132 | - $list = $domainModel->where('status', '=', 1)->where('amp_status', 1)->where(function ($query) use ($end_day) { | 119 | + $list = $domainModel->where('status', '=', 1)->where('amp_status', 1)->where('amp_type', 1)->where(function ($query) use ($end_day) { |
| 133 | $query->whereNull('amp_certificate_end_time')->orWhere('amp_certificate_end_time', '<', $end_day); | 120 | $query->whereNull('amp_certificate_end_time')->orWhere('amp_certificate_end_time', '<', $end_day); |
| 134 | })->get()->toArray(); | 121 | })->get()->toArray(); |
| 135 | foreach ($list as $v) { | 122 | foreach ($list as $v) { |
| 136 | - //更新amp站点证书到期时间 | ||
| 137 | $domain_array = parse_url($v['domain']); | 123 | $domain_array = parse_url($v['domain']); |
| 138 | $host = $domain_array['host'] ?? $domain_array['path']; | 124 | $host = $domain_array['host'] ?? $domain_array['path']; |
| 139 | $host_array = explode('.', $host); | 125 | $host_array = explode('.', $host); |
| @@ -144,25 +130,36 @@ class DomainInfo extends Command | @@ -144,25 +130,36 @@ class DomainInfo extends Command | ||
| 144 | } | 130 | } |
| 145 | $amp_domain = implode('.', $host_array); | 131 | $amp_domain = implode('.', $host_array); |
| 146 | 132 | ||
| 147 | - $data = []; | ||
| 148 | - $ssl = $this->updateDomainSsl($amp_domain); | ||
| 149 | - $ssl['from'] && $data['amp_certificate_start_time'] = $ssl['from']; | ||
| 150 | - $ssl['to'] && $data['amp_certificate_end_time'] = $ssl['to']; | ||
| 151 | - | ||
| 152 | $project_info = $projectModel->read(['id' => $v['project_id']], ['serve_id']); | 133 | $project_info = $projectModel->read(['id' => $v['project_id']], ['serve_id']); |
| 153 | - if ($v['amp_type'] == 1 && $ssl['to'] < $end_day && $project_info) { | 134 | + if (!$project_info) { |
| 135 | + continue; | ||
| 136 | + } | ||
| 137 | + | ||
| 154 | $servers_ip_info = $serverIpModel->read(['id' => $project_info['serve_id']], ['servers_id', 'ip', 'domain']); | 138 | $servers_ip_info = $serverIpModel->read(['id' => $project_info['serve_id']], ['servers_id', 'ip', 'domain']); |
| 155 | - if ($servers_ip_info && $servers_ip_info['servers_id'] != ServerConfig::SELF_SITE_ID && $this->check_cname($amp_domain, $servers_ip_info)) { | ||
| 156 | - //非自建站项目,申请免费证书 | ||
| 157 | - $this->updateAmpPrivate($v); | 139 | + if (!$servers_ip_info) { |
| 140 | + continue; | ||
| 141 | + } | ||
| 158 | 142 | ||
| 159 | - $ssl_new = $this->updateDomainSsl($amp_domain); | ||
| 160 | - $ssl_new['from'] && $data['amp_certificate_start_time'] = $ssl_new['from']; | ||
| 161 | - $ssl_new['to'] && $data['amp_certificate_end_time'] = $ssl_new['to']; | 143 | + //过滤自建站项目域名 |
| 144 | + if ($servers_ip_info['servers_id'] == ServerConfig::SELF_SITE_ID) { | ||
| 145 | + continue; | ||
| 162 | } | 146 | } |
| 147 | + | ||
| 148 | + //过滤已解析到别的ip的域名 | ||
| 149 | + if (!$this->check_cname($amp_domain, $servers_ip_info)) { | ||
| 150 | + continue; | ||
| 163 | } | 151 | } |
| 164 | 152 | ||
| 165 | - $domainModel->edit($data, ['id' => $v['id']]); | 153 | + //创建更新站点证书任务 |
| 154 | + $task_info = $domainCreateTaskModel->read(['type' => DomainCreateTask::TYPE_AMP, 'domain_id' => $v['id'], 'status' => ['<', DomainCreateTask::STATUS_SUC]]); | ||
| 155 | + if (!$task_info) { | ||
| 156 | + $domainCreateTaskModel->add([ | ||
| 157 | + 'server_id' => $servers_ip_info['servers_id'], | ||
| 158 | + 'project_id' => $v['project_id'], | ||
| 159 | + 'domain_id' => $v['id'], | ||
| 160 | + 'type' => DomainCreateTask::TYPE_AMP | ||
| 161 | + ]); | ||
| 162 | + } | ||
| 166 | } | 163 | } |
| 167 | } | 164 | } |
| 168 | 165 | ||
| @@ -176,172 +173,43 @@ class DomainInfo extends Command | @@ -176,172 +173,43 @@ class DomainInfo extends Command | ||
| 176 | $customModel = new CountryCustom(); | 173 | $customModel = new CountryCustom(); |
| 177 | $projectModel = new Project(); | 174 | $projectModel = new Project(); |
| 178 | $serverIpModel = new ServersIp(); | 175 | $serverIpModel = new ServersIp(); |
| 176 | + $domainCreateTaskModel = new DomainCreateTask(); | ||
| 179 | $end_day = date('Y-m-d H:i:s', time() + 3 * 24 * 3600);//3天后到期 | 177 | $end_day = date('Y-m-d H:i:s', time() + 3 * 24 * 3600);//3天后到期 |
| 180 | - $list = $customModel->where('status', 1)->where('is_create', 1)->where(function ($query) use ($end_day) { | 178 | + $list = $customModel->where('status', 1)->where('is_create', 1)->where('type', 1)->where(function ($query) use ($end_day) { |
| 181 | $query->whereNull('certificate_end_time')->orWhere('certificate_end_time', '<', $end_day); | 179 | $query->whereNull('certificate_end_time')->orWhere('certificate_end_time', '<', $end_day); |
| 182 | })->get()->toArray(); | 180 | })->get()->toArray(); |
| 183 | foreach ($list as $v) { | 181 | foreach ($list as $v) { |
| 184 | - //更新证书到期时间 | ||
| 185 | - $data = []; | ||
| 186 | - $ssl = $this->updateDomainSsl($v['custom_domain']); | ||
| 187 | - $ssl['from'] && $data['certificate_start_time'] = $ssl['from']; | ||
| 188 | - $ssl['to'] && $data['certificate_end_time'] = $ssl['to']; | ||
| 189 | - | ||
| 190 | $project_info = $projectModel->read(['id' => $v['project_id']], ['serve_id']); | 182 | $project_info = $projectModel->read(['id' => $v['project_id']], ['serve_id']); |
| 191 | - if ($v['type'] == 1 && $ssl['to'] < $end_day && $project_info) { | ||
| 192 | - $servers_ip_info = $serverIpModel->read(['id' => $project_info['serve_id']], ['servers_id', 'ip', 'domain']); | ||
| 193 | - if ($servers_ip_info && $servers_ip_info['servers_id'] != ServerConfig::SELF_SITE_ID && $this->check_cname($v['custom_domain'], $servers_ip_info)) { | ||
| 194 | - //申请免费证书 | ||
| 195 | - $this->updateCustomPrivate($v['custom_domain']); | ||
| 196 | - | ||
| 197 | - $ssl_new = $this->updateDomainSsl($v['domain']); | ||
| 198 | - $ssl_new['from'] && $data['certificate_start_time'] = $ssl_new['from']; | ||
| 199 | - $ssl_new['to'] && $data['certificate_end_time'] = $ssl_new['to']; | ||
| 200 | - } | ||
| 201 | - } | ||
| 202 | - | ||
| 203 | - $customModel->edit($data, ['id' => $v['id']]); | ||
| 204 | - } | 183 | + if (!$project_info) { |
| 184 | + continue; | ||
| 205 | } | 185 | } |
| 206 | 186 | ||
| 207 | - /** | ||
| 208 | - * @remark :更新主站证书 | ||
| 209 | - * @name :updatePrivate | ||
| 210 | - * @author :lyh | ||
| 211 | - * @method :post | ||
| 212 | - * @time :2023/12/8 16:16 | ||
| 213 | - */ | ||
| 214 | - public function updatePrivate($param) | ||
| 215 | - { | ||
| 216 | - $url = 'https://' . $param['domain'] . '/api/applySsl/'; | ||
| 217 | - $param = [ | ||
| 218 | - "domain" => $param['domain'], | ||
| 219 | - "rewrite" => $param['extend_config'], | ||
| 220 | - 'other_domain' => $param['other_domain'], | ||
| 221 | - 'is_https' => $param['is_https'], | ||
| 222 | - 'not_allow_country' => $param['not_allow_country'], | ||
| 223 | - 'not_allow_ip' => $param['not_allow_ip'], | ||
| 224 | - 'is_redirect' => $param['is_redirect'] | ||
| 225 | - ]; | ||
| 226 | - return $this->curlRequest($url, $param); | 187 | + $servers_ip_info = $serverIpModel->read(['id' => $project_info['serve_id']], ['servers_id', 'ip', 'domain']); |
| 188 | + if (!$servers_ip_info) { | ||
| 189 | + continue; | ||
| 227 | } | 190 | } |
| 228 | 191 | ||
| 229 | - /** | ||
| 230 | - * 更新amp站证书 | ||
| 231 | - * @param $param | ||
| 232 | - * @return array | ||
| 233 | - * @author Akun | ||
| 234 | - * @date 2024/02/26 10:25 | ||
| 235 | - */ | ||
| 236 | - public function updateAmpPrivate($param) | ||
| 237 | - { | ||
| 238 | - $url = 'https://' . $param['domain'] . '/api/createSiteAmp/'; | ||
| 239 | - $param = [ | ||
| 240 | - "domain" => $param['domain'], | ||
| 241 | - 'not_allow_country' => $param['not_allow_country'], | ||
| 242 | - 'not_allow_ip' => $param['not_allow_ip'], | ||
| 243 | - 'is_redirect' => $param['is_redirect'] | ||
| 244 | - ]; | ||
| 245 | - return $this->curlRequest($url, $param); | 192 | + //过滤自建站项目域名 |
| 193 | + if ($servers_ip_info['servers_id'] == ServerConfig::SELF_SITE_ID) { | ||
| 194 | + continue; | ||
| 246 | } | 195 | } |
| 247 | 196 | ||
| 248 | - /** | ||
| 249 | - * 更新小语种自定义站证书 | ||
| 250 | - * @param $domain | ||
| 251 | - * @return array | ||
| 252 | - * @author Akun | ||
| 253 | - * @date 2024/03/23 10:07 | ||
| 254 | - */ | ||
| 255 | - public function updateCustomPrivate($domain) | ||
| 256 | - { | ||
| 257 | - $url = 'http://' . $domain . '/api/applySsl'; | ||
| 258 | - $param = [ | ||
| 259 | - 'domain' => $domain, | ||
| 260 | - 'rewrite' => [], | ||
| 261 | - 'other_domain' => [], | ||
| 262 | - 'is_https' => 1 | ||
| 263 | - ]; | ||
| 264 | - | ||
| 265 | - return $this->curlRequest($url, $param); | 197 | + //过滤已解析到别的ip的域名 |
| 198 | + if (!$this->check_cname($v['custom_domain'], $servers_ip_info)) { | ||
| 199 | + continue; | ||
| 266 | } | 200 | } |
| 267 | 201 | ||
| 268 | - public function curlRequest($url, $data, $method = 'POST', $header = [], $time_out = 60) | ||
| 269 | - { | ||
| 270 | - $ch = curl_init(); | ||
| 271 | - curl_setopt($ch, CURLOPT_TIMEOUT, $time_out); | ||
| 272 | - curl_setopt($ch, CURLOPT_URL, $url); | ||
| 273 | - curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); | ||
| 274 | - curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, FALSE); | ||
| 275 | - curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, FALSE); | ||
| 276 | - if ($data) | ||
| 277 | - curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($data)); | ||
| 278 | - curl_setopt($ch, CURLOPT_HTTPHEADER, array_merge([ | ||
| 279 | - 'Expect:', | ||
| 280 | - 'Content-type: application/json', | ||
| 281 | - 'Accept: application/json', | ||
| 282 | - ], $header) | ||
| 283 | - ); | ||
| 284 | - curl_setopt($ch, CURLOPT_CUSTOMREQUEST, $method); | ||
| 285 | - $response = curl_exec($ch); | ||
| 286 | - $code = curl_getinfo($ch, CURLINFO_HTTP_CODE); | ||
| 287 | - curl_close($ch); | ||
| 288 | - return [$code, $response]; | ||
| 289 | - } | ||
| 290 | - | ||
| 291 | - /** | ||
| 292 | - * @remark :获取域名证书有效时间 | ||
| 293 | - * @name :updateDomainSsl | ||
| 294 | - * @author :lyh | ||
| 295 | - * @method :post | ||
| 296 | - * @time :2023/9/11 15:07 | ||
| 297 | - */ | ||
| 298 | - public function updateDomainSsl($domain) | ||
| 299 | - { | ||
| 300 | - $valid_from = ''; | ||
| 301 | - $valid_to = ''; | ||
| 302 | - try { | ||
| 303 | - $context = stream_context_create([ | ||
| 304 | - 'ssl' => [ | ||
| 305 | - 'capture_peer_cert' => true, | ||
| 306 | - 'capture_peer_cert_chain' => false, | ||
| 307 | - 'verify_peer' => false, | ||
| 308 | - 'verify_peer_name' => false | ||
| 309 | - ], | 202 | + //创建更新站点证书任务 |
| 203 | + $task_info = $domainCreateTaskModel->read(['type' => DomainCreateTask::TYPE_CUSTOM, 'domain_id' => $v['id'], 'status' => ['<', DomainCreateTask::STATUS_SUC]]); | ||
| 204 | + if (!$task_info) { | ||
| 205 | + $domainCreateTaskModel->add([ | ||
| 206 | + 'server_id' => $servers_ip_info['servers_id'], | ||
| 207 | + 'project_id' => $v['project_id'], | ||
| 208 | + 'domain_id' => $v['id'], | ||
| 209 | + 'type' => DomainCreateTask::TYPE_CUSTOM | ||
| 310 | ]); | 210 | ]); |
| 311 | - $stream = stream_socket_client('ssl://' . $domain . ':443', $errno, $errstr, 30, STREAM_CLIENT_CONNECT, $context); | ||
| 312 | - if ($stream) { | ||
| 313 | - $remote_cert = stream_context_get_params($stream)['options']['ssl']['peer_certificate']; | ||
| 314 | - if ($remote_cert) { | ||
| 315 | - $valid_from = date('Y-m-d H:i:s', openssl_x509_parse($remote_cert)['validFrom_time_t']); | ||
| 316 | - $valid_to = date('Y-m-d H:i:s', openssl_x509_parse($remote_cert)['validTo_time_t']); | ||
| 317 | - } | ||
| 318 | } | 211 | } |
| 319 | - fclose($stream); | ||
| 320 | - } catch (\Exception $e) { | ||
| 321 | - $valid_from = ''; | ||
| 322 | - $valid_to = ''; | ||
| 323 | - } | ||
| 324 | - return ['from' => $valid_from, 'to' => $valid_to]; | ||
| 325 | - } | ||
| 326 | - | ||
| 327 | - /** | ||
| 328 | - * @remark :更新域名有效时间 | ||
| 329 | - * @name :updateDomain | ||
| 330 | - * @author :lyh | ||
| 331 | - * @method :post | ||
| 332 | - * @time :2023/9/11 15:11 | ||
| 333 | - */ | ||
| 334 | - public function updateDomain($domain) | ||
| 335 | - { | ||
| 336 | - $url = 'http://openai.waimaoq.com/v1/whois_api?domain=' . $domain; | ||
| 337 | - $response = http_get($url); | ||
| 338 | - $start = date('Y-m-d H:i:s'); | ||
| 339 | - $end = date('Y-m-d H:i:s'); | ||
| 340 | - if ($response['code'] == 200) { | ||
| 341 | - $start = $response['text']['creation_date']; | ||
| 342 | - $end = $response['text']['expiration_date']; | ||
| 343 | } | 212 | } |
| 344 | - return ['start' => $start, 'end' => $end]; | ||
| 345 | } | 213 | } |
| 346 | 214 | ||
| 347 | /** | 215 | /** |
-
请 注册 或 登录 后发表评论