forgeplus-react/src/forge/Main/Detail.js

613 lines
22 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import React, { Component } from 'react';
import { Spin, Tooltip } from 'antd';
import { Link, Route, Switch, withRouter } from 'react-router-dom';
import '../css/index.css'
import './list.css';
import Loadable from 'react-loadable';
import Loading from '../../Loading';
import axios from 'axios';
import img_1 from '../Images/1.png';
import img_2 from '../Images/2.png';
import img_3 from '../Images/3.png';
import img_6 from '../Images/6.png';
import img_7 from '../Images/7.png';
import img_parise from '../Images/parise.png';
import img_focus from '../Images/focus.png';
import img_parised from '../Images/parised.png';
import img_focused from '../Images/focused.png';
import img_fork from '../Images/fork.png';
import img_milepost from '../Images/milepost.png';
const FileNew = Loadable({
loader: () => import('../Newfile/Index'),
loading: Loading,
})
const Setting = Loadable({
loader: () => import('../Settings/Index'),
loading: Loading,
})
const TagList = Loadable({
loader: () => import('../Order/Tags'),
loading: Loading,
})
const OrderNew = Loadable({
loader: () => import('../Order/New'),
loading: Loading,
})
const OrderDetail = Loadable({
loader: () => import('../Order/Detail'),
loading: Loading,
})
const OrderIndex = Loadable({
loader: () => import('../Order/order'),
loading: Loading,
})
const CoderRootIndex = Loadable({
loader: () => import('./CoderRootIndex'),
loading: Loading,
})
const OrderMilepost = Loadable({
loader: () => import('../Order/Milepost'),
loading: Loading,
})
const OrdernewMilepost = Loadable({
loader: () => import('../Order/newMilepost'),
loading: Loading,
})
const OrderupdateMilepost = Loadable({
loader: () => import('../Order/UpdateMilepost'),
loading: Loading,
})
const OrderupdateDetail = Loadable({
loader: () => import('../Order/UpdateDetail'),
loading: Loading,
})
const OrdercopyDetail = Loadable({
loader: () => import('../Order/CopyDetail'),
loading: Loading,
})
//合并请求
const MergeIndexDetail = Loadable({
loader: () => import('../Merge/merge'),
loading: Loading,
})
const CreateMerge = Loadable({
loader: () => import('../Merge/NewMerge'),
loading: Loading,
})
const MessageCount = Loadable({
loader: () => import('../Merge/MessageCount'),
loading: Loading,
})
const MilepostDetail = Loadable({
loader: () => import('../Order/MilepostDetail'),
loading: Loading,
})
const WatchUsers = Loadable({
loader: () => import('../UsersList/watch_users'),
loading: Loading,
})
const PraiseUsers = Loadable({
loader: () => import('../UsersList/praise_users'),
loading: Loading,
})
const ForkUsers = Loadable({
loader: () => import('../UsersList/fork_users'),
loading: Loading,
})
const TrendsIndex = Loadable({
loader: () => import('../Activity/Activity'),
loading: Loading,
})
/**
* permissionManager:管理员Reporter报告人员(只有读取权限)Developer开发人员除不能设置仓库信息外
*/
class Detail extends Component {
constructor(props) {
super(props);
this.state = {
isSpin: true,
projectDetail: undefined,
isManager: false,
isReporter: false,
isDeveloper: false,
project_id: undefined,
watchers_count: undefined,
praises_count: undefined,
forked_count: undefined,
watched: false,
praised: false,
http_url: undefined,
author: undefined,
branchs: undefined,
branchList: undefined,
}
}
componentDidMount = () => {
this.getDetail();
}
componentDidUpdate = (prevState) => {
if ((prevState.match.params.projectsId !== this.props.match.params.projectsId)) {
this.getDetail();
}
}
getDetail = () => {
const { projectsId } = this.props.match.params;
const url = `/repositories/${projectsId}.json`;
axios.get(url).then((result) => {
if (result) {
this.setState({
projectDetail: result.data,
project_id: result.data.project_id,
isManager: result.data.permission && result.data.permission === "Manager",
isReporter: result.data.permission && result.data.permission === "Reporter",
isDeveloper: result.data.permission && result.data.permission === "Developer",
http_url: result.data.clone_url,
author: result.data.author,
praised: result.data.praised,
watched: result.data.watched,
watchers_count: result.data.watchers_count,
praises_count: result.data.praises_count,
forked_count: result.data.forked_count,
isSpin:false
})
}
}).catch((error) => { })
}
// 关注和取消关注
focusFunc = (flag) => {
const { project_id } = this.state;
axios({
method: flag? 'delete' : 'post',
url: `/watchers/${flag? 'unfollow' : 'follow'}.json`,
params: {
target_type: "project",
id: project_id
}
})
.then(result => {
if(result && result.data.status === 0){
this.setWatchersCount(result.data.watchers_count, result.data.watched);
}
})
.catch(error => {
console.log(error);
});
}
// 点赞和取消点赞
pariseFunc = (flag) => {
const { project_id } = this.state;
axios({
method: flag ? 'delete' : 'post',
url: `/projects/${project_id}/praise_tread/${flag ? 'unlike' : 'like'}.json`
})
.then(result => {
if (result && result.data.status === 0) {
this.setPraisesCount(result.data.praises_count, result.data.praised)
}
})
.catch(error => {
console.log(error);
});
}
setWatchersCount = (count, is_watched) => {
this.setState({
watched: is_watched,
watchers_count: count
})
}
setPraisesCount = (count, is_praised) => {
this.setState({
praised: is_praised,
praises_count: count
})
}
// fork项目
forkFunc = () => {
// if (!checkIfLogin) {
// this.props.showLoginDialog();
// return;
// }
this.setState({
isSpin: true
})
const { project_id } = this.state;
const url = `/projects/${project_id}/forks.json`;
axios.post(url).then(result => {
if (result && result.data.status === 0) {
this.props.history.push(`/projects/${result.data.id}/coders`);
this.props.showNotification(result.data.message);
}
this.setState({
isSpin: false
})
}).catch(error => {
this.setState({
isSpin: false
})
console.log(error);
})
}
// 获取分支列表
getBranch = (id) => {
const url = `/projects/${id}/branches.json`;
axios.get(url).then((result) => {
if (result && result.data.length > 0) {
const branchs = [];
result.data.map((item, key) => {
branchs.push({
index: key,
name: item.name
})
})
this.setState({
branchList: result.data,
branchs,
})
}
}).catch((error) => { })
}
// 同步镜像
synchronismMirror=()=>{
const { repo_id } = this.state.projectDetail;
this.setState({
isSpin:true
})
const url = `/repositories/${repo_id}/sync_mirror.json`;
axios.post(url).then(result=>{
if(result && result.data && result.data.status === 0){
this.props.showNotification("镜像同步成功!");
this.getDetail();
}else{
this.props.showNotification("镜像同步失败!");
this.setState({
isSpin:false
})
}
}).catch(error=>{
console.log(error);
})
}
render() {
const { projectDetail, watchers_count, praises_count, forked_count, isSpin, isManager, watched, praised } = this.state;
const url = this.props.history.location.pathname;
const urlArr = url.split("/");
const urlFlag = (urlArr.length === 3);
const { projectsId } = this.props.match.params;
const { state } = this.props.history.location;
const text = (
projectDetail && projectDetail.forked_from_project_id && projectDetail.fork_info ?
<React.Fragment>
<span>forked from </span>
<Link to={`/users/${projectDetail.fork_info.fork_project_user_login}/projects`} className="show-user-link color-grey-ccc">{projectDetail.fork_info.fork_project_user_name}</Link>
<span> / </span>
<Link to={`/projects/${projectDetail.forked_from_project_id}/coders`} className="color-grey-ccc">{projectDetail.fork_info.fork_form_name}</Link>
</React.Fragment> : ""
);
const mirror = (
<React.Fragment>
<span>镜像自 </span>
<a href={projectDetail && projectDetail.mirror_url} target="_blank" style={{color:"#fff"}}>{projectDetail && projectDetail.mirror_url}</a>
</React.Fragment>
)
const common ={
getDetail:this.getDetail
}
return (
<div>
<Spin spinning={isSpin}>
<div className="detailHeader-wrapper">
<div className="normal">
<div className="f-wrap-between mb15" style={{ position: "relative" }}>
<p className="font-18 color-white df flex-1 lineH2 mt15" style={{ alignItems: "center" }}>
{projectDetail && projectDetail.author &&
<Link to={`/users/${projectDetail.author.login}/projects`} className="show-user-link color-white">
{projectDetail.author.name}
</Link>
}
<span className="ml5 mr5">/</span>
<span className="hide-1 flex-1 df">
<Link to={`/projects/${projectsId}/coders`} className="color-white font-22">{projectDetail && projectDetail.name}</Link>
{
projectDetail && projectDetail.forked_from_project_id && projectDetail.fork_info ?
<Tooltip placement={'right'} title={text}>
<Link to={`/projects/${projectDetail.forked_from_project_id}/coders`}
className="ml10" >
<i className="iconfont icon-fork font-18 fl mt6" style={{ color: "#8D90E3" }}></i>
</Link>
</Tooltip> : ""
}
{
projectDetail && projectDetail.type && projectDetail.type === 2 ?
<Tooltip placement={'right'} title={mirror}>
<i className="iconfont icon-jingxiang font-18 fl mt6 ml10" style={{ color: "#8D90E3" }}></i>
</Tooltip>:""
}
</span>
</p>
<span className="df mt25">
{
projectDetail && projectDetail.type && projectDetail.type === 2 ?
<a className="synchronism ml30" onClick={this.synchronismMirror}>同步镜像</a>:""
}
<span className="detail_tag_btn">
<a className="detail_tag_btn_name" onClick={() => this.focusFunc(watched)}>
<img src={watched ? img_focused : img_focus} alt="" width="14px" />
{watched ? '取消关注' : '关注'}
</a>
<Link className="detail_tag_btn_count" to={{pathname:`/projects/${projectsId}/watch_users`, state}}>
{watchers_count}
</Link>
</span>
<span className="detail_tag_btn">
<a className="detail_tag_btn_name" onClick={() => this.pariseFunc(praised)}>
<img src={praised ? img_parised : img_parise} width="13px" alt="" />
{praised ? '取消点赞' : '点赞'}
</a>
<Link className="detail_tag_btn_count" to={{pathname:`/projects/${projectsId}/praise_users`,state}}>
{praises_count}
</Link>
{/* <span className="detail_tag_btn_count">{praises_count}</span> */}
</span>
<span className="detail_tag_btn">
<a className="detail_tag_btn_name" onClick={this.forkFunc}>
<img src={img_fork} alt="" width="10px"/>Fork</a>
<Link className="detail_tag_btn_count" to={{pathname:`/projects/${projectsId}/fork_users`,state}}>
{forked_count}
</Link>
{/* <span className="detail_tag_btn_count">{forked_count}</span> */}
</span>
</span>
</div>
<div className="f-wrap-between">
<ul className="headerMenu-wrapper">
<li className={(url.indexOf("coders") > -1 || urlFlag) ? "active" : ""}>
<Link to={{ pathname: `/projects/${projectsId}/coders`, state }}>
<img alt="" src={img_1} width="18" />代码库
{ projectDetail && projectDetail.commits_count ? <span>{projectDetail.commits_count}</span>:""}
</Link>
</li>
<li className={(url.indexOf("orders") > -1 && !(url.indexOf("Milepost") > 0 || url.indexOf("meilpost") > 0 || url.indexOf("tags") > 0)) ? "active" : ""}>
<Link to={{ pathname: `/projects/${projectsId}/orders`, state }}>
<img alt="" src={img_2} width="12" />任务
{ projectDetail && projectDetail.issues_count ? <span>{projectDetail.issues_count}</span> :""}
</Link>
</li>
<li className={url.indexOf("merge") > -1 ? "active" : ""}>
<Link to={{ pathname: `/projects/${projectsId}/merge`, state }}>
<img alt="" src={img_3} width="13" />合并请求
{ projectDetail && projectDetail.pull_requests_count ? <span>{projectDetail.issues_count}</span> : "" }
</Link>
</li>
{/* <li className={url.indexOf("version") > -1 ? "active" : ""}>
<Link to={{ pathname: `/projects/${projectsId}/version`, state }}>
<img alt="" src={img_4} width="16" />版本发布
{projectDetail && projectDetail.version_releases_count && <span>{projectDetail.version_releases_count}</span>}
</Link>
</li> */}
<li className={(url.indexOf("Milepost") > -1 || url.indexOf("meilpost") > -1) ? "active" : ""}>
<Link to={{ pathname: `/projects/${projectsId}/orders/Milepost`, state }}>
<img alt="" src={img_milepost} width="16" />里程碑
{projectDetail && projectDetail.version_count && <span>{projectDetail.version_count}</span>}
</Link>
</li>
<li className={url.indexOf("trends") > -1 ? "active" : ""}>
<Link to={{ pathname: `/projects/${projectsId}/trends`, state }}>
<img alt="" src={img_6} width="16" />动态
</Link>
</li>
{
isManager &&
<li className={url.indexOf("setting") > 0 ? "active" : ""}><Link to={`/projects/${projectsId}/setting`}><img alt="" src={img_7} width="19" />仓库设置</Link></li>
}
</ul>
</div>
</div>
</div>
<Switch {...this.props}>
{/* 新建文件 */}
<Route path="/projects/:projectsId/coders/:branch/newfile/:path"
render={
(props) => (<FileNew {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
<Route path="/projects/:projectsId/coders/:branch/newfile"
render={
(props) => (<FileNew {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
{/* 标签列表 */}
<Route path="/projects/:projectsId/orders/tags"
render={
(props) => (<TagList {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
{/* 仓库设置 */}
<Route path="/projects/:projectsId/setting"
render={
(props) => (<Setting {...this.props} {...props} {...this.state} {...common} />)
}
></Route>
{/* 任务详情 */}
<Route path="/projects/:projectsId/orders/:orderId/detail"
render={
(props) => (<OrderDetail {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
{/* 里程碑 */}
<Route path="/projects/:projectsId/orders/Milepost"
render={
(props) => (<OrderMilepost {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
{/* 新建里程碑 */}
<Route path="/projects/:projectsId/orders/meilpost"
render={
(props) => (<OrdernewMilepost {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
{/*里程碑详情*/}
<Route path="/projects/:projectsId/orders/:meilid/MilepostDetail"
render={
(props) => (<MilepostDetail {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
{/*修改里程碑*/}
<Route path="/projects/:projectsId/orders/:meilid/meilpost"
render={
(props) => (<OrderupdateMilepost {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
{/* 里程碑页面新建任务 */}
<Route path="/projects/:projectsId/orders/:milepostId/new"
render={
(props) => (<OrderNew {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
{/* 新建任务 */}
<Route path="/projects/:projectsId/orders/new"
render={
(props) => (<OrderNew {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
{/* 修改详情 */}
<Route path="/projects/:projectsId/orders/:orderId/updatedetail"
render={
(props) => (<OrderupdateDetail {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
{/* 复制详情 */}
<Route path="/projects/:projectsId/orders/:orderId/copyetail"
render={
(props) => (<OrdercopyDetail {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
{/* 动态 */}
<Route path="/projects/:projectsId/trends"
render={
(props) => (<TrendsIndex {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
{/* 代码Index */}
<Route path="/projects/:projectsId/orders"
render={
(props) => (<OrderIndex {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
<Route path="/projects/:projectsId/merge/new"
render={
(props) => (<CreateMerge {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
<Route path="/projects/:projectsId/merge/:mergeId/UpdateMerge"
render={
(props) => (<MessageCount {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
<Route path="/projects/:projectsId/merge/:mergeId/Messagecount"
render={
(props) => (<MessageCount {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
<Route path="/projects/:projectsId/merge/:mergeId/MergeSubmit"
render={
(props) => (<MessageCount {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
<Route path="/projects/:projectsId/merge"
render={
(props) => (<MergeIndexDetail {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
<Route path="/projects/:projectsId/coders/filesurl"
render={
(props) => (<CoderRootIndex {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
<Route path="/projects/:projectsId/coders"
render={
(props) => (<CoderRootIndex {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
<Route path="/projects/:projectsId"
render={
(props) => (<CoderRootIndex {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
<Route path="/projects/:projectsId/watch_users"
render={
(props) => (<WatchUsers {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
<Route path="/projects/:projectsId/praise_users"
render={
(props) => (<PraiseUsers {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
<Route path="/projects/:projectsId/fork_users"
render={
(props) => (<ForkUsers {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
<Route path="/projects/:projectsId"
render={
(props) => (<CoderRootIndex {...this.props} {...props} {...this.state} {...common}/>)
}
></Route>
</Switch>
</Spin>
</div>
)
}
}
export default withRouter(Detail);