GIT-0001 feat(achivments): add new icons

This commit is contained in:
bakhirev 2023-07-27 09:48:52 +03:00
parent a21bb43b00
commit 9bb99aec2e
25 changed files with 221 additions and 148 deletions

View file

@ -1,16 +1,16 @@
{
"files": {
"main.css": "./static/css/main.78b5b883.css",
"main.js": "./static/js/main.0fc28d3c.js",
"static/media/warning.svg": "./static/media/warning.e39a87773603f3ab157f.svg",
"main.css": "./static/css/main.33cc195e.css",
"main.js": "./static/js/main.405a9477.js",
"index.html": "./index.html",
"static/media/warning.svg": "./static/media/warning.e39a87773603f3ab157f.svg",
"static/media/info.svg": "./static/media/info.954631f6b19e3fe9c495.svg",
"static/media/alert.svg": "./static/media/alert.41e2b99c481139c13074.svg",
"main.78b5b883.css.map": "./static/css/main.78b5b883.css.map",
"main.0fc28d3c.js.map": "./static/js/main.0fc28d3c.js.map"
"main.33cc195e.css.map": "./static/css/main.33cc195e.css.map",
"main.405a9477.js.map": "./static/js/main.405a9477.js.map"
},
"entrypoints": [
"static/css/main.78b5b883.css",
"static/js/main.0fc28d3c.js"
"static/css/main.33cc195e.css",
"static/js/main.405a9477.js"
]
}

View file

@ -1 +1 @@
<!doctype html><html lang="en"><head><meta charset="utf-8"/><script type="text/javascript">var report=[]</script><script src="/dump.git"></script><link rel="icon" href="./favicon.svg"/><meta name="viewport" content="width=device-width,initial-scale=1"/><meta name="theme-color" content="#000000"/><meta name="description" content="Web site created using create-react-app"/><link rel="apple-touch-icon" href="./logo192.png"/><link rel="manifest" href="./manifest.json"/><title>ASSAYO</title><script defer="defer" src="./static/js/main.0fc28d3c.js"></script><link href="./static/css/main.78b5b883.css" rel="stylesheet"></head><body><noscript>You need to enable JavaScript to run this app.</noscript><div id="root"></div></body></html>
<!doctype html><html lang="ru"><head><meta name="viewport" content="width=device-width,height=device-height,initial-scale=1,user-scalable=no,maximum-scale=1"><meta http-equiv="Content-Type" content="text/html; charset=utf-8"><meta http-equiv="Cache-Control" content="no-cache"><meta http-equiv="cleartype" content="on"><meta name="HandheldFriendly" content="True"><meta name="format-detection" content="telephone=no"><meta name="format-detection" content="address=no"><meta name="apple-mobile-web-app-capable" content="yes"><meta name="apple-mobile-web-app-status-bar-style" content="black-translucent"><script type="text/javascript">var report=[]</script><script src="/dump.git"></script><script src="./dump.git"></script><script src="../dump.git"></script><script src="./dump-0.git"></script><script src="./dump-1.git"></script><script src="./dump-2.git"></script><script src="./dump-3.git"></script><script src="./dump-4.git"></script><script src="./dump-5.git"></script><script src="./dump-6.git"></script><script src="./report/dump-0.git"></script><script src="./report/dump-1.git"></script><script src="./report/dump-2.git"></script><script src="./report/dump-3.git"></script><script src="./report/dump-4.git"></script><script src="./report/dump-5.git"></script><script src="./report/dump-6.git"></script><link rel="icon" href="./favicon.svg"/><link rel="apple-touch-icon" href="./logo192.png"/><link rel="manifest" href="./manifest.json"/><title>ASSAYO</title><meta name="description" content="Простой и быстрый отчёт по истории коммитов в git."><meta name="keywords" content="git, статистика, аудит, история, log, мониторинг, контроль сотрудников"><meta name="author" content="Bakhirev Aleksei"><meta name="copyright" content="(c) Bakhirev Aleksei"><meta http-equiv="Reply-to" content="alexey-bakhirev@yandex.ru"><meta name="application-name" content="GIT Статистика"><meta name="msapplication-tooltip" content="Простой и быстрый отчёт по истории коммитов в git."><meta property="og:title" content="GIT Статистика"><meta property="og:description" content="Простой и быстрый отчёт по истории коммитов в git."><meta property="og:image" content="http://assayo.jp/assets/seo/custom_icon_256.png"><meta property="og:site_name" content="Assayo"><meta property="og:url" content="http://assayo.jp/"><meta name="twitter:card" content="summary"><meta name="twitter:title" content="GIT Статистика"><meta name="twitter:description" content="Простой и быстрый отчёт по истории коммитов в git."><meta name="twitter:creator" content="Bakhirev Aleksei"><meta name="twitter:image:src" content="http://assayo.jp/assets/seo/custom_icon_256.png"><meta name="twitter:domain" content="assayo.jp"><meta name="twitter:site" content="assayo.jp"><meta itemprop="name" content="GIT Статистика"><meta itemprop="description" content="Простой и быстрый отчёт по истории коммитов в git."><meta itemprop="image" content="http://assayo.jp/assets/seo/custom_icon_256.png"><script defer="defer" src="./static/js/main.405a9477.js"></script><link href="./static/css/main.33cc195e.css" rel="stylesheet"></head><body><noscript>You need to enable JavaScript to run this app.</noscript><div id="root"></div></body></html>

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View file

