[exam] add progress do update the same time

This commit is contained in:
xiaomlove
2021-04-27 02:44:44 +08:00
parent 465fd2bca8
commit d1b7561aae
17 changed files with 97 additions and 81 deletions

View File

@@ -29,9 +29,9 @@
<template #title>
<span>System</span>
</template>
<el-menu-item-group>
<el-menu-item index="/agent-allow"><i class="el-icon-menu" />Agent allow</el-menu-item>
</el-menu-item-group>
<!-- <el-menu-item-group>-->
<!-- <el-menu-item index="/agent-allow"><i class="el-icon-menu" />Agent allow</el-menu-item>-->
<!-- </el-menu-item-group>-->
<el-menu-item-group>
<el-menu-item index="/exam"><i class="el-icon-menu" />Exam</el-menu-item>
</el-menu-item-group>

View File

@@ -6,7 +6,7 @@
</div>
<div class="right">
<el-button type="primary" size="small" icon="el-icon-plus" @click="handleAdd">Add</el-button>
<!-- <el-button type="primary" size="small" icon="el-icon-plus" @click="handleAdd">Add</el-button>-->
</div>
</div>
</template>

View File

@@ -45,8 +45,7 @@ class Test extends Command
public function handle()
{
$rep = new ExamRepository();
// $r = $rep->assignToUser(3);
echo new A;
$r = $rep->addProgress(1, 1, 250, 1);
dd($r);
}
}

View File

@@ -22,13 +22,13 @@ class Exam extends NexusModel
];
const INDEX_UPLOADED = 1;
const INDEX_SEED_TIME_AVERGAGE = 2;
const INDEX_SEED_TIME_AVERAGE = 2;
const INDEX_DOWNLOADED = 3;
const INDEX_BONUS = 4;
public static $indexes = [
self::INDEX_UPLOADED => ['name' => 'Uploaded', 'unit' => 'GB'],
self::INDEX_SEED_TIME_AVERGAGE => ['name' => 'Seed Time Average', 'unit' => 'Hour'],
self::INDEX_SEED_TIME_AVERAGE => ['name' => 'Seed Time Average', 'unit' => 'Hour'],
self::INDEX_DOWNLOADED => ['name' => 'Downloaded', 'unit' => 'GB'],
self::INDEX_BONUS => ['name' => 'Bonus', 'unit' => ''],
];
@@ -41,7 +41,7 @@ class Exam extends NexusModel
self::FILTER_USER_REGISTER_TIME_RANGE => ['name' => 'User Register Time Range'],
];
public function getStatusTextAttribute()
public function getStatusTextAttribute(): string
{
return self::$status[$this->status]['text'] ?? '';
}

View File

@@ -4,7 +4,7 @@ namespace App\Models;
class ExamUser extends NexusModel
{
protected $fillable = ['exam_id', 'uid', 'status', 'result'];
protected $fillable = ['exam_id', 'uid', 'status', 'progress'];
public $timestamps = true;
@@ -17,7 +17,7 @@ class ExamUser extends NexusModel
];
protected $casts = [
'result' => 'json'
'progress' => 'json'
];
public function getStatusTextAttribute()

View File

