OWL ITS + 탐지시스템(인터넷 진흥원)
이민희
2022-03-03 2b0d6901597206d1c24abad0ff3ac0889f9194dd
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
package kr.wisestone.owl.service.impl;
 
import kr.wisestone.owl.domain.*;
import kr.wisestone.owl.mapper.DepartmentMapper;
import kr.wisestone.owl.repository.UserDepartmentRepository;
import kr.wisestone.owl.service.*;
import kr.wisestone.owl.web.condition.DepartmentCondition;
import kr.wisestone.owl.web.condition.UserCondition;
import kr.wisestone.owl.web.form.DepartmentForm;
import org.jsoup.Jsoup;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.ui.Model;
import com.google.common.collect.Lists;
import kr.wisestone.owl.common.ExcelConditionCheck;
import kr.wisestone.owl.constant.Constants;
import kr.wisestone.owl.constant.MsgConstants;
import kr.wisestone.owl.exception.OwlRuntimeException;
import kr.wisestone.owl.repository.DepartmentRepository;
import kr.wisestone.owl.util.ConvertUtil;
import kr.wisestone.owl.vo.*;
import kr.wisestone.owl.web.view.ExcelView;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Pageable;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.stereotype.Service;
import org.springframework.web.servlet.ModelAndView;
 
import javax.servlet.http.HttpServletRequest;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
 
@Service
public class DepartmentServiceImpl extends AbstractServiceImpl<Department, Long, JpaRepository<Department, Long>> implements DepartmentService {
 
    private static final Logger log = LoggerFactory.getLogger(IssueServiceImpl.class);
 
    @Autowired
    private DepartmentRepository departmentRepository;
 
    @Autowired
    private UserDepartmentService userDepartmentService;
 
    @Autowired
    private DepartmentMapper departmentMapper;
 
    @Autowired
    private DepartmentService departmentService;
 
    @Autowired
    private WorkflowDepartmentService workflowDepartmentService;
 
    @Autowired
    private ProjectRoleDepartmentService projectRoleDepartmentService;
 
    @Autowired
    private IssueDepartmentService issueDepartmentService;
 
    @Autowired
    private ProjectRoleService projectRoleService;
 
    @Autowired
    private IssueTypeService issueTypeService;
 
    @Autowired
    private WorkspaceService workspaceService;
 
    @Autowired
    private ExcelView excelView;
 
    @Autowired
    private ExcelConditionCheck excelConditionCheck;
 
    @Override
    protected JpaRepository<Department, Long> getRepository() {
        return this.departmentRepository;
    }
 
    // 부서 추가
    @Override
    public Department add(DepartmentForm departmentForm) {
        Department department = ConvertUtil.copyProperties(departmentForm, Department.class);
        departmentRepository.saveAndFlush(department);
        return department;
    }
 
    // 부서 목록을 가져온다.
    @Override
    public List<DepartmentVo>find(Map<String, Object> resJsonData,
                                            DepartmentCondition condition, Pageable pageable) {
        condition.setPage(pageable.getPageNumber() * pageable.getPageSize());
        condition.setPageSize(pageable.getPageSize());
 
        List<Map<String, Object>> results = this.departmentMapper.find(condition);
        Long totalDepartmentCount = this.departmentMapper.count(condition);
 
        return this.convertDepartmentVoToMap(results, totalDepartmentCount, pageable, resJsonData);
    }
 
    // 부서 상세 조회한다.
    @Override
    public void detail(Map<String, Object> resJsonData, DepartmentCondition departmentCondition) {
        DepartmentVo departmentVo = new DepartmentVo();
 
        Long departmentId = departmentCondition.getId();
        if (departmentId != null) {
            Department department = this.getDepartment(departmentId);
            departmentVo = ConvertUtil.copyProperties(department, DepartmentVo.class);
        }
        resJsonData.put(Constants.RES_KEY_CONTENTS, departmentVo);
    }
 
    // 부서 정보를 수정한다.
    @Override
    public void modify(DepartmentForm departmentForm) {
        Department department = ConvertUtil.copyProperties(departmentForm, Department.class);
        departmentRepository.saveAndFlush(department);
    }
 