@ -1,74 +0,0 @@
/*! regenerator-runtime -- Copyright (c) 2014-present, Facebook, Inc. -- license (MIT): https://github.com/facebook/regenerator/blob/main/LICENSE */
/**
* @license React
* react-dom.production.min.js
*
* Copyright (c) Facebook, Inc. and its affiliates.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*/
/**
* @license React
* react-jsx-runtime.production.min.js
*
* Copyright (c) Facebook, Inc. and its affiliates.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*/
/**
* @license React
* react.production.min.js
*
* Copyright (c) Facebook, Inc. and its affiliates.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*/
/**
* @license React
* scheduler.production.min.js
*
* Copyright (c) Facebook, Inc. and its affiliates.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*/
/**
* @remix-run/router v1.3.1
*
* Copyright (c) Remix Software Inc.
*
* This source code is licensed under the MIT license found in the
* LICENSE.md file in the root directory of this source tree.
*
* @license MIT
*/
/**
* React Router DOM v6.8.0
*
* Copyright (c) Remix Software Inc.
*
* This source code is licensed under the MIT license found in the
* LICENSE.md file in the root directory of this source tree.
*
* @license MIT
*/
/**
* React Router v6.8.0
*
* Copyright (c) Remix Software Inc.
*
* This source code is licensed under the MIT license found in the
* LICENSE.md file in the root directory of this source tree.
*
* @license MIT
*/

File diff suppressed because one or more lines are too long

View file

@ -1,21 +1,64 @@
<!DOCTYPE html>
<html lang="en">
<html lang="ru">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, height=device-height, initial-scale=1.0, user-scalable=no, maximum-scale=1.0">
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<meta http-equiv="Cache-Control" content="no-cache">
<meta http-equiv="cleartype" content="on">
<meta name="HandheldFriendly" content="True">
<meta name="format-detection" content="telephone=no">
<meta name="format-detection" content="address=no">
<meta name="apple-mobile-web-app-capable" content="yes">
<meta name="apple-mobile-web-app-status-bar-style" content="black-translucent">
<script type="text/javascript">
var report = [];
</script>
<script src='/dump.git'></script>
<script src='./dump.git'></script>
<script src='../dump.git'></script>
<script src='./dump-0.git'></script>
<script src='./dump-1.git'></script>
<script src='./dump-2.git'></script>
<script src='./dump-3.git'></script>
<script src='./dump-4.git'></script>
<script src='./dump-5.git'></script>
<script src='./dump-6.git'></script>
<script src='./report/dump-0.git'></script>
<script src='./report/dump-1.git'></script>
<script src='./report/dump-2.git'></script>
<script src='./report/dump-3.git'></script>
<script src='./report/dump-4.git'></script>
<script src='./report/dump-5.git'></script>
<script src='./report/dump-6.git'></script>
<link rel="icon" href="%PUBLIC_URL%/favicon.svg" />
<meta name="viewport" content="width=device-width, initial-scale=1" />
<meta name="theme-color" content="#000000" />
<meta
name="description"
content="Web site created using create-react-app"
/>
<link rel="apple-touch-icon" href="%PUBLIC_URL%/logo192.png" />
<link rel="manifest" href="%PUBLIC_URL%/manifest.json" />
<title>ASSAYO</title>
<meta name="description" content="Простой и быстрый отчёт по истории коммитов в git.">
<meta name="keywords" content="git, статистика, аудит, история, log, мониторинг, контроль сотрудников">
<meta name="author" content="Bakhirev Aleksei">
<meta name="copyright" content="(c) Bakhirev Aleksei">
<meta http-equiv="Reply-to" content="alexey-bakhirev@yandex.ru">
<meta name="application-name" content="GIT Статистика">
<meta name="msapplication-tooltip" content="Простой и быстрый отчёт по истории коммитов в git.">
<meta property="og:title" content="GIT Статистика">
<meta property="og:description" content="Простой и быстрый отчёт по истории коммитов в git.">
<meta property="og:image" content="http://assayo.jp/assets/seo/custom_icon_256.png">
<meta property="og:site_name" content="Assayo">
<meta property="og:url" content="http://assayo.jp/">
<meta name="twitter:card" content="summary">
<meta name="twitter:title" content="GIT Статистика">
<meta name="twitter:description" content="Простой и быстрый отчёт по истории коммитов в git.">
<meta name="twitter:creator" content="Bakhirev Aleksei">
<meta name="twitter:image:src" content="http://assayo.jp/assets/seo/custom_icon_256.png">
<meta name="twitter:domain" content="assayo.jp">
<meta name="twitter:site" content="assayo.jp">
<meta itemprop="name" content="GIT Статистика">
<meta itemprop="description" content="Простой и быстрый отчёт по истории коммитов в git.">
<meta itemprop="image" content="http://assayo.jp/assets/seo/custom_icon_256.png">
</head>
<body>
<noscript>You need to enable JavaScript to run this app.</noscript>