@@ -11,7 +11,7 @@ class NexusModel extends Model
public $timestamps = false;
protected $perPage = 2;
// protected $perPage = 2;
/**
* 为数组 / JSON 序列化准备日期。

View File

@@ -57,8 +57,6 @@ class User extends Authenticatable
self::CLASS_STAFF_LEADER => ['text' => 'Staff Leader'],
];
protected $perPage = 2;
public function getClassTextAttribute(): string
{
return self::$classes[$this->class]['text'] ?? '';

View File

@@ -208,6 +208,7 @@ class ExamRepository extends BaseRepository
public function addProgress(int $examUserId, int $indexId, int $value, int $torrentId)
{
$logPrefix = "examUserId: $examUserId, indexId: $indexId, value: $value, torrentId: $torrentId";
$examUser = ExamUser::query()->with(['exam', 'user'])->findOrFail($examUserId);
if ($examUser->status != ExamUser::STATUS_NORMAL) {
throw new \InvalidArgumentException("ExamUser: $examUserId is not normal.");
@@ -226,7 +227,7 @@ class ExamRepository extends BaseRepository
}
$torrentFields = ['id', 'visible', 'banned'];
$torrent = Torrent::query()->findOrFail($torrentId, $torrentFields);
$torrent->checkIsNormal(true, $torrentFields);
$torrent->checkIsNormal($torrentFields);
$user = $examUser->user;
$user->checkIsNormal();
@@ -238,8 +239,12 @@ class ExamRepository extends BaseRepository
'index' => $indexId,
'value' => $value,
];
do_log('[addProgress] ' . nexus_json_encode($data));
return $examUser->progresses()->create($data);
do_log("$logPrefix [addProgress] " . nexus_json_encode($data));
$newProgress = $examUser->progresses()->create($data);
$examProgress = $this->calculateProgress($examUser);
do_log("$logPrefix [updateProgress] " . nexus_json_encode($examProgress));
$examUser->update(['progress' => $examProgress]);
return $newProgress;
}
public function getUserExamProgress($uid, $status = null)
@@ -256,11 +261,17 @@ class ExamRepository extends BaseRepository
if ($examUsers->count() > 1) {
do_log("$logPrefix, user exam more than 1.", 'warning');
}
/** @var ExamUser $examUser */
$examUser = $examUsers->first();
/** @var Exam $exam */
$progress = $this->calculateProgress($examUser);
do_log("$logPrefix, progress: " . nexus_json_encode($progress));
$examUser->progress = $progress;
return $examUser;
}
private function calculateProgress(ExamUser $examUser)
{
$exam = $examUser->exam;
$logPrefix .= ", exam: " . $exam->id;
$logPrefix = ", examUser: " . $examUser->id;
if ($examUser->begin) {
$logPrefix .= ", begin from examUser: " . $examUser->id;
$begin = $examUser->begin;
@@ -289,8 +300,9 @@ class ExamRepository extends BaseRepository
->get();
do_log("$logPrefix, query: " . last_query() . ", progressSum: " . $progressSum->toJson());
$examUser->progress = $progressSum->pluck('sum', 'index')->toArray();
return $examUser;
return $progressSum->pluck('sum', 'index')->toArray();
}

View File

@@ -3,7 +3,8 @@
if (!empty($_SERVER['HTTP_X_REQUEST_ID'])) {
define('REQUEST_ID', $_SERVER['HTTP_X_REQUEST_ID']);
} else {
define('REQUEST_ID', intval(LARAVEL_START * 10000));
$requestId = str_replace('.', '', LARAVEL_START);
define('REQUEST_ID', str_pad($requestId, 14, "0", STR_PAD_RIGHT));
}
define('IN_NEXUS', false);

View File

@@ -20,7 +20,7 @@ class CreateExamUsersTable extends Migration
$table->integer('status')->default(0);
$table->dateTime('begin')->nullable();
$table->dateTime('end')->nullable();
$table->text('result')->nullable();
$table->text('progress')->nullable();
$table->timestamps();
});
}

View File

@@ -2601,7 +2601,7 @@ if ($msgalert)
$exam = new \Nexus\Exam\Exam();
$examHtml = $exam->render($CURUSER['id']);
if (!empty($examHtml)) {
msgalert("messages.php", $examHtml, "green");
msgalert("messages.php", $examHtml, "blue");
}
}
if ($offlinemsg)

View File

@@ -533,3 +533,10 @@ function formatDatetime($datetime, $format = 'Y-m-d H:i:s')
}
return $datetime;
}
function formatTtl($seconds)
{
if ($seconds < 60) {
return $seconds . "seconds";
}
}

View File

@@ -324,6 +324,10 @@ $lang_functions = array
'exam_progress_result' => '结果',
'exam_progress_result_pass_yes' => '通过!',
'exam_progress_result_pass_no' => '<bold style="color: red">未通过!</bold>',
'exam_index_' . \App\Models\Exam::INDEX_UPLOADED => '上传量',
'exam_index_' . \App\Models\Exam::INDEX_SEED_TIME_AVERAGE => '平均做种时间',
'exam_index_' . \App\Models\Exam::INDEX_DOWNLOADED => '下载量',
'exam_index_' . \App\Models\Exam::INDEX_BONUS => '魔力值',
);
?>

View File

