forked from ddrilling/asb_cloud_front
Merge branch 'master' of https://bitbucket.org/frolovng/asb_cloud_front_react
This commit is contained in:
commit
e586e7ae59
@ -2,7 +2,7 @@ import { useState, useEffect } from 'react'
|
|||||||
import { DepositService } from '../services/api'
|
import { DepositService } from '../services/api'
|
||||||
import LoaderPortal from './LoaderPortal'
|
import LoaderPortal from './LoaderPortal'
|
||||||
import { TreeSelect } from 'antd'
|
import { TreeSelect } from 'antd'
|
||||||
import { useHistory } from 'react-router-dom'
|
import { useHistory, useRouteMatch } from 'react-router-dom'
|
||||||
import { notify } from "./factory"
|
import { notify } from "./factory"
|
||||||
import '../styles/wellTreeSelect.css'
|
import '../styles/wellTreeSelect.css'
|
||||||
|
|
||||||
@ -10,6 +10,7 @@ export default function WellTreeSelector() {
|
|||||||
const [wellsTree, setWellsTree] = useState([])
|
const [wellsTree, setWellsTree] = useState([])
|
||||||
const [showLoader, setShowLoader] = useState(false)
|
const [showLoader, setShowLoader] = useState(false)
|
||||||
const history = useHistory()
|
const history = useHistory()
|
||||||
|
const routeMatch = useRouteMatch('/:route/:id')
|
||||||
|
|
||||||
const updateWellsList = async () => {
|
const updateWellsList = async () => {
|
||||||
setShowLoader(true)
|
setShowLoader(true)
|
||||||
@ -21,8 +22,8 @@ export default function WellTreeSelector() {
|
|||||||
value: `/deposit/${deposit.id}`,
|
value: `/deposit/${deposit.id}`,
|
||||||
children: deposit.clusters.map(cluster => ({
|
children: deposit.clusters.map(cluster => ({
|
||||||
title: cluster.caption,
|
title: cluster.caption,
|
||||||
key: `/cluster/${cluster.id}/all`,
|
key: `/cluster/${cluster.id}`,
|
||||||
value: `/cluster/${cluster.id}/all`,
|
value: `/cluster/${cluster.id}`,
|
||||||
children: cluster.wells.map(well => ({
|
children: cluster.wells.map(well => ({
|
||||||
title: well.caption,
|
title: well.caption,
|
||||||
key: `/well/${well.id}`,
|
key: `/well/${well.id}`,
|
||||||
@ -56,6 +57,7 @@ export default function WellTreeSelector() {
|
|||||||
treeData={wellsTree}
|
treeData={wellsTree}
|
||||||
treeDefaultExpandAll
|
treeDefaultExpandAll
|
||||||
onSelect={onSelect}
|
onSelect={onSelect}
|
||||||
|
value = {routeMatch?.url}
|
||||||
/>
|
/>
|
||||||
</LoaderPortal>
|
</LoaderPortal>
|
||||||
)
|
)
|
||||||
|
231
src/pages/Cluster/ClusterSections.jsx
Normal file
231
src/pages/Cluster/ClusterSections.jsx
Normal file
@ -0,0 +1,231 @@
|
|||||||
|
import { Table, Tag, Button, Badge, Divider, Modal } from "antd";
|
||||||
|
import { useParams } from "react-router-dom";
|
||||||
|
import { LineChartOutlined, ProfileOutlined } from "@ant-design/icons";
|
||||||
|
import { useState, useEffect } from "react";
|
||||||
|
import {
|
||||||
|
makeTextColumn,
|
||||||
|
makeNumericColumnPlanFact,
|
||||||
|
calcAndUpdateStatsBySections,
|
||||||
|
} from "../../components/Table";
|
||||||
|
|
||||||
|
const filtersMinMax = [
|
||||||
|
{
|
||||||
|
text: "min",
|
||||||
|
value: "min",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
text: "max",
|
||||||
|
value: "max",
|
||||||
|
},
|
||||||
|
];
|
||||||
|
|
||||||
|
const filtersSectionsType = [];
|
||||||
|
|
||||||
|
const ModalWindowButton = ({
|
||||||
|
buttonIcon,
|
||||||
|
buttonText,
|
||||||
|
modalTitle,
|
||||||
|
modalContent,
|
||||||
|
}) => {
|
||||||
|
const [isModalVisible, setIsModalVisible] = useState(false);
|
||||||
|
|
||||||
|
let content =
|
||||||
|
typeof modalContent === "string" ? (
|
||||||
|
<img src={modalContent} alt="" style={{ width: "100%" }} />
|
||||||
|
) : (
|
||||||
|
modalContent
|
||||||
|
);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<Button
|
||||||
|
type="secondary"
|
||||||
|
onClick={() => setIsModalVisible(true)}
|
||||||
|
icon={buttonIcon}
|
||||||
|
>
|
||||||
|
{buttonText}
|
||||||
|
</Button>
|
||||||
|
<Modal
|
||||||
|
title={modalTitle}
|
||||||
|
centered
|
||||||
|
visible={isModalVisible}
|
||||||
|
onOk={() => setIsModalVisible(false)}
|
||||||
|
onCancel={() => setIsModalVisible(false)}
|
||||||
|
width={1400}
|
||||||
|
>
|
||||||
|
{content}
|
||||||
|
</Modal>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
const columns = [
|
||||||
|
makeTextColumn("скв №", "caption"),
|
||||||
|
makeTextColumn("Секция", "sectionType", filtersSectionsType),
|
||||||
|
makeNumericColumnPlanFact("Глубина", "sectionWellDepth", filtersMinMax),
|
||||||
|
makeNumericColumnPlanFact(
|
||||||
|
"Продолжительность",
|
||||||
|
"sectionBuildDays",
|
||||||
|
filtersMinMax
|
||||||
|
), //Цикл строительства
|
||||||
|
makeNumericColumnPlanFact("МСП", "sectionRateOfPenetration", filtersMinMax),
|
||||||
|
makeNumericColumnPlanFact(
|
||||||
|
"Рейсовая скорость",
|
||||||
|
"sectionRouteSpeed",
|
||||||
|
filtersMinMax
|
||||||
|
),
|
||||||
|
makeNumericColumnPlanFact("Спуск КНБК", "sectionBhaDownSpeed", filtersMinMax), //Скорость спуска КНБК
|
||||||
|
makeNumericColumnPlanFact("Подъем КНБК", "sectionBhaUpSpeed", filtersMinMax), //Скорость подъема КНБК
|
||||||
|
makeNumericColumnPlanFact(
|
||||||
|
"Скорость спуска ОК",
|
||||||
|
"sectionCasingDownSpeed",
|
||||||
|
filtersMinMax
|
||||||
|
),
|
||||||
|
makeNumericColumnPlanFact(
|
||||||
|
"НПВ, сут",
|
||||||
|
"nonProductiveTime",
|
||||||
|
filtersMinMax,
|
||||||
|
"70px"
|
||||||
|
),
|
||||||
|
{
|
||||||
|
title: "TVD",
|
||||||
|
render: (_, record) => (
|
||||||
|
<ModalWindowButton
|
||||||
|
buttonIcon={<LineChartOutlined />}
|
||||||
|
modalTitle={`График по скв.:${record.caption}`}
|
||||||
|
/>
|
||||||
|
),
|
||||||
|
//modalContent = {resources['Chart' + record.caption]}/>,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Операции",
|
||||||
|
render: (_, record) => (
|
||||||
|
<ModalWindowButton
|
||||||
|
buttonIcon={<ProfileOutlined />}
|
||||||
|
modalTitle={`Операции по скв.:${record.caption}`}
|
||||||
|
/>
|
||||||
|
),
|
||||||
|
//modalContent = {resources['Table' + record.caption]},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Подрядчики",
|
||||||
|
dataIndex: "companies",
|
||||||
|
render: (item) =>
|
||||||
|
item?.map((company) => <Tag color="blue">{company.caption}</Tag>),
|
||||||
|
},
|
||||||
|
];
|
||||||
|
|
||||||
|
export default function ClusterSections({ clusterData }) {
|
||||||
|
let { id } = useParams();
|
||||||
|
const [wellsStat, setWellsStat] = useState([]);
|
||||||
|
const [selectedWells, setSelectedWells] = useState([]);
|
||||||
|
const [selectedWellsKeys, setSelectedWellsKeys] = useState([]);
|
||||||
|
|
||||||
|
calcAndUpdateStatsBySections(wellsStat ?? [], [
|
||||||
|
"sectionWellDepthPlan",
|
||||||
|
"sectionWellDepthFact",
|
||||||
|
"sectionBuildDaysPlan",
|
||||||
|
"sectionBuildDaysFact",
|
||||||
|
"sectionRateOfPenetrationPlan",
|
||||||
|
"sectionRateOfPenetrationFact",
|
||||||
|
"sectionRouteSpeedPlan",
|
||||||
|
"sectionRouteSpeedFact",
|
||||||
|
"sectionBhaDownSpeedPlan",
|
||||||
|
"sectionBhaDownSpeedFact",
|
||||||
|
"sectionBhaUpSpeedPlan",
|
||||||
|
"sectionBhaUpSpeedFact",
|
||||||
|
"sectionCasingDownSpeedPlan",
|
||||||
|
"sectionCasingDownSpeedFact",
|
||||||
|
"nonProductiveTimePlan",
|
||||||
|
"nonProductiveTimeFact",
|
||||||
|
]);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
let rows = [];
|
||||||
|
|
||||||
|
clusterData.statsWells?.forEach((el) => {
|
||||||
|
el.sections.forEach((section) => {
|
||||||
|
let row = {
|
||||||
|
key: el.caption + section.id,
|
||||||
|
id: el.caption + section.id,
|
||||||
|
caption: el.caption,
|
||||||
|
sectionType: section.caption,
|
||||||
|
sectionWellDepthPlan: section.plan.wellDepthEnd,
|
||||||
|
sectionWellDepthFact: section.fact.wellDepthEnd,
|
||||||
|
sectionBuildDaysPlan: (
|
||||||
|
Math.abs(
|
||||||
|
new Date(section.plan.start) - new Date(section.plan.end)
|
||||||
|
) /
|
||||||
|
(1000 * 60 * 60 * 24)
|
||||||
|
).toFixed(2),
|
||||||
|
sectionBuildDaysFact: (
|
||||||
|
Math.abs(
|
||||||
|
new Date(section.fact.start) - new Date(section.fact.end)
|
||||||
|
) /
|
||||||
|
(1000 * 60 * 60 * 24)
|
||||||
|
).toFixed(2),
|
||||||
|
sectionRateOfPenetrationPlan: section.plan.rop.toFixed(2),
|
||||||
|
sectionRateOfPenetrationFact: section.fact.rop.toFixed(2),
|
||||||
|
sectionRouteSpeedPlan: section.plan.routeSpeed.toFixed(2),
|
||||||
|
sectionRouteSpeedFact: section.fact.routeSpeed.toFixed(2),
|
||||||
|
sectionBhaDownSpeedPlan: section.plan.bhaDownSpeed.toFixed(2),
|
||||||
|
sectionBhaDownSpeedFact: section.fact.bhaDownSpeed.toFixed(2),
|
||||||
|
sectionBhaUpSpeedPlan: section.plan.bhaUpSpeed.toFixed(2),
|
||||||
|
sectionBhaUpSpeedFact: section.fact.bhaUpSpeed.toFixed(2),
|
||||||
|
sectionCasingDownSpeedPlan: section.plan.casingDownSpeed.toFixed(2),
|
||||||
|
sectionCasingDownSpeedFact: section.fact.casingDownSpeed.toFixed(2),
|
||||||
|
nonProductiveTimePlan: section.plan.nonProductiveHours.toFixed(2),
|
||||||
|
nonProductiveTimeFact: section.fact.nonProductiveHours.toFixed(2),
|
||||||
|
companies: el.companies,
|
||||||
|
};
|
||||||
|
|
||||||
|
rows.push(row);
|
||||||
|
|
||||||
|
if (!filtersSectionsType.some((el) => el.text === section.caption))
|
||||||
|
filtersSectionsType.push({
|
||||||
|
text: section.caption,
|
||||||
|
value: section.caption,
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
setWellsStat(rows);
|
||||||
|
}, [id, clusterData]);
|
||||||
|
|
||||||
|
const rowSelection = {
|
||||||
|
selectedRowKeys: selectedWellsKeys,
|
||||||
|
onChange: (keys, items) => {
|
||||||
|
setSelectedWells(items);
|
||||||
|
setSelectedWellsKeys(keys);
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<Table
|
||||||
|
columns={columns}
|
||||||
|
dataSource={wellsStat}
|
||||||
|
size={"small"}
|
||||||
|
bordered
|
||||||
|
scroll={{ x: true, y: 620 }}
|
||||||
|
rowSelection={rowSelection}
|
||||||
|
pagination={false}
|
||||||
|
/>
|
||||||
|
<Divider />
|
||||||
|
<Badge.Ribbon text="комбинированная скважина" color="gray">
|
||||||
|
<h3>
|
||||||
|
Выбранные секции<></>
|
||||||
|
</h3>
|
||||||
|
</Badge.Ribbon>
|
||||||
|
<Table
|
||||||
|
columns={columns}
|
||||||
|
dataSource={selectedWells}
|
||||||
|
rowSelection={rowSelection}
|
||||||
|
size={"small"}
|
||||||
|
bordered
|
||||||
|
scroll={{ x: true }}
|
||||||
|
pagination={false}
|
||||||
|
/>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
}
|
125
src/pages/Cluster/ClusterWells.jsx
Normal file
125
src/pages/Cluster/ClusterWells.jsx
Normal file
@ -0,0 +1,125 @@
|
|||||||
|
import { useParams } from "react-router-dom";
|
||||||
|
import { Link } from "react-router-dom";
|
||||||
|
import { useState, useEffect } from "react";
|
||||||
|
import { Table, Tag, Button } from "antd";
|
||||||
|
import {
|
||||||
|
makeTextColumn,
|
||||||
|
makeGroupColumn,
|
||||||
|
makeNumericColumn,
|
||||||
|
makeNumericColumnPlanFact,
|
||||||
|
calcAndUpdateStatsBySections,
|
||||||
|
} from "../../components/Table";
|
||||||
|
|
||||||
|
const filtersMinMax = [
|
||||||
|
{
|
||||||
|
text: "min",
|
||||||
|
value: "min",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
text: "max",
|
||||||
|
value: "max",
|
||||||
|
},
|
||||||
|
];
|
||||||
|
|
||||||
|
const filtersWellsType = [
|
||||||
|
{
|
||||||
|
text: "Наклонно-направленная",
|
||||||
|
value: "Наклонно-направленная",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
text: "Горизонтальная",
|
||||||
|
value: "Горизонтальная",
|
||||||
|
},
|
||||||
|
];
|
||||||
|
|
||||||
|
export default function ClusterWells({ clusterData }) {
|
||||||
|
let { id } = useParams();
|
||||||
|
const [wellsStat, setWellsStat] = useState([]);
|
||||||
|
|
||||||
|
calcAndUpdateStatsBySections(wellsStat ?? [], [
|
||||||
|
"factStart",
|
||||||
|
"factEnd",
|
||||||
|
"periodPlan",
|
||||||
|
"periodFact",
|
||||||
|
"rateOfPenetrationPlan",
|
||||||
|
"rateOfPenetrationFact",
|
||||||
|
"routeSpeedPlan",
|
||||||
|
"routeSpeedFact",
|
||||||
|
"notProductiveTime",
|
||||||
|
]);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
let tableData = clusterData.statsWells?.map((el) => {
|
||||||
|
return {
|
||||||
|
key: el.id,
|
||||||
|
id: el.id,
|
||||||
|
caption: el.caption,
|
||||||
|
wellType: el.wellType,
|
||||||
|
factStart: new Date(el.total.fact.start).toLocaleString(),
|
||||||
|
factEnd: new Date(el.total.fact.end).toLocaleString(),
|
||||||
|
periodPlan: (
|
||||||
|
Math.abs(
|
||||||
|
new Date(el.total.plan.start) - new Date(el.total.plan.end)
|
||||||
|
) /
|
||||||
|
(1000 * 60 * 60 * 24)
|
||||||
|
).toFixed(2),
|
||||||
|
periodFact: (
|
||||||
|
Math.abs(
|
||||||
|
new Date(el.total.fact.start) - new Date(el.total.fact.end)
|
||||||
|
) /
|
||||||
|
(1000 * 60 * 60 * 24)
|
||||||
|
).toFixed(2),
|
||||||
|
rateOfPenetrationPlan: el.total.plan.rop.toFixed(2),
|
||||||
|
rateOfPenetrationFact: el.total.fact.rop.toFixed(2),
|
||||||
|
routeSpeedPlan: el.total.plan.routeSpeed.toFixed(2),
|
||||||
|
routeSpeedFact: el.total.fact.routeSpeed.toFixed(2),
|
||||||
|
notProductiveTimePlan: el.total.plan.nonProductiveHours.toFixed(2),
|
||||||
|
notProductiveTimeFact: el.total.fact.nonProductiveHours.toFixed(2),
|
||||||
|
companies: el.companies,
|
||||||
|
};
|
||||||
|
});
|
||||||
|
|
||||||
|
setWellsStat(tableData);
|
||||||
|
}, [id, clusterData]);
|
||||||
|
|
||||||
|
const columns = [
|
||||||
|
makeTextColumn("скв №", "caption", null, null, (_, item) => (
|
||||||
|
<Link to={`/well/${item.id}`}>{item.caption}</Link>
|
||||||
|
)),
|
||||||
|
makeTextColumn("Тип скв.", "wellType", filtersWellsType),
|
||||||
|
makeGroupColumn("Фактические сроки", [
|
||||||
|
makeNumericColumn("начало", "factStart"),
|
||||||
|
makeNumericColumn("окончание", "factEnd"),
|
||||||
|
]),
|
||||||
|
makeNumericColumnPlanFact("Продолжительность", "period", filtersMinMax),
|
||||||
|
makeNumericColumnPlanFact("МСП", "rateOfPenetration", filtersMinMax),
|
||||||
|
makeNumericColumnPlanFact("Рейсовая скорость", "routeSpeed", filtersMinMax),
|
||||||
|
makeNumericColumnPlanFact("НПВ, сут", "notProductiveTime", filtersMinMax),
|
||||||
|
{
|
||||||
|
title: "График глубина-день",
|
||||||
|
render: (_, item) => <Button>Открыть</Button>,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Таблица по операциям",
|
||||||
|
render: (_) => <Button>Открыть</Button>,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Подрядчики",
|
||||||
|
key: "companies",
|
||||||
|
dataIndex: "companies",
|
||||||
|
render: (item) =>
|
||||||
|
item.map((company) => <Tag color="blue">{company.caption}</Tag>),
|
||||||
|
},
|
||||||
|
];
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Table
|
||||||
|
columns={columns}
|
||||||
|
dataSource={wellsStat}
|
||||||
|
size={"small"}
|
||||||
|
bordered
|
||||||
|
pagination={false}
|
||||||
|
rowKey={(record) => record.id}
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
}
|
67
src/pages/Cluster/index.jsx
Normal file
67
src/pages/Cluster/index.jsx
Normal file
@ -0,0 +1,67 @@
|
|||||||
|
import { Layout, Menu } from "antd";
|
||||||
|
import { Link, Switch, Route, Redirect, useParams } from "react-router-dom";
|
||||||
|
import { useState, useEffect } from "react";
|
||||||
|
import ClusterWells from "./ClusterWells";
|
||||||
|
import ClusterSections from "./ClusterSections";
|
||||||
|
import LoaderPortal from "../../components/LoaderPortal";
|
||||||
|
import { invokeWebApiWrapperAsync } from "../../components/factory";
|
||||||
|
import { WellOperationStatService } from "../../services/api";
|
||||||
|
|
||||||
|
const { Content } = Layout;
|
||||||
|
|
||||||
|
export default function Cluster() {
|
||||||
|
let { idClaster, tab } = useParams();
|
||||||
|
const [data, setData] = useState([]);
|
||||||
|
const [showLoader, setShowLoader] = useState(false);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
invokeWebApiWrapperAsync(
|
||||||
|
async () => {
|
||||||
|
const clusterData = await WellOperationStatService.getStatCluster(
|
||||||
|
idClaster
|
||||||
|
);
|
||||||
|
setData(clusterData);
|
||||||
|
},
|
||||||
|
setShowLoader,
|
||||||
|
`Не удалось загрузить данные по кусту "${idClaster}"`
|
||||||
|
);
|
||||||
|
}, [idClaster]);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<Layout>
|
||||||
|
<Menu
|
||||||
|
mode="horizontal"
|
||||||
|
selectable={true}
|
||||||
|
selectedKeys={[tab]}
|
||||||
|
className="well_menu"
|
||||||
|
>
|
||||||
|
<Menu.Item key="wells">
|
||||||
|
<Link to={`/cluster/${idClaster}/wells`}>Скважины</Link>
|
||||||
|
</Menu.Item>
|
||||||
|
<Menu.Item key="sections">
|
||||||
|
<Link to={`/cluster/${idClaster}/sections`}>Секции</Link>
|
||||||
|
</Menu.Item>
|
||||||
|
</Menu>
|
||||||
|
</Layout>
|
||||||
|
|
||||||
|
<Layout>
|
||||||
|
<LoaderPortal show={showLoader}>
|
||||||
|
<Content className="site-layout-background">
|
||||||
|
<Switch>
|
||||||
|
<Route path="/cluster/:id/wells">
|
||||||
|
<ClusterWells clusterData={data} />
|
||||||
|
</Route>
|
||||||
|
<Route path="/cluster/:id/sections">
|
||||||
|
<ClusterSections clusterData={data} />
|
||||||
|
</Route>
|
||||||
|
<Route path="/">
|
||||||
|
<Redirect to={`/cluster/${idClaster}/wells`} />
|
||||||
|
</Route>
|
||||||
|
</Switch>
|
||||||
|
</Content>
|
||||||
|
</LoaderPortal>
|
||||||
|
</Layout>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
}
|
@ -1,58 +0,0 @@
|
|||||||
import { Layout, Menu } from "antd";
|
|
||||||
import { Link, Switch, Route, useParams } from "react-router-dom";
|
|
||||||
import { useState, useEffect } from "react"
|
|
||||||
import ClusterWells from './ClusterWells'
|
|
||||||
import ClusterSections from './ClusterSections'
|
|
||||||
import LoaderPortal from '../components/LoaderPortal'
|
|
||||||
import {invokeWebApiWrapperAsync} from '../components/factory'
|
|
||||||
import {WellOperationStatService} from "../services/api";
|
|
||||||
|
|
||||||
const { Content } = Layout;
|
|
||||||
|
|
||||||
export default function ClusterInfo() {
|
|
||||||
let { id } = useParams();
|
|
||||||
let { tab } = useParams()
|
|
||||||
const [data, setData] = useState([]);
|
|
||||||
const [showLoader, setShowLoader] = useState(false)
|
|
||||||
|
|
||||||
useEffect(() => {
|
|
||||||
invokeWebApiWrapperAsync(
|
|
||||||
async () => {
|
|
||||||
const clusterData = await WellOperationStatService.getStatCluster(id)
|
|
||||||
setData(clusterData)
|
|
||||||
},
|
|
||||||
setShowLoader,
|
|
||||||
`Не удалось загрузить данные по кусту "${id}"`)
|
|
||||||
} ,[id])
|
|
||||||
|
|
||||||
return(<>
|
|
||||||
<Layout>
|
|
||||||
<Menu mode="horizontal"
|
|
||||||
selectable={true}
|
|
||||||
selectedKeys={[tab]}
|
|
||||||
className="well_menu">
|
|
||||||
<Menu.Item key="all">
|
|
||||||
<Link to={`/cluster/${id}/all`}>Скважины</Link>
|
|
||||||
</Menu.Item>
|
|
||||||
<Menu.Item key="sections">
|
|
||||||
<Link to={`/cluster/${id}/sections`}>Секции</Link>
|
|
||||||
</Menu.Item>
|
|
||||||
</Menu>
|
|
||||||
</Layout>
|
|
||||||
|
|
||||||
<Layout>
|
|
||||||
<LoaderPortal show={showLoader}>
|
|
||||||
<Content className="site-layout-background">
|
|
||||||
<Switch>
|
|
||||||
<Route path="/cluster/:id/all">
|
|
||||||
<ClusterWells clusterData = {data}/>
|
|
||||||
</Route>
|
|
||||||
<Route path="/cluster/:id/sections">
|
|
||||||
<ClusterSections clusterData = {data}/>
|
|
||||||
</Route>
|
|
||||||
</Switch>
|
|
||||||
</Content>
|
|
||||||
</LoaderPortal>
|
|
||||||
</Layout>
|
|
||||||
</>)
|
|
||||||
}
|
|
@ -1,183 +0,0 @@
|
|||||||
import { Table, Tag, Button, Badge, Divider, Modal} from "antd"
|
|
||||||
import { useParams } from "react-router-dom";
|
|
||||||
import { LineChartOutlined, ProfileOutlined } from '@ant-design/icons'
|
|
||||||
import { useState, useEffect } from "react"
|
|
||||||
import { makeTextColumn, makeNumericColumnPlanFact, calcAndUpdateStatsBySections } from '../components/Table/index'
|
|
||||||
|
|
||||||
|
|
||||||
const filtersMinMax = [
|
|
||||||
{
|
|
||||||
text: "min",
|
|
||||||
value: "min",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
text: "max",
|
|
||||||
value: "max",
|
|
||||||
},
|
|
||||||
]
|
|
||||||
|
|
||||||
const filtersSectionsType = [ ]
|
|
||||||
|
|
||||||
const ModalWindowButton = ({buttonIcon, buttonText, modalTitle, modalContent}) =>{
|
|
||||||
const [isModalVisible, setIsModalVisible] = useState(false)
|
|
||||||
|
|
||||||
let content = (typeof(modalContent)==="string")
|
|
||||||
? <img src={modalContent} alt="" style={{width: "100%"}}/>
|
|
||||||
: modalContent
|
|
||||||
|
|
||||||
return (
|
|
||||||
<>
|
|
||||||
<Button
|
|
||||||
type="secondary"
|
|
||||||
onClick={() => setIsModalVisible(true)}
|
|
||||||
icon={buttonIcon}
|
|
||||||
>{buttonText}</Button>
|
|
||||||
<Modal
|
|
||||||
title={modalTitle}
|
|
||||||
centered
|
|
||||||
visible={isModalVisible}
|
|
||||||
onOk={() => setIsModalVisible(false)}
|
|
||||||
onCancel={() => setIsModalVisible(false)}
|
|
||||||
width={1400}>
|
|
||||||
{content}
|
|
||||||
</Modal>
|
|
||||||
</>
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
const columns = [
|
|
||||||
makeTextColumn('скв №', 'caption'),
|
|
||||||
makeTextColumn('Секция', 'sectionType', filtersSectionsType),
|
|
||||||
makeNumericColumnPlanFact('Глубина', 'sectionWellDepth', filtersMinMax),
|
|
||||||
makeNumericColumnPlanFact('Продолжительность', 'sectionBuildDays', filtersMinMax), //Цикл строительства
|
|
||||||
makeNumericColumnPlanFact('МСП', 'sectionRateOfPenetration', filtersMinMax),
|
|
||||||
makeNumericColumnPlanFact('Рейсовая скорость', 'sectionRouteSpeed', filtersMinMax),
|
|
||||||
makeNumericColumnPlanFact('Спуск КНБК', 'sectionBhaDownSpeed', filtersMinMax),//Скорость спуска КНБК
|
|
||||||
makeNumericColumnPlanFact('Подъем КНБК', 'sectionBhaUpSpeed', filtersMinMax),//Скорость подъема КНБК
|
|
||||||
makeNumericColumnPlanFact('Скорость спуска ОК', 'sectionCasingDownSpeed', filtersMinMax),
|
|
||||||
makeNumericColumnPlanFact('НПВ, сут', 'nonProductiveTime', filtersMinMax, '70px'),
|
|
||||||
{
|
|
||||||
title: "TVD",
|
|
||||||
render: (_, record) => <ModalWindowButton
|
|
||||||
buttonIcon={<LineChartOutlined/>}
|
|
||||||
modalTitle={`График по скв.:${record.caption}`}/>
|
|
||||||
//modalContent = {resources['Chart' + record.caption]}/>,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Операции",
|
|
||||||
render: (_, record) => <ModalWindowButton
|
|
||||||
buttonIcon={<ProfileOutlined/>}
|
|
||||||
modalTitle={`Операции по скв.:${record.caption}`}/>
|
|
||||||
//modalContent = {resources['Table' + record.caption]},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Подрядчики",
|
|
||||||
dataIndex: "companies",
|
|
||||||
render: (item) =>
|
|
||||||
item?.map((company) => <Tag color="blue">{company.caption}</Tag>),
|
|
||||||
},
|
|
||||||
]
|
|
||||||
|
|
||||||
|
|
||||||
export default function ClusterSections({clusterData}) {
|
|
||||||
let { id } = useParams()
|
|
||||||
const [wellsStat, setWellsStat] = useState([])
|
|
||||||
const [selectedWells, setSelectedWells] = useState([])
|
|
||||||
const [selectedWellsKeys, setSelectedWellsKeys] = useState([])
|
|
||||||
|
|
||||||
calcAndUpdateStatsBySections(wellsStat ?? [], [
|
|
||||||
"sectionWellDepthPlan",
|
|
||||||
"sectionWellDepthFact",
|
|
||||||
"sectionBuildDaysPlan",
|
|
||||||
"sectionBuildDaysFact",
|
|
||||||
"sectionRateOfPenetrationPlan",
|
|
||||||
"sectionRateOfPenetrationFact",
|
|
||||||
"sectionRouteSpeedPlan",
|
|
||||||
"sectionRouteSpeedFact",
|
|
||||||
"sectionBhaDownSpeedPlan",
|
|
||||||
"sectionBhaDownSpeedFact",
|
|
||||||
"sectionBhaUpSpeedPlan",
|
|
||||||
"sectionBhaUpSpeedFact",
|
|
||||||
"sectionCasingDownSpeedPlan",
|
|
||||||
"sectionCasingDownSpeedFact",
|
|
||||||
"nonProductiveTimePlan",
|
|
||||||
"nonProductiveTimeFact"
|
|
||||||
])
|
|
||||||
|
|
||||||
useEffect(() => {
|
|
||||||
let rows = []
|
|
||||||
|
|
||||||
clusterData.statsWells?.forEach(el => {
|
|
||||||
el.sections.forEach(section => {
|
|
||||||
let row = {
|
|
||||||
key: el.caption + section.id,
|
|
||||||
id: el.caption + section.id,
|
|
||||||
caption: el.caption,
|
|
||||||
sectionType: section.caption,
|
|
||||||
sectionWellDepthPlan: section.plan.wellDepthEnd,
|
|
||||||
sectionWellDepthFact: section.fact.wellDepthEnd,
|
|
||||||
sectionBuildDaysPlan: (Math.abs(new Date(section.plan.start) -
|
|
||||||
new Date(section.plan.end)) / (1000 * 60 * 60 * 24)).toFixed(2),
|
|
||||||
sectionBuildDaysFact: (Math.abs(new Date(section.fact.start) -
|
|
||||||
new Date(section.fact.end)) / (1000 * 60 * 60 * 24)).toFixed(2),
|
|
||||||
sectionRateOfPenetrationPlan: section.plan.rop.toFixed(2),
|
|
||||||
sectionRateOfPenetrationFact: section.fact.rop.toFixed(2),
|
|
||||||
sectionRouteSpeedPlan: section.plan.routeSpeed.toFixed(2),
|
|
||||||
sectionRouteSpeedFact: section.fact.routeSpeed.toFixed(2),
|
|
||||||
sectionBhaDownSpeedPlan: section.plan.bhaDownSpeed.toFixed(2),
|
|
||||||
sectionBhaDownSpeedFact: section.fact.bhaDownSpeed.toFixed(2),
|
|
||||||
sectionBhaUpSpeedPlan: section.plan.bhaUpSpeed.toFixed(2),
|
|
||||||
sectionBhaUpSpeedFact: section.fact.bhaUpSpeed.toFixed(2),
|
|
||||||
sectionCasingDownSpeedPlan: section.plan.casingDownSpeed.toFixed(2),
|
|
||||||
sectionCasingDownSpeedFact: section.fact.casingDownSpeed.toFixed(2),
|
|
||||||
nonProductiveTimePlan: section.plan.nonProductiveHours.toFixed(2),
|
|
||||||
nonProductiveTimeFact: section.fact.nonProductiveHours.toFixed(2),
|
|
||||||
companies: el.companies
|
|
||||||
}
|
|
||||||
|
|
||||||
rows.push(row)
|
|
||||||
|
|
||||||
if(!filtersSectionsType.some(el => el.text === section.caption))
|
|
||||||
filtersSectionsType.push({text: section.caption, value: section.caption})
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
setWellsStat(rows)
|
|
||||||
|
|
||||||
}, [id, clusterData])
|
|
||||||
|
|
||||||
const rowSelection = {
|
|
||||||
selectedRowKeys: selectedWellsKeys,
|
|
||||||
onChange: (keys, items) => {
|
|
||||||
setSelectedWells(items)
|
|
||||||
setSelectedWellsKeys(keys)
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
return (
|
|
||||||
<>
|
|
||||||
<Table
|
|
||||||
columns={columns}
|
|
||||||
dataSource={wellsStat}
|
|
||||||
size={"small"}
|
|
||||||
bordered
|
|
||||||
scroll={{ x: true, y: 620}}
|
|
||||||
rowSelection={rowSelection}
|
|
||||||
pagination={false}
|
|
||||||
/>
|
|
||||||
<Divider/>
|
|
||||||
<Badge.Ribbon text="комбинированная скважина" color="gray">
|
|
||||||
<h3>Выбранные секции<></></h3>
|
|
||||||
</Badge.Ribbon>
|
|
||||||
<Table
|
|
||||||
columns={columns}
|
|
||||||
dataSource={selectedWells}
|
|
||||||
rowSelection={rowSelection}
|
|
||||||
size={"small"}
|
|
||||||
bordered
|
|
||||||
scroll={{ x: true}}
|
|
||||||
pagination={false}
|
|
||||||
/>
|
|
||||||
</>
|
|
||||||
)
|
|
||||||
}
|
|
@ -1,143 +0,0 @@
|
|||||||
import {useParams} from "react-router-dom";
|
|
||||||
import {Link} from "react-router-dom";
|
|
||||||
import LoaderPortal from '../components/LoaderPortal'
|
|
||||||
import { useState, useEffect } from "react";
|
|
||||||
import {ClusterService} from '../services/api'
|
|
||||||
import { notify } from "../components/factory"
|
|
||||||
import {Table, Tag, Button} from 'antd';
|
|
||||||
|
|
||||||
const columns = [
|
|
||||||
{
|
|
||||||
title: 'скв №',
|
|
||||||
key: 'caption',
|
|
||||||
dataIndex: 'caption',
|
|
||||||
render: (_, item) => <Link to={`/well/${item.id}`}>{item.caption}</Link>
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'Тип скв.',
|
|
||||||
key: 'wellType',
|
|
||||||
dataIndex: 'wellType',
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'Фактические сроки бурения',
|
|
||||||
children: [
|
|
||||||
{
|
|
||||||
title: 'начало',
|
|
||||||
key: 'factStart',
|
|
||||||
dataIndex: 'factStart',
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'окончание',
|
|
||||||
key: 'factEnd',
|
|
||||||
dataIndex: 'factEnd',
|
|
||||||
},
|
|
||||||
]
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'Продолжительность бурения',
|
|
||||||
children: [
|
|
||||||
{
|
|
||||||
title: 'план',
|
|
||||||
key: 'periodPlan',
|
|
||||||
dataIndex: 'periodPlan',
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'факт',
|
|
||||||
key: 'periodFact',
|
|
||||||
dataIndex: 'periodFact',
|
|
||||||
},
|
|
||||||
]
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'МСП за скв',
|
|
||||||
children: [
|
|
||||||
{
|
|
||||||
title: 'план',
|
|
||||||
key: 'rateOfPenetrationPlan',
|
|
||||||
dataIndex: 'rateOfPenetrationPlan',
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'факт',
|
|
||||||
key: 'rateOfPenetrationFact',
|
|
||||||
dataIndex: 'rateOfPenetrationFact',
|
|
||||||
},
|
|
||||||
],
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'Рейсовая скорость за скв',
|
|
||||||
children: [
|
|
||||||
{
|
|
||||||
title: 'план',
|
|
||||||
key: 'routeSpeedPlan',
|
|
||||||
dataIndex: 'routeSpeedPlan',
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'факт',
|
|
||||||
key: 'routeSpeedFact',
|
|
||||||
dataIndex: 'routeSpeedFact',
|
|
||||||
},
|
|
||||||
],
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'Секции',
|
|
||||||
key: 'sections',
|
|
||||||
dataIndex: 'sections',
|
|
||||||
render: (item) => (<span>таблица по секциям</span>)
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'График глубина-день',
|
|
||||||
render: _ => (<Button>Открыть</Button>)
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'Таблица по операциям',
|
|
||||||
render: _ => (<Button>Открыть</Button>)
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'Подрядчики',
|
|
||||||
key: 'companies',
|
|
||||||
dataIndex: 'companies',
|
|
||||||
render: (item) => item.map(company => <Tag color="blue">{company.caption}</Tag>)
|
|
||||||
},
|
|
||||||
];
|
|
||||||
|
|
||||||
export default function ClusterStat() {
|
|
||||||
let { id } = useParams()
|
|
||||||
const [clusterTitle, setClusterTitle] = useState("")
|
|
||||||
const [wellsStat, setWellsStat] = useState(null)
|
|
||||||
const [showLoader, setShowLoader] = useState(false)
|
|
||||||
|
|
||||||
useEffect(()=>{
|
|
||||||
const updateWellsStat = async() => {
|
|
||||||
setShowLoader(true)
|
|
||||||
try{
|
|
||||||
const msInDay = 1000*60*60*24
|
|
||||||
const data = await ClusterService.getStat(id)
|
|
||||||
const wellsStat = data.wellsStat.map(w=>({...w,
|
|
||||||
periodPlan: (new Date(w.planEnd) - new Date(w.planStart))/msInDay,
|
|
||||||
periodFact: (new Date(w.factEnd) - new Date(w.factStart))/msInDay,
|
|
||||||
}))
|
|
||||||
setWellsStat(wellsStat)
|
|
||||||
setClusterTitle(data.caption)
|
|
||||||
}
|
|
||||||
catch(ex) {
|
|
||||||
notify(`Не удалось загрузить статистику по скважинам куста "${id}"`, 'error')
|
|
||||||
console.log(ex)
|
|
||||||
}
|
|
||||||
setShowLoader(false)
|
|
||||||
}
|
|
||||||
updateWellsStat()
|
|
||||||
},[id])
|
|
||||||
|
|
||||||
return(
|
|
||||||
<LoaderPortal show={showLoader}>
|
|
||||||
<h3>{clusterTitle}</h3>
|
|
||||||
<Table
|
|
||||||
columns={columns}
|
|
||||||
dataSource={wellsStat}
|
|
||||||
size={'small'}
|
|
||||||
bordered
|
|
||||||
pagination={false}
|
|
||||||
rowKey={(record) => record.id}
|
|
||||||
/>
|
|
||||||
</LoaderPortal>)
|
|
||||||
}
|
|
@ -1,113 +0,0 @@
|
|||||||
import { useParams } from "react-router-dom";
|
|
||||||
import { Link } from "react-router-dom";
|
|
||||||
import { useState, useEffect } from "react";
|
|
||||||
import { Table, Tag, Button } from 'antd';
|
|
||||||
import { makeTextColumn, makeGroupColumn, makeNumericColumn,
|
|
||||||
makeNumericColumnPlanFact, calcAndUpdateStatsBySections } from '../components/Table/index'
|
|
||||||
|
|
||||||
|
|
||||||
const filtersMinMax = [
|
|
||||||
{
|
|
||||||
text: "min",
|
|
||||||
value: "min",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
text: "max",
|
|
||||||
value: "max",
|
|
||||||
},
|
|
||||||
]
|
|
||||||
|
|
||||||
const filtersWellsType = [
|
|
||||||
{
|
|
||||||
text: "Наклонно-направленная",
|
|
||||||
value: "Наклонно-направленная",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
text: "Горизонтальная",
|
|
||||||
value: "Горизонтальная",
|
|
||||||
}
|
|
||||||
]
|
|
||||||
|
|
||||||
|
|
||||||
export default function ClusterWells({clusterData}) {
|
|
||||||
let { id } = useParams()
|
|
||||||
const [wellsStat, setWellsStat] = useState([])
|
|
||||||
|
|
||||||
calcAndUpdateStatsBySections(wellsStat ?? [], [
|
|
||||||
"factStart",
|
|
||||||
"factEnd",
|
|
||||||
"periodPlan",
|
|
||||||
"periodFact",
|
|
||||||
"rateOfPenetrationPlan",
|
|
||||||
"rateOfPenetrationFact",
|
|
||||||
"routeSpeedPlan",
|
|
||||||
"routeSpeedFact",
|
|
||||||
"notProductiveTime"
|
|
||||||
])
|
|
||||||
|
|
||||||
useEffect(() => {
|
|
||||||
let tableData = clusterData.statsWells?.map(el => {
|
|
||||||
return {
|
|
||||||
key: el.id,
|
|
||||||
id: el.id,
|
|
||||||
caption: el.caption,
|
|
||||||
wellType: el.wellType,
|
|
||||||
factStart: new Date(el.total.fact.start).toLocaleString(),
|
|
||||||
factEnd: new Date(el.total.fact.end).toLocaleString(),
|
|
||||||
periodPlan: (Math.abs(new Date(el.total.plan.start) -
|
|
||||||
new Date(el.total.plan.end)) / (1000 * 60 * 60 * 24)).toFixed(2),
|
|
||||||
periodFact: (Math.abs(new Date(el.total.fact.start) -
|
|
||||||
new Date(el.total.fact.end)) / (1000 * 60 * 60 * 24)).toFixed(2),
|
|
||||||
rateOfPenetrationPlan: el.total.plan.rop.toFixed(2),
|
|
||||||
rateOfPenetrationFact: el.total.fact.rop.toFixed(2),
|
|
||||||
routeSpeedPlan: el.total.plan.routeSpeed.toFixed(2),
|
|
||||||
routeSpeedFact: el.total.fact.routeSpeed.toFixed(2),
|
|
||||||
notProductiveTimePlan: el.total.plan.nonProductiveHours.toFixed(2),
|
|
||||||
notProductiveTimeFact: el.total.fact.nonProductiveHours.toFixed(2),
|
|
||||||
companies: el.companies
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
setWellsStat(tableData)
|
|
||||||
|
|
||||||
}, [id, clusterData])
|
|
||||||
|
|
||||||
const columns = [
|
|
||||||
makeTextColumn('скв №', 'caption', null, null,
|
|
||||||
(_, item) => <Link to={`/well/${item.id}`}>{item.caption}</Link>),
|
|
||||||
makeTextColumn('Тип скв.', 'wellType', filtersWellsType),
|
|
||||||
makeGroupColumn( 'Фактические сроки', [
|
|
||||||
makeNumericColumn('начало', 'factStart'),
|
|
||||||
makeNumericColumn('окончание', 'factEnd'),
|
|
||||||
]),
|
|
||||||
makeNumericColumnPlanFact('Продолжительность', 'period', filtersMinMax),
|
|
||||||
makeNumericColumnPlanFact('МСП', 'rateOfPenetration', filtersMinMax),
|
|
||||||
makeNumericColumnPlanFact('Рейсовая скорость', 'routeSpeed', filtersMinMax),
|
|
||||||
makeNumericColumnPlanFact('НПВ, сут', 'notProductiveTime', filtersMinMax),
|
|
||||||
{
|
|
||||||
title: 'График глубина-день',
|
|
||||||
render: (_, item) => (<Button>Открыть</Button>)
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'Таблица по операциям',
|
|
||||||
render: _ => (<Button>Открыть</Button>)
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: 'Подрядчики',
|
|
||||||
key: 'companies',
|
|
||||||
dataIndex: 'companies',
|
|
||||||
render: (item) => item.map(company => <Tag color="blue">{company.caption}</Tag>)
|
|
||||||
},
|
|
||||||
];
|
|
||||||
|
|
||||||
return (
|
|
||||||
<Table
|
|
||||||
columns={columns}
|
|
||||||
dataSource={wellsStat}
|
|
||||||
size={'small'}
|
|
||||||
bordered
|
|
||||||
pagination={false}
|
|
||||||
rowKey={(record) => record.id}
|
|
||||||
/>
|
|
||||||
)
|
|
||||||
}
|
|
@ -1,31 +1,30 @@
|
|||||||
import Deposit from './Deposit'
|
|
||||||
import ClusterInfo from './ClusterInfo'
|
|
||||||
import Well from "./Well";
|
|
||||||
import LayoutPortal from '../components/LayoutPortal'
|
|
||||||
import { Redirect, Route, Switch } from "react-router-dom";
|
import { Redirect, Route, Switch } from "react-router-dom";
|
||||||
|
import Deposit from "./Deposit";
|
||||||
|
import Cluster from "./Cluster";
|
||||||
|
import Well from "./Well";
|
||||||
|
import LayoutPortal from "../components/LayoutPortal";
|
||||||
|
|
||||||
export default function Main() {
|
export default function Main() {
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Switch>
|
<Switch>
|
||||||
<Route path="/well/:idWell/">
|
|
||||||
<LayoutPortal>
|
|
||||||
<Well/>
|
|
||||||
</LayoutPortal>
|
|
||||||
</Route>
|
|
||||||
<Route path="/deposit">
|
<Route path="/deposit">
|
||||||
<LayoutPortal noSheet>
|
<LayoutPortal noSheet>
|
||||||
<Deposit />
|
<Deposit />
|
||||||
</LayoutPortal>
|
</LayoutPortal>
|
||||||
</Route>
|
</Route>
|
||||||
<Route path="/cluster/:id/:tab">
|
<Route path="/cluster/:idClaster/:tab?">
|
||||||
<LayoutPortal>
|
<LayoutPortal>
|
||||||
<ClusterInfo />
|
<Cluster />
|
||||||
|
</LayoutPortal>
|
||||||
|
</Route>
|
||||||
|
<Route path="/well/:idWell/:tab?">
|
||||||
|
<LayoutPortal>
|
||||||
|
<Well />
|
||||||
</LayoutPortal>
|
</LayoutPortal>
|
||||||
</Route>
|
</Route>
|
||||||
<Route path="/">
|
<Route path="/">
|
||||||
<Redirect to={{ pathname: `/deposit` }} />
|
<Redirect to={{ pathname: `/deposit` }} />
|
||||||
</Route>
|
</Route>
|
||||||
</Switch>
|
</Switch>
|
||||||
)
|
);
|
||||||
}
|
}
|
||||||
|
@ -1,19 +1,25 @@
|
|||||||
import { Layout, Menu } from "antd";
|
import { Layout, Menu } from "antd";
|
||||||
import { FolderOutlined, FundViewOutlined, AlertOutlined, FilePdfOutlined, DatabaseOutlined } from "@ant-design/icons";
|
import {
|
||||||
|
FolderOutlined,
|
||||||
|
FundViewOutlined,
|
||||||
|
AlertOutlined,
|
||||||
|
FilePdfOutlined,
|
||||||
|
DatabaseOutlined,
|
||||||
|
} from "@ant-design/icons";
|
||||||
import { Link, Redirect, Route, Switch, useParams } from "react-router-dom";
|
import { Link, Redirect, Route, Switch, useParams } from "react-router-dom";
|
||||||
import TelemetryView from "./TelemetryView";
|
import TelemetryView from "./TelemetryView";
|
||||||
import Messages from "./Messages";
|
import Messages from "./Messages";
|
||||||
import Report from "./Report";
|
import Report from "./Report";
|
||||||
import Archive from "./Archive";
|
import Archive from "./Archive";
|
||||||
import Documents from "./Documents";
|
import Documents from "./Documents";
|
||||||
import LastData from './LastData'
|
import LastData from "./LastData";
|
||||||
import { makeMenuItems } from "./Documents/menuItems";
|
import { makeMenuItems } from "./Documents/menuItems";
|
||||||
import WellOperations from "./WellOperations";
|
import WellOperations from "./WellOperations";
|
||||||
|
|
||||||
const { Content } = Layout;
|
const { Content } = Layout;
|
||||||
|
|
||||||
export default function Well() {
|
export default function Well() {
|
||||||
let { idWell } = useParams();
|
let { idWell, tab } = useParams();
|
||||||
const rootPath = `/well/${idWell}`;
|
const rootPath = `/well/${idWell}`;
|
||||||
|
|
||||||
const { SubMenu } = Menu;
|
const { SubMenu } = Menu;
|
||||||
@ -21,30 +27,34 @@ export default function Well() {
|
|||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<Layout>
|
<Layout>
|
||||||
<Menu mode="horizontal" selectable={true} className="well_menu">
|
<Menu
|
||||||
<Menu.Item key="1" icon={<FundViewOutlined />}>
|
mode="horizontal"
|
||||||
|
selectable={true}
|
||||||
|
selectedKeys={[tab]}
|
||||||
|
className="well_menu"
|
||||||
|
>
|
||||||
|
<Menu.Item key="telemetry" icon={<FundViewOutlined />}>
|
||||||
<Link to={`${rootPath}/telemetry`}>Мониторинг</Link>
|
<Link to={`${rootPath}/telemetry`}>Мониторинг</Link>
|
||||||
</Menu.Item>
|
</Menu.Item>
|
||||||
<Menu.Item key="2" icon={<AlertOutlined />}>
|
<Menu.Item key="message" icon={<AlertOutlined />}>
|
||||||
<Link to={`${rootPath}/message`}>Сообщения</Link>
|
<Link to={`${rootPath}/message`}>Сообщения</Link>
|
||||||
</Menu.Item>
|
</Menu.Item>
|
||||||
<Menu.Item key="3" icon={<FilePdfOutlined />}>
|
<Menu.Item key="report" icon={<FilePdfOutlined />}>
|
||||||
<Link to={`${rootPath}/report`}>Рапорт</Link>
|
<Link to={`${rootPath}/report`}>Рапорт</Link>
|
||||||
</Menu.Item>
|
</Menu.Item>
|
||||||
<Menu.Item key="5" icon={<FolderOutlined />}>
|
<Menu.Item key="operations" icon={<FolderOutlined />}>
|
||||||
<Link to={`${rootPath}/operations/plan`}>
|
<Link to={`${rootPath}/operations/plan`}>Операции по скважине</Link>
|
||||||
Операции по скважине
|
|
||||||
</Link>
|
|
||||||
</Menu.Item>
|
</Menu.Item>
|
||||||
<Menu.Item key="7" icon={<DatabaseOutlined/>}>
|
<Menu.Item key="archive" icon={<DatabaseOutlined />}>
|
||||||
<Link to={`${rootPath}/archive`}>Архив</Link>
|
<Link to={`${rootPath}/archive`}>Архив</Link>
|
||||||
</Menu.Item>
|
</Menu.Item>
|
||||||
<SubMenu
|
<SubMenu
|
||||||
key="documentsSub"
|
key="document"
|
||||||
title={
|
title={
|
||||||
<Link
|
<Link
|
||||||
to={`${rootPath}/document/fluidService`}
|
to={`${rootPath}/document/fluidService`}
|
||||||
className="linkDocuments">
|
className="linkDocuments"
|
||||||
|
>
|
||||||
Документы
|
Документы
|
||||||
</Link>
|
</Link>
|
||||||
}
|
}
|
||||||
@ -53,7 +63,7 @@ export default function Well() {
|
|||||||
>
|
>
|
||||||
{makeMenuItems(rootPath)}
|
{makeMenuItems(rootPath)}
|
||||||
</SubMenu>
|
</SubMenu>
|
||||||
<Menu.Item key="9" icon={<FolderOutlined />}>
|
<Menu.Item key="lastData" icon={<FolderOutlined />}>
|
||||||
<Link to={`${rootPath}/lastData`}>Последние данные</Link>
|
<Link to={`${rootPath}/lastData`}>Последние данные</Link>
|
||||||
</Menu.Item>
|
</Menu.Item>
|
||||||
</Menu>
|
</Menu>
|
||||||
|
Loading…
Reference in New Issue
Block a user