Compare commits

...

2 Commits

Author SHA1 Message Date
于宏哲PHP 5000aa31e8 Merge branch 'master' of http://gitlab.frkj.cc/php/zhjwxt 7 months ago
于宏哲PHP 237ebe5660 1 7 months ago
  1. 9
      admin/src/app/views/contract/contract.vue
  2. 2
      admin/src/app/views/order_table/components/order-table-edit.vue
  3. 6686
      admin/yarn.lock
  4. 4
      niucloud/app/adminapi/controller/contract/ContractDistribution.php
  5. 2
      niucloud/app/adminapi/route/salary.php
  6. 8
      niucloud/app/api/controller/apiController/Chat.php
  7. 7
      niucloud/app/api/controller/apiController/OrderTable.php
  8. 44
      niucloud/app/api/controller/apiController/PhysicalTest.php
  9. 6
      niucloud/app/api/controller/personnel/WechatBind.php
  10. 10
      niucloud/app/api/route/route.php
  11. 2
      niucloud/app/api/route/student.php
  12. 2
      niucloud/app/common.php
  13. 2
      niucloud/app/model/attendance/Attendance.php
  14. 5
      niucloud/app/service/admin/classroom/ClassroomService.php
  15. 5
      niucloud/app/service/admin/contract/ContractDistributionService.php
  16. 11
      niucloud/app/service/admin/order_table/OrderTableService.php
  17. 2
      niucloud/app/service/admin/personnel/PersonnelService.php
  18. 1
      niucloud/app/service/api/apiService/ContractService.php
  19. 10
      niucloud/app/service/api/apiService/OrderTableService.php
  20. 5
      niucloud/app/service/api/apiService/ResourceSharingService.php
  21. 22
      niucloud/app/service/api/apiService/TeachingResearchService.php
  22. 14
      niucloud/app/service/api/personnel/WechatBindService.php
  23. 22
      niucloud/app/service/api/student/PhysicalTestService.php
  24. 3
      niucloud/composer.json
  25. 2
      uniapp/api/member.js
  26. 4
      uniapp/common/config.js
  27. 2
      uniapp/manifest.json
  28. 31
      uniapp/pages-market/clue/add_clues.vue
  29. 2
      uniapp/pages-market/clue/index.vue
  30. 54
      uniapp/pages-market/my/set_up.vue
  31. 1
      uniapp/pages-student/orders/index.vue
  32. 2
      uniapp/pages-student/physical-test/index.vue

9
admin/src/app/views/contract/contract.vue