@@ -316,7 +316,19 @@ $lang_functions = array
'text_required' => '不能為空',
'text_invalid' => '非法',
'text_technical_info' => '技術信息',
'text_technical_info_help_text' => '文件技術信息來自軟件 <b><a href="https://mediaarea.net/en/MediaInfo" target=\'_blank\'>MediaInfo</a></b>,用該軟件打開文件,點擊菜單視圖(View)->文件(Text),在框中右鍵->全選,再右鍵->復制,粘貼到這裏來。'
'text_technical_info_help_text' => '文件技術信息來自軟件 <b><a href="https://mediaarea.net/en/MediaInfo" target=\'_blank\'>MediaInfo</a></b>,用該軟件打開文件,點擊菜單視圖(View)->文件(Text),在框中右鍵->全選,再右鍵->復制,粘貼到這裏來。',
'exam_name' => '考核名稱',
'exam_time_range' => '考核時間',
'exam_index' => '考核指標',
'exam_require' => '要求',
'exam_progress_current' => '當前',
'exam_progress_result' => '結果',
'exam_progress_result_pass_yes' => '通過!',
'exam_progress_result_pass_no' => '<bold style="color: red">未通過!</bold>',
'exam_index_' . \App\Models\Exam::INDEX_UPLOADED => '上傳量',
'exam_index_' . \App\Models\Exam::INDEX_SEED_TIME_AVERAGE => '平均做種時間',
'exam_index_' . \App\Models\Exam::INDEX_DOWNLOADED => '下載量',
'exam_index_' . \App\Models\Exam::INDEX_BONUS => '魔力值',
);
?>

View File

@@ -317,7 +317,19 @@ $lang_functions = array
'text_required' => 'Required',
'text_invalid' => 'Invalid',
'text_technical_info' => 'Technical Info',
'text_technical_info_help_text' => 'Technical Information comes from software <b><a href="https://mediaarea.net/en/MediaInfo" target=\'_blank\'>MediaInfo</a></b>open file, click the view menu > text > right click in the box > select all > copy > past into this box.'
'text_technical_info_help_text' => 'Technical Information comes from software <b><a href="https://mediaarea.net/en/MediaInfo" target=\'_blank\'>MediaInfo</a></b>open file, click the view menu > text > right click in the box > select all > copy > past into this box.',
'exam_name' => 'Exam Name',
'exam_time_range' => 'Exam Time',
'exam_index' => 'Exam Index',
'exam_require' => 'Require',
'exam_progress_current' => 'Current',
'exam_progress_result' => 'Result',
'exam_progress_result_pass_yes' => 'Pass!',
'exam_progress_result_pass_no' => '<bold style="color: red">Not Pass!</bold>',
'exam_index_' . \App\Models\Exam::INDEX_UPLOADED => 'Uploaded',
'exam_index_' . \App\Models\Exam::INDEX_SEED_TIME_AVERAGE => 'Seed Time Average',
'exam_index_' . \App\Models\Exam::INDEX_DOWNLOADED => 'Downloaded',
'exam_index_' . \App\Models\Exam::INDEX_BONUS => 'Bonus',
);
?>

View File

@@ -25,10 +25,10 @@ class Exam
$currentValue = $userExam->progress[$index['index']] ?? 0;
$unit = ExamModel::$indexes[$index['index']]['unit'] ?? '';
$row[] = sprintf(
'%s%s, %s%s %s, %s%s %s, %s%s',
$lang_functions['exam_index'] . ($key + 1), ExamModel::$indexes[$index['index']]['name'] ?? '',
'%s%s, %s%s %s, %s%s, %s%s',
$lang_functions['exam_index'] . ($key + 1), $lang_functions['exam_index_' . $index['index']] ?? '',
$lang_functions['exam_require'], $requireValue, $unit,
$lang_functions['exam_progress_current'], $currentValue, $unit,
$lang_functions['exam_progress_current'], $this->formatCurrentValue($index['index'], $currentValue),
$lang_functions['exam_progress_result'],
$currentValue >= $requireValue ? $lang_functions['exam_progress_result_pass_yes'] : $lang_functions['exam_progress_result_pass_no']
);
@@ -36,4 +36,16 @@ class Exam
}
return nl2br(implode("\n", $row));
}
private function formatCurrentValue($indexId, $value)
{
if ($indexId == ExamModel::INDEX_DOWNLOADED || $indexId == ExamModel::INDEX_UPLOADED) {
return mksize($value);
}
if ($indexId == ExamModel::INDEX_SEED_TIME_AVERAGE) {
return mkprettytime($value);
}
return $value;
}
}