    // 부서를 삭제한다.
    @Override
    public void remove(DepartmentForm departmentForm) {
        if (departmentForm.getRemoveIds().size() < 1) {
            throw new OwlRuntimeException(
                    this.messageAccessor.getMessage(MsgConstants.DEPARTMENT_REMOVE_NOT_SELECT));
        }
 
        for (Long id : departmentForm.getRemoveIds()) {
            if (this.departmentService.countInDepartment(id)) {
                //  사용자가 부서에 속해 있는지 체크
                throw new OwlRuntimeException(
                        this.messageAccessor.getMessage(MsgConstants.DEPARTMENT_ALREADY_IN_USE));
 
            } else if (this.workflowDepartmentService.usingDepartment(id)) {
                //  워크플로우에서 해당 부서를 사용하고 있는지 체크
                throw new OwlRuntimeException(
                        this.messageAccessor.getMessage(MsgConstants.DEPARTMENT_ALREADY_IN_USE_IN_WORKFLOW));
 
            } else if (this.projectRoleDepartmentService.usingDepartment(id)) {
                //  프로젝트의 담당부서인지 체크
                throw new OwlRuntimeException(
                        this.messageAccessor.getMessage(MsgConstants.DEPARTMENT_ALREADY_IN_USE_IN_PROJECT));
 
            } else if (this.issueDepartmentService.usingDepartment(id)) {
                //  이슈의 담당부서로 되어있는지 체크
                throw new OwlRuntimeException(
                        this.messageAccessor.getMessage(MsgConstants.DEPARTMENT_ALREADY_IN_USE_IN_ISSUE));
 
            } else {
                this.departmentRepository.deleteById(id);
            }
        }
        this.departmentRepository.flush();
    }
 
    //  프로젝트에 참여하는 부서 정보를 조회한다.
    @Override
    @Transactional(readOnly = true)
    public List<Map<String, Object>> findProjectDepartment(Project project) {
        DepartmentCondition departmentCondition = new DepartmentCondition();
        departmentCondition.setProjectId(project.getId());
        return this.departmentMapper.findProjectDepartment(departmentCondition);
    }
 
    //  프로젝트에 참여하는 부서 목록을 가져온다.
    @Override
    @Transactional(readOnly = true)
    public void findProjectDepartment(Map<String, Object> resJsonData, DepartmentCondition departmentCondition) {
        ProjectRole projectRole = this.projectRoleService.findByProjectIdAndRoleType(departmentCondition.getProjectId(), ProjectRole.TYPE_DEFAULT);
        List<ProjectRoleDepartment> projectRoleDepartments = this.projectRoleDepartmentService.findByProjectRoleId(projectRole.getId());
        List<DepartmentVo> departmentVos = Lists.newArrayList();
 
        for (ProjectRoleDepartment projectRoleDepartment : projectRoleDepartments) {
            DepartmentVo departmentVo = ConvertUtil.copyProperties(projectRoleDepartment.getDepartment(), DepartmentVo.class);
            departmentVo.setByName(departmentVo.getDepartmentName());
            departmentVos.add(departmentVo);
        }
 
        resJsonData.put(Constants.RES_KEY_CONTENTS, departmentVos);
    }
 
    //  워크플로우에 속해있는 부서 목록 조회
    @Override
    @Transactional(readOnly = true)
    public void findWorkflowDepartment(Map<String, Object> resJsonData, DepartmentCondition departmentCondition) {
        List<DepartmentVo> departmentVos = findWorkflowDepartment(departmentCondition.getIssueTypeId());
        resJsonData.put(Constants.RES_KEY_CONTENTS, departmentVos);
    }
 
    //  워크플로우에 속해있는 부서 목록 조회
    @Override
    @Transactional(readOnly = true)
    public List<DepartmentVo> findWorkflowDepartment(Long issueTypeId) {
        List<WorkflowDepartment> workflowDepartmentList = this.findWorkflowDepartmentByIssueTypeId(issueTypeId);
        List<DepartmentVo> departmentVos = Lists.newArrayList();
 
        if(workflowDepartmentList != null && workflowDepartmentList.size()>0){
            for(WorkflowDepartment workflowDepartment : workflowDepartmentList){
                DepartmentVo departmentVo = ConvertUtil.copyProperties(workflowDepartment.getDepartment(), DepartmentVo.class);
                departmentVo.setByName(departmentVo.getDepartmentName());
                departmentVos.add(departmentVo);
            }
        }
        return departmentVos;
    }
 
    // 이슈 유형(워크플로우)에 있는 담당부서 조회
    private List<WorkflowDepartment> findWorkflowDepartmentByIssueTypeId(Long issueTypeId) {
        Long workflowId = this.getWorkflowId(issueTypeId);
        return this.workflowDepartmentService.find(workflowId);
    }
 
    private Long getWorkflowId(Long issueTypeId) {
        IssueType issueType = this.issueTypeService.getIssueType(issueTypeId);
        return issueType.getWorkflow().getId();
    }
 