View file

@ -15,13 +15,42 @@ if (module.hot) {
}
// @ts-ignore
console.log(ru + '');
console.dir(ru + '');
render(
<React.StrictMode>
<HashRouter>
<Authorization/>
</HashRouter>
</React.StrictMode>,
document.getElementById('root'),
);
function getParametersFromString(text: string) {
return Object.fromEntries((text || '')
.substring(1, Infinity)
.split('&')
.map((token: string) => token.split('=')));
}
function renderReactApplication() {
render(
<React.StrictMode>
<HashRouter>
<Authorization/>
</HashRouter>
</React.StrictMode>,
document.getElementById('root'),
);
}
function loadApplication() {
const parameters = {
...getParametersFromString(location.search),
...getParametersFromString(location.hash),
};
if (!parameters.dump) {
return renderReactApplication();
}
const script = document.createElement('script');
script.src = parameters.dump;
script.async = true;
script.onload = renderReactApplication;
script.onerror = renderReactApplication;
document.body.appendChild(script);
}
loadApplication();

View file

@ -39,6 +39,19 @@ export function getOnDrop(setLoading: Function, onChange: Function) {
setLoading(false);
if (!dropItems.length) return;
if (dropItems[0].type === 'application/json') {
Promise.all(
dropItems.map((file: any) => file.text()),
).then((text: string[]) => {
const telegrammMessages = text
.map(file => JSON.parse(file)?.messages)
.flat(1);
// @ts-ignore
onChange('telegramm', telegrammMessages);
});
return;
}
Promise.all(
dropItems.map((file: any) => file.text()),
).then((text: string[]) => {

View file

@ -13,6 +13,7 @@ localization.parse('ru', `
§ sidebar.team.timestamp: Все коммиты
§ sidebar.team.changes: Все изменения
§ sidebar.team.words: Популярные слова
§ sidebar.team.top: Рейтинг
§ sidebar.person.total: Общая информация
§ sidebar.person.money: Стоимость работы
§ sidebar.person.speed: Скорость

View file

@ -71,6 +71,7 @@ export default class DataGripByAuthor {
static #updateWordStatistics(commit: ICommit, total = {}) {
const LIMIT_WORD_LENGTH = 2;
const disabledWords = { for: 1, fix: 1 };
commit.message.toLowerCase().split(' ').forEach(word => {
if (word.length <= LIMIT_WORD_LENGTH || disabledWords[word]) return;
total[word] = total[word]

View file

@ -17,22 +17,29 @@ export default function getAchievementByAuthor(author: string) {
if (statistic.hours.filter((hour: number) => hour > 18 || hour < 5).length === 0) list.push('commitsAfter1800');
// Раб божий - есть коммит на каждый час суток
if ((new Set(statistic.hours)).size === 24) list.push('workEveryTime');
// Залётный - 1..5 коммитов за все время проекта
if (statistic.commits <= 5) list.push('userNotWork');
// Мёртвая душа - 6..60 коммитов за все время проекта
if (statistic.commits >= 6 && statistic.commits <= 60) list.push('userIsDied');
// Скорострел - меньше дня на задачу
if (statistic.daysForTask < 1) list.push('lessDaysForTask');
// Со слоу - больше двух дней на задачу (?)
if (statistic.daysForTask > 2) list.push('more2DaysForTask');
if (statistic.isStaff) {
// Залётный - это не его основной проект
list.push('userNotWork');
} else {
// Мёртвая душа - работал, но уволился
if (statistic.isDismissed) list.push('userIsDied');
// Скорострел - меньше дня на задачу
if (statistic.daysForTask < 1) list.push('lessDaysForTask');
// Со слоу - больше двух дней на задачу (?)
if (statistic.daysForTask > 2) list.push('more2DaysForTask');
// Добро пожаловать - не уволили в течении трех месяцев с начала работы
if (statistic.allDaysInProject > 90) list.push('more90DaysInProject');
// Чёрт - отработал 666 дней на проекте
if (statistic.allDaysInProject > 666) list.push('more666DaysInProject');
// Флеш-рояль - отработал 777 дней на проекте
if (statistic.allDaysInProject > 777) list.push('more777DaysInProject');
}
// Ни единого разрыва - 0 дней без коммитов
if (statistic.lazyDays === 0) list.push('zeroLazyDays');
// Стрельба холостыми - коммиты есть, а закрытых задач нет
if (statistic.commits > 0 && statistic.tasks === 0) list.push('workNotWork');
// сказал как отрезал - в среднем 1 коммит на таск
if (statistic.tasks / statistic.commits) list.push('oneCommitOneTask');
// Добро пожаловать - не уволили в течении трех месяцев с начала работы
if (statistic.allDaysInProject > 90) list.push('more90DaysInProject');
return list.reduce((acc: any, type: string) => {
const index = ALL_ACHIEVEMENTS[type][2];

View file

@ -57,33 +57,41 @@ class AchievementsByCompetition {
const allDaysInProject = this.#getFirstAndLast(total.allDaysInProject);
// Старожил - больше всего дней на проекте
achievements[allDaysInProject.first].push('moreDaysInProject');
// Сосунок - меньше всего дней на проекте
// А это кто? - меньше всего дней на проекте
achievements[allDaysInProject.last].push('lessDaysInProject');
const firstCommit = this.#getFirstAndLast(total.firstCommit);
// Адам - первый стабильны сотрудник на проекте
achievements[firstCommit.last].push('adam');
const moreRefactoring = this.#getFirstAndLast(total.moreRefactoring);
// Главный редактор - сделал больше всех меток «рефакторинг»
achievements[moreRefactoring.first].push('moreRefactoring');
this.authors = achievements;
}
#getTotalByAuthor(statisticByAuthor: any) {
const achievements = {};
const total: any = {
nameLength: [],
maxMessage: [],
midMessage: [],
tasks: [],
days: [],
lazyDays: [],
allDaysInProject: [],
};
const total: IHashMap<any> = {};
statisticByAuthor.forEach((statistic: any) => {
achievements[statistic.author] = [];
total.nameLength.push([statistic.author, statistic.author.length]);
total.maxMessage.push([statistic.author, statistic.messageLength[statistic.messageLength.length - 1]]);
total.midMessage.push([statistic.author, statistic.middleMessageLength]);
total.tasks.push([statistic.author, statistic.tasks.length]);
total.days.push([statistic.author, statistic.days]);
total.lazyDays.push([statistic.author, statistic.lazyDays]);
total.allDaysInProject.push([statistic.author, statistic.allDaysInProject]);
const addData = (property: string, count: number) => {
if (!total[property]) total[property] = [];
total[property].push([statistic.author, count]);
};
addData('nameLength', statistic.author.length);
addData('maxMessage', statistic.messageLength[statistic.messageLength.length - 1]);
addData('midMessage', statistic.middleMessageLength);
addData('tasks', statistic.tasks.length);
addData('days', statistic.days);
addData('moreRefactoring', statistic.types.refactor);
if (statistic.isStaff) return;
addData('allDaysInProject', statistic.allDaysInProject);
addData('lazyDays', statistic.lazyDays);
addData('firstCommit', statistic.firstCommit.milliseconds);
});
Object.keys(total).forEach(achievement => {

View file

@ -4,15 +4,14 @@ export default {
commitsAfter1500: ['Сова', '70% коммитов после 15:00', ACHIEVEMENT_TYPE.NORMAL],
commitsBefore1500: ['Раняя пташка', '70% коммитов до обеда', ACHIEVEMENT_TYPE.NORMAL],
commitsAfter1800: ['Делу время', 'нет ни одного коммита после 18:00', ACHIEVEMENT_TYPE.GOOD],
userNotWork: ['Залётный', 'меньше 5 коммитов за всё время проекта', ACHIEVEMENT_TYPE.NORMAL],
userIsDied: ['Мёртвая душа', 'от 6 до 60 коммитов за все время проекта', ACHIEVEMENT_TYPE.NORMAL],
workEveryTime: ['Раб божий', 'есть коммит на каждый час суток', ACHIEVEMENT_TYPE.BAD],
workNotWork: ['Стрельба холостыми', 'коммиты есть, а закрытых задач нет', ACHIEVEMENT_TYPE.BAD], // нет картинки
moreTasks: ['Батя грит малаца', 'больше всего закрытых задач', ACHIEVEMENT_TYPE.GOOD], // нет картинки
userNotWork: ['Залётный', 'это не его основной проект', ACHIEVEMENT_TYPE.NORMAL],
userIsDied: ['Мёртвая душа', 'работал, но уволился', ACHIEVEMENT_TYPE.NORMAL],
lessTasks: ['Зашел и вышел', 'меньше всего закрытых задач', ACHIEVEMENT_TYPE.BAD],
moreTasks: ['Батя грит малаца', 'больше всего закрытых задач', ACHIEVEMENT_TYPE.GOOD], // нет картинки
everyMessageLong: ['Мастер красноречия', 'стабильно самые длинные подписи коммитов', ACHIEVEMENT_TYPE.NORMAL],
everyMessageShort: ['Болтун находка для шпиона', 'стабильно, самые короткие подписи коммитов', ACHIEVEMENT_TYPE.BAD],
longestMessage: ['А разговоров то было...', 'самая длинная подпись коммита за все время', ACHIEVEMENT_TYPE.NORMAL],
shortestName: ['Размер не главное', 'самое короткое имя', ACHIEVEMENT_TYPE.NORMAL], // нет картинки
longestName: ['Азим Азиз Иль Ам Кадир Имран II', 'самое длинное имя', ACHIEVEMENT_TYPE.NORMAL],
moreCommits: ['Мастер бекапов', 'больше всего коммитов', ACHIEVEMENT_TYPE.NORMAL],
@ -22,7 +21,6 @@ export default {
lessLazyDays: ['Папа Карло', 'меньше всего дней без коммитов', ACHIEVEMENT_TYPE.GOOD],
zeroLazyDays: ['Ни единого разрыва', 'ни одного дня без коммитов', ACHIEVEMENT_TYPE.GOOD],
moreWorkDays: ['Ценный работник', 'больше всего рабочих дней', ACHIEVEMENT_TYPE.GOOD],
lessWorkDays: ['Дальше без меня', 'меньше всего рабочих дней', ACHIEVEMENT_TYPE.BAD],
moreScopes: ['Стартапер', 'сделал больше всего фичей', ACHIEVEMENT_TYPE.GOOD], // нет картинки
lessScopes: ['Щегол', 'сделал меньше всего фичей', ACHIEVEMENT_TYPE.BAD],
moreDaysForTask: ['Улитка на склоне', 'работа по задачам идёт медленнее чем у остальных', ACHIEVEMENT_TYPE.BAD],
@ -31,4 +29,18 @@ export default {
lessDaysInProject: ['А это кто?', 'меньше всего дней на проекте', ACHIEVEMENT_TYPE.NORMAL],
more90DaysInProject: ['Добро пожаловать', 'не уволили на испытательном', ACHIEVEMENT_TYPE.GOOD],
lessDaysForTask: ['Скорострел', 'работа по задачам идёт быстрее чем у остальных', ACHIEVEMENT_TYPE.GOOD],
// нет картинки
longestMessage: ['А разговоров то было...', 'самая длинная подпись коммита за все время', ACHIEVEMENT_TYPE.NORMAL],
moreRefactoring: ['Главный редактор', 'сделал больше всех меток «рефакторинг»', ACHIEVEMENT_TYPE.GOOD],
adam: ['Адам', 'первый стабильны сотрудник на проекте', ACHIEVEMENT_TYPE.NORMAL],
more666DaysInProject: ['Чёрт', 'отработал 666 дней на проекте', ACHIEVEMENT_TYPE.GOOD],
more777DaysInProject: ['Флеш-рояль', 'отработал 777 дней на проекте', ACHIEVEMENT_TYPE.GOOD],
lessWorkDays: ['Дальше без меня', 'меньше всего рабочих дней', ACHIEVEMENT_TYPE.BAD],
moreTasksInDay: ['Шумахер', 'рекорд по количеству закрытых задач в день', ACHIEVEMENT_TYPE.GOOD], // нет картинки
moreCreateCode: ['Созидатель', 'склонен больше остальных добавлять код', ACHIEVEMENT_TYPE.NORMAL],
moreRemoveCode: ['Разрушитель', 'склонен больше остальных удалять код', ACHIEVEMENT_TYPE.NORMAL],
moreChangeCode: ['Реформатор', 'склонен больше остальных изменять код', ACHIEVEMENT_TYPE.NORMAL],
moreStyle: ['Полиция моды', 'склонен больше остальных изменять CSS', ACHIEVEMENT_TYPE.GOOD],
};

View file

@ -1,19 +1,22 @@
import React, { useEffect } from 'react';
import React, { useEffect, useState } from 'react';
import { Routes, Route } from 'react-router-dom';
import { observer } from 'mobx-react-lite';
import dataGripStore from 'ts/store/DataGrip';
import DropZone from 'ts/components/DropZone';
import SplashScreen from 'ts/components/SplashScreen';
import Confirm from 'ts/components/ModalWindow/Confirm';
import PageWrapper from '../../PageWrapper';
import Main from '../../Main/index';
// import Main from '../../Main/index';
import Team from '../../Team/index';
import Person from '../../Person/index';
import Welcome from '../../Welcome/index';
import Settings from '../../Settings/index';
const Success = observer((): React.ReactElement => {
const [showSplashScreen, setShowSplashScreen] = useState<boolean>(true);
useEffect(() => {
// @ts-ignore
dataGripStore.setCommits(window?.report || []);
@ -22,7 +25,12 @@ const Success = observer((): React.ReactElement => {
const dropArea = (
<DropZone
onChange={(type: string, data: any[]) => {
setShowSplashScreen(false);
if (type === 'dump') dataGripStore.setCommits(data);
if (type === 'telegramm') dataGripStore.setTelegrammMessages(data);
setTimeout(() => {
setShowSplashScreen(true);
});
}}
/>
);
@ -59,10 +67,13 @@ const Success = observer((): React.ReactElement => {
<Route
path="*"
element={(
<Main />
<PageWrapper>
<Team />
</PageWrapper>
)}
/>
</Routes>
{showSplashScreen && <SplashScreen />}
</>
) : (
<>

View file

@ -34,7 +34,6 @@ function Changes({ statistic }: IChangesProps) {
return (
<>
<Title title="Рекомендации и факты"/>
<RecommendationsWrapper recommendations={recommendations} />
<Title title="Количество изменённых строк по дням"/>
<PageWrapper template="box">

View file

@ -19,6 +19,7 @@ const TITLES = {
timestamp: 'Все коммиты',
week: 'Распределение коммитов по дням недели',
words: 'Популярные слова в комментарии к коммиту',
top: 'Рейтинг',
settings: 'Настройки',
},
person: {

View file

@ -96,6 +96,14 @@ function SideBarTeam({ page }: ISideBarProps) {
icon="./assets/menu/team_words.svg"
isSelected={page === 'words'}
/>
<SideBarMenuGap/>
<SideBarMenuItem
id="top"
link="/team/top"
title="sidebar.team.top"
icon="./assets/menu/team_words.svg"
isSelected={page === 'top'}
/>
</>
);
}

View file

@ -19,7 +19,7 @@ function SideBar() {
value={type || 'team'}
options={[
{ id: 'team', title: 'Команда', icon: './assets/switch/team.svg' },
{ id: 'person', title: 'Люди', icon: './assets/switch/person.svg' },
{ id: 'person', title: 'Сотрудник', icon: './assets/switch/person.svg' },
]}
onChange={(newType: string) => {
if (newType === type) return;

View file

@ -17,7 +17,7 @@
display: inline-block;
width: 50%;
max-width: 50%;
padding: 8px 20px;
padding: 8px 0;
margin: 0;
font-size: var(--font-s);

View file

@ -168,7 +168,7 @@ const Author = observer((): React.ReactElement => {
<PageWrapper>
<PageColumn>
<Description
text="*Часть статитики* (скорость работы, затраченные деньги и т.п.) *по сотрудникам с типом Помошник не считается*, т.к. это эпизодическая роль в проекте. Предпологаем, что они не влияют на проект, а их правками можно пренебречь на фоне общего объема работы."
text="*Часть статитики* (скорость работы, затраченные деньги и т.п.) *по сотрудникам с типом «Помошник» не считается*, т.к. это эпизодическая роль в проекте. Предпологаем, что они не влияют на проект, а их правками можно пренебречь на фоне общего объема работы."
/>
</PageColumn>
<PageColumn>

View file

@ -18,6 +18,7 @@ import { ColumnTypesEnum } from 'ts/components/Table/interfaces/Column';
import LineChart from 'ts/components/LineChart';
import getOptions from 'ts/components/LineChart/helpers/getOptions';
import RecommendationsWrapper from 'ts/components/Recommendations/wrapper';
import Description from 'ts/components/Description';
import { getMaxByLength } from 'ts/pages/Common/helpers/getMax';
@ -123,6 +124,11 @@ const Type = observer((): React.ReactElement => {
<Pagination />
</DataLoader>
</PageWrapper>
<PageWrapper>
<Description
text="*Персональный вклад* считается по количеству коммитов, а не объему измененных строк или файлов. Поэтому следует так же смотреть раздел «Анализ файлов», чтобы оценить масштаб изменений."
/>
</PageWrapper>
</>
);
});

View file

@ -13,6 +13,7 @@ import Tree from './components/Tree';
import Type from './components/Type';
import Week from './components/Week';
import Year from './components/Year';
import Top from './components/Top';
function Team() {
const { type, page } = useParams<any>();
@ -34,6 +35,7 @@ function Team() {
{page === 'tree' && <Tree/>}
{page === 'type' && <Type/>}
{page === 'sprint' && <Tempo/>}
{page === 'top' && <Top/>}
</>
);
}

View file

@ -6,6 +6,7 @@ import achievements from 'ts/helpers/achievement/byCompetition';
import dataGrip from 'ts/helpers/DataGrip';
import getFileTreeWithStatistic from 'ts/helpers/DataGrip/helpers/tree';
import Parser from 'ts/helpers/Parser';
import ParserTelegramm from 'ts/helpers/ParserTelegramm';
import { setDefaultValues } from 'ts/pages/Settings/helpers/getEmptySettings';
import settingsStore from './Settings';
@ -34,16 +35,21 @@ class DataGripStore implements IDataGripStore {
dataGrip: observable,
showApplication: observable,
setCommits: action,
setTelegrammMessages: action,
});
}
setCommits(dump?: string[]) {
setCommits(dump?: string[], type?: string) {
dataGrip.clear();
const parser = type === 'telegramm'
? ParserTelegramm
: Parser;
const {
commits,
fileList,
fileTree,
} = Parser(dump || [], (commit: ICommit) => dataGrip.addCommit(commit));
} = parser(dump || [], (commit: ICommit) => dataGrip.addCommit(commit));
this.commits = commits;
this.fileList = fileList;
@ -59,13 +65,20 @@ class DataGripStore implements IDataGripStore {
);
}
dataGrip.updateByInitialization();
achievements.updateByDataGrip(dataGrip.author.statistic);
this.dataGrip = null;
this.dataGrip = dataGrip;
console.dir(dataGrip);
}
updateChars() {
setTelegrammMessages(dump?: any[]) {
return this.setCommits(dump, 'telegramm');
}
updateChars() { // todo: remove, never use
console.log('s');
return;
dataGrip.updateByFilters();
if (!dataGrip.author.list.length) return;
achievements.updateByDataGrip(dataGrip.author.statistic);