View File

@@ -4,7 +4,7 @@
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Laravel</title>
<title>NexusPHP</title>
<!-- Fonts -->
<link href="https://fonts.googleapis.com/css2?family=Nunito:wght@400;600;700&display=swap" rel="stylesheet">
@@ -22,40 +22,18 @@
</head>
<body class="antialiased">
<div class="relative flex items-top justify-center min-h-screen bg-gray-100 dark:bg-gray-900 sm:items-center py-4 sm:pt-0">
@if (Route::has('login'))
<div class="hidden fixed top-0 right-0 px-6 py-4 sm:block">
@auth
<a href="{{ url('/home') }}" class="text-sm text-gray-700 underline">Home</a>
@else
<a href="{{ route('login') }}" class="text-sm text-gray-700 underline">Log in</a>
@if (Route::has('register'))
<a href="{{ route('register') }}" class="ml-4 text-sm text-gray-700 underline">Register</a>
@endif
@endauth
</div>
@endif
<div class="max-w-6xl mx-auto sm:px-6 lg:px-8">
<div class="flex justify-center pt-8 sm:justify-start sm:pt-0">
<svg viewBox="0 0 651 192" fill="none" xmlns="http://www.w3.org/2000/svg" class="h-16 w-auto text-gray-700 sm:h-20">
<g clip-path="url(#clip0)" fill="#EF3B2D">
<path d="M248.032 44.676h-16.466v100.23h47.394v-14.748h-30.928V44.676zM337.091 87.202c-2.101-3.341-5.083-5.965-8.949-7.875-3.865-1.909-7.756-2.864-11.669-2.864-5.062 0-9.69.931-13.89 2.792-4.201 1.861-7.804 4.417-10.811 7.661-3.007 3.246-5.347 6.993-7.016 11.239-1.672 4.249-2.506 8.713-2.506 13.389 0 4.774.834 9.26 2.506 13.459 1.669 4.202 4.009 7.925 7.016 11.169 3.007 3.246 6.609 5.799 10.811 7.66 4.199 1.861 8.828 2.792 13.89 2.792 3.913 0 7.804-.955 11.669-2.863 3.866-1.908 6.849-4.533 8.949-7.875v9.021h15.607V78.182h-15.607v9.02zm-1.431 32.503c-.955 2.578-2.291 4.821-4.009 6.73-1.719 1.91-3.795 3.437-6.229 4.582-2.435 1.146-5.133 1.718-8.091 1.718-2.96 0-5.633-.572-8.019-1.718-2.387-1.146-4.438-2.672-6.156-4.582-1.719-1.909-3.032-4.152-3.938-6.73-.909-2.577-1.36-5.298-1.36-8.161 0-2.864.451-5.585 1.36-8.162.905-2.577 2.219-4.819 3.938-6.729 1.718-1.908 3.77-3.437 6.156-4.582 2.386-1.146 5.059-1.718 8.019-1.718 2.958 0 5.656.572 8.091 1.718 2.434 1.146 4.51 2.674 6.229 4.582 1.718 1.91 3.054 4.152 4.009 6.729.953 2.577 1.432 5.298 1.432 8.162-.001 2.863-.479 5.584-1.432 8.161zM463.954 87.202c-2.101-3.341-5.083-5.965-8.949-7.875-3.865-1.909-7.756-2.864-11.669-2.864-5.062 0-9.69.931-13.89 2.792-4.201 1.861-7.804 4.417-10.811 7.661-3.007 3.246-5.347 6.993-7.016 11.239-1.672 4.249-2.506 8.713-2.506 13.389 0 4.774.834 9.26 2.506 13.459 1.669 4.202 4.009 7.925 7.016 11.169 3.007 3.246 6.609 5.799 10.811 7.66 4.199 1.861 8.828 2.792 13.89 2.792 3.913 0 7.804-.955 11.669-2.863 3.866-1.908 6.849-4.533 8.949-7.875v9.021h15.607V78.182h-15.607v9.02zm-1.432 32.503c-.955 2.578-2.291 4.821-4.009 6.73-1.719 1.91-3.795 3.437-6.229 4.582-2.435 1.146-5.133 1.718-8.091 1.718-2.96 0-5.633-.572-8.019-1.718-2.387-1.146-4.438-2.672-6.156-4.582-1.719-1.909-3.032-4.152-3.938-6.73-.909-2.577-1.36-5.298-1.36-8.161 0-2.864.451-5.585 1.36-8.162.905-2.577 2.219-4.819 3.938-6.729 1.718-1.908 3.77-3.437 6.156-4.582 2.386-1.146 5.059-1.718 8.019-1.718 2.958 0 5.656.572 8.091 1.718 2.434 1.146 4.51 2.674 6.229 4.582 1.718 1.91 3.054 4.152 4.009 6.729.953 2.577 1.432 5.298 1.432 8.162 0 2.863-.479 5.584-1.432 8.161zM650.772 44.676h-15.606v100.23h15.606V44.676zM365.013 144.906h15.607V93.538h26.776V78.182h-42.383v66.724zM542.133 78.182l-19.616 51.096-19.616-51.096h-15.808l25.617 66.724h19.614l25.617-66.724h-15.808zM591.98 76.466c-19.112 0-34.239 15.706-34.239 35.079 0 21.416 14.641 35.079 36.239 35.079 12.088 0 19.806-4.622 29.234-14.688l-10.544-8.158c-.006.008-7.958 10.449-19.832 10.449-13.802 0-19.612-11.127-19.612-16.884h51.777c2.72-22.043-11.772-40.877-33.023-40.877zm-18.713 29.28c.12-1.284 1.917-16.884 18.589-16.884 16.671 0 18.697 15.598 18.813 16.884h-37.402zM184.068 43.892c-.024-.088-.073-.165-.104-.25-.058-.157-.108-.316-.191-.46-.056-.097-.137-.176-.203-.265-.087-.117-.161-.242-.265-.345-.085-.086-.194-.148-.29-.223-.109-.085-.206-.182-.327-.252l-.002-.001-.002-.002-35.648-20.524a2.971 2.971 0 00-2.964 0l-35.647 20.522-.002.002-.002.001c-.121.07-.219.167-.327.252-.096.075-.205.138-.29.223-.103.103-.178.228-.265.345-.066.089-.147.169-.203.265-.083.144-.133.304-.191.46-.031.085-.08.162-.104.25-.067.249-.103.51-.103.776v38.979l-29.706 17.103V24.493a3 3 0 00-.103-.776c-.024-.088-.073-.165-.104-.25-.058-.157-.108-.316-.191-.46-.056-.097-.137-.176-.203-.265-.087-.117-.161-.242-.265-.345-.085-.086-.194-.148-.29-.223-.109-.085-.206-.182-.327-.252l-.002-.001-.002-.002L40.098 1.396a2.971 2.971 0 00-2.964 0L1.487 21.919l-.002.002-.002.001c-.121.07-.219.167-.327.252-.096.075-.205.138-.29.223-.103.103-.178.228-.265.345-.066.089-.147.169-.203.265-.083.144-.133.304-.191.46-.031.085-.08.162-.104.25-.067.249-.103.51-.103.776v122.09c0 1.063.568 2.044 1.489 2.575l71.293 41.045c.156.089.324.143.49.202.078.028.15.074.23.095a2.98 2.98 0 001.524 0c.069-.018.132-.059.2-.083.176-.061.354-.119.519-.214l71.293-41.045a2.971 2.971 0 001.489-2.575v-38.979l34.158-19.666a2.971 2.971 0 001.489-2.575V44.666a3.075 3.075 0 00-.106-.774zM74.255 143.167l-29.648-16.779 31.136-17.926.001-.001 34.164-19.669 29.674 17.084-21.772 12.428-43.555 24.863zm68.329-76.259v33.841l-12.475-7.182-17.231-9.92V49.806l12.475 7.182 17.231 9.92zm2.97-39.335l29.693 17.095-29.693 17.095-29.693-17.095 29.693-17.095zM54.06 114.089l-12.475 7.182V46.733l17.231-9.92 12.475-7.182v74.537l-17.231 9.921zM38.614 7.398l29.693 17.095-29.693 17.095L8.921 24.493 38.614 7.398zM5.938 29.632l12.475 7.182 17.231 9.92v79.676l.001.005-.001.006c0 .114.032.221.045.333.017.146.021.294.059.434l.002.007c.032.117.094.222.14.334.051.124.088.255.156.371a.036.036 0 00.004.009c.061.105.149.191.222.288.081.105.149.22.244.314l.008.01c.084.083.19.142.284.215.106.083.202.178.32.247l.013.005.011.008 34.139 19.321v34.175L5.939 144.867V29.632h-.001zm136.646 115.235l-65.352 37.625V148.31l48.399-27.628 16.953-9.677v33.862zm35.646-61.22l-29.706 17.102V66.908l17.231-9.92 12.475-7.182v33.841z"/>
</g>
</svg>
</div>
<div class="mt-8 bg-white dark:bg-gray-800 overflow-hidden shadow sm:rounded-lg">
<div class="grid grid-cols-1 md:grid-cols-2">
<div class="p-6">
<div class="flex items-center">
<svg fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="2" viewBox="0 0 24 24" class="w-8 h-8 text-gray-500"><path d="M12 6.253v13m0-13C10.832 5.477 9.246 5 7.5 5S4.168 5.477 3 6.253v13C4.168 18.477 5.754 18 7.5 18s3.332.477 4.5 1.253m0-13C13.168 5.477 14.754 5 16.5 5c1.747 0 3.332.477 4.5 1.253v13C19.832 18.477 18.247 18 16.5 18c-1.746 0-3.332.477-4.5 1.253"></path></svg>
<div class="ml-4 text-lg leading-7 font-semibold"><a href="https://laravel.com/docs" class="underline text-gray-900 dark:text-white">Documentation</a></div>
<div class="ml-4 text-lg leading-7 font-semibold"><a href="https://nexusphp.org" class="underline text-gray-900 dark:text-white">NexusPHP</a></div>
</div>
<div class="ml-12">
<div class="mt-2 text-gray-600 dark:text-gray-400 text-sm">
Laravel has wonderful, thorough documentation covering every aspect of the framework. Whether you are new to the framework or have previous experience with Laravel, we recommend reading all of the documentation from beginning to end.
功能完善、生态丰富、久经市场检验的 PT 建站系统。
</div>
</div>
</div>
@@ -63,12 +41,12 @@
<div class="p-6 border-t border-gray-200 dark:border-gray-700 md:border-t-0 md:border-l">
<div class="flex items-center">
<svg fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="2" viewBox="0 0 24 24" class="w-8 h-8 text-gray-500"><path d="M3 9a2 2 0 012-2h.93a2 2 0 001.664-.89l.812-1.22A2 2 0 0110.07 4h3.86a2 2 0 011.664.89l.812 1.22A2 2 0 0018.07 7H19a2 2 0 012 2v9a2 2 0 01-2 2H5a2 2 0 01-2-2V9z"></path><path d="M15 13a3 3 0 11-6 0 3 3 0 016 0z"></path></svg>
<div class="ml-4 text-lg leading-7 font-semibold"><a href="https://laracasts.com" class="underline text-gray-900 dark:text-white">Laracasts</a></div>
<div class="ml-4 text-lg leading-7 font-semibold"><a href="https://laravel.com" class="underline text-gray-900 dark:text-white">Lavavel</a></div>
</div>
<div class="ml-12">
<div class="mt-2 text-gray-600 dark:text-gray-400 text-sm">
Laracasts offers thousands of video tutorials on Laravel, PHP, and JavaScript development. Check them out, see for yourself, and massively level up your development skills in the process.
当今最流行的 PHP 开发框架。
</div>
</div>
</div>
@@ -76,12 +54,12 @@
<div class="p-6 border-t border-gray-200 dark:border-gray-700">
<div class="flex items-center">
<svg fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="2" viewBox="0 0 24 24" class="w-8 h-8 text-gray-500"><path d="M7 8h10M7 12h4m1 8l-4-4H5a2 2 0 01-2-2V6a2 2 0 012-2h14a2 2 0 012 2v8a2 2 0 01-2 2h-3l-4 4z"></path></svg>
<div class="ml-4 text-lg leading-7 font-semibold"><a href="https://laravel-news.com/" class="underline text-gray-900 dark:text-white">Laravel News</a></div>
<div class="ml-4 text-lg leading-7 font-semibold"><a href="https://doc.nexusphp.org/" class="underline text-gray-900 dark:text-white">使用文档</a></div>
</div>
<div class="ml-12">
<div class="mt-2 text-gray-600 dark:text-gray-400 text-sm">
Laravel News is a community driven portal and newsletter aggregating all of the latest and most important news in the Laravel ecosystem, including new package releases and tutorials.
包含安装、配置、使用等知识。
</div>
</div>
</div>
@@ -89,12 +67,12 @@
<div class="p-6 border-t border-gray-200 dark:border-gray-700 md:border-l">
<div class="flex items-center">
<svg fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="2" viewBox="0 0 24 24" class="w-8 h-8 text-gray-500"><path d="M3.055 11H5a2 2 0 012 2v1a2 2 0 002 2 2 2 0 012 2v2.945M8 3.935V5.5A2.5 2.5 0 0010.5 8h.5a2 2 0 012 2 2 2 0 104 0 2 2 0 012-2h1.064M15 20.488V18a2 2 0 012-2h3.064M21 12a9 9 0 11-18 0 9 9 0 0118 0z"></path></svg>
<div class="ml-4 text-lg leading-7 font-semibold text-gray-900 dark:text-white">Vibrant Ecosystem</div>
<div class="ml-4 text-lg leading-7 font-semibold text-gray-900 dark:text-white"><a href="https://github.com/xiaomlove/nexusphp" class="underline text-gray-900 dark:text-white">源代码</a></div>
</div>
<div class="ml-12">
<div class="mt-2 text-gray-600 dark:text-gray-400 text-sm">
Laravel's robust library of first-party tools and libraries, such as <a href="https://forge.laravel.com" class="underline">Forge</a>, <a href="https://vapor.laravel.com" class="underline">Vapor</a>, <a href="https://nova.laravel.com" class="underline">Nova</a>, and <a href="https://envoyer.io" class="underline">Envoyer</a> help you take your projects to the next level. Pair them with powerful open source libraries like <a href="https://laravel.com/docs/billing" class="underline">Cashier</a>, <a href="https://laravel.com/docs/dusk" class="underline">Dusk</a>, <a href="https://laravel.com/docs/broadcasting" class="underline">Echo</a>, <a href="https://laravel.com/docs/horizon" class="underline">Horizon</a>, <a href="https://laravel.com/docs/sanctum" class="underline">Sanctum</a>, <a href="https://laravel.com/docs/telescope" class="underline">Telescope</a>, and more.
为之贡献代码、提出功能建议或反馈 bug。
</div>
</div>
</div>
@@ -102,28 +80,9 @@
</div>
<div class="flex justify-center mt-4 sm:items-center sm:justify-between">
<div class="text-center text-sm text-gray-500 sm:text-left">
<div class="flex items-center">
<svg fill="none" stroke-linecap="round" stroke-linejoin="round" stroke-width="2" viewBox="0 0 24 24" stroke="currentColor" class="-mt-px w-5 h-5 text-gray-400">
<path d="M3 3h2l.4 2M7 13h10l4-8H5.4M7 13L5.4 5M7 13l-2.293 2.293c-.63.63-.184 1.707.707 1.707H17m0 0a2 2 0 100 4 2 2 0 000-4zm-8 2a2 2 0 11-4 0 2 2 0 014 0z"></path>
</svg>
<a href="https://laravel.bigcartel.com" class="ml-1 underline">
Shop
</a>
<svg fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="2" viewBox="0 0 24 24" class="ml-4 -mt-px w-5 h-5 text-gray-400">
<path d="M4.318 6.318a4.5 4.5 0 000 6.364L12 20.364l7.682-7.682a4.5 4.5 0 00-6.364-6.364L12 7.636l-1.318-1.318a4.5 4.5 0 00-6.364 0z"></path>
</svg>
<a href="https://github.com/sponsors/taylorotwell" class="ml-1 underline">
Sponsor
</a>
</div>
</div>
<div class="ml-4 text-center text-sm text-gray-500 sm:text-right sm:ml-0">
Laravel v{{ Illuminate\Foundation\Application::VERSION }} (PHP v{{ PHP_VERSION }})
Nexus PHP 1.6 + Laravel v{{ Illuminate\Foundation\Application::VERSION }} (PHP v{{ PHP_VERSION }})
</div>
</div>
</div>