    // 부서 목록을 엑셀로 다운로드 한다.
    @Override
    public ModelAndView downloadExcel(HttpServletRequest request, Model model) {
 
        ModelAndView modelAndView = this.workspaceService.checkUseExcelDownload(model);
        if (modelAndView != null) {
            return modelAndView;
        }
 
        Map<String, Object> conditions = new HashMap<>();
        //  엑셀 다운로드에 필요한 검색 조건 정보를 추출하고 검색 조건 추출에 오류가 발생하면 경고를 표시해준다.
        modelAndView = this.excelConditionCheck.checkCondition(conditions, request, model);
        if (modelAndView != null) {
            return modelAndView;
        }
 
        DepartmentCondition departmentCondition = DepartmentCondition.make(conditions);
 
 
        List<Map<String, Object>> results = this.departmentMapper.find(departmentCondition);
        List<DepartmentVo> departmentVos = ConvertUtil.convertListToListClass(results, DepartmentVo.class);
        // code_ko_KR 에 code명 설정
        ExportExcelVo excelInfo = new ExportExcelVo();
        excelInfo.setFileName(this.messageAccessor.message("부서 목록"));
        excelInfo.addAttrInfos(new ExportExcelAttrVo("departmentName", this.messageAccessor.message("department.departmentName"), 6, ExportExcelAttrVo.ALIGN_CENTER));
        excelInfo.addAttrInfos(new ExportExcelAttrVo("departmentDescription", this.messageAccessor.message("department.departmentDescription"), 20, ExportExcelAttrVo.ALIGN_CENTER));
        excelInfo.addAttrInfos(new ExportExcelAttrVo("departmentCount", this.messageAccessor.message("department.departmentCount"), 3, ExportExcelAttrVo.ALIGN_CENTER));
 
        //  DepartmentVos 데이터를 엑셀에서 표시할 수 있는 데이터로 변경한다.
        List<Map<String, Object>> convertExcelViewToDepartmentMaps = this.convertExcelViewToDepartmentVos(departmentVos);
 
        excelInfo.setDatas(convertExcelViewToDepartmentMaps);
 
        model.addAttribute(Constants.EXCEL, excelInfo);
        return new ModelAndView(this.excelView);
 
    }
 
    @Override
    public boolean countInDepartment(Long id) {
        boolean result = false;
        List<UserDepartment> usingDepartments = this.userDepartmentService.findByDepartmentId(id);
        if(usingDepartments != null && usingDepartments.size() > 0){
            result = true;
        }
        return result;
    }
 
    //  DepartmentVos 데이터를 엑셀에서 표시할 수 있는 데이터로 변경한다.
    private List<Map<String, Object>> convertExcelViewToDepartmentVos(List<DepartmentVo> departmentVos) {
        List<Map<String, Object>> results = Lists.newArrayList();
 
        for (DepartmentVo departmentVo : departmentVos){
            try {
                Map<String, Object> result = new HashMap<>();
                result.put("departmentName", departmentVo.getDepartmentName());
                result.put("departmentCount", departmentVo.getDepartmentCount());
 
                String description= "";
 
                if(departmentVo.getDepartmentDescription() != null){
                    description = Jsoup.parse(departmentVo.getDepartmentDescription()).text(); //HTML 태그 제거
                    description = description.replaceAll("\\<.*?>", ""); //공백 제거
                }
                result.put("departmentDescription", description);
                results.add(result);
            } catch (Exception e) {
                log.error("엑셀 다운로드 오류 발생");
            }
        }
        return results;
    }
 
    // 사용자 부서 ID로 조회한다.
    @Override
    public Department getDepartment(Long id) {
        if (id == null) {
            throw new OwlRuntimeException(
                    this.messageAccessor.getMessage(MsgConstants.DEPARTMENT_NOT_EXIST));
        }
 
        Department department = this.findOne(id);
 
        if (department == null) {
            throw new OwlRuntimeException(
                    this.messageAccessor.getMessage(MsgConstants.DEPARTMENT_NOT_EXIST));
        }
 
        return department;
    }
 
    @Override
    public List<Map<String, Object>> findByDepartmentIds(UserCondition condition) {
        return this.departmentMapper.findByDepartmentIds(condition);
    }
 
    //  검색 결과를 DepartmentVo 로 변환한다.
    private List<DepartmentVo> convertDepartmentVoToMap(List<Map<String, Object>> results, Long totalDepartmentsCount, Pageable pageable, Map<String, Object> resJsonData) {
        List<DepartmentVo> departmentVos = Lists.newArrayList();
 
        for (Map<String, Object> result : results) {
            DepartmentVo departmentVo = ConvertUtil.convertMapToClass(result, DepartmentVo.class);
            departmentVo.setByName(departmentVo.getDepartmentName());
            departmentVos.add(departmentVo);
        }
        
        int totalPage = (int) Math.ceil((totalDepartmentsCount - 1) / pageable.getPageSize()) + 1;
 
        resJsonData.put(Constants.RES_KEY_CONTENTS, departmentVos);
        resJsonData.put(Constants.REQ_KEY_PAGE_VO, new ResPage(pageable.getPageNumber(), pageable.getPageSize(),
                totalPage, totalDepartmentsCount));
 
        return departmentVos;
    }
}