update allocation
This commit is contained in:
		
							parent
							
								
									fe75a08c3d
								
							
						
					
					
						commit
						a855787a47
					
				| 
						 | 
				
			
			@ -260,4 +260,14 @@ class JiraController extends Controller
 | 
			
		|||
            return response()->json(['error' => $e->getMessage()], 500);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public function getDetailIssueById(Request $request)
 | 
			
		||||
    {
 | 
			
		||||
        $data = $this->jiraService->getDetailIssueByKey($request->issueKey);
 | 
			
		||||
 | 
			
		||||
        return response()->json([
 | 
			
		||||
            'data' => $data,
 | 
			
		||||
            'status' => true
 | 
			
		||||
        ], 200);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -104,6 +104,7 @@ Route::middleware('api')
 | 
			
		|||
                Route::get('/all-issue-by-project', [JiraController::class, 'fetchIssuesByProject']);
 | 
			
		||||
                Route::get('/worklogs', [JiraController::class, 'getAllUserWorkLogs'])->middleware('check.permission:admin.staff');
 | 
			
		||||
                Route::get('/allocation', [JiraController::class, 'getAllUserDoing'])->middleware('check.permission:admin.staff');
 | 
			
		||||
                Route::get('/issue/detail', [JiraController::class, 'getDetailIssueById'])->middleware('check.permission:admin.staff');
 | 
			
		||||
            });
 | 
			
		||||
 | 
			
		||||
            Route::group([
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -238,9 +238,9 @@ class JiraService
 | 
			
		|||
            $users_data[$user['displayName']]['total_est'] = 0; 
 | 
			
		||||
            $body = [
 | 
			
		||||
                'expand' => ['names', 'schema'],
 | 
			
		||||
                'fields' => ['summary', 'status', 'timeoriginalestimate', 'timespent', 'assignee', 'project'],
 | 
			
		||||
                'fields' => ['summary', 'status', 'timeoriginalestimate', 'timespent', 'assignee', 'project', 'updated'],
 | 
			
		||||
                'jql' => sprintf(
 | 
			
		||||
                    "assignee = '%s' AND status IN ('to do', 'in progress')",
 | 
			
		||||
                    "assignee = '%s' AND status IN ('to do', 'in progress') ORDER BY updated DESC",
 | 
			
		||||
                    $user['accountId']
 | 
			
		||||
                ),
 | 
			
		||||
                'maxResults' => 50,
 | 
			
		||||
| 
						 | 
				
			
			@ -289,4 +289,11 @@ class JiraService
 | 
			
		|||
        return ['projects' => $groupedIssues, 'users' => $users_data, 'warningList' => $user_warning];
 | 
			
		||||
        // return $projects;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public function getDetailIssueByKey($issueKey)
 | 
			
		||||
    {
 | 
			
		||||
        $issueResponse = $this->client->get("/rest/api/3/issue/{$issueKey}?expand=changelog");
 | 
			
		||||
        $issueDetail = json_decode($issueResponse->getBody()->getContents(), true);
 | 
			
		||||
        return $issueDetail;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -15,6 +15,7 @@ export const getAllProjects = API_URL + 'v1/admin/jira/all-project'
 | 
			
		|||
export const getAllIssuesByProject = API_URL + 'v1/admin/jira/all-issue-by-project'
 | 
			
		||||
export const getAllUserWorklogs = API_URL + 'v1/admin/jira/worklogs'
 | 
			
		||||
export const getAllUserDoing = API_URL + 'v1/admin/jira/allocation'
 | 
			
		||||
export const getDetailIssByKey = API_URL + 'v1/admin/jira/issue/detail'
 | 
			
		||||
 | 
			
		||||
//Timekeeping
 | 
			
		||||
export const getTheTimesheet = API_URL + 'v1/admin/timekeeping'
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,16 +1,20 @@
 | 
			
		|||
import {
 | 
			
		||||
  Avatar,
 | 
			
		||||
  Badge,
 | 
			
		||||
  Box,
 | 
			
		||||
  Card,
 | 
			
		||||
  Loader,
 | 
			
		||||
  Modal,
 | 
			
		||||
  Popover,
 | 
			
		||||
  Text
 | 
			
		||||
  Text,
 | 
			
		||||
  Tooltip
 | 
			
		||||
} from '@mantine/core'
 | 
			
		||||
import { useDisclosure } from '@mantine/hooks'
 | 
			
		||||
import { useEffect, useState } from 'react'
 | 
			
		||||
import classes from './Allocation.module.css'
 | 
			
		||||
import { get } from '@/rtk/helpers/apiService'
 | 
			
		||||
import { getAllUserDoing } from '@/api/Admin'
 | 
			
		||||
import { getAllUserDoing, getDetailIssByKey } from '@/api/Admin'
 | 
			
		||||
import moment from 'moment'
 | 
			
		||||
interface UserInfo {
 | 
			
		||||
  self: string
 | 
			
		||||
  accountId: string
 | 
			
		||||
| 
						 | 
				
			
			@ -42,6 +46,7 @@ interface IssueFields {
 | 
			
		|||
  timeoriginalestimate: number
 | 
			
		||||
  project: ProjectInfo
 | 
			
		||||
  status: StatusInfo
 | 
			
		||||
  updated: string
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
interface ProjectInfo {
 | 
			
		||||
| 
						 | 
				
			
			@ -71,7 +76,9 @@ interface StatusInfo {
 | 
			
		|||
}
 | 
			
		||||
 | 
			
		||||
const Allocation = () => {
 | 
			
		||||
  const [loading, { toggle }] = useDisclosure(true)
 | 
			
		||||
  const [loading, setLoading] = useState(true)
 | 
			
		||||
  const [opened, setOpened] = useState(false)
 | 
			
		||||
  const [issDetail, setIssDetail] = useState("")
 | 
			
		||||
  // const [data, setData] = useState<any>({
 | 
			
		||||
  //   projects: {
 | 
			
		||||
  //     IPS_Pro: {
 | 
			
		||||
| 
						 | 
				
			
			@ -3281,7 +3288,7 @@ const Allocation = () => {
 | 
			
		|||
    try {
 | 
			
		||||
      const res = await get(getAllUserDoing)
 | 
			
		||||
      if (res.status) {
 | 
			
		||||
      toggle()
 | 
			
		||||
      setLoading(false)
 | 
			
		||||
      setData(res.data)
 | 
			
		||||
      }
 | 
			
		||||
    } catch (error) {
 | 
			
		||||
| 
						 | 
				
			
			@ -3289,6 +3296,30 @@ const Allocation = () => {
 | 
			
		|||
    }
 | 
			
		||||
  }
 | 
			
		||||
  // console.log(data)
 | 
			
		||||
 | 
			
		||||
  const getStateChanges = (changelog:any) => {
 | 
			
		||||
    return changelog.histories.map((history:any) => {
 | 
			
		||||
        const author = history.author.displayName;
 | 
			
		||||
        const created = history.created;
 | 
			
		||||
        const changes = history.items.map((item:any) => {
 | 
			
		||||
            return `${item.field} changed from ${item.fromString} ➔ ${item.toString}`;
 | 
			
		||||
        }).join(', ');
 | 
			
		||||
 | 
			
		||||
        return changes ? `${author} made changes on ${created}: ${changes}` : null;
 | 
			
		||||
    }).filter(Boolean).join('\n');
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
  const getDetailIssueByKey = async(key:string) =>{
 | 
			
		||||
    try {
 | 
			
		||||
      const res = await get(getDetailIssByKey, {issueKey: key})
 | 
			
		||||
      if(res.status){
 | 
			
		||||
        setIssDetail(getStateChanges(res?.data?.changelog))
 | 
			
		||||
        setOpened(true)
 | 
			
		||||
      }
 | 
			
		||||
    } catch (error) {
 | 
			
		||||
      console.log(error)
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
  useEffect(() => {
 | 
			
		||||
    getAll()
 | 
			
		||||
  }, [])
 | 
			
		||||
| 
						 | 
				
			
			@ -3436,10 +3467,19 @@ const Allocation = () => {
 | 
			
		|||
                                </Box>
 | 
			
		||||
                              </Popover.Target>
 | 
			
		||||
                              <Popover.Dropdown>
 | 
			
		||||
                                <Text size="xs">
 | 
			
		||||
                                
 | 
			
		||||
                                <Text size="xs" style={{maxHeight:'50vh', overflow:'auto'}}>
 | 
			
		||||
                                  {userData.issues?.map((iss: Issue) => {
 | 
			
		||||
                                    const date = new Date(iss.fields.updated)
 | 
			
		||||
                                    return (
 | 
			
		||||
                                      <Box>
 | 
			
		||||
                                      <Tooltip label='Click to view history'>
 | 
			
		||||
                                      <Box className={ Date.now() - date.getTime() > 172800000*5 ? classes['blinking-background']: ''} 
 | 
			
		||||
                                      style={{margin:'10px 0', borderRadius:'10px', cursor:'pointer'}}
 | 
			
		||||
                                      onClick={async()=>{
 | 
			
		||||
                                        setLoading(true)
 | 
			
		||||
                                        await getDetailIssueByKey(iss.key)
 | 
			
		||||
                                        setLoading(false)}}
 | 
			
		||||
                                      >
 | 
			
		||||
                                        <Text fw={600}>
 | 
			
		||||
                                          <a
 | 
			
		||||
                                            href={
 | 
			
		||||
| 
						 | 
				
			
			@ -3464,18 +3504,24 @@ const Allocation = () => {
 | 
			
		|||
                                        </Text>
 | 
			
		||||
                                        <Text fw={600} ml={'50px'}>
 | 
			
		||||
                                          Time spent:{' '}
 | 
			
		||||
                                          {iss.fields.timespent / 60 / 60}
 | 
			
		||||
                                          <Badge size='xs' bg={'orange'}>{iss.fields.timespent / 60 / 60}h</Badge>
 | 
			
		||||
                                        </Text>
 | 
			
		||||
                                        <Text fw={600} ml={'50px'}>
 | 
			
		||||
                                          EST:{' '}
 | 
			
		||||
                                          {iss.fields.timeoriginalestimate /
 | 
			
		||||
                                          <Badge size='xs'>{iss.fields.timeoriginalestimate /
 | 
			
		||||
                                            60 /
 | 
			
		||||
                                            60}
 | 
			
		||||
                                            60}h</Badge>
 | 
			
		||||
                                        </Text>
 | 
			
		||||
                                        <Text fw={600} ml={'50px'}>
 | 
			
		||||
                                          Updated:{' '}
 | 
			
		||||
                                          <Badge size='xs'>{iss.fields.updated}</Badge>
 | 
			
		||||
                                        </Text>
 | 
			
		||||
                                      </Box>
 | 
			
		||||
                                      </Tooltip>
 | 
			
		||||
                                    )
 | 
			
		||||
                                  })}
 | 
			
		||||
                                </Text>
 | 
			
		||||
                                
 | 
			
		||||
                              </Popover.Dropdown>
 | 
			
		||||
                            </Popover>
 | 
			
		||||
                          </Box>
 | 
			
		||||
| 
						 | 
				
			
			@ -3549,7 +3595,11 @@ const Allocation = () => {
 | 
			
		|||
          </Box>
 | 
			
		||||
        </Box>
 | 
			
		||||
      </div>
 | 
			
		||||
      <Modal title={<b>HISTORY</b>} onClose={()=>setOpened(false) } opened={opened} fullScreen>
 | 
			
		||||
        <pre>{issDetail}</pre>
 | 
			
		||||
      </Modal>
 | 
			
		||||
    </div>
 | 
			
		||||
    
 | 
			
		||||
  )
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
		Reference in New Issue