@ -133,13 +133,13 @@
<div class="file-upload-area"> <div class="file-upload-area">
<input <input
type="file" type="file"
accept=".docx,.doc" accept=".docx"
@change="handleFileSelect" @change="handleFileSelect"
class="file-input" class="file-input"
ref="fileInput" ref="fileInput"
:key="fileInputKey" :key="fileInputKey"
/> />
<div class="upload-tip">支持 .docx .doc 格式文件文件大小不超过 10MB</div> <div class="upload-tip">支持 .docx 格式文件文件大小不超过 10MB</div>
<div v-if="uploadForm.file_name" class="file-info"> <div v-if="uploadForm.file_name" class="file-info">
<span>📄 {{ uploadForm.file_name }}</span> <span>📄 {{ uploadForm.file_name }}</span>
<button type="button" @click="clearFile" class="clear-file-btn">×</button> <button type="button" @click="clearFile" class="clear-file-btn">×</button>
@ -1465,6 +1465,7 @@ const handleFileSelect = (event: Event) => {
const target = event.target as HTMLInputElement const target = event.target as HTMLInputElement
const file = target.files?.[0] const file = target.files?.[0]
console.log('📁 文件选择事件触发:', file) console.log('📁 文件选择事件触发:', file)
if (!file) { if (!file) {
@ -1476,11 +1477,11 @@ const handleFileSelect = (event: Event) => {
// - .docx .doc // - .docx .doc
const fileName = file.name.toLowerCase() const fileName = file.name.toLowerCase()
const allowedExtensions = ['.docx', '.doc'] const allowedExtensions = ['.docx']
const isValidType = allowedExtensions.some(ext => fileName.endsWith(ext)) const isValidType = allowedExtensions.some(ext => fileName.endsWith(ext))
if (!isValidType) { if (!isValidType) {
ElMessage.error('只支持上传 .docx 和 .doc 格式的文件!') ElMessage.error('只支持上传 .docx格式的文件!')
// input // input
uploadForm.file_data = null uploadForm.file_data = null
uploadForm.file_name = '' uploadForm.file_name = ''

2
admin/src/app/views/order_table/components/order-table-edit.vue

@ -51,7 +51,7 @@
<el-form-item :label="t('orderAmount')" prop="order_amount"> <el-form-item :label="t('orderAmount')" prop="order_amount">
<el-input v-model="formData.order_amount" :placeholder="t('orderAmountPlaceholder')" class="input-width" disabled/> <el-input v-model="formData.order_amount" :placeholder="t('orderAmountPlaceholder')" class="input-width" :disabled="formData.payment_type != 'deposit'"/>
</el-form-item> </el-form-item>

6686
admin/yarn.lock

File diff suppressed because it is too large

4
niucloud/app/adminapi/controller/contract/ContractDistribution.php

@ -103,7 +103,7 @@ class ContractDistribution extends BaseAdminController
if ($type == 1) { if ($type == 1) {
// 内部员工 - 从school_personnel表查询 // 内部员工 - 从school_personnel表查询
$personnel = \think\facade\Db::table('school_personnel') $personnel = \think\facade\Db::table('school_personnel')
->where('status', 1) ->where('status', 2)
->where('deleted_at', 0) ->where('deleted_at', 0)
->field('id, name, phone, email, account_type as role') ->field('id, name, phone, email, account_type as role')
->select() ->select()
@ -117,7 +117,7 @@ class ContractDistribution extends BaseAdminController
} else { } else {
// 外部会员 // 外部会员
$personnel = \think\facade\Db::table('member') $personnel = \think\facade\Db::table('member')
->where('status', 1) ->where('status', 2)
->field('member_id as id, nickname as name, mobile as phone, email') ->field('member_id as id, nickname as name, mobile as phone, email')
->select() ->select()
->toArray(); ->toArray();

2
niucloud/app/adminapi/route/salary.php

@ -43,7 +43,7 @@ Route::group('salary', function () {
// 工资条管理 // 工资条管理
Route::group('payroll', function () { Route::group('payroll', function () {
Route::get('list', 'salary.Payroll/list'); Route::get('list', 'salary.Payroll/list');
Route::get('info/:id', 'salary.Payroll/info'); Route::get('info', 'salary.Payroll/info');
Route::post('add', 'salary.Payroll/add'); Route::post('add', 'salary.Payroll/add');
Route::post('edit', 'salary.Payroll/edit'); Route::post('edit', 'salary.Payroll/edit');
Route::post('delete', 'salary.Payroll/delete'); Route::post('delete', 'salary.Payroll/delete');

8
niucloud/app/api/controller/apiController/Chat.php

@ -24,14 +24,18 @@ use core\base\BaseApiService;
*/ */
class Chat extends BaseApiService class Chat extends BaseApiService
{ {
public function __construct()
{
parent::__construct();
}
//获取好友关系列表 //获取好友关系列表
public function getChatFriendsList(Request $request) public function getChatFriendsList(Request $request)
{ {
$personnel_id = $request->param('personnel_id', '');//员工人力资源表id(两个参数2选1) $personnel_id = $request->param('personnel_id', '');//员工人力资源表id(两个参数2选1)
$customer_resources_id = $request->param('customer_resources_id', '');//学生资源表id(两个参数2选1) $customer_resources_id = $request->param('customer_resources_id', '');//学生资源表id(两个参数2选1)
if (empty($personnel_id) && empty($customer_resources_id)) { if (empty($personnel_id) && empty($customer_resources_id)) {
return fail('缺少参数'); // return fail('缺少参数');
$personnel_id = $this->member_id;
} }
$where = [ $where = [

7
niucloud/app/api/controller/apiController/OrderTable.php

@ -175,6 +175,13 @@ class OrderTable extends BaseApiService
["payment_id", ""], // 支付单号(可选) ["payment_id", ""], // 支付单号(可选)
]); ]);
$order = new \app\model\order_table\OrderTable();
$info = $order->where(['id' => $params['order_id']])->find();
if(!$params['order_status']){
$params['order_status'] = $info['order_status'] == 'pending' ? 'paid' : $info['order_status'];
}
// 验证必要参数 // 验证必要参数
if(empty($params['order_id']) || empty($params['order_status'])) { if(empty($params['order_id']) || empty($params['order_status'])) {
return fail('缺少必要参数'); return fail('缺少必要参数');

44
niucloud/app/api/controller/apiController/PhysicalTest.php

@ -15,6 +15,8 @@ use app\Request;
use app\service\api\apiService\ChatService; use app\service\api\apiService\ChatService;
use app\service\api\apiService\PhysicalTestService; use app\service\api\apiService\PhysicalTestService;
use core\base\BaseApiService; use core\base\BaseApiService;
use Exception;
use Imagick;
/** /**
* 体测报告-控制器相关接口 * 体测报告-控制器相关接口
@ -156,4 +158,46 @@ class PhysicalTest extends BaseApiService
return fail('上传失败:' . $e->getMessage()); return fail('上传失败:' . $e->getMessage());
} }
} }
public function pdfToImage(Request $request){
$pdfUrl = $request->param('pdf_url', '');
$saveDir = public_path() . "/uploads/pdf_images/";
if (!is_dir($saveDir)) {
mkdir($saveDir, 0777, true);
}
$tempPdf = $saveDir . uniqid() . ".pdf";
file_put_contents($tempPdf, file_get_contents($pdfUrl));
try {
$imagick = new Imagick();
$imagick->setResolution(150, 150); // 清晰度 DPI
$imagick->readImage($tempPdf."[0]"); // 只取第一页
$imagick->setImageFormat('jpg'); // 输出 jpg
$imagePath = $saveDir . uniqid("pdf_preview_") . ".jpg";
$imagick->writeImage($imagePath);
$imagick->clear();
$imagick->destroy();
// 删除临时 PDF
unlink($tempPdf);
// 返回 URL
$imageUrl = "https://api.hnhbty.cn/uploads/pdf_images/" . basename($imagePath);
header('Content-Type: application/json');
echo json_encode([
'code' => 1,
'data' => ['image_url' => $imageUrl]
]);
} catch (Exception $e) {
echo json_encode([
'code' => 0,
'message' => $e->getMessage()
]);
}
}
} }

6
niucloud/app/api/controller/personnel/WechatBind.php

@ -73,10 +73,12 @@ class WechatBind extends BaseApiController
{ {
$data = $this->request->params([ $data = $this->request->params([
['code', ''], ['code', ''],
['state', ''] ['state', ''],
['personnel_id',''],
['from','']
]); ]);
return (new WechatBindService())->wechatCallback($data['code'], $data['state']); return (new WechatBindService())->wechatCallback($data['code'], $data['state'],$data['personnel_id'],$data['from']);
} }
/** /**

10
niucloud/app/api/route/route.php

@ -52,6 +52,9 @@ Route::group(function () {
//微信公众号授权相关接口(不需要token验证) //微信公众号授权相关接口(不需要token验证)
Route::get('personnel/wechatAuthorize', 'personnel.WechatBind/wechatAuthorize'); Route::get('personnel/wechatAuthorize', 'personnel.WechatBind/wechatAuthorize');
Route::get('personnel/wechatCallback', 'personnel.WechatBind/wechatCallback'); Route::get('personnel/wechatCallback', 'personnel.WechatBind/wechatCallback');
}); });
/** /**
@ -166,7 +169,8 @@ Route::group(function () {
Route::get('test', 'login.Login/test'); Route::get('test', 'login.Login/test');
Route::get('class_reminder', 'login.Login/class_reminder'); Route::get('class_reminder', 'login.Login/class_reminder');
//员工端-订单管理-更新支付状态
Route::post('orderTable/updatePaymentStatus', 'apiController.OrderTable/updatePaymentStatus');
})->middleware(ApiChannel::class) })->middleware(ApiChannel::class)
->middleware(ApiCheckToken::class) ->middleware(ApiCheckToken::class)
->middleware(ApiLog::class); ->middleware(ApiLog::class);
@ -310,8 +314,6 @@ Route::group(function () {
Route::get('orderTable/info', 'apiController.OrderTable/info'); Route::get('orderTable/info', 'apiController.OrderTable/info');
//员工端-订单管理-创建 //员工端-订单管理-创建
Route::post('orderTable/add', 'apiController.OrderTable/add'); Route::post('orderTable/add', 'apiController.OrderTable/add');
//员工端-订单管理-更新支付状态
Route::post('orderTable/updatePaymentStatus', 'apiController.OrderTable/updatePaymentStatus');
//员工端-查询订单支付状态 //员工端-查询订单支付状态
Route::get('checkOrderPaymentStatus', 'apiController.OrderTable/checkOrderPaymentStatus'); Route::get('checkOrderPaymentStatus', 'apiController.OrderTable/checkOrderPaymentStatus');
@ -394,6 +396,7 @@ Route::group(function () {
Route::get('class/jlGetClasses/list', 'apiController.classApi/jlGetClassesList'); Route::get('class/jlGetClasses/list', 'apiController.classApi/jlGetClassesList');
//体测报告-列表 //体测报告-列表
Route::get('class/physicalTest', 'apiController.classApi/PhysicalTestList'); Route::get('class/physicalTest', 'apiController.classApi/PhysicalTestList');
//体测报告-详情 //体测报告-详情
Route::get('class/physicalTest/info', 'apiController.classApi/PhysicalTestInfo'); Route::get('class/physicalTest/info', 'apiController.classApi/PhysicalTestInfo');
//获取学员详情 //获取学员详情
@ -616,6 +619,7 @@ Route::group(function () {
// 员工端生成合同 // 员工端生成合同
Route::post('contract/confirmGenerateContract', 'apiController.Contract/confirmGenerateContract'); Route::post('contract/confirmGenerateContract', 'apiController.Contract/confirmGenerateContract');
})->middleware(ApiChannel::class) })->middleware(ApiChannel::class)
->middleware(ApiPersonnelCheckToken::class, true) ->middleware(ApiPersonnelCheckToken::class, true)
->middleware(ApiLog::class); ->middleware(ApiLog::class);

2
niucloud/app/api/route/student.php

@ -46,7 +46,7 @@ Route::group('physical-test', function () {
// 获取体测趋势数据 // 获取体测趋势数据
Route::get('trend', 'app\api\controller\student\PhysicalTestController@getPhysicalTestTrend'); Route::get('trend', 'app\api\controller\student\PhysicalTestController@getPhysicalTestTrend');
// PDF转图片分享 // PDF转图片分享
Route::post('share/:test_id', 'app\api\controller\student\PhysicalTestController@sharePhysicalTestPdf'); Route::post('share', 'app\api\controller\student\PhysicalTestController@sharePhysicalTestPdf');
})->middleware(['ApiCheckToken']); })->middleware(['ApiCheckToken']);
// 课程预约管理 // 课程预约管理

2
niucloud/app/common.php

@ -14,7 +14,7 @@ use app\service\core\upload\CoreImageService;
use app\service\core\sys\CoreSysConfigService; use app\service\core\sys\CoreSysConfigService;
use app\service\admin\performance\PerformanceService; use app\service\admin\performance\PerformanceService;
// 应用公共文件 // 应用公共文件123
/** /**
* 接口操作成功,返回信息 * 接口操作成功,返回信息

2
niucloud/app/model/attendance/Attendance.php

@ -116,7 +116,7 @@ class Attendance extends BaseModel
$val = (String)$data['status']; $val = (String)$data['status'];
if ((!empty($val) || isset($val)) && $val !== '') { if ((!empty($val) || isset($val)) && $val !== '') {
$dict = Dict::where('key',$key)->find(); $dict = Dict::where('key',$key)->find();
$dictionary = $dict['dictionary'] ?? []; $dictionary = $dict['dictionary'] ? json_decode(json_decode($dict['dictionary'],true),true) : [];
// 查找匹配的 name // 查找匹配的 name
$res = ''; $res = '';
foreach ($dictionary as $item) { foreach ($dictionary as $item) {

5
niucloud/app/service/admin/classroom/ClassroomService.php

@ -70,6 +70,8 @@ class ClassroomService extends BaseAdminService
*/ */
public function add(array $data) public function add(array $data)
{ {
$campus = new Campus();
$data['campus_name'] = $campus->where(['id' => $data['campus_id']])->value('campus_name');
$res = $this->model->create($data); $res = $this->model->create($data);
return $res->id; return $res->id;
@ -83,7 +85,8 @@ class ClassroomService extends BaseAdminService
*/ */
public function edit(int $id, array $data) public function edit(int $id, array $data)
{ {
$campus = new Campus();
$data['campus_name'] = $campus->where(['id' => $data['campus_id']])->value('campus_name');
$this->model->where([['id', '=', $id]])->update($data); $this->model->where([['id', '=', $id]])->update($data);
return true; return true;
} }

5
niucloud/app/service/admin/contract/ContractDistributionService.php

@ -72,10 +72,9 @@ class ContractDistributionService extends BaseAdminService
'contract_id' => $contractId, 'contract_id' => $contractId,
'personnel_id' => $personnelId, 'personnel_id' => $personnelId,
'type' => $type, 'type' => $type,
'status' => 'pending', 'status' => 1,
'source_type' => 'manual', 'source_type' => 'manual',
'source_id' => null, 'source_id' => null
'created_at' => time()
]; ];
$this->model->create($data); $this->model->create($data);

11
niucloud/app/service/admin/order_table/OrderTableService.php

@ -87,15 +87,16 @@ class OrderTableService extends BaseAdminService
public function add(array $data) public function add(array $data)
{ {
$personnel = new Personnel(); $personnel = new Personnel();
$data['staff_id'] = $personnel->where(['sys_user_id' => $this->uid])->value("id"); // $data['staff_id'] = $personnel->where(['sys_user_id' => $this->uid])->value("id");
if(!$data['staff_id']){ // if(!$data['staff_id']){
return fail("操作失败"); // return fail("操作人员角色不对");
} // }
$cr = new CustomerResources(); $cr = new CustomerResources();
$data['campus_id'] = $cr->where(['id' => $data['resource_id']])->value("campus"); $data['campus_id'] = $cr->where(['id' => $data['resource_id']])->value("campus");
// $data['staff_id'] = 1; $data['staff_id'] = 51;
$res = $this->model->create($data); $res = $this->model->create($data);
return success("操作成功"); return success("操作成功");

2
niucloud/app/service/admin/personnel/PersonnelService.php

@ -170,7 +170,7 @@ class PersonnelService extends BaseAdminService
} }
} }
$this->model->where([['id', '=', $id]])->update($data); $this->model->where([['id', '=', $id]])->update($data);
unset($info['birthday']);
(new PersonnelInfo())->where(['person_id' => $id])->update($info); (new PersonnelInfo())->where(['person_id' => $id])->update($info);
Db::commit(); Db::commit();

1
niucloud/app/service/api/apiService/ContractService.php

@ -48,6 +48,7 @@ class ContractService extends BaseApiService
return $res; return $res;
} }
// 查询合同签订记录,关联合同表 // 查询合同签订记录,关联合同表
// type=1是给员工签的合同,关联的是school_personnel表 // type=1是给员工签的合同,关联的是school_personnel表
$contractSignModel = new ContractSign(); $contractSignModel = new ContractSign();

10
niucloud/app/service/api/apiService/OrderTableService.php

@ -223,17 +223,23 @@ class OrderTableService extends BaseApiService
*/ */
public function handlePaymentSuccess(array $orderArray) public function handlePaymentSuccess(array $orderArray)
{ {
if($orderArray['payment_type'] !== 'deposit'){
// 1. 为学员分配课程 // 1. 为学员分配课程
$this->assignCourseToStudent($orderArray); $this->assignCourseToStudent($orderArray);
// 2. 创建合同签署记录 // 2. 创建合同签署记录
$this->createContractSign($orderArray); $this->createContractSign($orderArray);
// 4.处理赠品
$this->handleGift($orderArray);
}
if($orderArray['payment_type'] == 'deposit'){
// 3. 创建支付记录 // 3. 创建支付记录
$this->createPaymentRecord($orderArray); $this->createPaymentRecord($orderArray);
}
// 4.处理赠品
$this->handleGift($orderArray);
} }
/** /**

5
niucloud/app/service/api/apiService/ResourceSharingService.php

@ -299,6 +299,11 @@ class ResourceSharingService extends BaseApiService
$paid_resource_ids = $order_model->where('order_status', 'paid')->column('resource_id'); $paid_resource_ids = $order_model->where('order_status', 'paid')->column('resource_id');
$all_resource_ids = (new CustomerResources())->column('id'); $all_resource_ids = (new CustomerResources())->column('id');
$deal_resource_ids = array_diff($all_resource_ids, $paid_resource_ids); $deal_resource_ids = array_diff($all_resource_ids, $paid_resource_ids);
} else if ($where['deal_type'] === '定金') {
// 没有付费订单的资源
$paid_resource_ids = $order_model->where('payment_type', 'deposit')->column('resource_id');
$all_resource_ids = (new CustomerResources())->column('id');
$deal_resource_ids = array_diff($all_resource_ids, $paid_resource_ids);
} }
if (isset($deal_resource_ids)) { if (isset($deal_resource_ids)) {

22
niucloud/app/service/api/apiService/TeachingResearchService.php

@ -48,12 +48,12 @@ class TeachingResearchService extends BaseApiService
} }
if ($id !== null && $id !== '') { if ($id !== null && $id !== '') {
// 根据personnel_id获取sys_user_id // 根据personnel_id获取sys_user_id
$sys_user_id = Db::table('school_personnel') // $sys_user_id = Db::table('school_personnel')
->where('id', $id) // ->where('id', $id)
->value('sys_user_id'); // ->value('sys_user_id');
if ($sys_user_id) { if ($id) {
$where[] = [Db::raw("FIND_IN_SET($sys_user_id, user_permission)"), '>', 0]; $where[] = [Db::raw("FIND_IN_SET($id, user_permission)"), '>', 0];
} }
} }
$search_model = $LessonCourseTeaching->where($where)->field($field)->order($order); $search_model = $LessonCourseTeaching->where($where)->field($field)->order($order);
@ -80,14 +80,16 @@ class TeachingResearchService extends BaseApiService
$where = []; $where = [];
if ($id !== null && $id !== '') { if ($id !== null && $id !== '') {
// 根据personnel_id获取sys_user_id // 根据personnel_id获取sys_user_id
$sys_user_id = Db::table('school_personnel') // $sys_user_id = Db::table('school_personnel')
->where('id', $id) // ->where('id', $id)
->value('sys_user_id'); // ->value('sys_user_id');
if ($sys_user_id) {
$where[] = [Db::raw("FIND_IN_SET($sys_user_id, user_permission)"), '>', 0]; if ($id) {
$where[] = [Db::raw("FIND_IN_SET($id, user_permission)"), '>', 0];
} }
} }
$list = $LessonCourseTeaching->where($where)->distinct(true)->column('table_type'); $list = $LessonCourseTeaching->where($where)->distinct(true)->column('table_type');
return $list; return $list;
} }

14
niucloud/app/service/api/personnel/WechatBindService.php

@ -149,11 +149,14 @@ class WechatBindService extends BaseApiService
if (empty($redirect_uri)) { if (empty($redirect_uri)) {
throw new ApiException('回调地址不能为空'); throw new ApiException('回调地址不能为空');
} }
$state_data = json_decode($state, true);
try { try {
// 使用现有的微信授权服务 // 使用现有的微信授权服务
$core_wechat_service = new CoreWechatServeService(); $core_wechat_service = new CoreWechatServeService();
$callback_url = $core_wechat_service->authorization($redirect_uri . '?state=' . urlencode($state), 'snsapi_userinfo'); $callback_url = $core_wechat_service->authorization($redirect_uri . '?state=' . urlencode($state).'&personnel_id='.$state_data['personnel_id'].'&from='.$state_data['from'], 'snsapi_userinfo');
// 直接跳转到微信授权页面 // 直接跳转到微信授权页面
return redirect($callback_url); return redirect($callback_url);
@ -169,7 +172,7 @@ class WechatBindService extends BaseApiService
* @param string $state 状态参数 * @param string $state 状态参数
* @return Response * @return Response
*/ */
public function wechatCallback(string $code, string $state) public function wechatCallback(string $code, string $state, string $personnel_id, string $from)
{ {
try { try {
if (empty($code)) { if (empty($code)) {
@ -178,7 +181,8 @@ class WechatBindService extends BaseApiService
// 解析state参数 // 解析state参数
$state_data = json_decode(urldecode($state), true); $state_data = json_decode(urldecode($state), true);
if (!$state_data || !isset($state_data['personnel_id'])) {
if (!$personnel_id) {
return $this->buildCallbackPage('wechat_bind_error', '参数错误'); return $this->buildCallbackPage('wechat_bind_error', '参数错误');
} }
@ -186,11 +190,11 @@ class WechatBindService extends BaseApiService
$official_openid = $this->getOfficialOpenid($code); $official_openid = $this->getOfficialOpenid($code);
// 绑定公众号openid // 绑定公众号openid
$bind_result = $this->bindOfficialOpenid($state_data['personnel_id'], $official_openid); $bind_result = $this->bindOfficialOpenid($personnel_id, $official_openid);
if ($bind_result) { if ($bind_result) {
// 根据来源返回不同的页面 // 根据来源返回不同的页面
if (isset($state_data['from']) && $state_data['from'] === 'h5') { if ($from == 'h5') {
// H5环境,返回简单的成功页面 // H5环境,返回简单的成功页面
return $this->buildH5SuccessPage('微信绑定成功!'); return $this->buildH5SuccessPage('微信绑定成功!');
} else { } else {

22
niucloud/app/service/api/student/PhysicalTestService.php

@ -211,16 +211,26 @@ class PhysicalTestService extends BaseService
throw new CommonException('体测记录不存在'); throw new CommonException('体测记录不存在');
} }
// 本地保存路径
$saveDir = public_path() . "/upload/pdf_images/";
if (!is_dir($saveDir)) {
mkdir($saveDir, 0777, true);
}
// 下载远程 PDF 到本地临时文件
$pdfPath = $saveDir . uniqid() . ".pdf";
file_put_contents($pdfPath, file_get_contents($physicalTest['physical_test_report']));
// 获取第一个PDF文件 // 获取第一个PDF文件
$files = explode(',', $physicalTest['physical_test_report']); // $files = explode('/upload', $physicalTest['physical_test_report']);
$pdfFile = trim($files[0]); // $pdfFile = '/upload'.trim($files[0]);
if (!$pdfFile) { if (!$pdfPath) {
throw new CommonException('PDF文件路径无效'); throw new CommonException('PDF文件路径无效');
} }
// 构建完整文件路径
$pdfPath = public_path() . $pdfFile;
if (!file_exists($pdfPath)) { if (!file_exists($pdfPath)) {
throw new CommonException('PDF文件不存在'); throw new CommonException('PDF文件不存在');
@ -257,7 +267,7 @@ class PhysicalTestService extends BaseService
return [ return [
'image_url' => get_image_url($imagePath), 'image_url' => get_image_url($imagePath),
'image_path' => $imagePath, 'image_path' => $imagePath,
'pdf_url' => get_image_url($pdfFile), 'pdf_url' => get_image_url($pdfPath),
'message' => 'PDF转换为图片成功,可以分享给朋友了' 'message' => 'PDF转换为图片成功,可以分享给朋友了'
]; ];

3
niucloud/composer.json

@ -60,7 +60,8 @@
"hyperf/pimple": "~2.2.0", "hyperf/pimple": "~2.2.0",
"365taofang/huaweicloud-sdk-php-obs": "^3.23", "365taofang/huaweicloud-sdk-php-obs": "^3.23",
"ext-openssl": "*", "ext-openssl": "*",
"phpoffice/phpword": "^1.3" "phpoffice/phpword": "^1.3",
"ext-imagick": "*"
}, },
"require-dev": { "require-dev": {
"symfony/var-dumper": "v6.0.19", "symfony/var-dumper": "v6.0.19",

2
uniapp/api/member.js

@ -71,7 +71,7 @@ export default {
// 生成体测分享图片 // 生成体测分享图片
async generateShareImage(data = {}) { async generateShareImage(data = {}) {
return await http.post('/share-image', data); return await http.post('/physical-test/share', data);
}, },
//↓↓↓↓↓↓↓↓↓↓↓↓-----添加孩子相关接口-----↓↓↓↓↓↓↓↓↓↓↓↓ //↓↓↓↓↓↓↓↓↓↓↓↓-----添加孩子相关接口-----↓↓↓↓↓↓↓↓↓↓↓↓

4
uniapp/common/config.js

@ -3,8 +3,8 @@
const env = 'prod' const env = 'prod'
const isMockEnabled = false // 默认禁用Mock优先模式,仅作为回退 const isMockEnabled = false // 默认禁用Mock优先模式,仅作为回退
const isDebug = false // 默认启用调试模式 const isDebug = false // 默认启用调试模式
const devurl = 'http://localhost:20080/api' const devurl = 'https://api.hnhbty.cn/api'
const devimgurl = 'http://localhost:20080' const devimgurl = 'https://api.hnhbty.cn'
const produrl = 'https://api.hnhbty.cn/api' const produrl = 'https://api.hnhbty.cn/api'
const prodimgurl = 'https://api.hnhbty.cn' const prodimgurl = 'https://api.hnhbty.cn'
// API配置 - 支持环境变量 // API配置 - 支持环境变量

2
uniapp/manifest.json

@ -1,6 +1,6 @@
{ {
"name" : "智慧教务", "name" : "智慧教务",
"appid" : "__UNI__D7D400A", "appid" : "__UNI__70E6889",
"description" : "", "description" : "",
"versionName" : "1.0.0", "versionName" : "1.0.0",
"versionCode" : "100", "versionCode" : "100",

31
uniapp/pages-market/clue/add_clues.vue

@ -347,13 +347,13 @@
</view> </view>
</view> </view>
</fui-form-item> </fui-form-item>
<view style="color: #ffffff;width: 100%;text-align: left;margin: 10px;"> <!-- <view style="color: #ffffff;width: 100%;text-align: left;margin: 10px;">
时间/距离 时间/距离
</view> </view> -->
<!--可选上课时间--> <!--可选上课时间-->
<fui-form-item <fui-form-item
label="1、 可选上课时间" label="四、可选上课时间"
labelWidth="240" labelWidth="240"
labelSize='26' labelSize='26'
prop="" prop=""
@ -381,7 +381,7 @@
</fui-form-item> </fui-form-item>
<!--承诺到访时间--> <!--承诺到访时间-->
<fui-form-item <fui-form-item
label="2、 承诺到访时间" label="五、承诺到访时间"
labelSize='26' labelSize='26'
labelWidth="240" labelWidth="240"
prop="" prop=""
@ -393,14 +393,14 @@
<view <view
class="input-title" class="input-title"
style="margin-right:14rpx;" style="margin-right:14rpx;"
@click="openDate(`promised_visit_time`)"> @click="openDateTime(`promised_visit_time`)">
{{ (formData.promised_visit_time) ? formData.promised_visit_time : '点击选择' }} {{ (formData.promised_visit_time) ? formData.promised_visit_time : '点击选择' }}
</view> </view>
</view> </view>
</fui-form-item> </fui-form-item>
<!--距离--> <!--距离-->
<fui-form-item <fui-form-item
label="3、 距离" label="六、距离"
labelSize='26' labelSize='26'
label-width="210" label-width="210"
prop="title" prop="title"
@ -417,7 +417,7 @@
</view> </view>
</fui-form-item> </fui-form-item>
<!-- 决策人 --> <!-- 决策人 -->
<fui-form-item label="、决策人" labelSize='26' prop="decision_maker" background='#434544' labelColor='#fff' <fui-form-item label="、决策人" labelSize='26' prop="decision_maker" background='#434544' labelColor='#fff'
:bottomBorder='false'> :bottomBorder='false'>
<view class="input-title" style="margin-right:14rpx;"> <view class="input-title" style="margin-right:14rpx;">
<view class="input-title" style="margin-right:14rpx;" @click="openCicker('decision_maker')"> <view class="input-title" style="margin-right:14rpx;" @click="openCicker('decision_maker')">
@ -427,7 +427,7 @@
</fui-form-item> </fui-form-item>
<!-- 情感粘度 --> <!-- 情感粘度 -->
<fui-form-item <fui-form-item
label="、情感粘度" label="、情感粘度"
labelSize='26' labelSize='26'
label-width="210" label-width="210"
prop="emotional_stickiness_score" background='#434544' labelColor='#fff' prop="emotional_stickiness_score" background='#434544' labelColor='#fff'
@ -440,8 +440,9 @@
</fui-form-item> </fui-form-item>
<!--沟通备注--> <!--沟通备注-->
<fui-form-item <fui-form-item
label="沟通备注" label="九、沟通备注"
labelSize='26' labelSize='26'
label-width="210"
prop="title" prop="title"
background='#434544' background='#434544'
labelColor='#fff' labelColor='#fff'
@ -471,7 +472,7 @@
<fui-date-picker <fui-date-picker
:show="date_picker_show" :show="date_picker_show"
type="5" type="5"
:startYear="2020" :startYear="2025"
:endYear="2030" :endYear="2030"
:value="getCurrentDate()" :value="getCurrentDate()"
@change="change_date" @change="change_date"
@ -481,8 +482,8 @@
<!-- 日期时间选择器 --> <!-- 日期时间选择器 -->
<fui-date-picker <fui-date-picker
:show="datetime_picker_show" :show="datetime_picker_show"
type="1" type="5"
:startYear="2020" :startYear="2025"
:endYear="2030" :endYear="2030"
:value="getCurrentDateTime()" :value="getCurrentDateTime()"
@change="change_datetime" @change="change_datetime"
@ -1671,7 +1672,7 @@ export default {
// //
this.$nextTick(() => { this.$nextTick(() => {
this.date_picker_show = true this.datetime_picker_show = true
}) })
}, },
// //
@ -1751,6 +1752,8 @@ export default {
} }
} }
let input_name = this.datetime_picker_input_name let input_name = this.datetime_picker_input_name
this.formData[input_name] = val this.formData[input_name] = val

2
uniapp/pages-market/clue/index.vue

@ -416,7 +416,7 @@
attendanceIndex: 0, attendanceIndex: 0,
attendanceOptions: ['全部', '一访未到', '一访已到', '二访未到', '二访已到', '未到访'], attendanceOptions: ['全部', '一访未到', '一访已到', '二访未到', '二访已到', '未到访'],
dealIndex: 0, dealIndex: 0,
dealOptions: ['全部', '已成交', '未成交'], dealOptions: ['全部', '已成交','定金', '未成交'],
validIndex: 0, validIndex: 0,
validOptions: ['全部', '有效', '无效'], validOptions: ['全部', '有效', '无效'],
communicationIndex: 0, communicationIndex: 0,

54
uniapp/pages-market/my/set_up.vue

@ -15,26 +15,28 @@
</template> </template>
<script> <script>
import {Api_url} from '@/common/config.js' import {
import apiRoute from '@/api/apiRoute.js' Api_url
} from '@/common/config.js'
import apiRoute from '@/api/apiRoute.js'
export default { export default {
data() { data() {
return { return {
userInfo:{}
} }
}, },
methods: { methods: {
//退 //退
loginOut(){ loginOut() {
this.$util.loginOut() this.$util.loginOut()
}, },
privacy_agreement(type){ privacy_agreement(type) {
uni.navigateTo({ uni.navigateTo({
url: '/pages-common/privacy_agreement?type='+type url: '/pages-common/privacy_agreement?type=' + type
}) })
}, },
update_pass(){ update_pass() {
uni.navigateTo({ uni.navigateTo({
url: '/pages-market/my/update_pass' url: '/pages-market/my/update_pass'
}) })
@ -87,7 +89,8 @@ import apiRoute from '@/api/apiRoute.js'
} }
}, },
// //
async buildwx(){ async buildwx() {
await this.getUserInfo()//
try { try {
console.log('开始微信绑定流程') console.log('开始微信绑定流程')
@ -98,7 +101,7 @@ import apiRoute from '@/api/apiRoute.js'
// #endif // #endif
// #ifdef H5 // #ifdef H5
console.log('H5环境') // await this.bindWeixinInH5()
if (this.isWeixinBrowser()) { if (this.isWeixinBrowser()) {
console.log('微信浏览器环境') console.log('微信浏览器环境')
await this.bindWeixinInH5() await this.bindWeixinInH5()
@ -176,6 +179,7 @@ import apiRoute from '@/api/apiRoute.js'
// H5 // H5
async bindWeixinInH5() { async bindWeixinInH5() {
uni.showLoading({ uni.showLoading({
title: '正在跳转微信授权...' title: '正在跳转微信授权...'
}) })
@ -185,11 +189,13 @@ import apiRoute from '@/api/apiRoute.js'
const baseUrl = Api_url const baseUrl = Api_url
const redirectUri = encodeURIComponent(`${baseUrl}/personnel/wechatCallback`) const redirectUri = encodeURIComponent(`${baseUrl}/personnel/wechatCallback`)
const state = encodeURIComponent(JSON.stringify({ const state = encodeURIComponent(JSON.stringify({
personnel_id: this.$store.state.userInfo.id, personnel_id: this.userInfo?.id,
from: 'h5', from: 'h5',
timestamp: Date.now() timestamp: Date.now()
})) }))
const authUrl = `${baseUrl}/personnel/wechatAuthorize?redirect_uri=${redirectUri}&state=${state}` const authUrl = `${baseUrl}/personnel/wechatAuthorize?redirect_uri=${redirectUri}&state=${state}`
console.log('H5授权URL:', authUrl) console.log('H5授权URL:', authUrl)
@ -207,7 +213,28 @@ import apiRoute from '@/api/apiRoute.js'
}) })
} }
}, },
async getUserInfo() {
let data = {}
let res = await apiRoute.getPersonnelInfo(data);
if (res.code != 1) {
uni.showToast({
title: res.msg,
icon: 'none'
})
return
}
res.data.cameus_dept_arr.forEach((v, k) => {
let d_arr = []
v.dept_arr.forEach((dv, dk) => {
d_arr.push(dv.dept_name)
})
//
v.dept_name_str = d_arr.join(',')
})
this.userInfo = res.data
},
// openid // openid
getMiniProgramOpenid() { getMiniProgramOpenid() {
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
@ -338,7 +365,7 @@ import apiRoute from '@/api/apiRoute.js'
const redirectUri = encodeURIComponent(`${baseUrl}/personnel/wechatCallback`) const redirectUri = encodeURIComponent(`${baseUrl}/personnel/wechatCallback`)
const state = encodeURIComponent(JSON.stringify({ const state = encodeURIComponent(JSON.stringify({
mini_openid: miniOpenid, mini_openid: miniOpenid,
personnel_id: this.$store.state.userInfo.id, personnel_id: this.userInfo?.id,
from: 'miniprogram', from: 'miniprogram',
timestamp: Date.now() timestamp: Date.now()
})) }))
@ -358,12 +385,13 @@ import apiRoute from '@/api/apiRoute.js'
</script> </script>
<style lang="less" scoped> <style lang="less" scoped>
.assemble{ .assemble {
width: 100%; width: 100%;
height: 100vh; height: 100vh;
background: #333333; background: #333333;
} }
.option{
.option {
margin-bottom: 20rpx; margin-bottom: 20rpx;
background: #404045; background: #404045;
width: 100%; width: 100%;

1
uniapp/pages-student/orders/index.vue

@ -317,6 +317,7 @@
try { try {
// //
const userInfo = uni.getStorageSync('userInfo') const userInfo = uni.getStorageSync('userInfo')
if (userInfo && userInfo.id) { if (userInfo && userInfo.id) {
// URLstudent_id使ID // URLstudent_id使ID
if (!this.studentId) { if (!this.studentId) {

2
uniapp/pages-student/physical-test/index.vue

@ -279,7 +279,7 @@
try { try {
// APIPDF // APIPDF
const response = await apiRoute.convertPdfToImage({ const response = await apiRoute.generateShareImage({
pdf_url: pdfUrl, pdf_url: pdfUrl,
test_id: testId, test_id: testId,
pdf_index: pdfIndex pdf_index: pdfIndex

Loading…
Cancel
Save