package com.aegis.web.controller.camera;

import java.util.List;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.aegis.common.annotation.Log;
import com.aegis.common.core.controller.BaseController;
import com.aegis.common.core.domain.AjaxResult;
import com.aegis.common.core.page.TableDataInfo;
import com.aegis.common.enums.BusinessType;
import com.aegis.common.utils.StringUtils;
import com.aegis.camera.domain.Camera;
import com.aegis.camera.service.ICameraService;
import com.aegis.camera.service.StreamSessionService;
import com.aegis.camera.service.ZLMediaKitService;

/**
 * 摄像头Controller
 * 
 * @author aegis
 */
@RestController
@RequestMapping("/api/cameras")
public class CameraController extends BaseController {

    @Autowired
    private ICameraService cameraService;

    @Autowired
    private ZLMediaKitService zlMediaKitService;

    @Autowired
    private StreamSessionService streamSessionService;

    /**
     * 查询摄像头列表
     */
    @PreAuthorize("@ss.hasPermi('camera:camera:list')")
    @GetMapping("/list")
    public TableDataInfo list(Camera camera) {
        startPage();
        List<Camera> list = cameraService.listByCondition(camera);
        return getDataTable(list);
    }

    /**
     * 根据ID获取摄像头详情
     */
    @PreAuthorize("@ss.hasPermi('camera:camera:query')")
    @GetMapping(value = "/{id}")
    public AjaxResult getInfo(@PathVariable Long id) {
        return success(cameraService.getById(id));
    }

    /**
     * 新增摄像头
     */
    @PreAuthorize("@ss.hasPermi('camera:camera:add')")
    @Log(title = "摄像头管理", businessType = BusinessType.INSERT)
    @PostMapping
    public AjaxResult add(@Validated @RequestBody Camera camera) {
        if (StringUtils.isNotEmpty(camera.getCameraCode())) {
            // 检查编码唯一性在Service中处理
        }
        return toAjax(cameraService.save(camera));
    }

    /**
     * 修改摄像头
     */
    @PreAuthorize("@ss.hasPermi('camera:camera:edit')")
    @Log(title = "摄像头管理", businessType = BusinessType.UPDATE)
    @PutMapping
    public AjaxResult edit(@Validated @RequestBody Camera camera) {
        if (StringUtils.isNotEmpty(camera.getCameraCode())) {
            // 检查编码唯一性在Service中处理
        }
        return toAjax(cameraService.updateById(camera));
    }

    /**
     * 删除摄像头
     */
    @PreAuthorize("@ss.hasPermi('camera:camera:remove')")
    @Log(title = "摄像头管理", businessType = BusinessType.DELETE)
    @DeleteMapping("/{ids}")
    public AjaxResult remove(@PathVariable Long[] ids) {
        // 删除前先停止所有相关流
        for (Long id : ids) {
            try {
                Camera camera = cameraService.getById(id);
                if (camera != null && streamSessionService.isStreamActive(id)) {
                    zlMediaKitService.stopStream(camera);
                    streamSessionService.unregisterStream(id);
                }
            } catch (Exception e) {
                // 记录错误但不阻止删除操作
                logger.warn("删除摄像头时停止流失败，摄像头ID: {}", id, e);
            }
        }
        return toAjax(cameraService.removeByIds(java.util.Arrays.asList(ids)));
    }

    /**
     * 启动摄像头流（按需启动）
     */
    @PreAuthorize("@ss.hasPermi('camera:camera:query')")
    @Log(title = "摄像头管理", businessType = BusinessType.UPDATE)
    @PostMapping("/{id}/start")
    public AjaxResult startStream(@PathVariable Long id) {
        Camera camera = cameraService.getById(id);
        if (camera == null) {
            return error("摄像头不存在");
        }
        if (StringUtils.isBlank(camera.getProtocol())) {
            return error("摄像头协议类型未配置");
        }
        
        try {
            // 如果流已存在，先停止再启动（确保状态一致）
            if (streamSessionService.isStreamActive(id)) {
                zlMediaKitService.stopStream(camera);
                streamSessionService.unregisterStream(id);
            }
            
            // 启动流
            boolean started = zlMediaKitService.startStream(camera);
            if (started) {
                // 注册流会话
                streamSessionService.registerStream(id);
                // 返回播放地址
                java.util.Map<String, String> playUrls = zlMediaKitService.getPlayUrls(camera.getCameraCode());
                return success(playUrls);
            } else {
                return error("启动流失败，请检查摄像头配置和网络连接");
            }
        } catch (Exception e) {
            logger.error("启动摄像头流失败，摄像头ID: {}", id, e);
            return error("启动流失败：" + e.getMessage());
        }
    }

    /**
     * 停止摄像头流
     */
    @PreAuthorize("@ss.hasPermi('camera:camera:query')")
    @Log(title = "摄像头管理", businessType = BusinessType.UPDATE)
    @PostMapping("/{id}/stop")
    public AjaxResult stopStream(@PathVariable Long id) {
        Camera camera = cameraService.getById(id);
        if (camera == null) {
            return error("摄像头不存在");
        }
        
        try {
            zlMediaKitService.stopStream(camera);
            streamSessionService.unregisterStream(id);
            return success("流已停止");
        } catch (Exception e) {
            logger.error("停止摄像头流失败，摄像头ID: {}", id, e);
            return error("停止流失败：" + e.getMessage());
        }
    }

    /**
     * 获取摄像头播放地址（仅当流已启动时返回）
     */
    @PreAuthorize("@ss.hasPermi('camera:camera:query')")
    @GetMapping("/{id}/playUrls")
    public AjaxResult getPlayUrls(@PathVariable Long id) {
        Camera camera = cameraService.getById(id);
        if (camera == null) {
            return error("摄像头不存在");
        }
        
        // 检查流是否活跃
        if (!streamSessionService.isStreamActive(id)) {
            return error("流未启动，请先启动流");
        }
        
        try {
            // 更新最后访问时间，表示仍有用户在观看
            streamSessionService.updateLastAccess(id);
            java.util.Map<String, String> playUrls = zlMediaKitService.getPlayUrls(camera.getCameraCode());
            return success(playUrls);
        } catch (Exception e) {
            logger.error("获取播放地址失败，摄像头ID: {}", id, e);
            return error("获取播放地址失败：" + e.getMessage());
        }
    }
}