Compare commits
33
Commits
planka-0.2.5
...
master
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
01535ecf51 | ||
|
|
1217969e22 | ||
|
|
e410e21363 | ||
|
|
a0f584e814 | ||
|
|
135f5eccb5 | ||
|
|
10001db8cf | ||
|
|
7ee351fe30 | ||
|
|
73746b83d1 | ||
|
|
f9a7b38ce9 | ||
|
|
1f261fe7b6 | ||
|
|
80bee30463 | ||
|
|
a9957481b6 | ||
|
|
36b05a5478 | ||
|
|
af91512abf | ||
|
|
8fd0f682d9 | ||
|
|
9699fbe76a | ||
|
|
4176a62f1a | ||
|
|
c12f0844d7 | ||
|
|
e6644eb745 | ||
|
|
b2e1fba9a0 | ||
|
|
818ae4a6df | ||
|
|
0de0e809ac | ||
|
|
da727c0a0b | ||
|
|
4841a65c77 | ||
|
|
0ec4b619d9 | ||
|
|
12f05adde7 | ||
|
|
c594e8bd71 | ||
|
|
f84166406f | ||
|
|
82b2ba298d | ||
|
|
38b6805ba1 | ||
|
|
6a7a582045 | ||
|
|
c53a00b4ba | ||
|
|
52103c775b |
@@ -1 +1,2 @@
|
||||
#!/bin/sh
|
||||
npx lint-staged
|
||||
|
||||
@@ -15,13 +15,13 @@ type: application
|
||||
# This is the chart version. This version number should be incremented each time you make changes
|
||||
# to the chart and its templates, including the app version.
|
||||
# Versions are expected to follow Semantic Versioning (https://semver.org/)
|
||||
version: 0.2.5
|
||||
version: 0.2.8
|
||||
|
||||
# This is the version number of the application being deployed. This version number should be
|
||||
# incremented each time you make changes to the application. Versions are not expected to
|
||||
# follow Semantic Versioning. They should reflect the version the application is using.
|
||||
# It is recommended to use it with quotes.
|
||||
appVersion: "1.20.1"
|
||||
appVersion: "1.22.0"
|
||||
|
||||
dependencies:
|
||||
- alias: postgresql
|
||||
|
||||
@@ -11,6 +11,10 @@ spec:
|
||||
selector:
|
||||
matchLabels:
|
||||
{{- include "planka.selectorLabels" . | nindent 6 }}
|
||||
{{- if .Values.persistence.enabled }}
|
||||
strategy:
|
||||
type: Recreate
|
||||
{{- end }}
|
||||
template:
|
||||
metadata:
|
||||
{{- with .Values.podAnnotations }}
|
||||
|
||||
@@ -1 +0,0 @@
|
||||
REACT_APP_VERSION=1.20.1
|
||||
Generated
+2055
-7110
File diff suppressed because it is too large
Load Diff
+12
-11
@@ -65,7 +65,7 @@
|
||||
"dequal": "^2.0.3",
|
||||
"easymde": "^2.18.0",
|
||||
"history": "^5.3.0",
|
||||
"i18next": "^23.12.2",
|
||||
"i18next": "^23.15.1",
|
||||
"i18next-browser-languagedetector": "^8.0.0",
|
||||
"initials": "^3.1.2",
|
||||
"js-cookie": "^3.0.5",
|
||||
@@ -77,18 +77,18 @@
|
||||
"node-sass": "^9.0.0",
|
||||
"photoswipe": "^5.4.4",
|
||||
"prop-types": "^15.8.1",
|
||||
"react": "^18.2.0",
|
||||
"react": "18.2.0",
|
||||
"react-app-rewired": "^2.2.1",
|
||||
"react-beautiful-dnd": "^13.1.1",
|
||||
"react-datepicker": "^4.25.0",
|
||||
"react-dom": "^18.2.0",
|
||||
"react-dom": "18.2.0",
|
||||
"react-dropzone": "^14.2.3",
|
||||
"react-i18next": "^15.0.0",
|
||||
"react-i18next": "^15.0.2",
|
||||
"react-input-mask": "^2.0.4",
|
||||
"react-markdown": "^8.0.7",
|
||||
"react-photoswipe-gallery": "^2.2.7",
|
||||
"react-redux": "^8.1.3",
|
||||
"react-router-dom": "^6.23.1",
|
||||
"react-router-dom": "^6.26.2",
|
||||
"react-scripts": "5.0.1",
|
||||
"react-simplemde-editor": "^5.2.0",
|
||||
"react-textarea-autosize": "^8.5.3",
|
||||
@@ -107,17 +107,18 @@
|
||||
"zxcvbn": "^4.4.2"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@testing-library/jest-dom": "^6.4.5",
|
||||
"@babel/plugin-proposal-private-property-in-object": "^7.21.11",
|
||||
"@testing-library/jest-dom": "^6.5.0",
|
||||
"@testing-library/react": "^15.0.7",
|
||||
"@testing-library/user-event": "^14.5.2",
|
||||
"babel-preset-airbnb": "^5.0.0",
|
||||
"chai": "^4.4.1",
|
||||
"chai": "^4.5.0",
|
||||
"eslint": "^8.57.0",
|
||||
"eslint-config-airbnb": "^19.0.4",
|
||||
"eslint-plugin-import": "^2.29.1",
|
||||
"eslint-plugin-jsx-a11y": "^6.8.0",
|
||||
"eslint-plugin-react": "^7.34.2",
|
||||
"eslint-plugin-import": "^2.30.0",
|
||||
"eslint-plugin-jsx-a11y": "^6.10.0",
|
||||
"eslint-plugin-react": "^7.36.1",
|
||||
"eslint-plugin-react-hooks": "^4.6.2",
|
||||
"react-test-renderer": "^18.2.0"
|
||||
"react-test-renderer": "18.2.0"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<link rel="icon" href="%PUBLIC_URL%/favicon.ico" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1, user-scalable=no" />
|
||||
<meta name="theme-color" content="#000000" />
|
||||
<meta
|
||||
name="description"
|
||||
|
||||
@@ -1,15 +1,14 @@
|
||||
import http from './http';
|
||||
import socket from './socket';
|
||||
|
||||
/* Actions */
|
||||
|
||||
const createAccessToken = (data, headers) => http.post('/access-tokens', data, headers);
|
||||
const createAccessToken = (data, headers) =>
|
||||
http.post('/access-tokens?withHttpOnlyToken=true', data, headers);
|
||||
|
||||
const exchangeForAccessTokenUsingOidc = (data, headers) =>
|
||||
http.post('/access-tokens/exchange-using-oidc', data, headers);
|
||||
http.post('/access-tokens/exchange-using-oidc?withHttpOnlyToken=true', data, headers);
|
||||
|
||||
const deleteCurrentAccessToken = (headers) =>
|
||||
socket.delete('/access-tokens/me', undefined, headers);
|
||||
const deleteCurrentAccessToken = (headers) => http.delete('/access-tokens/me', undefined, headers);
|
||||
|
||||
export default {
|
||||
createAccessToken,
|
||||
|
||||
@@ -5,7 +5,7 @@ import Config from '../constants/Config';
|
||||
const http = {};
|
||||
|
||||
// TODO: add all methods
|
||||
['GET', 'POST'].forEach((method) => {
|
||||
['GET', 'POST', 'DELETE'].forEach((method) => {
|
||||
http[method.toLowerCase()] = (url, data, headers) => {
|
||||
const formData =
|
||||
data &&
|
||||
@@ -19,6 +19,7 @@ const http = {};
|
||||
method,
|
||||
headers,
|
||||
body: formData,
|
||||
credentials: 'include',
|
||||
})
|
||||
.then((response) =>
|
||||
response.json().then((body) => ({
|
||||
|
||||
Binary file not shown.
|
Before Width: | Height: | Size: 559 KiB After Width: | Height: | Size: 184 KiB |
@@ -1,6 +1,8 @@
|
||||
:global(#app) {
|
||||
.wrapper {
|
||||
height: 100%;
|
||||
max-height: 100vh;
|
||||
max-width: 100vw;
|
||||
position: fixed;
|
||||
width: 100%;
|
||||
z-index: -1;
|
||||
|
||||
@@ -48,16 +48,6 @@
|
||||
min-width: 100%;
|
||||
}
|
||||
|
||||
.panel {
|
||||
align-items: center;
|
||||
display: flex;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.panelItem {
|
||||
margin-right: 20px;
|
||||
}
|
||||
|
||||
.wrapper {
|
||||
margin: 0 20px;
|
||||
}
|
||||
|
||||
@@ -3,12 +3,13 @@
|
||||
align-items: center;
|
||||
display: flex;
|
||||
flex: 0 0 auto;
|
||||
margin-right: 20px;
|
||||
}
|
||||
|
||||
.actions {
|
||||
align-items: center;
|
||||
display: flex;
|
||||
gap: 20px;
|
||||
justify-content: flex-start;
|
||||
margin: 20px 20px;
|
||||
}
|
||||
|
||||
|
||||
@@ -50,6 +50,10 @@
|
||||
transition: width 0.2s ease;
|
||||
width: 280px;
|
||||
|
||||
@media only screen and (max-width: 797px) {
|
||||
width: 220px;
|
||||
}
|
||||
|
||||
input {
|
||||
font-size: 13px;
|
||||
}
|
||||
|
||||
@@ -24,6 +24,7 @@ const Card = React.memo(
|
||||
index,
|
||||
name,
|
||||
dueDate,
|
||||
isDueDateCompleted,
|
||||
stopwatch,
|
||||
coverUrl,
|
||||
boardId,
|
||||
@@ -120,7 +121,7 @@ const Card = React.memo(
|
||||
)}
|
||||
{dueDate && (
|
||||
<span className={classNames(styles.attachment, styles.attachmentLeft)}>
|
||||
<DueDate value={dueDate} size="tiny" />
|
||||
<DueDate value={dueDate} isCompleted={isDueDateCompleted} size="tiny" />
|
||||
</span>
|
||||
)}
|
||||
{stopwatch && (
|
||||
@@ -221,6 +222,7 @@ Card.propTypes = {
|
||||
index: PropTypes.number.isRequired,
|
||||
name: PropTypes.string.isRequired,
|
||||
dueDate: PropTypes.instanceOf(Date),
|
||||
isDueDateCompleted: PropTypes.bool,
|
||||
stopwatch: PropTypes.object, // eslint-disable-line react/forbid-prop-types
|
||||
coverUrl: PropTypes.string,
|
||||
boardId: PropTypes.string.isRequired,
|
||||
@@ -255,6 +257,7 @@ Card.propTypes = {
|
||||
|
||||
Card.defaultProps = {
|
||||
dueDate: undefined,
|
||||
isDueDateCompleted: undefined,
|
||||
stopwatch: undefined,
|
||||
coverUrl: undefined,
|
||||
};
|
||||
|
||||
@@ -21,6 +21,14 @@
|
||||
background: #ebeef0;
|
||||
color: #516b7a;
|
||||
}
|
||||
|
||||
@media only screen and (max-width: 797px) {
|
||||
&:focus,
|
||||
&:active {
|
||||
background: #ebeef0;
|
||||
color: #516b7a;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.attachment {
|
||||
@@ -55,6 +63,12 @@
|
||||
box-shadow: 0 1px 0 #ccc;
|
||||
position: relative;
|
||||
|
||||
@media only screen and (max-width: 797px) {
|
||||
.target {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
|
||||
&:hover {
|
||||
background: #f5f6f7;
|
||||
border-bottom-color: rgba(9, 30, 66, 0.25);
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
.dropzone {
|
||||
background: white;
|
||||
font-size: 20px;
|
||||
font-weight: 700;
|
||||
font-weight: bold;
|
||||
height: 100%;
|
||||
line-height: 30px;
|
||||
opacity: 0.7;
|
||||
|
||||
@@ -16,7 +16,7 @@
|
||||
.contentError {
|
||||
color: #fff;
|
||||
font-size: 20px;
|
||||
font-weight: 700;
|
||||
font-weight: bold;
|
||||
height: 20px;
|
||||
width: 470px;
|
||||
}
|
||||
|
||||
@@ -35,7 +35,7 @@
|
||||
color: #5e6c84;
|
||||
display: block;
|
||||
font-size: 18px;
|
||||
font-weight: 700;
|
||||
font-weight: bold;
|
||||
height: 100%;
|
||||
line-height: 80px;
|
||||
overflow: hidden;
|
||||
@@ -50,7 +50,7 @@
|
||||
.name {
|
||||
color: #17394d;
|
||||
font-size: 14px;
|
||||
font-weight: 700;
|
||||
font-weight: bold;
|
||||
line-height: 20px;
|
||||
word-wrap: break-word;
|
||||
}
|
||||
|
||||
@@ -2,7 +2,7 @@ import React, { useCallback, useRef, useState } from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import classNames from 'classnames';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { Button, Grid, Icon, Modal } from 'semantic-ui-react';
|
||||
import { Button, Checkbox, Grid, Icon, Modal } from 'semantic-ui-react';
|
||||
import { usePopup } from '../../lib/popup';
|
||||
import { Markdown } from '../../lib/custom-ui';
|
||||
|
||||
@@ -32,6 +32,7 @@ const CardModal = React.memo(
|
||||
name,
|
||||
description,
|
||||
dueDate,
|
||||
isDueDateCompleted,
|
||||
stopwatch,
|
||||
isSubscribed,
|
||||
isActivitiesFetching,
|
||||
@@ -118,6 +119,12 @@ const CardModal = React.memo(
|
||||
[onUpdate],
|
||||
);
|
||||
|
||||
const handleDueDateCompletionChange = useCallback(() => {
|
||||
onUpdate({
|
||||
isDueDateCompleted: !isDueDateCompleted,
|
||||
});
|
||||
}, [isDueDateCompleted, onUpdate]);
|
||||
|
||||
const handleStopwatchUpdate = useCallback(
|
||||
(newStopwatch) => {
|
||||
onUpdate({
|
||||
@@ -300,13 +307,24 @@ const CardModal = React.memo(
|
||||
context: 'title',
|
||||
})}
|
||||
</div>
|
||||
<span className={styles.attachment}>
|
||||
<span className={classNames(styles.attachment, styles.attachmentDueDate)}>
|
||||
{canEdit ? (
|
||||
<DueDateEditPopup defaultValue={dueDate} onUpdate={handleDueDateUpdate}>
|
||||
<DueDate value={dueDate} />
|
||||
</DueDateEditPopup>
|
||||
<>
|
||||
<Checkbox
|
||||
checked={isDueDateCompleted}
|
||||
disabled={!canEdit}
|
||||
onChange={handleDueDateCompletionChange}
|
||||
/>
|
||||
<DueDateEditPopup defaultValue={dueDate} onUpdate={handleDueDateUpdate}>
|
||||
<DueDate
|
||||
withStatusIcon
|
||||
value={dueDate}
|
||||
isCompleted={isDueDateCompleted}
|
||||
/>
|
||||
</DueDateEditPopup>
|
||||
</>
|
||||
) : (
|
||||
<DueDate value={dueDate} />
|
||||
<DueDate withStatusIcon value={dueDate} isCompleted={isDueDateCompleted} />
|
||||
)}
|
||||
</span>
|
||||
</div>
|
||||
@@ -515,14 +533,19 @@ const CardModal = React.memo(
|
||||
<Icon name="copy outline" className={styles.actionIcon} />
|
||||
{t('action.duplicate')}
|
||||
</Button>
|
||||
<Button fluid className={styles.actionButton} onClick={handleCopyLinkClick}>
|
||||
<Icon name={isLinkCopied ? 'linkify' : 'unlink'} className={styles.actionIcon} />
|
||||
{isLinkCopied
|
||||
? t('common.linkIsCopied')
|
||||
: t('action.copyLink', {
|
||||
context: 'title',
|
||||
})}
|
||||
</Button>
|
||||
{window.isSecureContext && (
|
||||
<Button fluid className={styles.actionButton} onClick={handleCopyLinkClick}>
|
||||
<Icon
|
||||
name={isLinkCopied ? 'linkify' : 'unlink'}
|
||||
className={styles.actionIcon}
|
||||
/>
|
||||
{isLinkCopied
|
||||
? t('common.linkIsCopied')
|
||||
: t('action.copyLink', {
|
||||
context: 'title',
|
||||
})}
|
||||
</Button>
|
||||
)}
|
||||
<DeletePopup
|
||||
title="common.deleteCard"
|
||||
content="common.areYouSureYouWantToDeleteThisCard"
|
||||
@@ -557,6 +580,7 @@ CardModal.propTypes = {
|
||||
name: PropTypes.string.isRequired,
|
||||
description: PropTypes.string,
|
||||
dueDate: PropTypes.instanceOf(Date),
|
||||
isDueDateCompleted: PropTypes.bool,
|
||||
stopwatch: PropTypes.object, // eslint-disable-line react/forbid-prop-types
|
||||
isSubscribed: PropTypes.bool.isRequired,
|
||||
isActivitiesFetching: PropTypes.bool.isRequired,
|
||||
@@ -611,6 +635,7 @@ CardModal.propTypes = {
|
||||
CardModal.defaultProps = {
|
||||
description: undefined,
|
||||
dueDate: undefined,
|
||||
isDueDateCompleted: false,
|
||||
stopwatch: undefined,
|
||||
};
|
||||
|
||||
|
||||
@@ -25,12 +25,21 @@
|
||||
|
||||
.actions {
|
||||
margin-bottom: 24px;
|
||||
|
||||
@media only screen and (max-width: 797px) {
|
||||
flex: 1;
|
||||
}
|
||||
|
||||
@media only screen and (max-width: 425px) {
|
||||
padding: 0;
|
||||
width: 100%;
|
||||
}
|
||||
}
|
||||
|
||||
.actionsTitle {
|
||||
color: #8c8c8c;
|
||||
font-size: 12px;
|
||||
font-weight: 500;
|
||||
font-weight: normal;
|
||||
letter-spacing: 0.04em;
|
||||
margin-top: 16px;
|
||||
text-transform: uppercase;
|
||||
@@ -49,6 +58,12 @@
|
||||
max-width: 100%;
|
||||
}
|
||||
|
||||
.attachmentDueDate {
|
||||
align-items: center;
|
||||
display: flex;
|
||||
gap: 4px;
|
||||
}
|
||||
|
||||
.attachments {
|
||||
display: inline-block;
|
||||
margin: 0 8px 8px 0;
|
||||
@@ -62,6 +77,11 @@
|
||||
|
||||
.contentPadding {
|
||||
padding: 8px 8px 0 16px;
|
||||
|
||||
@media only screen and (max-width: 797px) {
|
||||
padding-right: 16px;
|
||||
width: 100% !important;
|
||||
}
|
||||
}
|
||||
|
||||
.cursorPointer {
|
||||
@@ -138,7 +158,7 @@
|
||||
.headerTitle {
|
||||
color: #17394d;
|
||||
font-size: 20px;
|
||||
font-weight: 700;
|
||||
font-weight: bold;
|
||||
line-height: 24px;
|
||||
}
|
||||
|
||||
@@ -154,6 +174,11 @@
|
||||
|
||||
.modalPadding {
|
||||
padding: 0px;
|
||||
|
||||
@media only screen and (max-width: 797px) {
|
||||
display: flex;
|
||||
flex-flow: column nowrap;
|
||||
}
|
||||
}
|
||||
|
||||
.moduleHeader {
|
||||
@@ -184,6 +209,15 @@
|
||||
|
||||
.sidebarPadding {
|
||||
padding: 8px 16px 0 8px;
|
||||
|
||||
@media only screen and (max-width: 797px) {
|
||||
align-items: flex-start;
|
||||
display: flex;
|
||||
flex-flow: row wrap;
|
||||
gap: 10px;
|
||||
padding-left: 16px;
|
||||
width: 100% !important;
|
||||
}
|
||||
}
|
||||
|
||||
.text {
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
box-shadow: none;
|
||||
color: #17394d;
|
||||
font-size: 20px;
|
||||
font-weight: 700;
|
||||
font-weight: bold;
|
||||
line-height: 24px;
|
||||
margin: -5px;
|
||||
overflow: hidden;
|
||||
|
||||
@@ -4,6 +4,7 @@
|
||||
border-radius: 4px;
|
||||
bottom: 20px;
|
||||
box-shadow: #b04632 0 1px 0;
|
||||
max-width: calc(100% - 40px);
|
||||
padding: 12px 18px;
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
|
||||
@@ -1,8 +1,10 @@
|
||||
import upperFirst from 'lodash/upperFirst';
|
||||
import React from 'react';
|
||||
import React, { useEffect, useRef } from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import classNames from 'classnames';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { Icon } from 'semantic-ui-react';
|
||||
import { useForceUpdate } from '../../lib/hooks';
|
||||
|
||||
import getDateFormat from '../../utils/get-date-format';
|
||||
|
||||
@@ -14,6 +16,12 @@ const SIZES = {
|
||||
MEDIUM: 'medium',
|
||||
};
|
||||
|
||||
const STATUSES = {
|
||||
DUE_SOON: 'dueSoon',
|
||||
OVERDUE: 'overdue',
|
||||
COMPLETED: 'completed',
|
||||
};
|
||||
|
||||
const LONG_DATE_FORMAT_BY_SIZE = {
|
||||
tiny: 'longDate',
|
||||
small: 'longDate',
|
||||
@@ -26,8 +34,47 @@ const FULL_DATE_FORMAT_BY_SIZE = {
|
||||
medium: 'fullDateTime',
|
||||
};
|
||||
|
||||
const DueDate = React.memo(({ value, size, isDisabled, onClick }) => {
|
||||
const STATUS_ICON_PROPS_BY_STATUS = {
|
||||
[STATUSES.DUE_SOON]: {
|
||||
name: 'hourglass half',
|
||||
color: 'orange',
|
||||
},
|
||||
[STATUSES.OVERDUE]: {
|
||||
name: 'hourglass end',
|
||||
color: 'red',
|
||||
},
|
||||
[STATUSES.COMPLETED]: {
|
||||
name: 'checkmark',
|
||||
color: 'green',
|
||||
},
|
||||
};
|
||||
|
||||
const getStatus = (dateTime, isCompleted) => {
|
||||
if (isCompleted) {
|
||||
return STATUSES.COMPLETED;
|
||||
}
|
||||
|
||||
const secondsLeft = Math.floor((dateTime.getTime() - new Date().getTime()) / 1000);
|
||||
|
||||
if (secondsLeft <= 0) {
|
||||
return STATUSES.OVERDUE;
|
||||
}
|
||||
|
||||
if (secondsLeft <= 24 * 60 * 60) {
|
||||
return STATUSES.DUE_SOON;
|
||||
}
|
||||
|
||||
return null;
|
||||
};
|
||||
|
||||
const DueDate = React.memo(({ value, size, isCompleted, isDisabled, withStatusIcon, onClick }) => {
|
||||
const [t] = useTranslation();
|
||||
const forceUpdate = useForceUpdate();
|
||||
|
||||
const statusRef = useRef(null);
|
||||
statusRef.current = getStatus(value, isCompleted);
|
||||
|
||||
const intervalRef = useRef(null);
|
||||
|
||||
const dateFormat = getDateFormat(
|
||||
value,
|
||||
@@ -35,11 +82,34 @@ const DueDate = React.memo(({ value, size, isDisabled, onClick }) => {
|
||||
FULL_DATE_FORMAT_BY_SIZE[size],
|
||||
);
|
||||
|
||||
useEffect(() => {
|
||||
if ([null, STATUSES.DUE_SOON].includes(statusRef.current)) {
|
||||
intervalRef.current = setInterval(() => {
|
||||
const status = getStatus(value, isCompleted);
|
||||
|
||||
if (status !== statusRef.current) {
|
||||
forceUpdate();
|
||||
}
|
||||
|
||||
if (status === STATUSES.OVERDUE) {
|
||||
clearInterval(intervalRef.current);
|
||||
}
|
||||
}, 1000);
|
||||
}
|
||||
|
||||
return () => {
|
||||
if (intervalRef.current) {
|
||||
clearInterval(intervalRef.current);
|
||||
}
|
||||
};
|
||||
}, [value, isCompleted, forceUpdate]);
|
||||
|
||||
const contentNode = (
|
||||
<span
|
||||
className={classNames(
|
||||
styles.wrapper,
|
||||
styles[`wrapper${upperFirst(size)}`],
|
||||
!withStatusIcon && statusRef.current && styles[`wrapper${upperFirst(statusRef.current)}`],
|
||||
onClick && styles.wrapperHoverable,
|
||||
)}
|
||||
>
|
||||
@@ -47,6 +117,10 @@ const DueDate = React.memo(({ value, size, isDisabled, onClick }) => {
|
||||
value,
|
||||
postProcess: 'formatDate',
|
||||
})}
|
||||
{withStatusIcon && statusRef.current && (
|
||||
// eslint-disable-next-line react/jsx-props-no-spreading
|
||||
<Icon {...STATUS_ICON_PROPS_BY_STATUS[statusRef.current]} className={styles.statusIcon} />
|
||||
)}
|
||||
</span>
|
||||
);
|
||||
|
||||
@@ -62,14 +136,19 @@ const DueDate = React.memo(({ value, size, isDisabled, onClick }) => {
|
||||
DueDate.propTypes = {
|
||||
value: PropTypes.instanceOf(Date).isRequired,
|
||||
size: PropTypes.oneOf(Object.values(SIZES)),
|
||||
isCompleted: PropTypes.bool.isRequired,
|
||||
isDisabled: PropTypes.bool,
|
||||
withStatusIcon: PropTypes.bool,
|
||||
onClick: PropTypes.func,
|
||||
onCompletionToggle: PropTypes.func,
|
||||
};
|
||||
|
||||
DueDate.defaultProps = {
|
||||
size: SIZES.MEDIUM,
|
||||
isDisabled: false,
|
||||
withStatusIcon: false,
|
||||
onClick: undefined,
|
||||
onCompletionToggle: undefined,
|
||||
};
|
||||
|
||||
export default DueDate;
|
||||
|
||||
@@ -8,16 +8,17 @@
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
.statusIcon {
|
||||
line-height: 1;
|
||||
margin: 0 0 0 8px;
|
||||
}
|
||||
|
||||
.wrapper {
|
||||
background: #dce0e4;
|
||||
border: none;
|
||||
border-radius: 3px;
|
||||
color: #6a808b;
|
||||
display: inline-block;
|
||||
outline: none;
|
||||
text-align: left;
|
||||
transition: background 0.3s ease;
|
||||
vertical-align: top;
|
||||
}
|
||||
|
||||
.wrapperHoverable:hover {
|
||||
@@ -43,4 +44,21 @@
|
||||
line-height: 20px;
|
||||
padding: 6px 12px;
|
||||
}
|
||||
|
||||
/* Statuses */
|
||||
|
||||
.wrapperDueSoon {
|
||||
background: #f2711c;
|
||||
color: #fff;
|
||||
}
|
||||
|
||||
.wrapperOverdue {
|
||||
background: #db2828;
|
||||
color: #fff;
|
||||
}
|
||||
|
||||
.wrapperCompleted {
|
||||
background: #21ba45;
|
||||
color: #fff;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
:global(#app) {
|
||||
.wrapper {
|
||||
max-width: 100vw;
|
||||
position: fixed;
|
||||
width: 100%;
|
||||
z-index: 1;
|
||||
|
||||
@@ -87,7 +87,12 @@
|
||||
}
|
||||
|
||||
.userName {
|
||||
display: none;
|
||||
margin-right: 10px;
|
||||
|
||||
@media only screen and (min-width: 797px) {
|
||||
display: block;
|
||||
}
|
||||
}
|
||||
|
||||
.wrapper {
|
||||
|
||||
@@ -17,7 +17,7 @@ const SIZES = {
|
||||
|
||||
const Label = React.memo(({ name, color, size, isDisabled, onClick }) => {
|
||||
const contentNode = (
|
||||
<div
|
||||
<span
|
||||
title={name}
|
||||
className={classNames(
|
||||
styles.wrapper,
|
||||
@@ -28,7 +28,7 @@ const Label = React.memo(({ name, color, size, isDisabled, onClick }) => {
|
||||
)}
|
||||
>
|
||||
{name || '\u00A0'}
|
||||
</div>
|
||||
</span>
|
||||
);
|
||||
|
||||
return onClick ? (
|
||||
|
||||
@@ -11,17 +11,17 @@
|
||||
|
||||
.wrapper {
|
||||
border-radius: 3px;
|
||||
box-sizing: border-box;
|
||||
color: #fff;
|
||||
font-weight: 400;
|
||||
outline: none;
|
||||
display: inline-block;
|
||||
font-weight: normal;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
text-shadow: 1px 1px 0 rgba(0, 0, 0, 0.2);
|
||||
vertical-align: top;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
.wrapperNameless{
|
||||
.wrapperNameless {
|
||||
width: 40px;
|
||||
}
|
||||
|
||||
|
||||
@@ -80,6 +80,12 @@
|
||||
&:hover .target {
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
@media only screen and (max-width: 797px) {
|
||||
.target {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.headerEditable {
|
||||
@@ -103,6 +109,15 @@
|
||||
background: rgba(9, 30, 66, 0.13);
|
||||
color: #516b7a;
|
||||
}
|
||||
|
||||
@media only screen and (max-width: 797px) {
|
||||
|
||||
&:focus,
|
||||
&:active {
|
||||
background: rgba(9, 30, 66, 0.13);
|
||||
color: #516b7a;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.headerName {
|
||||
|
||||
@@ -18,6 +18,11 @@ const createMessage = (error) => {
|
||||
}
|
||||
|
||||
switch (error.message) {
|
||||
case 'Invalid credentials':
|
||||
return {
|
||||
type: 'error',
|
||||
content: 'common.invalidCredentials',
|
||||
};
|
||||
case 'Invalid email or username':
|
||||
return {
|
||||
type: 'error',
|
||||
@@ -116,6 +121,7 @@ const Login = React.memo(
|
||||
useEffect(() => {
|
||||
if (wasSubmitting && !isSubmitting && error) {
|
||||
switch (error.message) {
|
||||
case 'Invalid credentials':
|
||||
case 'Invalid email or username':
|
||||
emailOrUsernameField.current.select();
|
||||
|
||||
|
||||
@@ -11,6 +11,10 @@
|
||||
vertical-align: top;
|
||||
width: 36px;
|
||||
|
||||
@media only screen and (max-width: 797px) {
|
||||
margin-left: 10px;
|
||||
}
|
||||
|
||||
&:hover {
|
||||
background: rgba(0, 0, 0, 0.32);
|
||||
}
|
||||
|
||||
@@ -10,13 +10,10 @@
|
||||
|
||||
.wrapper {
|
||||
background: #dce0e4;
|
||||
border: none;
|
||||
border-radius: 3px;
|
||||
color: #6a808b;
|
||||
display: inline-block;
|
||||
font-variant-numeric: tabular-nums;
|
||||
outline: none;
|
||||
text-align: left;
|
||||
transition: background 0.3s ease;
|
||||
vertical-align: top;
|
||||
}
|
||||
|
||||
@@ -14,12 +14,10 @@
|
||||
}
|
||||
|
||||
.wrapper {
|
||||
border: none;
|
||||
border-radius: 50%;
|
||||
color: #fff;
|
||||
display: inline-block;
|
||||
line-height: 1;
|
||||
outline: none;
|
||||
text-align: center;
|
||||
vertical-align: top;
|
||||
}
|
||||
@@ -32,7 +30,6 @@
|
||||
|
||||
.wrapperTiny {
|
||||
font-size: 10px;
|
||||
font-weight: 400;
|
||||
height: 24px;
|
||||
line-height: 20px;
|
||||
padding: 2px 0;
|
||||
@@ -41,7 +38,6 @@
|
||||
|
||||
.wrapperSmall {
|
||||
font-size: 12px;
|
||||
font-weight: 400;
|
||||
height: 28px;
|
||||
padding: 8px 0;
|
||||
width: 28px;
|
||||
@@ -49,7 +45,6 @@
|
||||
|
||||
.wrapperMedium {
|
||||
font-size: 14px;
|
||||
font-weight: 500;
|
||||
height: 32px;
|
||||
padding: 10px 0;
|
||||
width: 32px;
|
||||
@@ -57,7 +52,6 @@
|
||||
|
||||
.wrapperLarge {
|
||||
font-size: 14px;
|
||||
font-weight: 500;
|
||||
height: 36px;
|
||||
padding: 12px 0 10px;
|
||||
width: 36px;
|
||||
@@ -65,7 +59,6 @@
|
||||
|
||||
.wrapperMassive {
|
||||
font-size: 36px;
|
||||
font-weight: 500;
|
||||
height: 100px;
|
||||
padding: 32px 0 10px;
|
||||
width: 100px;
|
||||
|
||||
@@ -2,7 +2,7 @@ import React from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { Image, Tab } from 'semantic-ui-react';
|
||||
|
||||
import Config from '../../constants/Config';
|
||||
import version from '../../version';
|
||||
|
||||
import logo from '../../assets/images/logo.png';
|
||||
|
||||
@@ -15,7 +15,7 @@ const AboutPane = React.memo(() => {
|
||||
<Tab.Pane attached={false} className={styles.wrapper}>
|
||||
<Image centered src={logo} size="large" />
|
||||
<div className={styles.version}>
|
||||
{t('common.version')} {Config.VERSION}
|
||||
{t('common.version')} {version}
|
||||
</div>
|
||||
</Tab.Pane>
|
||||
);
|
||||
|
||||
@@ -1,13 +1,12 @@
|
||||
const VERSION = process.env.REACT_APP_VERSION;
|
||||
|
||||
const { BASE_URL } = window;
|
||||
|
||||
const BASE_PATH = BASE_URL.replace(/^.*\/\/[^/]*(.*)[^?#]*.*$/, '$1');
|
||||
|
||||
const SERVER_BASE_URL =
|
||||
process.env.REACT_APP_SERVER_BASE_URL ||
|
||||
(process.env.NODE_ENV === 'production' ? BASE_URL : 'http://localhost:1337');
|
||||
const SERVER_BASE_PATH = SERVER_BASE_URL.replace(/^.*\/\/[^/]*(.*)[^?#]*.*$/, '$1');
|
||||
|
||||
const SERVER_BASE_PATH = SERVER_BASE_URL.replace(/^.*\/\/[^/]*(.*)[^?#]*.*$/, '$1');
|
||||
const SERVER_HOST_NAME = SERVER_BASE_URL.replace(/^(.*\/\/[^/?#]*).*$/, '$1');
|
||||
|
||||
const ACCESS_TOKEN_KEY = 'accessToken';
|
||||
@@ -18,7 +17,6 @@ const POSITION_GAP = 65535;
|
||||
const ACTIVITIES_LIMIT = 50;
|
||||
|
||||
export default {
|
||||
VERSION,
|
||||
BASE_PATH,
|
||||
SERVER_BASE_URL,
|
||||
SERVER_BASE_PATH,
|
||||
|
||||
@@ -20,10 +20,8 @@ const makeMapStateToProps = () => {
|
||||
const allLabels = selectors.selectLabelsForCurrentBoard(state);
|
||||
const currentUserMembership = selectors.selectCurrentUserMembershipForCurrentBoard(state);
|
||||
|
||||
const { name, dueDate, stopwatch, coverUrl, boardId, listId, isPersisted } = selectCardById(
|
||||
state,
|
||||
id,
|
||||
);
|
||||
const { name, dueDate, isDueDateCompleted, stopwatch, coverUrl, boardId, listId, isPersisted } =
|
||||
selectCardById(state, id);
|
||||
|
||||
const users = selectUsersByCardId(state, id);
|
||||
const labels = selectLabelsByCardId(state, id);
|
||||
@@ -38,6 +36,7 @@ const makeMapStateToProps = () => {
|
||||
index,
|
||||
name,
|
||||
dueDate,
|
||||
isDueDateCompleted,
|
||||
stopwatch,
|
||||
coverUrl,
|
||||
boardId,
|
||||
|
||||
@@ -21,6 +21,7 @@ const mapStateToProps = (state) => {
|
||||
name,
|
||||
description,
|
||||
dueDate,
|
||||
isDueDateCompleted,
|
||||
stopwatch,
|
||||
isSubscribed,
|
||||
isActivitiesFetching,
|
||||
@@ -49,6 +50,7 @@ const mapStateToProps = (state) => {
|
||||
name,
|
||||
description,
|
||||
dueDate,
|
||||
isDueDateCompleted,
|
||||
stopwatch,
|
||||
isSubscribed,
|
||||
isActivitiesFetching,
|
||||
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -64,7 +64,7 @@
|
||||
|
||||
.markdown-body b,
|
||||
.markdown-body strong {
|
||||
font-weight: 600;
|
||||
font-weight: bold; // 600
|
||||
}
|
||||
|
||||
.markdown-body dfn {
|
||||
@@ -73,7 +73,7 @@
|
||||
|
||||
.markdown-body h1 {
|
||||
margin: .67em 0;
|
||||
font-weight: 600;
|
||||
font-weight: bold; // 600
|
||||
padding-bottom: .3em;
|
||||
font-size: 2em;
|
||||
border-bottom: 1px solid hsla(210, 18%, 87%, 1);
|
||||
@@ -253,34 +253,34 @@
|
||||
.markdown-body h6 {
|
||||
margin-top: 24px;
|
||||
margin-bottom: 16px;
|
||||
font-weight: 600;
|
||||
font-weight: bold; // 600
|
||||
line-height: 1.25;
|
||||
}
|
||||
|
||||
.markdown-body h2 {
|
||||
font-weight: 600;
|
||||
font-weight: bold; // 600
|
||||
padding-bottom: .3em;
|
||||
font-size: 1.5em;
|
||||
border-bottom: 1px solid hsla(210, 18%, 87%, 1);
|
||||
}
|
||||
|
||||
.markdown-body h3 {
|
||||
font-weight: 600;
|
||||
font-weight: bold; // 600
|
||||
font-size: 1.25em;
|
||||
}
|
||||
|
||||
.markdown-body h4 {
|
||||
font-weight: 600;
|
||||
font-weight: bold; // 600
|
||||
font-size: 1em;
|
||||
}
|
||||
|
||||
.markdown-body h5 {
|
||||
font-weight: 600;
|
||||
font-weight: bold; // 600
|
||||
font-size: .875em;
|
||||
}
|
||||
|
||||
.markdown-body h6 {
|
||||
font-weight: 600;
|
||||
font-weight: bold; // 600
|
||||
font-size: .85em;
|
||||
color: #57606a;
|
||||
}
|
||||
@@ -481,7 +481,7 @@
|
||||
font-family: "Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol";
|
||||
font-size: 1em;
|
||||
font-style: normal !important;
|
||||
font-weight: 400;
|
||||
font-weight: normal; // 400
|
||||
line-height: 1;
|
||||
vertical-align: -0.075em;
|
||||
}
|
||||
@@ -650,7 +650,7 @@
|
||||
margin-top: 16px;
|
||||
font-size: 1em;
|
||||
font-style: italic;
|
||||
font-weight: 600;
|
||||
font-weight: bold; // 600
|
||||
}
|
||||
|
||||
.markdown-body dl dd {
|
||||
@@ -659,7 +659,7 @@
|
||||
}
|
||||
|
||||
.markdown-body table th {
|
||||
font-weight: 600;
|
||||
font-weight: bold; // 600
|
||||
}
|
||||
|
||||
.markdown-body table th,
|
||||
@@ -868,7 +868,7 @@
|
||||
}
|
||||
|
||||
.markdown-body .csv-data th {
|
||||
font-weight: 600;
|
||||
font-weight: bold; // 600
|
||||
background: #f6f8fa;
|
||||
border-top: 0;
|
||||
}
|
||||
@@ -912,7 +912,7 @@
|
||||
}
|
||||
|
||||
.markdown-body .task-list-item label {
|
||||
font-weight: 400;
|
||||
font-weight: normal;
|
||||
}
|
||||
|
||||
.markdown-body .task-list-item.enabled label {
|
||||
|
||||
Vendored
+2568
-2729
File diff suppressed because one or more lines are too long
@@ -0,0 +1,252 @@
|
||||
import dateFns from 'date-fns/locale/ar';
|
||||
|
||||
export default {
|
||||
dateFns,
|
||||
|
||||
format: {
|
||||
date: 'M/d/yyyy',
|
||||
time: 'p',
|
||||
dateTime: '$t(format:date) $t(format:time)',
|
||||
longDate: 'MMM d',
|
||||
longDateTime: "MMMM d 'at' p",
|
||||
fullDate: 'MMM d, y',
|
||||
fullDateTime: "MMMM d, y 'at' p",
|
||||
},
|
||||
|
||||
translation: {
|
||||
common: {
|
||||
aboutPlanka: 'حول Planka',
|
||||
account: 'الحساب',
|
||||
actions: 'إجراءات',
|
||||
addAttachment_title: 'إضافة مرفق',
|
||||
addComment: 'إضافة تعليق',
|
||||
addManager_title: 'إضافة مدير',
|
||||
addMember_title: 'إضافة عضو',
|
||||
addUser_title: 'إضافة مستخدم',
|
||||
administrator: 'المدير',
|
||||
all: 'الكل',
|
||||
allChangesWillBeAutomaticallySavedAfterConnectionRestored:
|
||||
'سيتم حفظ جميع التغييرات تلقائياً<br />بعد استعادة الإتصال.',
|
||||
areYouSureYouWantToDeleteThisAttachment: 'هل أنت متأكد أنك تريد حذف هذا المرفق؟',
|
||||
areYouSureYouWantToDeleteThisBoard: 'هل أنت متأكد أنك تريد حذف هذه اللوحة؟',
|
||||
areYouSureYouWantToDeleteThisCard: 'هل أنت متأكد أنك تريد حذف هذه البطاقة؟',
|
||||
areYouSureYouWantToDeleteThisComment: 'هل أنت متأكد أنك تريد حذف هذا التعليق؟',
|
||||
areYouSureYouWantToDeleteThisLabel: 'هل أنت متأكد أنك تريد حذف هذا الملصق؟',
|
||||
areYouSureYouWantToDeleteThisList: 'هل أنت متأكد أنك تريد حذف هذه القائمة؟',
|
||||
areYouSureYouWantToDeleteThisProject: 'هل أنت متأكد أنك تريد حذف هذا المشروع؟',
|
||||
areYouSureYouWantToDeleteThisTask: 'هل أنت متأكد أنك تريد حذف هذه المهمة؟',
|
||||
areYouSureYouWantToDeleteThisUser: 'هل أنت متأكد أنك تريد حذف هذا المستخدم؟',
|
||||
areYouSureYouWantToLeaveBoard: 'هل أنت متأكد أنك تريد مغادرة اللوحة؟',
|
||||
areYouSureYouWantToLeaveProject: 'هل أنت متأكد أنك تريد مغادرة المشروع؟',
|
||||
areYouSureYouWantToRemoveThisManagerFromProject:
|
||||
'هل أنت متأكد أنك تريد إزالة هذا المدير من المشروع؟',
|
||||
areYouSureYouWantToRemoveThisMemberFromBoard:
|
||||
'هل أنت متأكد أنك تريد إزالة هذا العضو من اللوحة؟',
|
||||
attachment: 'مرفق',
|
||||
attachments: 'مرفقات',
|
||||
authentication: 'المصادقة',
|
||||
background: 'الخلفية',
|
||||
board: 'لوحة',
|
||||
boardNotFound_title: 'لم يتم العثور على اللوحة',
|
||||
canComment: 'يمكن التعليق',
|
||||
canEditContentOfBoard: 'يمكن تعديل محتوى اللوحة.',
|
||||
canOnlyViewBoard: 'يمكن فقط عرض اللوحة.',
|
||||
cardActions_title: 'إجراءات البطاقة',
|
||||
cardNotFound_title: 'لم يتم العثور على البطاقة',
|
||||
cardOrActionAreDeleted: 'تم حذف البطاقة أو الإجراء.',
|
||||
color: 'اللون',
|
||||
copy_inline: 'نسخ',
|
||||
createBoard_title: 'إنشاء لوحة',
|
||||
createLabel_title: 'إنشاء ملصق',
|
||||
createNewOneOrSelectExistingOne: 'أنشئ واحدة جديدة أو اختر<br />واحدة موجودة.',
|
||||
createProject_title: 'إنشاء مشروع',
|
||||
createTextFile_title: 'إنشاء ملف نصي',
|
||||
currentPassword: 'كلمة المرور الحالية',
|
||||
dangerZone_title: 'منطقة الخطر',
|
||||
date: 'تاريخ',
|
||||
dueDate: 'تاريخ الاستحقاق',
|
||||
dueDate_title: 'تاريخ الاستحقاق',
|
||||
deleteAttachment_title: 'حذف المرفق',
|
||||
deleteBoard_title: 'حذف اللوحة',
|
||||
deleteCard_title: 'حذف البطاقة',
|
||||
deleteComment_title: 'حذف التعليق',
|
||||
deleteLabel_title: 'حذف الملصق',
|
||||
deleteList_title: 'حذف القائمة',
|
||||
deleteProject_title: 'حذف المشروع',
|
||||
deleteTask_title: 'حذف المهمة',
|
||||
deleteUser_title: 'حذف المستخدم',
|
||||
description: 'الوصف',
|
||||
detectAutomatically: 'الكشف تلقائياً',
|
||||
dropFileToUpload: 'أفلت الملف لرفعه',
|
||||
editor: 'محرر',
|
||||
editAttachment_title: 'تعديل المرفق',
|
||||
editAvatar_title: 'تحرير الصورة الرمزية',
|
||||
editBoard_title: 'تعديل اللوحة',
|
||||
editDueDate_title: 'تعديل تاريخ الاستحقاق',
|
||||
editEmail_title: 'تعديل البريد الإلكتروني',
|
||||
editInformation_title: 'تعديل المعلومات',
|
||||
editLabel_title: 'تعديل الملصق',
|
||||
editPassword_title: 'تعديل كلمة المرور',
|
||||
editPermissions_title: 'تعديل الأذونات',
|
||||
editStopwatch_title: 'تعديل المؤقت',
|
||||
editUsername_title: 'تعديل اسم المستخدم',
|
||||
email: 'البريد الإلكتروني',
|
||||
emailAlreadyInUse: 'البريد الإلكتروني مستخدم بالفعل',
|
||||
enterCardTitle: 'أدخل عنوان البطاقة... [Ctrl+Enter] لفتحها تلقائيًا.',
|
||||
enterDescription: 'أدخل الوصف...',
|
||||
enterFilename: 'أدخل اسم الملف',
|
||||
enterListTitle: 'أدخل عنوان القائمة...',
|
||||
enterProjectTitle: 'أدخل عنوان المشروع',
|
||||
enterTaskDescription: 'أدخل وصف المهمة...',
|
||||
filterByLabels_title: 'تصفية حسب الملصقات',
|
||||
filterByMembers_title: 'تصفية حسب الأعضاء',
|
||||
fromComputer_title: 'من الكمبيوتر',
|
||||
fromTrello: 'من Trello',
|
||||
general: 'عام',
|
||||
hours: 'ساعات',
|
||||
importBoard_title: 'استيراد اللوحة',
|
||||
invalidCurrentPassword: 'كلمة المرور الحالية غير صالحة',
|
||||
labels: 'الملصقات',
|
||||
language: 'اللغة',
|
||||
leaveBoard_title: 'غادر اللوحة',
|
||||
leaveProject_title: 'غادر المشروع',
|
||||
linkIsCopied: 'تم نسخ الرابط',
|
||||
list: 'القائمة',
|
||||
listActions_title: 'قائمة الإجراءات',
|
||||
managers: 'المديرون',
|
||||
managerActions_title: 'إجراءات المدير',
|
||||
members: 'الأعضاء',
|
||||
memberActions_title: 'إجراءات العضو',
|
||||
minutes: 'الدقائق',
|
||||
moveCard_title: 'نقل البطاقة',
|
||||
name: 'الاسم',
|
||||
newestFirst: 'الأحدث أولاً',
|
||||
newEmail: 'بريد إلكتروني جديد',
|
||||
newPassword: 'كلمة سر جديدة',
|
||||
newUsername: 'مستخدم جديد',
|
||||
noConnectionToServer: 'لا يوجد اتصال بالخادم',
|
||||
noBoards: 'لا توجد لوحات',
|
||||
noLists: 'لاتوجد قوائم',
|
||||
noProjects: 'لاتوجد مشاريع',
|
||||
notifications: 'الإشعارات',
|
||||
noUnreadNotifications: 'لاتوجد إشعارات غير مقروءة',
|
||||
oldestFirst: 'الأقدم أولاً',
|
||||
openBoard_title: 'فتح اللوحة',
|
||||
optional_inline: 'اختياري',
|
||||
organization: 'المنظمة',
|
||||
phone: 'الهاتف',
|
||||
preferences: 'التفضيلات',
|
||||
pressPasteShortcutToAddAttachmentFromClipboard:
|
||||
'نصيحة: اضغط على Ctrl-V (Cmd-V على Mac) لإضافة مرفق من الحافظة.',
|
||||
project: 'مشروع',
|
||||
projectNotFound_title: 'المشروع غير موجود',
|
||||
removeManager_title: 'إزالة المدير',
|
||||
removeMember_title: 'إزالة العضو',
|
||||
searchLabels: 'البحث عن التصنيفات...',
|
||||
searchMembers: 'البحث عن الأعضاء...',
|
||||
searchUsers: 'البحث عن المستخدمين...',
|
||||
searchCards: 'البحث عن البطاقات...',
|
||||
seconds: 'ثواني',
|
||||
selectBoard: 'اختر لوحة',
|
||||
selectList: 'اختر قائمة',
|
||||
selectPermissions_title: 'حدد الأذونات',
|
||||
selectProject: 'حدد المشروع',
|
||||
settings: 'الإعدادات',
|
||||
sortList_title: 'فرز القائمة',
|
||||
stopwatch: 'المؤقت',
|
||||
subscribeToMyOwnCardsByDefault: 'الاشتراك في بطاقاتي الخاصة إفتراضياً',
|
||||
taskActions_title: 'إجراءات المهمة',
|
||||
tasks: 'المهام',
|
||||
thereIsNoPreviewAvailableForThisAttachment: 'لا يوجد معاينة متاحة لهذا المرفق.',
|
||||
time: 'الوقت',
|
||||
title: 'العنوان',
|
||||
userActions_title: 'إجراءات المستخدم',
|
||||
userAddedThisCardToList: '<0>{{user}}</0><1> تمت إضافة هذه البطاقة إلى {{list}}</1>',
|
||||
userLeftNewCommentToCard: '{{user}} ترك تعليق جديد «{{comment}}» إلى <2>{{card}}</2>',
|
||||
userMovedCardFromListToList: '{{user}} انتقل <2>{{card}}</2> من {{fromList}} إلى {{toList}}',
|
||||
userMovedThisCardFromListToList:
|
||||
'<0>{{user}}</0><1> نُقلت هذه البطاقة من {{fromList}} إلى {{toList}}</1>',
|
||||
username: 'اسم المستخدم',
|
||||
usernameAlreadyInUse: 'اسم المستخدم تم استخدامه بالفعل',
|
||||
users: 'المستخدمين',
|
||||
version: 'الإصدار',
|
||||
viewer: 'مشاهد',
|
||||
writeComment: 'اكتب تعليقاً...',
|
||||
},
|
||||
|
||||
action: {
|
||||
addAnotherCard: 'إضافة بطاقة أخرى',
|
||||
addAnotherList: 'إضافة قائمة أخرى',
|
||||
addAnotherTask: 'إضافة مهمة أخرى',
|
||||
addCard: 'إضافة بطاقة',
|
||||
addCard_title: 'إضافة بطاقة',
|
||||
addComment: 'إضافة تعليق',
|
||||
addList: 'إضافة قائمة',
|
||||
addMember: 'إضافة عضو',
|
||||
addMoreDetailedDescription: 'إضافة وصف أكثر تفصيلاً',
|
||||
addTask: 'إضافة مهمة',
|
||||
addToCard: 'إضافة إلى البطاقة',
|
||||
addUser: 'إضافة مستخدم',
|
||||
copyLink_title: 'نسخ الرابط',
|
||||
createBoard: 'إنشاء لوحة',
|
||||
createFile: 'إنشاء ملف',
|
||||
createLabel: 'إنشاء ملصق',
|
||||
createNewLabel: 'إنشاء ملصق جديد',
|
||||
createProject: 'إنشاء مشروع',
|
||||
delete: 'حذف',
|
||||
deleteAttachment: 'حذف المرفق',
|
||||
deleteAvatar: 'حذف الصورة الرمزية',
|
||||
deleteBoard: 'حذف اللوحة',
|
||||
deleteCard: 'حذف البطاقة',
|
||||
deleteCard_title: 'حذف البطاقة',
|
||||
deleteComment: 'حذف التعليق',
|
||||
deleteImage: 'حذف الصورة',
|
||||
deleteLabel: 'حذف الملصق',
|
||||
deleteList: 'حذف القائمة',
|
||||
deleteList_title: 'حذف القائمة',
|
||||
deleteProject: 'حذف المشروع',
|
||||
deleteProject_title: 'حذف المشروع',
|
||||
deleteTask: 'حذف المهمة',
|
||||
deleteTask_title: 'حذف المهمة',
|
||||
deleteUser: 'حذف المستخدم',
|
||||
duplicate: 'تكرار',
|
||||
duplicateCard_title: 'تكرار البطاقة',
|
||||
edit: 'تعديل',
|
||||
editDueDate_title: 'تعديل تاريخ الاستحقاق',
|
||||
editDescription_title: 'تعديل الوصف',
|
||||
editEmail_title: 'تعديل البريد الإلكتروني',
|
||||
editInformation_title: 'تعديل المعلومات',
|
||||
editPassword_title: 'تعديل كلمة المرور',
|
||||
editPermissions: 'تعديل الأذونات',
|
||||
editStopwatch_title: 'تعديل المؤقت',
|
||||
editTitle_title: 'تعديل العنوان',
|
||||
editUsername_title: 'تعديل اسم المستخدم',
|
||||
hideDetails: 'إخفاء التفاصيل',
|
||||
import: 'استيراد',
|
||||
leaveBoard: 'غادر اللوحة',
|
||||
leaveProject: 'غادر المشروع',
|
||||
logOut_title: 'تسجيل الخروج',
|
||||
makeCover_title: 'إصنع غلافاً',
|
||||
move: 'نقل',
|
||||
moveCard_title: 'نقل البطاقة',
|
||||
remove: 'حذف',
|
||||
removeBackground: 'إزالة الخلفية',
|
||||
removeCover_title: 'إزالة الغلاف',
|
||||
removeFromBoard: 'إزالة اللوحة',
|
||||
removeFromProject: 'إزالة المشروع',
|
||||
removeManager: 'إزالة المدير',
|
||||
removeMember: 'إزالة العضو',
|
||||
save: 'حفظ',
|
||||
showAllAttachments: 'إظهار جميع المرفقات ({{hidden}} hidden)',
|
||||
showDetails: 'إظهار التفاصيل',
|
||||
showFewerAttachments: 'عرض مرفقات أقل',
|
||||
sortList_title: 'فرز القائمة',
|
||||
start: 'ابدأ',
|
||||
stop: 'توقف',
|
||||
subscribe: 'اشترك',
|
||||
unsubscribe: 'إلغاء الاشتراك',
|
||||
uploadNewAvatar: 'رفع صورة رمزية جديدة',
|
||||
uploadNewImage: 'رفع صورة جديدة',
|
||||
},
|
||||
},
|
||||
};
|
||||
@@ -0,0 +1,8 @@
|
||||
import login from './login';
|
||||
|
||||
export default {
|
||||
language: 'ar-YE',
|
||||
country: 'ye',
|
||||
name: 'العربية',
|
||||
embeddedLocale: login,
|
||||
};
|
||||
@@ -0,0 +1,23 @@
|
||||
export default {
|
||||
translation: {
|
||||
common: {
|
||||
emailOrUsername: 'البريد الإلكتروني أو اسم المستخدم',
|
||||
invalidEmailOrUsername: 'البريد الإلكتروني أو اسم المستخدم غير صالح',
|
||||
invalidCredentials: 'بيانات الاعتماد غير صالحة',
|
||||
invalidPassword: 'كلمة المرور غير صالحة',
|
||||
logInToPlanka: 'تسجيل الدخول إلى Planka',
|
||||
noInternetConnection: 'لا يوجد اتصال بالإنترنت',
|
||||
pageNotFound_title: 'الصفحة غير موجودة',
|
||||
password: 'كلمة المرور',
|
||||
projectManagement: 'إدارة المشروع',
|
||||
serverConnectionFailed: 'فشل الاتصال بالخادم',
|
||||
unknownError: 'خطأ غير معروف، يرجى المحاولة لاحقاً',
|
||||
useSingleSignOn: 'استخدم تسجيل الدخول الموحد',
|
||||
},
|
||||
|
||||
action: {
|
||||
logIn: 'تسجيل الدخول',
|
||||
logInWithSSO: 'تسجيل الدخول باستخدام SSO',
|
||||
},
|
||||
},
|
||||
};
|
||||
@@ -3,6 +3,7 @@ export default {
|
||||
common: {
|
||||
emailOrUsername: 'E-mail or username',
|
||||
invalidEmailOrUsername: 'Invalid e-mail or username',
|
||||
invalidCredentials: 'Invalid credentials',
|
||||
invalidPassword: 'Invalid password',
|
||||
logInToPlanka: 'Log in to Planka',
|
||||
noInternetConnection: 'No internet connection',
|
||||
|
||||
@@ -43,7 +43,7 @@ export default {
|
||||
boardNotFound_title: 'Tablero no encontrado',
|
||||
cardActions_title: 'Acciones de las tarjetas',
|
||||
cardNotFound_title: 'tarjeta no encontrada',
|
||||
cardOrActionAreDeleted: 'La tarjeta o la acción está eliminada.',
|
||||
cardOrActionAreDeleted: 'La tarjeta o la acción está borrada.',
|
||||
color: 'Color',
|
||||
createBoard_title: 'Crear Tablero',
|
||||
createLabel_title: 'Crear Etiqueta',
|
||||
@@ -53,7 +53,7 @@ export default {
|
||||
currentPassword: 'Contraseña Actual',
|
||||
date: 'Fecha',
|
||||
dueDate_title: 'Fecha de Vencimiento',
|
||||
deleteAttachment_title: 'Eliminar Adjunto',
|
||||
deleteAttachment_title: 'Borrar Adjunto',
|
||||
deleteBoard_title: 'Borrar Tablero',
|
||||
deleteCard_title: 'Borrar tarjeta',
|
||||
deleteComment_title: 'Borrar Comentario',
|
||||
@@ -72,7 +72,7 @@ export default {
|
||||
editLabel_title: 'Editar Etiqueta',
|
||||
editPassword_title: 'Editar Contraseña',
|
||||
editStopwatch_title: 'Editar Temporizador',
|
||||
editUsername_title: 'Edit nombre de usuario',
|
||||
editUsername_title: 'Editar nombre de usuario',
|
||||
email: 'Correo',
|
||||
emailAlreadyInUse: 'El correo ya está en uso',
|
||||
enterCardTitle: 'Escribe el título de la tarjeta...',
|
||||
@@ -85,8 +85,8 @@ export default {
|
||||
filterByMembers_title: 'Filtrar por Miembros',
|
||||
fromComputer_title: 'Desde Computador',
|
||||
hours: 'Horas',
|
||||
invalidCurrentPassword: 'Contraseña actual invalida',
|
||||
labels: 'Etíquetas',
|
||||
invalidCurrentPassword: 'Contraseña actual inválida',
|
||||
labels: 'Etiquetas',
|
||||
list: 'Lista',
|
||||
listActions_title: 'Acciónes de Lista',
|
||||
members: 'Miembros',
|
||||
@@ -168,14 +168,14 @@ export default {
|
||||
deleteProject_title: 'Borrar Proyecto',
|
||||
deleteTask: 'Borrar tarea',
|
||||
deleteTask_title: 'Borrar Tarea',
|
||||
deleteUser: 'Delete usuario',
|
||||
deleteUser: 'Borrar usuario',
|
||||
edit: 'Editar',
|
||||
editDueDate_title: 'Editar Fecha de Vencimiento',
|
||||
editDescription_title: 'Editar Descripción',
|
||||
editEmail_title: 'Editar Correo',
|
||||
editPassword_title: 'Editar Contraseña',
|
||||
editStopwatch_title: 'Edit Temporizador',
|
||||
editTitle_title: 'Edit Título',
|
||||
editStopwatch_title: 'Editar Temporizador',
|
||||
editTitle_title: 'Editar Título',
|
||||
editUsername_title: 'Editar Nombre de Usuario',
|
||||
logOut_title: 'Cerrar Sesión',
|
||||
makeCover_title: 'Hacer Cubierta',
|
||||
|
||||
@@ -15,10 +15,12 @@ export default {
|
||||
|
||||
translation: {
|
||||
common: {
|
||||
aboutPlanka: 'À propos de Planka',
|
||||
account: 'Compte',
|
||||
actions: 'Actions',
|
||||
addAttachment_title: 'Ajouter une pièce jointe',
|
||||
addComment: 'Ajouter un commentaire',
|
||||
addManager_title: 'Ajouter un manager',
|
||||
addMember_title: 'Ajouter un membre',
|
||||
addUser_title: 'Ajouter un utilisateur',
|
||||
administrator: 'Administrateur',
|
||||
@@ -26,32 +28,43 @@ export default {
|
||||
allChangesWillBeAutomaticallySavedAfterConnectionRestored:
|
||||
'Toutes les modifications seront automatiquement enregistrées<br />une fois la connexion rétablie.',
|
||||
areYouSureYouWantToDeleteThisAttachment: 'Voulez-vous vraiment supprimer cette pièce jointe?',
|
||||
areYouSureYouWantToDeleteThisBoard: 'Êtes-vous sûr de vouloir supprimer ce forum?',
|
||||
areYouSureYouWantToDeleteThisBoard: 'Êtes-vous sûr de vouloir supprimer ce tableau?',
|
||||
areYouSureYouWantToDeleteThisCard: 'Voulez-vous vraiment supprimer cette carte?',
|
||||
areYouSureYouWantToDeleteThisComment: 'Êtes-vous sûr de vouloir supprimer ce commentaire?',
|
||||
areYouSureYouWantToDeleteThisLabel: 'Voulez-vous vraiment supprimer ce libellé?',
|
||||
areYouSureYouWantToDeleteThisLabel: 'Voulez-vous vraiment supprimer cette étiquette?',
|
||||
areYouSureYouWantToDeleteThisList: 'Êtes-vous sûr de vouloir supprimer cette liste?',
|
||||
areYouSureYouWantToDeleteThisProject: 'Êtes-vous sûr de vouloir supprimer ce projet?',
|
||||
areYouSureYouWantToDeleteThisTask: 'Êtes-vous sûr de vouloir supprimer cette tâche?',
|
||||
areYouSureYouWantToDeleteThisUser: 'Êtes-vous sûr de vouloir supprimer cet utilisateur?',
|
||||
areYouSureYouWantToLeaveBoard: 'Êtes-vous sûr de vouloir quitter ce tableau ?',
|
||||
areYouSureYouWantToLeaveProject: 'Êtes-vous sûr de vouloir quitter ce projet ?',
|
||||
areYouSureYouWantToRemoveThisManagerFromProject:
|
||||
'Êtes-vous sûr de vouloir supprimer ce manager du projet ?',
|
||||
areYouSureYouWantToRemoveThisMemberFromProject:
|
||||
'Êtes-vous sûr de vouloir supprimer ce membre du projet?',
|
||||
attachment: 'Attachement',
|
||||
attachment: 'Pièce jointe',
|
||||
attachments: 'Pièces jointes',
|
||||
authentication: 'Authentification',
|
||||
background: 'Arrière-plan',
|
||||
board: 'Tableau',
|
||||
boardNotFound_title: 'Carte non trouvée',
|
||||
canComment: 'Peut commenter',
|
||||
canEditContentOfBoard: 'Peut éditer le contenu du tableau.',
|
||||
canOnlyViewBoard: 'Peut uniquement voir le tableau.',
|
||||
cardActions_title: 'Actions sur la carte',
|
||||
cardNotFound_title: 'Carte non trouvée',
|
||||
cardOrActionAreDeleted: "La carte ou l'action sont supprimées.",
|
||||
color: 'Couleur',
|
||||
copy_inline: 'copie',
|
||||
createBoard_title: 'Créer un tableau',
|
||||
createLabel_title: 'Créer une étiquette',
|
||||
createNewOneOrSelectExistingOne: 'Créez-en un nouveau ou sélectionnez<br />un existant.',
|
||||
createProject_title: 'Créer un projet',
|
||||
createTextFile_title: 'Créer un fichier texte',
|
||||
currentPassword: 'Mot de passe actuel',
|
||||
dangerZone_title: 'Zone dangereuse',
|
||||
date: 'Date',
|
||||
dueDate: "Date d'échéance",
|
||||
dueDate_title: "Date d'échéance",
|
||||
deleteAttachment_title: 'Supprimer la pièce jointe',
|
||||
deleteBoard_title: 'Supprimer le tableau',
|
||||
@@ -63,67 +76,89 @@ export default {
|
||||
deleteTask_title: 'Supprimer la tâche',
|
||||
deleteUser_title: "Supprimer l'utilisateur",
|
||||
description: 'Description',
|
||||
detectAutomatically: 'Détecter automatiquement',
|
||||
dropFileToUpload: 'Déposer le fichier à télécharger',
|
||||
editor: 'Éditeur',
|
||||
editAttachment_title: 'Modifier la pièce jointe',
|
||||
editAvatar_title: 'Modifier Avatar',
|
||||
editBoard_title: 'Modifier le tableau',
|
||||
editDueDate_title: "Modifier la date d'échéance",
|
||||
editEmail_title: "Modifier l'e-mail",
|
||||
editEmail_title: "Modifier l'email",
|
||||
editInformation_title: 'Modifier les informations',
|
||||
editLabel_title: "Modifier l'étiquette",
|
||||
editPassword_title: 'Modifier le mot de passe',
|
||||
editPermissions_title: 'Modifier les permissions',
|
||||
editStopwatch_title: 'Modifier la minuterie',
|
||||
editUsername_title: "Modifier le nom d'utilisateur",
|
||||
email: 'E-mail',
|
||||
emailAlreadyInUse: 'Email déjà utilisé',
|
||||
enterCardTitle: 'Entrer le titre de la carte...',
|
||||
enterDescription: 'Entrez la description...',
|
||||
enterFilename: 'Entrez le nom du fichier',
|
||||
enterListTitle: 'Entrer le titre de la liste...',
|
||||
enterCardTitle: 'Saisir le titre de la carte... [Ctrl+Enter] pour ouvrir automatiquement',
|
||||
enterDescription: 'Saisir la description...',
|
||||
enterFilename: 'Saisir le nom du fichier',
|
||||
enterListTitle: 'Saisie le titre de la liste...',
|
||||
enterProjectTitle: 'Saisir le titre du projet',
|
||||
enterTaskDescription: 'Saisir la description de la tâche...',
|
||||
filterByLabels_title: 'Filtrer par libellés',
|
||||
filterByLabels_title: 'Filtrer par étiquettes',
|
||||
filterByMembers_title: 'Filtrer par membres',
|
||||
fromComputer_title: "Depuis l'ordinateur",
|
||||
hours: 'Les heures',
|
||||
fromTrello: 'Depuis Trello',
|
||||
general: 'Général',
|
||||
hours: 'Heures',
|
||||
importBoard_title: 'Importer un tableau',
|
||||
invalidCurrentPassword: 'Mot de passe actuel invalide',
|
||||
labels: 'Étiquettes',
|
||||
language: 'Langue',
|
||||
leaveBoard_title: 'Quitter le tableau',
|
||||
leaveProject_title: 'Quitter le projet',
|
||||
linkIsCopied: 'Le lien est copié',
|
||||
list: 'Lister',
|
||||
listActions_title: 'Liste des actions',
|
||||
managers: 'Managers',
|
||||
managerActions_title: 'Actions des managers',
|
||||
members: 'Membres',
|
||||
memberActions_title: 'Actions des membres',
|
||||
minutes: 'Minutes',
|
||||
moveCard_title: 'Déplacer la carte',
|
||||
name: 'Nom',
|
||||
newEmail: 'Nouveau courriel',
|
||||
newestFirst: 'Le plus récent en premier',
|
||||
newEmail: 'Nouveau email',
|
||||
newPassword: 'Nouveau mot de passe',
|
||||
newUsername: "Nouveau nom d'utilisateur",
|
||||
noConnectionToServer: 'Pas de connexion au serveur',
|
||||
noBoards: 'Pas de planches',
|
||||
noBoards: 'Pas de tableau',
|
||||
noLists: 'Pas de listes',
|
||||
noProjects: 'Pas de projets',
|
||||
notifications: 'Notifications',
|
||||
noUnreadNotifications: 'Aucune notification non lue.',
|
||||
openBoard_title: 'Open Board',
|
||||
oldestFirst: 'Le plus ancien en premier',
|
||||
openBoard_title: 'Ouvrir le tableau',
|
||||
optional_inline: 'optionnel',
|
||||
organization: 'Organisation',
|
||||
phone: 'Téléphone',
|
||||
preferences: 'Préférences',
|
||||
pressPasteShortcutToAddAttachmentFromClipboard: 'Conseil',
|
||||
pressPasteShortcutToAddAttachmentFromClipboard:
|
||||
'Conseil: appuyer sur Ctrl-V (Cmd-V sur Mac) pour ajouter une pièce jointe depuis le presse-papiers',
|
||||
project: 'Projet',
|
||||
projectNotFound_title: 'Projet introuvable',
|
||||
removeManager_title: 'Supprimer le manager',
|
||||
removeMember_title: 'Supprimer le membre',
|
||||
searchLabels: 'Chercher une étiquette...',
|
||||
searchMembers: 'Chercher un membre...',
|
||||
searchUsers: 'Chercher un utilisateur...',
|
||||
searchCards: 'Chercher une carte...',
|
||||
seconds: 'Secondes',
|
||||
selectBoard: 'Sélectionner une carte',
|
||||
selectBoard: 'Sélectionner un tableau',
|
||||
selectList: 'Sélectionner une liste',
|
||||
selectPermissions_title: 'Sélectionner les permissions',
|
||||
selectProject: 'Sélectionner un projet',
|
||||
settings: 'Réglages',
|
||||
sortList_title: 'Trier la liste',
|
||||
stopwatch: 'Minuteur',
|
||||
subscribeToMyOwnCardsByDefault: 'Abonnez-vous à mes propres cartes par défaut',
|
||||
taskActions_title: 'Actions de tâche',
|
||||
tasks: 'Tâches',
|
||||
thereIsNoPreviewAvailableForThisAttachment:
|
||||
"Il n'y a pas de prévisualisation de disponible pour cette pièce jointe.",
|
||||
time: 'Temps',
|
||||
title: 'Titre',
|
||||
userActions_title: "Actions de l'utilisateur",
|
||||
@@ -137,6 +172,8 @@ export default {
|
||||
username: "Nom d'utilisateur",
|
||||
usernameAlreadyInUse: "Nom d'utilisateur déjà utilisé",
|
||||
users: 'Utilisateurs',
|
||||
version: 'Version',
|
||||
viewer: 'Spectateur',
|
||||
writeComment: 'Écrire un commentaire...',
|
||||
},
|
||||
|
||||
@@ -148,10 +185,12 @@ export default {
|
||||
addCard_title: 'Ajouter une carte',
|
||||
addComment: 'Ajouter un commentaire',
|
||||
addList: 'Ajouter la liste',
|
||||
addMember: 'Ajouter un membre',
|
||||
addMoreDetailedDescription: 'Ajouter une description plus détaillée',
|
||||
addTask: 'Ajouter une tâche',
|
||||
addToCard: 'Ajouter à la carte',
|
||||
addUser: 'Ajouter un utilisateur',
|
||||
copyLink_title: 'Copier le lien',
|
||||
createBoard: 'Créer un tableau',
|
||||
createFile: 'Créer un fichier',
|
||||
createLabel: 'Créer une étiquette',
|
||||
@@ -174,14 +213,21 @@ export default {
|
||||
deleteTask_title: 'Supprimer la tâche',
|
||||
deleteUser: "Supprimer l'utilisateur",
|
||||
duplicate: 'Dupliquer',
|
||||
duplicateCard_title: 'Dupliquer la carte',
|
||||
edit: 'Modifier',
|
||||
editDueDate_title: "Modifier la date d'échéance",
|
||||
editDescription_title: 'Éditer la description',
|
||||
editEmail_title: "Modifier l'e-mail",
|
||||
editDescription_title: 'Modifier la description',
|
||||
editEmail_title: "Modifier l'email",
|
||||
editInformation_title: 'Modifier les informations',
|
||||
editPassword_title: 'Modifier le mot de passe',
|
||||
editPermissions: 'Modifier les permissions',
|
||||
editStopwatch_title: 'Modifier la minuterie',
|
||||
editTitle_title: 'Modifier le titre',
|
||||
editUsername_title: "Modifier le nom d'utilisateur",
|
||||
hideDetails: 'Cacher les détails',
|
||||
import: 'Importer',
|
||||
leaveBoard: 'Quitter le tableau',
|
||||
leaveProject: 'Quitter le projet',
|
||||
logOut_title: 'Se déconnecter',
|
||||
makeCover_title: 'Faire la jaquette',
|
||||
move: 'Déplacer',
|
||||
@@ -189,11 +235,15 @@ export default {
|
||||
remove: 'Supprimer',
|
||||
removeBackground: "Supprimer l'arrière-plan",
|
||||
removeCover_title: 'Supprimer la jaquette',
|
||||
removeFromBoard: 'Supprimer le tableau',
|
||||
removeFromProject: 'Supprimer du projet',
|
||||
removeManager: 'Supprimer le manager',
|
||||
removeMember: 'Supprimer le membre',
|
||||
save: 'Sauvegarder',
|
||||
showAllAttachments: 'Afficher toutes les pièces jointes ({{hidden}} masquées)',
|
||||
showDetails: 'Afficher les détails',
|
||||
showFewerAttachments: 'Afficher moins de pièces jointes',
|
||||
sortList_title: 'Trier la liste',
|
||||
start: 'Début',
|
||||
stop: 'Arrêter',
|
||||
subscribe: "S'abonner",
|
||||
|
||||
@@ -3,6 +3,7 @@ export default {
|
||||
common: {
|
||||
emailOrUsername: "Email ou nom d'utilisateur",
|
||||
invalidEmailOrUsername: "Email ou nom d'utilisateur invalide",
|
||||
invalidCredentials: 'Identifiants invalides',
|
||||
invalidPassword: 'Mot de passe invalide',
|
||||
logInToPlanka: 'Se connecter à Planka',
|
||||
noInternetConnection: 'Aucune connection internet',
|
||||
@@ -11,10 +12,12 @@ export default {
|
||||
projectManagement: 'Gestion de projet',
|
||||
serverConnectionFailed: 'Connection au serveur échouée',
|
||||
unknownError: 'Erreur inconnue, réessayez plus tard',
|
||||
useSingleSignOn: "Utiliser l'authentification unique",
|
||||
},
|
||||
|
||||
action: {
|
||||
logIn: 'Se connecter',
|
||||
logInWithSSO: "Se connecter avec l'authentification unique",
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
import arYE from './ar-YE';
|
||||
import bgBG from './bg-BG';
|
||||
import csCZ from './cs-CZ';
|
||||
import daDK from './da-DK';
|
||||
@@ -22,8 +23,10 @@ import trTR from './tr-TR';
|
||||
import ukUA from './uk-UA';
|
||||
import uzUZ from './uz-UZ';
|
||||
import zhCN from './zh-CN';
|
||||
import zhTW from './zh-TW';
|
||||
|
||||
const locales = [
|
||||
arYE,
|
||||
bgBG,
|
||||
csCZ,
|
||||
daDK,
|
||||
@@ -48,6 +51,7 @@ const locales = [
|
||||
ukUA,
|
||||
uzUZ,
|
||||
zhCN,
|
||||
zhTW,
|
||||
];
|
||||
|
||||
export default locales;
|
||||
|
||||
@@ -55,7 +55,7 @@ export default {
|
||||
cardNotFound: 'Карточка не найдена',
|
||||
cardOrActionAreDeleted: 'Карточка или действие удалены.',
|
||||
color: 'Цвет',
|
||||
connectionRestored: 'Соединение восстановлено',
|
||||
copy_inline: 'копировать',
|
||||
createBoard: 'Создание доски',
|
||||
createLabel: 'Создание метки',
|
||||
createNewOneOrSelectExistingOne: 'Создайте новую или выберите<br />уже существующую.',
|
||||
@@ -65,6 +65,7 @@ export default {
|
||||
dangerZone_title: 'Опасная зона',
|
||||
date: 'Дата',
|
||||
dueDate: 'Срок',
|
||||
dueDate_title: 'Срок исполнения',
|
||||
deleteAttachment: 'Удаление вложения',
|
||||
deleteBoard: 'Удаление доски',
|
||||
deleteCard: 'Удаление карточки',
|
||||
@@ -80,9 +81,8 @@ export default {
|
||||
editor: 'Редактор',
|
||||
editAttachment: 'Изменение вложения',
|
||||
editAvatar: 'Изменение аватара',
|
||||
editBoard: 'Изменение доски',
|
||||
editBackground: 'Изменение фона',
|
||||
editDueDate: 'Изменение срока',
|
||||
editBoard_title: 'Изменение доски',
|
||||
editDueDate_title: 'Изменить срок выполнения',
|
||||
editEmail: 'Изменение e-mail',
|
||||
editInformation: 'Изменение информации',
|
||||
editLabel: 'Изменение метки',
|
||||
@@ -90,10 +90,10 @@ export default {
|
||||
editPermissions: 'Редактирование разрешений',
|
||||
editStopwatch: 'Изменение секундомера',
|
||||
editTitle: 'Изменение названия',
|
||||
editUsername: 'Изменение имени пользователя',
|
||||
editUsername_title: 'Изменение имени пользователя',
|
||||
email: 'E-mail',
|
||||
emailAlreadyInUse: 'E-mail уже занят',
|
||||
enterCardTitle: 'Введите заголовок для этой карточки...',
|
||||
enterCardTitle: 'Введите заголовок для этой карточки... [Ctrl+Enter] для применения',
|
||||
enterDescription: 'Введите описание...',
|
||||
enterFilename: 'Введите название файла',
|
||||
enterListTitle: 'Введите заголовок списка...',
|
||||
@@ -110,14 +110,18 @@ export default {
|
||||
labels: 'Метки',
|
||||
language: 'Язык',
|
||||
leaveBoard: 'Покинуть доску',
|
||||
leaveProject: 'Покинуть проект',
|
||||
leaveProject_title: 'Покинуть проект',
|
||||
linkIsCopied: 'Ссылка скопирована',
|
||||
list: 'Список',
|
||||
listActions: 'Действия со списком',
|
||||
listActions_title: 'Действия со списком',
|
||||
managers: 'Менеджеры',
|
||||
managerActions_title: 'Действия Менеджера',
|
||||
members: 'Участники',
|
||||
memberActions_title: 'Действия участников',
|
||||
minutes: 'Минуты',
|
||||
moveCard: 'Перемещение карточки',
|
||||
moveCard_title: 'Перемещение карточки',
|
||||
name: 'Имя',
|
||||
newestFirst: 'Новые первые',
|
||||
newEmail: 'Новый e-mail',
|
||||
newPassword: 'Новый пароль',
|
||||
newUsername: 'Новое имя пользователя',
|
||||
@@ -127,7 +131,8 @@ export default {
|
||||
noProjects: 'Проектов нет',
|
||||
notifications: 'Уведомления',
|
||||
noUnreadNotifications: 'Уведомлений нет.',
|
||||
openBoard: 'Откройте доску',
|
||||
oldestFirst: 'Старые первые',
|
||||
openBoard_title: 'Откройте доску',
|
||||
optional_inline: 'необязательно',
|
||||
organization: 'Организация',
|
||||
phone: 'Телефон',
|
||||
@@ -135,10 +140,9 @@ export default {
|
||||
pressPasteShortcutToAddAttachmentFromClipboard:
|
||||
'Совет: нажмите Ctrl-V (Cmd-V на Mac), чтобы добавить вложение из буфера обмена.',
|
||||
project: 'Проект',
|
||||
projectActions: 'Действия с проектом',
|
||||
projectNotFound: 'Проект не найден',
|
||||
removeManager: 'Удалить менеджера',
|
||||
removeMember: 'Удаление участника',
|
||||
projectNotFound_title: 'Проект не найден',
|
||||
removeManager_title: 'Удалить менеджера',
|
||||
removeMember_title: 'Удаление участника',
|
||||
searchLabels: 'Поиск меток...',
|
||||
searchMembers: 'Поиск участников...',
|
||||
searchUsers: 'Поиск пользователей...',
|
||||
@@ -149,14 +153,15 @@ export default {
|
||||
selectPermissions: 'Выбор разрешений',
|
||||
selectProject: 'Выберите проект',
|
||||
settings: 'Настройки',
|
||||
sortList_title: 'Сортировка списка',
|
||||
stopwatch: 'Секундомер',
|
||||
subscribeToMyOwnCardsByDefault: 'По умолчанию подписываться на мои собственные карточки',
|
||||
taskActions: 'Действия с задачей',
|
||||
taskActions_title: 'Действия по задаче',
|
||||
tasks: 'Задачи',
|
||||
thereIsNoPreviewAvailableForThisAttachment: 'Предпросмотр для этого вложения недоступен.',
|
||||
time: 'Время',
|
||||
title: 'Название',
|
||||
userActions: 'Действия с пользователем',
|
||||
userActions_title: 'Действия с пользователем',
|
||||
userAddedThisCardToList: '<0>{{user}}</0><1> добавил(а) эту карточку в {{list}}</1>',
|
||||
userLeftNewCommentToCard: '{{user}} оставил(а) комментарий «{{comment}}» к <2>{{card}}</2>',
|
||||
userMovedCardFromListToList:
|
||||
@@ -176,6 +181,7 @@ export default {
|
||||
addAnotherList: 'Добавить еще один список',
|
||||
addAnotherTask: 'Добавить еще одну задачу',
|
||||
addCard: 'Добавить карточку',
|
||||
addCard_title: 'Добавить карточку',
|
||||
addComment: 'Добавить комментарий',
|
||||
addList: 'Добавить список',
|
||||
addMember: 'Добавить участника',
|
||||
@@ -183,6 +189,7 @@ export default {
|
||||
addTask: 'Добавить задачу',
|
||||
addToCard: 'Добавить на карточку',
|
||||
addUser: 'Добавить пользователя',
|
||||
copyLink_title: 'Копировать ссылку',
|
||||
createBoard: 'Создать доску',
|
||||
createFile: 'Создать файл',
|
||||
createLabel: 'Создать метку',
|
||||
@@ -193,38 +200,41 @@ export default {
|
||||
deleteAvatar: 'Удалить аватар',
|
||||
deleteBoard: 'Удалить доску',
|
||||
deleteCard: 'Удалить карточку',
|
||||
deleteCard_title: 'Удалить карточку',
|
||||
deleteComment: 'Удалить комментарий',
|
||||
deleteImage: 'Удалить изображение',
|
||||
deleteLabel: 'Удалить метку',
|
||||
deleteList: 'Удалить список',
|
||||
deleteList_title: 'Удалить список',
|
||||
deleteProject: 'Удалить проект',
|
||||
deleteProject_title: 'Удалить проект',
|
||||
deleteTask: 'Удалить задачу',
|
||||
deleteTask_title: 'Удалить задачу',
|
||||
deleteUser: 'Удалить пользователя',
|
||||
duplicate: 'Дублировать',
|
||||
duplicateCard_title: 'Дублировать карточку',
|
||||
edit: 'Изменить',
|
||||
editBackground: 'Изменить фон',
|
||||
editDueDate: 'Изменить срок',
|
||||
editDescription: 'Изменить описание',
|
||||
editEmail: 'Изменить e-mail',
|
||||
editInformation: 'Изменить информацию',
|
||||
editPassword: 'Изменить пароль',
|
||||
editDueDate_title: 'Изменить срок',
|
||||
editDescription_title: 'Изменить описание',
|
||||
editEmail_title: 'Изменить e-mail',
|
||||
editInformation_title: 'Изменить информацию',
|
||||
editPassword_title: 'Изменить пароль',
|
||||
editPermissions: 'Изменить разрешения',
|
||||
editStopwatch: 'Изменить секундомер',
|
||||
editTask: 'Изменить задачу',
|
||||
editTitle: 'Изменить название',
|
||||
editUsername: 'Изменить имя пользователя',
|
||||
editStopwatch_title: 'Изменить секундомер',
|
||||
editTitle_title: 'Изменить название',
|
||||
editUsername_title: 'Изменить имя пользователя',
|
||||
hideDetails: 'Скрыть подробности',
|
||||
import: 'Импорт',
|
||||
leaveBoard: 'Покинуть доску',
|
||||
leaveProject: 'Покинуть проект',
|
||||
logOut: 'Выйти',
|
||||
makeCover: 'Сделать обложкой',
|
||||
logOut_title: 'Выйти',
|
||||
makeCover_title: 'Сделать обложкой',
|
||||
move: 'Переместить',
|
||||
moveCard: 'Переместить карточку',
|
||||
moveCard_title: 'Переместить карточку',
|
||||
remove: 'Убрать',
|
||||
removeBackground: 'Убрать фон',
|
||||
removeCover: 'Убрать обложку',
|
||||
removeCover_title: 'Убрать обложку',
|
||||
removeFromBoard: 'Удалить из доски',
|
||||
removeFromProject: 'Удалить из проекта',
|
||||
removeManager: 'Удалить менеджера',
|
||||
|
||||
@@ -6,15 +6,17 @@ export default {
|
||||
invalidPassword: 'Неверный пароль',
|
||||
logInToPlanka: 'Вход в Planka',
|
||||
noInternetConnection: 'Нет соединения',
|
||||
pageNotFound: 'Страница не найдена',
|
||||
pageNotFound_title: 'Страница не найдена',
|
||||
password: 'Пароль',
|
||||
projectManagement: 'Управление проектами',
|
||||
serverConnectionFailed: 'Не могу подключиться к серверу',
|
||||
unknownError: 'Что-то пошло не так, попробуйте позже',
|
||||
useSingleSignOn: 'Используйте единый вход',
|
||||
},
|
||||
|
||||
action: {
|
||||
logIn: 'Войти',
|
||||
logInWithSSO: 'Войти с помощью единого входа',
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
@@ -0,0 +1,237 @@
|
||||
import dateFns from 'date-fns/locale/zh-TW';
|
||||
|
||||
export default {
|
||||
dateFns,
|
||||
|
||||
format: {
|
||||
date: 'M/d/yyyy',
|
||||
time: 'p',
|
||||
dateTime: '$t(format:date) $t(format:time)',
|
||||
longDate: 'MMM d',
|
||||
longDateTime: "MMMM d 'at' p",
|
||||
fullDate: 'MMM d, y',
|
||||
fullDateTime: "MMMM d, y 'at' p",
|
||||
},
|
||||
|
||||
translation: {
|
||||
common: {
|
||||
aboutPlanka: '關於 Planka',
|
||||
account: '帳號',
|
||||
actions: '操作',
|
||||
addAttachment_title: '添加附件',
|
||||
addComment: '添加評論',
|
||||
addManager_title: '添加管理員',
|
||||
addMember_title: '添加成員',
|
||||
addUser_title: '添加使用者',
|
||||
administrator: '管理員',
|
||||
all: '全部',
|
||||
allChangesWillBeAutomaticallySavedAfterConnectionRestored: '所有修改會在重新連線後自動保存',
|
||||
areYouSureYouWantToDeleteThisAttachment: '確認刪除此附件嗎?',
|
||||
areYouSureYouWantToDeleteThisBoard: '確認刪除此看板嗎?',
|
||||
areYouSureYouWantToDeleteThisCard: '確認刪除此卡片嗎?',
|
||||
areYouSureYouWantToDeleteThisComment: '確認刪除此評論嗎?',
|
||||
areYouSureYouWantToDeleteThisLabel: '確認刪除此標籤嗎?',
|
||||
areYouSureYouWantToDeleteThisList: '確認刪除此列表嗎?',
|
||||
areYouSureYouWantToDeleteThisProject: '確認刪除此專案嗎?',
|
||||
areYouSureYouWantToDeleteThisTask: '確認刪除此任務嗎?',
|
||||
areYouSureYouWantToDeleteThisUser: '確認刪除此使用者嗎?',
|
||||
areYouSureYouWantToLeaveBoard: '確認離開此看板嗎?',
|
||||
areYouSureYouWantToLeaveProject: '確認離開此專案嗎?',
|
||||
areYouSureYouWantToRemoveThisManagerFromProject: '確認從此專案中刪除該管理員嗎?',
|
||||
areYouSureYouWantToRemoveThisMemberFromBoard: '確認從此看板中刪除該成員嗎?',
|
||||
attachment: '附件',
|
||||
attachments: '附件',
|
||||
authentication: '驗證',
|
||||
background: '背景',
|
||||
board: '看板',
|
||||
boardNotFound_title: '看板不存在',
|
||||
canComment: '可以評論',
|
||||
canEditContentOfBoard: '可以編輯看板內容',
|
||||
canOnlyViewBoard: '僅可查看看板',
|
||||
cardActions_title: '卡片操作',
|
||||
cardNotFound_title: '卡片不存在',
|
||||
cardOrActionAreDeleted: '卡片或操作已經被刪除',
|
||||
color: '顏色',
|
||||
createBoard_title: '創建看板',
|
||||
createLabel_title: '創建標籤',
|
||||
createNewOneOrSelectExistingOne: '創建一個新的或選擇一個已創建的',
|
||||
createProject_title: '創建專案',
|
||||
createTextFile_title: '創建文本文件',
|
||||
currentPassword: '當前密碼',
|
||||
dangerZone_title: '危險區域',
|
||||
date: '日期',
|
||||
dueDate_title: '截止日期',
|
||||
deleteAttachment_title: '刪除附件',
|
||||
deleteBoard_title: '刪除看板',
|
||||
deleteCard_title: '刪除卡片',
|
||||
deleteComment_title: '刪除評論',
|
||||
deleteLabel_title: '刪除標籤',
|
||||
deleteList_title: '刪除列表',
|
||||
deleteProject_title: '刪除專案',
|
||||
deleteTask_title: '刪除任務',
|
||||
deleteUser_title: '刪除使用者',
|
||||
description: '描述',
|
||||
detectAutomatically: '自動偵測',
|
||||
dropFileToUpload: '拖放文件以上傳',
|
||||
editor: '編輯器',
|
||||
editAttachment_title: '編輯附件',
|
||||
editAvatar_title: '編輯頭像',
|
||||
editBoard_title: '編輯看板',
|
||||
editDueDate_title: '編輯截止時間',
|
||||
editEmail_title: '編輯郵箱',
|
||||
editInformation_title: '編輯信息',
|
||||
editLabel_title: '編輯標籤',
|
||||
editPassword_title: '修改密碼',
|
||||
editPermissions_title: '修改權限',
|
||||
editStopwatch_title: '修改計時',
|
||||
editUsername_title: '修改使用者名稱',
|
||||
email: '郵箱',
|
||||
emailAlreadyInUse: '郵箱已被使用',
|
||||
enterCardTitle: '輸入卡片標題...',
|
||||
enterDescription: '輸入描述...',
|
||||
enterFilename: '輸入文件名',
|
||||
enterListTitle: '輸入列表標題...',
|
||||
enterProjectTitle: '輸入專案標題',
|
||||
enterTaskDescription: '輸入任務描述...',
|
||||
filterByLabels_title: '通過標籤篩選',
|
||||
filterByMembers_title: '通過成員篩選',
|
||||
fromComputer_title: '來自電腦',
|
||||
fromTrello: '來自 Trello',
|
||||
general: '通用',
|
||||
hours: '小時',
|
||||
importBoard_title: '導入看板',
|
||||
invalidCurrentPassword: '當前密碼錯誤',
|
||||
labels: '標籤',
|
||||
language: '語言',
|
||||
leaveBoard_title: '離開看板',
|
||||
leaveProject_title: '離開專案',
|
||||
list: '列表',
|
||||
listActions_title: '列表操作',
|
||||
managers: '管理員',
|
||||
members: '成員',
|
||||
minutes: '分鐘',
|
||||
moveCard_title: '移動卡片',
|
||||
name: '姓名',
|
||||
newEmail: '新郵箱',
|
||||
newPassword: '新密碼',
|
||||
newUsername: '新使用者名稱',
|
||||
noConnectionToServer: '未連接到伺服器',
|
||||
noBoards: '沒有看板',
|
||||
noLists: '沒有列表',
|
||||
noProjects: '沒有專案',
|
||||
notifications: '通知',
|
||||
noUnreadNotifications: '沒有未讀通知',
|
||||
openBoard_title: '打開看板',
|
||||
optional_inline: '可選的',
|
||||
organization: '組織機構',
|
||||
phone: '電話',
|
||||
preferences: '偏好設定',
|
||||
pressPasteShortcutToAddAttachmentFromClipboard:
|
||||
'提示: 按下 Ctrl-V (Mac: Cmd-V) 從剪貼簿添加附件',
|
||||
project: '專案',
|
||||
projectNotFound_title: '專案未找到',
|
||||
removeManager_title: '刪除管理員',
|
||||
removeMember_title: '刪除成員',
|
||||
searchLabels: '搜尋標籤...',
|
||||
searchMembers: '搜尋成員...',
|
||||
searchUsers: '搜尋使用者...',
|
||||
seconds: '秒',
|
||||
selectBoard: '選擇看板',
|
||||
selectList: '選擇列表',
|
||||
selectPermissions_title: '選擇權限',
|
||||
selectProject: '選擇專案',
|
||||
settings: '設置',
|
||||
stopwatch: '碼表',
|
||||
subscribeToMyOwnCardsByDefault: '默認訂閱自己創建的卡片',
|
||||
taskActions_title: '任務操作',
|
||||
tasks: '任務',
|
||||
thereIsNoPreviewAvailableForThisAttachment: '此附件無法預覽',
|
||||
time: '時間',
|
||||
title: '標題',
|
||||
userActions_title: '使用者操作',
|
||||
userAddedThisCardToList: '<0>{{user}}</0><1> 向列表 {{list}} 添加了該卡片</1>',
|
||||
userLeftNewCommentToCard: '{{user}} 給 {{card}} 添加了一條新評論 「{{comment}}」',
|
||||
userMovedCardFromListToList:
|
||||
'{{user}} 將卡片 <2>{{card}}</2> 從 {{fromList}} 移動到 {{toList}}',
|
||||
userMovedThisCardFromListToList:
|
||||
'<0>{{user}}</0><1> 將該卡片從 {{fromList}} 移動到 {{toList}}</1>',
|
||||
username: '使用者名稱',
|
||||
usernameAlreadyInUse: '使用者名稱已被佔用',
|
||||
users: '使用者',
|
||||
version: '版本',
|
||||
viewer: '檢視',
|
||||
writeComment: '編寫評論...',
|
||||
},
|
||||
|
||||
action: {
|
||||
addAnotherCard: '添加另一個卡片',
|
||||
addAnotherList: '添加另一個列表',
|
||||
addAnotherTask: '添加另一個任務',
|
||||
addCard: '添加卡片',
|
||||
addCard_title: '添加卡片',
|
||||
addComment: '添加評論',
|
||||
addList: '添加列表',
|
||||
addMember: '添加成員',
|
||||
addMoreDetailedDescription: '添加更多詳細描述',
|
||||
addTask: '添加任務',
|
||||
addToCard: '添加到卡片',
|
||||
addUser: '添加使用者',
|
||||
createBoard: '創建看板',
|
||||
createFile: '創建文件',
|
||||
createLabel: '創建標籤',
|
||||
createNewLabel: '創建新標籤',
|
||||
createProject: '創建專案',
|
||||
delete: '刪除',
|
||||
deleteAttachment: '刪除附件',
|
||||
deleteAvatar: '刪除頭像',
|
||||
deleteBoard: '刪除看板',
|
||||
deleteCard: '刪除卡片',
|
||||
deleteCard_title: '刪除卡片',
|
||||
deleteComment: '刪除評論',
|
||||
deleteImage: '刪除圖片',
|
||||
deleteLabel: '刪除標籤',
|
||||
deleteList: '刪除列表',
|
||||
deleteList_title: '刪除列表',
|
||||
deleteProject: '刪除專案',
|
||||
deleteProject_title: '刪除專案',
|
||||
deleteTask: '刪除任務',
|
||||
deleteTask_title: '刪除任務',
|
||||
deleteUser: '刪除使用者',
|
||||
edit: '編輯',
|
||||
editDueDate_title: '編輯截止時間',
|
||||
editDescription_title: '編輯描述',
|
||||
editEmail_title: '編輯郵箱',
|
||||
editInformation_title: '編輯信息',
|
||||
editPassword_title: '編輯密碼',
|
||||
editPermissions: '編輯權限',
|
||||
editStopwatch_title: '編輯碼表',
|
||||
editTitle_title: '編輯標題',
|
||||
editUsername_title: '編輯使用者名稱',
|
||||
hideDetails: '隱藏詳情',
|
||||
import: '導入',
|
||||
leaveBoard: '離開看板',
|
||||
leaveProject: '離開專案',
|
||||
logOut_title: '登出',
|
||||
makeCover_title: '設置封面',
|
||||
move: '移動',
|
||||
moveCard_title: '移動卡片',
|
||||
remove: '刪除',
|
||||
removeBackground: '刪除背景',
|
||||
removeCover_title: '刪除封面',
|
||||
removeFromBoard: '從看板中刪除',
|
||||
removeFromProject: '從專案中刪除',
|
||||
removeManager: '刪除管理員',
|
||||
removeMember: '刪除成員',
|
||||
save: '保存',
|
||||
showAllAttachments: '顯示所有附件 ({{hidden}} 隱藏)',
|
||||
showDetails: '顯示詳情',
|
||||
showFewerAttachments: '顯示較少附件',
|
||||
start: '開始',
|
||||
stop: '結束',
|
||||
subscribe: '訂閱',
|
||||
unsubscribe: '取消訂閱',
|
||||
uploadNewAvatar: '上傳新頭像',
|
||||
uploadNewImage: '上傳圖片',
|
||||
},
|
||||
},
|
||||
};
|
||||
@@ -0,0 +1,8 @@
|
||||
import login from './login';
|
||||
|
||||
export default {
|
||||
language: 'zh-TW',
|
||||
country: 'tw',
|
||||
name: '繁體中文',
|
||||
embeddedLocale: login,
|
||||
};
|
||||
@@ -0,0 +1,22 @@
|
||||
export default {
|
||||
translation: {
|
||||
common: {
|
||||
emailOrUsername: '郵箱或使用者名稱',
|
||||
invalidEmailOrUsername: '無效的郵箱或使用者名稱',
|
||||
invalidPassword: '密碼錯誤',
|
||||
logInToPlanka: '登入至 Planka',
|
||||
noInternetConnection: '沒有網路連接',
|
||||
pageNotFound_title: '找不到頁面',
|
||||
password: '密碼',
|
||||
projectManagement: '專案管理',
|
||||
serverConnectionFailed: '伺服器連接失敗',
|
||||
unknownError: '未知錯誤,請稍後重試',
|
||||
useSingleSignOn: '使用單一登入',
|
||||
},
|
||||
|
||||
action: {
|
||||
logIn: '登入',
|
||||
logInWithSSO: '使用SSO登入',
|
||||
},
|
||||
},
|
||||
};
|
||||
@@ -20,6 +20,7 @@ export default class extends BaseModel {
|
||||
relatedName: 'ownCards',
|
||||
}),
|
||||
dueDate: attr(),
|
||||
isDueDateCompleted: attr(),
|
||||
stopwatch: attr(),
|
||||
isSubscribed: attr({
|
||||
getDefault: () => false,
|
||||
@@ -208,7 +209,16 @@ export default class extends BaseModel {
|
||||
if (payload.data.boardId && payload.data.boardId !== cardModel.boardId) {
|
||||
cardModel.deleteWithRelated();
|
||||
} else {
|
||||
cardModel.update(payload.data);
|
||||
cardModel.update({
|
||||
...payload.data,
|
||||
...(payload.data.dueDate === null && {
|
||||
isDueDateCompleted: null,
|
||||
}),
|
||||
...(payload.data.dueDate &&
|
||||
!cardModel.dueDate && {
|
||||
isDueDateCompleted: false,
|
||||
}),
|
||||
});
|
||||
}
|
||||
|
||||
break;
|
||||
@@ -248,6 +258,7 @@ export default class extends BaseModel {
|
||||
'name',
|
||||
'description',
|
||||
'dueDate',
|
||||
'isDueDateCompleted',
|
||||
'stopwatch',
|
||||
]),
|
||||
...payload.card,
|
||||
|
||||
@@ -6,8 +6,8 @@
|
||||
border: 0;
|
||||
color: #444444;
|
||||
font-size: 14px;
|
||||
font-family: "Museo Sans", "Helvetica Neue", Arial, Helvetica, sans-serif;
|
||||
font-weight: 400;
|
||||
font-family: "Nunitoga", "Helvetica Neue", Arial, Helvetica, sans-serif;
|
||||
// font-weight: 400;
|
||||
width: 100%;
|
||||
padding-bottom: 8px;
|
||||
}
|
||||
@@ -19,7 +19,7 @@
|
||||
.react-datepicker__current-month,
|
||||
.react-datepicker-time__header {
|
||||
color: #444;
|
||||
font-weight: 500;
|
||||
font-weight: normal;
|
||||
font-size: 14px;
|
||||
line-height: 32px;
|
||||
padding-bottom: 4px;
|
||||
@@ -38,7 +38,7 @@
|
||||
color: #444;
|
||||
display: inline-block;
|
||||
width: 40px;
|
||||
font-weight: 500;
|
||||
font-weight: normal;
|
||||
line-height: 28px;
|
||||
text-align: center;
|
||||
margin: 0;
|
||||
|
||||
@@ -0,0 +1 @@
|
||||
export default '1.22.0';
|
||||
@@ -0,0 +1 @@
|
||||
export default '<%= pkg.version %>';
|
||||
@@ -24,6 +24,8 @@ services:
|
||||
# Configure knex to accept SSL certificates
|
||||
# - KNEX_REJECT_UNAUTHORIZED_SSL_CERTIFICATE=false
|
||||
|
||||
# - SHOW_DETAILED_AUTH_ERRORS=false # Set to true to show more detailed authentication error messages. It should not be enabled without a rate limiter for security reasons.
|
||||
|
||||
# - ALLOW_ALL_TO_CREATE_PROJECTS=true
|
||||
|
||||
# - OIDC_ISSUER=
|
||||
@@ -35,6 +37,7 @@ services:
|
||||
# - OIDC_RESPONSE_MODE=fragment
|
||||
# - OIDC_USE_DEFAULT_RESPONSE_MODE=true
|
||||
# - OIDC_ADMIN_ROLES=admin
|
||||
# - OIDC_CLAIMS_SOURCE=userinfo
|
||||
# - OIDC_EMAIL_ATTRIBUTE=email
|
||||
# - OIDC_NAME_ATTRIBUTE=name
|
||||
# - OIDC_USERNAME_ATTRIBUTE=preferred_username
|
||||
@@ -117,7 +120,7 @@ services:
|
||||
- "5432:5432"
|
||||
restart: unless-stopped
|
||||
healthcheck:
|
||||
test: ["CMD-SHELL", "pg_isready -U postgres -d planka"]
|
||||
test: ["CMD-SHELL", "pg_isready -U user -d planka_db"]
|
||||
interval: 10s
|
||||
timeout: 5s
|
||||
retries: 5
|
||||
|
||||
@@ -31,6 +31,8 @@ services:
|
||||
# - DEFAULT_ADMIN_NAME=Demo Demo
|
||||
# - DEFAULT_ADMIN_USERNAME=demo
|
||||
|
||||
# - SHOW_DETAILED_AUTH_ERRORS=false # Set to true to show more detailed authentication error messages. It should not be enabled without a rate limiter for security reasons.
|
||||
|
||||
# - ALLOW_ALL_TO_CREATE_PROJECTS=true
|
||||
|
||||
# - OIDC_ISSUER=
|
||||
@@ -42,6 +44,7 @@ services:
|
||||
# - OIDC_RESPONSE_MODE=fragment
|
||||
# - OIDC_USE_DEFAULT_RESPONSE_MODE=true
|
||||
# - OIDC_ADMIN_ROLES=admin
|
||||
# - OIDC_CLAIMS_SOURCE=userinfo
|
||||
# - OIDC_EMAIL_ATTRIBUTE=email
|
||||
# - OIDC_NAME_ATTRIBUTE=name
|
||||
# - OIDC_USERNAME_ATTRIBUTE=preferred_username
|
||||
@@ -70,6 +73,7 @@ services:
|
||||
|
||||
# - SLACK_BOT_TOKEN=
|
||||
# - SLACK_CHANNEL_ID=
|
||||
# - GOOGLE_CHAT_WEBHOOK_URL=
|
||||
depends_on:
|
||||
postgres:
|
||||
condition: service_healthy
|
||||
|
||||
Generated
+259
-137
@@ -1,30 +1,31 @@
|
||||
{
|
||||
"name": "planka",
|
||||
"version": "1.20.1",
|
||||
"version": "1.22.0",
|
||||
"lockfileVersion": 3,
|
||||
"requires": true,
|
||||
"packages": {
|
||||
"": {
|
||||
"name": "planka",
|
||||
"version": "1.20.1",
|
||||
"version": "1.22.0",
|
||||
"hasInstallScript": true,
|
||||
"license": "AGPL-3.0",
|
||||
"dependencies": {
|
||||
"concurrently": "^8.2.2",
|
||||
"husky": "^9.0.1",
|
||||
"lint-staged": "^15.2.5"
|
||||
"genversion": "^3.2.0",
|
||||
"husky": "^9.1.6",
|
||||
"lint-staged": "^15.2.10"
|
||||
},
|
||||
"devDependencies": {
|
||||
"eslint": "^8.57.0",
|
||||
"eslint-config-prettier": "^9.1.0",
|
||||
"eslint-plugin-prettier": "^5.1.3",
|
||||
"prettier": "^3.3.0"
|
||||
"eslint-plugin-prettier": "^5.2.1",
|
||||
"prettier": "^3.3.3"
|
||||
}
|
||||
},
|
||||
"node_modules/@babel/runtime": {
|
||||
"version": "7.24.6",
|
||||
"resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.24.6.tgz",
|
||||
"integrity": "sha512-Ja18XcETdEl5mzzACGd+DKgaGJzPTCow7EglgwTmHdwokzDFYh/MHua6lU6DV/hjF2IaOJ4oX2nqnjG7RElKOw==",
|
||||
"version": "7.25.6",
|
||||
"resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.25.6.tgz",
|
||||
"integrity": "sha512-VBj9MYyDb9tuLq7yzqjgzt6Q+IBQLrGZfdjOekyEirZPHxXWoTSGUTMrpsfi58Up73d13NfYLv8HT9vmznjzhQ==",
|
||||
"dependencies": {
|
||||
"regenerator-runtime": "^0.14.0"
|
||||
},
|
||||
@@ -48,9 +49,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@eslint-community/regexpp": {
|
||||
"version": "4.10.0",
|
||||
"resolved": "https://registry.npmjs.org/@eslint-community/regexpp/-/regexpp-4.10.0.tgz",
|
||||
"integrity": "sha512-Cu96Sd2By9mCNTx2iyKOmq10v22jUVQv0lQnlGNy16oE9589yE+QADPbrMGCkA51cKZSg3Pu/aTJVTGfL/qjUA==",
|
||||
"version": "4.11.1",
|
||||
"resolved": "https://registry.npmjs.org/@eslint-community/regexpp/-/regexpp-4.11.1.tgz",
|
||||
"integrity": "sha512-m4DVN9ZqskZoLU5GlWZadwDnYo3vAEydiUayB9widCl9ffWx2IvPnp6n3on5rJmziJSw9Bv+Z3ChDVdMwXCY8Q==",
|
||||
"dev": true,
|
||||
"engines": {
|
||||
"node": "^12.0.0 || ^14.0.0 || >=16.0.0"
|
||||
@@ -92,6 +93,7 @@
|
||||
"version": "0.11.14",
|
||||
"resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.11.14.tgz",
|
||||
"integrity": "sha512-3T8LkOmg45BV5FICb15QQMsyUSWrQ8AygVfC7ZG32zOalnqrilm018ZVCw0eapXux8FtA33q8PSRSstjee3jSg==",
|
||||
"deprecated": "Use @eslint/config-array instead",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"@humanwhocodes/object-schema": "^2.0.2",
|
||||
@@ -119,6 +121,7 @@
|
||||
"version": "2.0.3",
|
||||
"resolved": "https://registry.npmjs.org/@humanwhocodes/object-schema/-/object-schema-2.0.3.tgz",
|
||||
"integrity": "sha512-93zYdMES/c1D69yZiKDBj0V24vqNzB/koF26KPaagAfd3P/4gUlh3Dys5ogAK+Exi9QyzlD8x/08Zt7wIKcDcA==",
|
||||
"deprecated": "Use @eslint/object-schema instead",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/@nodelib/fs.scandir": {
|
||||
@@ -175,9 +178,9 @@
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/acorn": {
|
||||
"version": "8.11.3",
|
||||
"resolved": "https://registry.npmjs.org/acorn/-/acorn-8.11.3.tgz",
|
||||
"integrity": "sha512-Y9rRfJG5jcKOE0CLisYbojUjIrIEE7AGMzA/Sm4BslANhbS+cDMpgBdcPT91oJ7OuJ9hYJBx59RjbhxVnrF8Xg==",
|
||||
"version": "8.12.1",
|
||||
"resolved": "https://registry.npmjs.org/acorn/-/acorn-8.12.1.tgz",
|
||||
"integrity": "sha512-tcpGyI9zbizT9JbV6oYE477V6mTlXvvi0T0G3SNIYE2apm/G5huBa1+K89VGeovbg+jycCrfhl3ADxErOuO6Jg==",
|
||||
"dev": true,
|
||||
"bin": {
|
||||
"acorn": "bin/acorn"
|
||||
@@ -212,11 +215,14 @@
|
||||
}
|
||||
},
|
||||
"node_modules/ansi-escapes": {
|
||||
"version": "6.2.1",
|
||||
"resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-6.2.1.tgz",
|
||||
"integrity": "sha512-4nJ3yixlEthEJ9Rk4vPcdBRkZvQZlYyu8j4/Mqz5sgIkddmEnH2Yj2ZrnP9S3tQOvSNRUIgVNF/1yPpRAGNRig==",
|
||||
"version": "7.0.0",
|
||||
"resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-7.0.0.tgz",
|
||||
"integrity": "sha512-GdYO7a61mR0fOlAsvC9/rIHf7L96sBc6dEWzeOu+KAea5bZyQRPIpojrVoI4AXGJS/ycu/fBTdLrUkA4ODrvjw==",
|
||||
"dependencies": {
|
||||
"environment": "^1.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=14.16"
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
@@ -250,17 +256,20 @@
|
||||
"integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/async": {
|
||||
"version": "3.2.6",
|
||||
"resolved": "https://registry.npmjs.org/async/-/async-3.2.6.tgz",
|
||||
"integrity": "sha512-htCUDlxyyCLMgaM3xXg0C0LW2xqfuQ6p05pCEIsXuyQ+a1koYKTuBMzRNwmybfLgvJDMd0r1LTn4+E0Ti6C2AA=="
|
||||
},
|
||||
"node_modules/balanced-match": {
|
||||
"version": "1.0.2",
|
||||
"resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz",
|
||||
"integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==",
|
||||
"dev": true
|
||||
"integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw=="
|
||||
},
|
||||
"node_modules/brace-expansion": {
|
||||
"version": "1.1.11",
|
||||
"resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz",
|
||||
"integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"balanced-match": "^1.0.0",
|
||||
"concat-map": "0.0.1"
|
||||
@@ -313,14 +322,14 @@
|
||||
}
|
||||
},
|
||||
"node_modules/cli-cursor": {
|
||||
"version": "4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-4.0.0.tgz",
|
||||
"integrity": "sha512-VGtlMu3x/4DOtIUwEkRezxUZ2lBacNJCHash0N0WeZDBS+7Ux1dm3XWAgWYxLJFMMdOeXMHXorshEFhbMSGelg==",
|
||||
"version": "5.0.0",
|
||||
"resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-5.0.0.tgz",
|
||||
"integrity": "sha512-aCj4O5wKyszjMmDT4tZj93kxyydN/K5zPWSCe6/0AV/AA1pqe5ZBIw0a2ZfPQV7lL5/yb5HsUreJ6UFAF1tEQw==",
|
||||
"dependencies": {
|
||||
"restore-cursor": "^4.0.0"
|
||||
"restore-cursor": "^5.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": "^12.20.0 || ^14.13.1 || >=16.0.0"
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
@@ -418,18 +427,17 @@
|
||||
"integrity": "sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w=="
|
||||
},
|
||||
"node_modules/commander": {
|
||||
"version": "12.1.0",
|
||||
"resolved": "https://registry.npmjs.org/commander/-/commander-12.1.0.tgz",
|
||||
"integrity": "sha512-Vw8qHK3bZM9y/P10u3Vib8o/DdkvA2OtPtZvD871QKjy74Wj1WSKFILMPRPSdUSx5RFK1arlJzEtA4PkFgnbuA==",
|
||||
"version": "7.2.0",
|
||||
"resolved": "https://registry.npmjs.org/commander/-/commander-7.2.0.tgz",
|
||||
"integrity": "sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw==",
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
"node": ">= 10"
|
||||
}
|
||||
},
|
||||
"node_modules/concat-map": {
|
||||
"version": "0.0.1",
|
||||
"resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz",
|
||||
"integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==",
|
||||
"dev": true
|
||||
"integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg=="
|
||||
},
|
||||
"node_modules/concurrently": {
|
||||
"version": "8.2.2",
|
||||
@@ -486,11 +494,11 @@
|
||||
}
|
||||
},
|
||||
"node_modules/debug": {
|
||||
"version": "4.3.5",
|
||||
"resolved": "https://registry.npmjs.org/debug/-/debug-4.3.5.tgz",
|
||||
"integrity": "sha512-pt0bNEmneDIvdL1Xsd9oDQ/wrQRkXDT4AUWlNZNPKvW5x/jyO9VFXkJUP07vQ2upmw5PlaITaPKc31jK13V+jg==",
|
||||
"version": "4.3.7",
|
||||
"resolved": "https://registry.npmjs.org/debug/-/debug-4.3.7.tgz",
|
||||
"integrity": "sha512-Er2nc/H7RrMXZBFCEim6TCmMk02Z8vLC2Rbi1KEBggpo0fS6l0S1nnapwmIi3yW/+GOJap1Krg4w0Hg80oCqgQ==",
|
||||
"dependencies": {
|
||||
"ms": "2.1.2"
|
||||
"ms": "^2.1.3"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=6.0"
|
||||
@@ -519,15 +527,40 @@
|
||||
"node": ">=6.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/ejs": {
|
||||
"version": "3.1.10",
|
||||
"resolved": "https://registry.npmjs.org/ejs/-/ejs-3.1.10.tgz",
|
||||
"integrity": "sha512-UeJmFfOrAQS8OJWPZ4qtgHyWExa088/MtK5UEyoJGFH67cDEXkZSviOiKRCZ4Xij0zxI3JECgYs3oKx+AizQBA==",
|
||||
"dependencies": {
|
||||
"jake": "^10.8.5"
|
||||
},
|
||||
"bin": {
|
||||
"ejs": "bin/cli.js"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=0.10.0"
|
||||
}
|
||||
},
|
||||
"node_modules/emoji-regex": {
|
||||
"version": "10.3.0",
|
||||
"resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-10.3.0.tgz",
|
||||
"integrity": "sha512-QpLs9D9v9kArv4lfDEgg1X/gN5XLnf/A6l9cs8SPZLRZR3ZkY9+kwIQTxm+fsSej5UMYGE8fdoaZVIBlqG0XTw=="
|
||||
"version": "10.4.0",
|
||||
"resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-10.4.0.tgz",
|
||||
"integrity": "sha512-EC+0oUMY1Rqm4O6LLrgjtYDvcVYTy7chDnM4Q7030tP4Kwj3u/pR6gP9ygnp2CJMK5Gq+9Q2oqmrFJAz01DXjw=="
|
||||
},
|
||||
"node_modules/environment": {
|
||||
"version": "1.1.0",
|
||||
"resolved": "https://registry.npmjs.org/environment/-/environment-1.1.0.tgz",
|
||||
"integrity": "sha512-xUtoPkMggbz0MPyPiIWr1Kp4aeWJjDZ6SMvURhimjdZgsRuDplF5/s9hcgGhyXMhs+6vpnuoiZ2kFiu3FMnS8Q==",
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/escalade": {
|
||||
"version": "3.1.2",
|
||||
"resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.2.tgz",
|
||||
"integrity": "sha512-ErCHMCae19vR8vQGe50xIsVomy19rg6gFu3+r3jkEO46suLMWBksvVyoGgQV+jOfl84ZSOSlmv6Gxa89PmTGmA==",
|
||||
"version": "3.2.0",
|
||||
"resolved": "https://registry.npmjs.org/escalade/-/escalade-3.2.0.tgz",
|
||||
"integrity": "sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==",
|
||||
"engines": {
|
||||
"node": ">=6"
|
||||
}
|
||||
@@ -612,13 +645,13 @@
|
||||
}
|
||||
},
|
||||
"node_modules/eslint-plugin-prettier": {
|
||||
"version": "5.1.3",
|
||||
"resolved": "https://registry.npmjs.org/eslint-plugin-prettier/-/eslint-plugin-prettier-5.1.3.tgz",
|
||||
"integrity": "sha512-C9GCVAs4Eq7ZC/XFQHITLiHJxQngdtraXaM+LoUFoFp/lHNl2Zn8f3WQbe9HvTBBQ9YnKFB0/2Ajdqwo5D1EAw==",
|
||||
"version": "5.2.1",
|
||||
"resolved": "https://registry.npmjs.org/eslint-plugin-prettier/-/eslint-plugin-prettier-5.2.1.tgz",
|
||||
"integrity": "sha512-gH3iR3g4JfF+yYPaJYkN7jEl9QbweL/YfkoRlNnuIEHEz1vHVlCmWOS+eGGiRuzHQXdJFCOTxRgvju9b8VUmrw==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"prettier-linter-helpers": "^1.0.0",
|
||||
"synckit": "^0.8.6"
|
||||
"synckit": "^0.9.1"
|
||||
},
|
||||
"engines": {
|
||||
"node": "^14.18.0 || >=16.0.0"
|
||||
@@ -687,9 +720,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/esquery": {
|
||||
"version": "1.5.0",
|
||||
"resolved": "https://registry.npmjs.org/esquery/-/esquery-1.5.0.tgz",
|
||||
"integrity": "sha512-YQLXUplAwJgCydQ78IMJywZCceoqk1oH01OERdSAJc/7U2AylwjhSCLDEtqwg811idIS/9fIU5GjG73IgjKMVg==",
|
||||
"version": "1.6.0",
|
||||
"resolved": "https://registry.npmjs.org/esquery/-/esquery-1.6.0.tgz",
|
||||
"integrity": "sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"estraverse": "^5.1.0"
|
||||
@@ -800,6 +833,33 @@
|
||||
"node": "^10.12.0 || >=12.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/filelist": {
|
||||
"version": "1.0.4",
|
||||
"resolved": "https://registry.npmjs.org/filelist/-/filelist-1.0.4.tgz",
|
||||
"integrity": "sha512-w1cEuf3S+DrLCQL7ET6kz+gmlJdbq9J7yXCSjK/OZCPA+qEN1WyF4ZAf0YYJa4/shHJra2t/d/r8SV4Ji+x+8Q==",
|
||||
"dependencies": {
|
||||
"minimatch": "^5.0.1"
|
||||
}
|
||||
},
|
||||
"node_modules/filelist/node_modules/brace-expansion": {
|
||||
"version": "2.0.1",
|
||||
"resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz",
|
||||
"integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==",
|
||||
"dependencies": {
|
||||
"balanced-match": "^1.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/filelist/node_modules/minimatch": {
|
||||
"version": "5.1.6",
|
||||
"resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.6.tgz",
|
||||
"integrity": "sha512-lKwV/1brpG6mBUFHtb7NUmtABCb2WZZmm2wNiOA5hAb8VdCS4B3dtMWyvcoViccwAW/COERjXLt0zP1zXUN26g==",
|
||||
"dependencies": {
|
||||
"brace-expansion": "^2.0.1"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=10"
|
||||
}
|
||||
},
|
||||
"node_modules/fill-range": {
|
||||
"version": "7.1.1",
|
||||
"resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.1.1.tgz",
|
||||
@@ -811,6 +871,14 @@
|
||||
"node": ">=8"
|
||||
}
|
||||
},
|
||||
"node_modules/find-package": {
|
||||
"version": "1.0.0",
|
||||
"resolved": "https://registry.npmjs.org/find-package/-/find-package-1.0.0.tgz",
|
||||
"integrity": "sha512-yVn71XCCaNgxz58ERTl8nA/8YYtIQDY9mHSrgFBfiFtdNNfY0h183Vh8BRkKxD8x9TUw3ec290uJKhDVxqGZBw==",
|
||||
"dependencies": {
|
||||
"parents": "^1.0.1"
|
||||
}
|
||||
},
|
||||
"node_modules/find-up": {
|
||||
"version": "5.0.0",
|
||||
"resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz",
|
||||
@@ -853,6 +921,22 @@
|
||||
"integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/genversion": {
|
||||
"version": "3.2.0",
|
||||
"resolved": "https://registry.npmjs.org/genversion/-/genversion-3.2.0.tgz",
|
||||
"integrity": "sha512-OIYSX6XYA8PHecLDCTri30hadSZfAjZ8Iq1+BBDXqLWP4dRLuJNLoNjsSWtTpw97IccK2LDWzkEstxAB8GdN7g==",
|
||||
"dependencies": {
|
||||
"commander": "^7.2.0",
|
||||
"ejs": "^3.1.9",
|
||||
"find-package": "^1.0.0"
|
||||
},
|
||||
"bin": {
|
||||
"genversion": "bin/genversion.js"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=10.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/get-caller-file": {
|
||||
"version": "2.0.5",
|
||||
"resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz",
|
||||
@@ -954,11 +1038,11 @@
|
||||
}
|
||||
},
|
||||
"node_modules/husky": {
|
||||
"version": "9.0.11",
|
||||
"resolved": "https://registry.npmjs.org/husky/-/husky-9.0.11.tgz",
|
||||
"integrity": "sha512-AB6lFlbwwyIqMdHYhwPe+kjOC3Oc5P3nThEoW/AaO2BX3vJDjWPFxYLxokUZOo6RNX20He3AaT8sESs9NJcmEw==",
|
||||
"version": "9.1.6",
|
||||
"resolved": "https://registry.npmjs.org/husky/-/husky-9.1.6.tgz",
|
||||
"integrity": "sha512-sqbjZKK7kf44hfdE94EoX8MZNk0n7HeW37O4YrVGCF4wzgQjp+akPAkfUK5LZ6KuR/6sqeAVuXHji+RzQgOn5A==",
|
||||
"bin": {
|
||||
"husky": "bin.mjs"
|
||||
"husky": "bin.js"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
@@ -968,9 +1052,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/ignore": {
|
||||
"version": "5.3.1",
|
||||
"resolved": "https://registry.npmjs.org/ignore/-/ignore-5.3.1.tgz",
|
||||
"integrity": "sha512-5Fytz/IraMjqpwfd34ke28PTVMjZjJG2MPn5t7OE4eUCUNf8BAa7b5WUS9/Qvr6mwOQS7Mk6vdsMno5he+T8Xw==",
|
||||
"version": "5.3.2",
|
||||
"resolved": "https://registry.npmjs.org/ignore/-/ignore-5.3.2.tgz",
|
||||
"integrity": "sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==",
|
||||
"dev": true,
|
||||
"engines": {
|
||||
"node": ">= 4"
|
||||
@@ -1083,6 +1167,23 @@
|
||||
"resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz",
|
||||
"integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw=="
|
||||
},
|
||||
"node_modules/jake": {
|
||||
"version": "10.9.2",
|
||||
"resolved": "https://registry.npmjs.org/jake/-/jake-10.9.2.tgz",
|
||||
"integrity": "sha512-2P4SQ0HrLQ+fw6llpLnOaGAvN2Zu6778SJMrCUwns4fOoG9ayrTiZk3VV8sCPkVZF8ab0zksVpS8FDY5pRCNBA==",
|
||||
"dependencies": {
|
||||
"async": "^3.2.3",
|
||||
"chalk": "^4.0.2",
|
||||
"filelist": "^1.0.4",
|
||||
"minimatch": "^3.1.2"
|
||||
},
|
||||
"bin": {
|
||||
"jake": "bin/cli.js"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=10"
|
||||
}
|
||||
},
|
||||
"node_modules/js-yaml": {
|
||||
"version": "4.1.0",
|
||||
"resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz",
|
||||
@@ -1136,9 +1237,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/lilconfig": {
|
||||
"version": "3.1.1",
|
||||
"resolved": "https://registry.npmjs.org/lilconfig/-/lilconfig-3.1.1.tgz",
|
||||
"integrity": "sha512-O18pf7nyvHTckunPWCV1XUNXU1piu01y2b7ATJ0ppkUkk8ocqVWBrYjJBCwHDjD/ZWcfyrA0P4gKhzWGi5EINQ==",
|
||||
"version": "3.1.2",
|
||||
"resolved": "https://registry.npmjs.org/lilconfig/-/lilconfig-3.1.2.tgz",
|
||||
"integrity": "sha512-eop+wDAvpItUys0FWkHIKeC9ybYrTGbU41U5K7+bttZZeohvnY7M9dZ5kB21GNWiFT2q1OoPTvncPCgSOVO5ow==",
|
||||
"engines": {
|
||||
"node": ">=14"
|
||||
},
|
||||
@@ -1147,20 +1248,20 @@
|
||||
}
|
||||
},
|
||||
"node_modules/lint-staged": {
|
||||
"version": "15.2.5",
|
||||
"resolved": "https://registry.npmjs.org/lint-staged/-/lint-staged-15.2.5.tgz",
|
||||
"integrity": "sha512-j+DfX7W9YUvdzEZl3Rk47FhDF6xwDBV5wwsCPw6BwWZVPYJemusQmvb9bRsW23Sqsaa+vRloAWogbK4BUuU2zA==",
|
||||
"version": "15.2.10",
|
||||
"resolved": "https://registry.npmjs.org/lint-staged/-/lint-staged-15.2.10.tgz",
|
||||
"integrity": "sha512-5dY5t743e1byO19P9I4b3x8HJwalIznL5E1FWYnU6OWw33KxNBSLAc6Cy7F2PsFEO8FKnLwjwm5hx7aMF0jzZg==",
|
||||
"dependencies": {
|
||||
"chalk": "~5.3.0",
|
||||
"commander": "~12.1.0",
|
||||
"debug": "~4.3.4",
|
||||
"debug": "~4.3.6",
|
||||
"execa": "~8.0.1",
|
||||
"lilconfig": "~3.1.1",
|
||||
"listr2": "~8.2.1",
|
||||
"micromatch": "~4.0.7",
|
||||
"lilconfig": "~3.1.2",
|
||||
"listr2": "~8.2.4",
|
||||
"micromatch": "~4.0.8",
|
||||
"pidtree": "~0.6.0",
|
||||
"string-argv": "~0.3.2",
|
||||
"yaml": "~2.4.2"
|
||||
"yaml": "~2.5.0"
|
||||
},
|
||||
"bin": {
|
||||
"lint-staged": "bin/lint-staged.js"
|
||||
@@ -1183,16 +1284,24 @@
|
||||
"url": "https://github.com/chalk/chalk?sponsor=1"
|
||||
}
|
||||
},
|
||||
"node_modules/lint-staged/node_modules/commander": {
|
||||
"version": "12.1.0",
|
||||
"resolved": "https://registry.npmjs.org/commander/-/commander-12.1.0.tgz",
|
||||
"integrity": "sha512-Vw8qHK3bZM9y/P10u3Vib8o/DdkvA2OtPtZvD871QKjy74Wj1WSKFILMPRPSdUSx5RFK1arlJzEtA4PkFgnbuA==",
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
},
|
||||
"node_modules/listr2": {
|
||||
"version": "8.2.1",
|
||||
"resolved": "https://registry.npmjs.org/listr2/-/listr2-8.2.1.tgz",
|
||||
"integrity": "sha512-irTfvpib/rNiD637xeevjO2l3Z5loZmuaRi0L0YE5LfijwVY96oyVn0DFD3o/teAok7nfobMG1THvvcHh/BP6g==",
|
||||
"version": "8.2.4",
|
||||
"resolved": "https://registry.npmjs.org/listr2/-/listr2-8.2.4.tgz",
|
||||
"integrity": "sha512-opevsywziHd3zHCVQGAj8zu+Z3yHNkkoYhWIGnq54RrCVwLz0MozotJEDnKsIBLvkfLGN6BLOyAeRrYI0pKA4g==",
|
||||
"dependencies": {
|
||||
"cli-truncate": "^4.0.0",
|
||||
"colorette": "^2.0.20",
|
||||
"eventemitter3": "^5.0.1",
|
||||
"log-update": "^6.0.0",
|
||||
"rfdc": "^1.3.1",
|
||||
"log-update": "^6.1.0",
|
||||
"rfdc": "^1.4.1",
|
||||
"wrap-ansi": "^9.0.0"
|
||||
},
|
||||
"engines": {
|
||||
@@ -1226,13 +1335,13 @@
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/log-update": {
|
||||
"version": "6.0.0",
|
||||
"resolved": "https://registry.npmjs.org/log-update/-/log-update-6.0.0.tgz",
|
||||
"integrity": "sha512-niTvB4gqvtof056rRIrTZvjNYE4rCUzO6X/X+kYjd7WFxXeJ0NwEFnRxX6ehkvv3jTwrXnNdtAak5XYZuIyPFw==",
|
||||
"version": "6.1.0",
|
||||
"resolved": "https://registry.npmjs.org/log-update/-/log-update-6.1.0.tgz",
|
||||
"integrity": "sha512-9ie8ItPR6tjY5uYJh8K/Zrv/RMZ5VOlOWvtZdEHYSTFKZfIBPQa9tOAEeAWhd+AnIneLJ22w5fjOYtoutpWq5w==",
|
||||
"dependencies": {
|
||||
"ansi-escapes": "^6.2.0",
|
||||
"cli-cursor": "^4.0.0",
|
||||
"slice-ansi": "^7.0.0",
|
||||
"ansi-escapes": "^7.0.0",
|
||||
"cli-cursor": "^5.0.0",
|
||||
"slice-ansi": "^7.1.0",
|
||||
"strip-ansi": "^7.1.0",
|
||||
"wrap-ansi": "^9.0.0"
|
||||
},
|
||||
@@ -1244,9 +1353,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/log-update/node_modules/ansi-regex": {
|
||||
"version": "6.0.1",
|
||||
"resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.0.1.tgz",
|
||||
"integrity": "sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA==",
|
||||
"version": "6.1.0",
|
||||
"resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.1.0.tgz",
|
||||
"integrity": "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
},
|
||||
@@ -1314,9 +1423,9 @@
|
||||
"integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w=="
|
||||
},
|
||||
"node_modules/micromatch": {
|
||||
"version": "4.0.7",
|
||||
"resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.7.tgz",
|
||||
"integrity": "sha512-LPP/3KorzCwBxfeUuZmaR6bG2kdeHSbe0P2tY3FLRU4vYrjYz5hI4QZwV0njUx3jeuKe67YukQ1LSPZBKDqO/Q==",
|
||||
"version": "4.0.8",
|
||||
"resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.8.tgz",
|
||||
"integrity": "sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==",
|
||||
"dependencies": {
|
||||
"braces": "^3.0.3",
|
||||
"picomatch": "^2.3.1"
|
||||
@@ -1336,11 +1445,21 @@
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/mimic-function": {
|
||||
"version": "5.0.1",
|
||||
"resolved": "https://registry.npmjs.org/mimic-function/-/mimic-function-5.0.1.tgz",
|
||||
"integrity": "sha512-VP79XUPxV2CigYP3jWwAUFSku2aKqBH7uTAapFWCBqutsbmDo96KY5o8uh6U+/YSIn5OxJnXp73beVkpqMIGhA==",
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/minimatch": {
|
||||
"version": "3.1.2",
|
||||
"resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz",
|
||||
"integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"brace-expansion": "^1.1.7"
|
||||
},
|
||||
@@ -1349,9 +1468,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/ms": {
|
||||
"version": "2.1.2",
|
||||
"resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz",
|
||||
"integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w=="
|
||||
"version": "2.1.3",
|
||||
"resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz",
|
||||
"integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA=="
|
||||
},
|
||||
"node_modules/natural-compare": {
|
||||
"version": "1.4.0",
|
||||
@@ -1466,6 +1585,14 @@
|
||||
"node": ">=6"
|
||||
}
|
||||
},
|
||||
"node_modules/parents": {
|
||||
"version": "1.0.1",
|
||||
"resolved": "https://registry.npmjs.org/parents/-/parents-1.0.1.tgz",
|
||||
"integrity": "sha512-mXKF3xkoUt5td2DoxpLmtOmZvko9VfFpwRwkKDHSNvgmpLAeBo18YDhcPbBzJq+QLCHMbGOfzia2cX4U+0v9Mg==",
|
||||
"dependencies": {
|
||||
"path-platform": "~0.11.15"
|
||||
}
|
||||
},
|
||||
"node_modules/path-exists": {
|
||||
"version": "4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz",
|
||||
@@ -1492,6 +1619,14 @@
|
||||
"node": ">=8"
|
||||
}
|
||||
},
|
||||
"node_modules/path-platform": {
|
||||
"version": "0.11.15",
|
||||
"resolved": "https://registry.npmjs.org/path-platform/-/path-platform-0.11.15.tgz",
|
||||
"integrity": "sha512-Y30dB6rab1A/nfEKsZxmr01nUotHX0c/ZiIAsCTatEe1CmS5Pm5He7fZ195bPT7RdquoaL8lLxFCMQi/bS7IJg==",
|
||||
"engines": {
|
||||
"node": ">= 0.8.0"
|
||||
}
|
||||
},
|
||||
"node_modules/picomatch": {
|
||||
"version": "2.3.1",
|
||||
"resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz",
|
||||
@@ -1524,9 +1659,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/prettier": {
|
||||
"version": "3.3.0",
|
||||
"resolved": "https://registry.npmjs.org/prettier/-/prettier-3.3.0.tgz",
|
||||
"integrity": "sha512-J9odKxERhCQ10OC2yb93583f6UnYutOeiV5i0zEDS7UGTdUt0u+y8erxl3lBKvwo/JHyyoEdXjwp4dke9oyZ/g==",
|
||||
"version": "3.3.3",
|
||||
"resolved": "https://registry.npmjs.org/prettier/-/prettier-3.3.3.tgz",
|
||||
"integrity": "sha512-i2tDNA0O5IrMO757lfrdQZCc2jPNDVntV0m/+4whiDfWaTKfMNgR7Qz0NAeGz/nRqF4m5/6CLzbP4/liHt12Ew==",
|
||||
"dev": true,
|
||||
"bin": {
|
||||
"prettier": "bin/prettier.cjs"
|
||||
@@ -1602,47 +1737,34 @@
|
||||
}
|
||||
},
|
||||
"node_modules/restore-cursor": {
|
||||
"version": "4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-4.0.0.tgz",
|
||||
"integrity": "sha512-I9fPXU9geO9bHOt9pHHOhOkYerIMsmVaWB0rA2AI9ERh/+x/i7MV5HKBNrg+ljO5eoPVgCcnFuRjJ9uH6I/3eg==",
|
||||
"version": "5.1.0",
|
||||
"resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-5.1.0.tgz",
|
||||
"integrity": "sha512-oMA2dcrw6u0YfxJQXm342bFKX/E4sG9rbTzO9ptUcR/e8A33cHuvStiYOwH7fszkZlZ1z/ta9AAoPk2F4qIOHA==",
|
||||
"dependencies": {
|
||||
"onetime": "^5.1.0",
|
||||
"signal-exit": "^3.0.2"
|
||||
"onetime": "^7.0.0",
|
||||
"signal-exit": "^4.1.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": "^12.20.0 || ^14.13.1 || >=16.0.0"
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/restore-cursor/node_modules/mimic-fn": {
|
||||
"version": "2.1.0",
|
||||
"resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-2.1.0.tgz",
|
||||
"integrity": "sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg==",
|
||||
"engines": {
|
||||
"node": ">=6"
|
||||
}
|
||||
},
|
||||
"node_modules/restore-cursor/node_modules/onetime": {
|
||||
"version": "5.1.2",
|
||||
"resolved": "https://registry.npmjs.org/onetime/-/onetime-5.1.2.tgz",
|
||||
"integrity": "sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg==",
|
||||
"version": "7.0.0",
|
||||
"resolved": "https://registry.npmjs.org/onetime/-/onetime-7.0.0.tgz",
|
||||
"integrity": "sha512-VXJjc87FScF88uafS3JllDgvAm+c/Slfz06lorj2uAY34rlUu0Nt+v8wreiImcrgAjjIHp1rXpTDlLOGw29WwQ==",
|
||||
"dependencies": {
|
||||
"mimic-fn": "^2.1.0"
|
||||
"mimic-function": "^5.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=6"
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/restore-cursor/node_modules/signal-exit": {
|
||||
"version": "3.0.7",
|
||||
"resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz",
|
||||
"integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ=="
|
||||
},
|
||||
"node_modules/reusify": {
|
||||
"version": "1.0.4",
|
||||
"resolved": "https://registry.npmjs.org/reusify/-/reusify-1.0.4.tgz",
|
||||
@@ -1654,9 +1776,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/rfdc": {
|
||||
"version": "1.3.1",
|
||||
"resolved": "https://registry.npmjs.org/rfdc/-/rfdc-1.3.1.tgz",
|
||||
"integrity": "sha512-r5a3l5HzYlIC68TpmYKlxWjmOP6wiPJ1vWv2HeLhNsRZMrCkxeqxiHlQ21oXmQ4F3SiryXBHhAD7JZqvOJjFmg=="
|
||||
"version": "1.4.1",
|
||||
"resolved": "https://registry.npmjs.org/rfdc/-/rfdc-1.4.1.tgz",
|
||||
"integrity": "sha512-q1b3N5QkRUWUl7iyylaaj3kOpIT0N2i9MqIEQXP73GVsN9cw3fdx8X63cEmWhJGi2PPCF23Ijp7ktmd39rawIA=="
|
||||
},
|
||||
"node_modules/rimraf": {
|
||||
"version": "3.0.2",
|
||||
@@ -1783,9 +1905,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/string-width": {
|
||||
"version": "7.1.0",
|
||||
"resolved": "https://registry.npmjs.org/string-width/-/string-width-7.1.0.tgz",
|
||||
"integrity": "sha512-SEIJCWiX7Kg4c129n48aDRwLbFb2LJmXXFrWBG4NGaRtMQ3myKPKbwrD1BKqQn74oCoNMBVrfDEr5M9YxCsrkw==",
|
||||
"version": "7.2.0",
|
||||
"resolved": "https://registry.npmjs.org/string-width/-/string-width-7.2.0.tgz",
|
||||
"integrity": "sha512-tsaTIkKW9b4N+AEj+SVA+WhJzV7/zMhcSu78mLKWSk7cXMOSHsBKFWUs0fWwq8QyK3MgJBQRX6Gbi4kYbdvGkQ==",
|
||||
"dependencies": {
|
||||
"emoji-regex": "^10.3.0",
|
||||
"get-east-asian-width": "^1.0.0",
|
||||
@@ -1799,9 +1921,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/string-width/node_modules/ansi-regex": {
|
||||
"version": "6.0.1",
|
||||
"resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.0.1.tgz",
|
||||
"integrity": "sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA==",
|
||||
"version": "6.1.0",
|
||||
"resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.1.0.tgz",
|
||||
"integrity": "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
},
|
||||
@@ -1872,9 +1994,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/synckit": {
|
||||
"version": "0.8.8",
|
||||
"resolved": "https://registry.npmjs.org/synckit/-/synckit-0.8.8.tgz",
|
||||
"integrity": "sha512-HwOKAP7Wc5aRGYdKH+dw0PRRpbO841v2DENBtjnR5HFWoiNByAl7vrx3p0G/rCyYXQsrxqtX48TImFtPcIHSpQ==",
|
||||
"version": "0.9.1",
|
||||
"resolved": "https://registry.npmjs.org/synckit/-/synckit-0.9.1.tgz",
|
||||
"integrity": "sha512-7gr8p9TQP6RAHusBOSLs46F4564ZrjV8xFmw5zCmgmhGUcw2hxsShhJ6CEiHQMgPDwAQ1fWHPM0ypc4RMAig4A==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"@pkgr/core": "^0.1.0",
|
||||
@@ -1913,9 +2035,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/tslib": {
|
||||
"version": "2.6.2",
|
||||
"resolved": "https://registry.npmjs.org/tslib/-/tslib-2.6.2.tgz",
|
||||
"integrity": "sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q=="
|
||||
"version": "2.7.0",
|
||||
"resolved": "https://registry.npmjs.org/tslib/-/tslib-2.7.0.tgz",
|
||||
"integrity": "sha512-gLXCKdN1/j47AiHiOkJN69hJmcbGTHI0ImLmbYLHykhgeN0jVGola9yVjFgzCUklsZQMW55o+dW7IXv3RCXDzA=="
|
||||
},
|
||||
"node_modules/type-check": {
|
||||
"version": "0.4.0",
|
||||
@@ -1990,9 +2112,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/wrap-ansi/node_modules/ansi-regex": {
|
||||
"version": "6.0.1",
|
||||
"resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.0.1.tgz",
|
||||
"integrity": "sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA==",
|
||||
"version": "6.1.0",
|
||||
"resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.1.0.tgz",
|
||||
"integrity": "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
},
|
||||
@@ -2040,9 +2162,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/yaml": {
|
||||
"version": "2.4.2",
|
||||
"resolved": "https://registry.npmjs.org/yaml/-/yaml-2.4.2.tgz",
|
||||
"integrity": "sha512-B3VqDZ+JAg1nZpaEmWtTXUlBneoGx6CPM9b0TENK6aoSu5t73dItudwdgmi6tHlIZZId4dZ9skcAQ2UbcyAeVA==",
|
||||
"version": "2.5.1",
|
||||
"resolved": "https://registry.npmjs.org/yaml/-/yaml-2.5.1.tgz",
|
||||
"integrity": "sha512-bLQOjaX/ADgQ20isPJRvF0iRUHIxVhYvr53Of7wGcWlO2jvtUlH5m87DsmulFVxRpNLOnI4tB6p/oh8D7kpn9Q==",
|
||||
"bin": {
|
||||
"yaml": "bin.mjs"
|
||||
},
|
||||
|
||||
+7
-5
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "planka",
|
||||
"version": "1.20.1",
|
||||
"version": "1.22.0",
|
||||
"private": true,
|
||||
"homepage": "https://plankanban.github.io/planka",
|
||||
"repository": {
|
||||
@@ -16,6 +16,7 @@
|
||||
"client:test": "npm test --prefix client",
|
||||
"docker:build": "docker build -t ghcr.io/plankanban/planka:local -f Dockerfile .",
|
||||
"docker:build:base": "docker build -t ghcr.io/plankanban/planka:base-local -f Dockerfile.base .",
|
||||
"gv": "genversion --source ./ --template client/version-template.ejs client/src/version.js",
|
||||
"postinstall": "(cd server && npm i && cd ../client && npm i)",
|
||||
"lint": "npm run server:lint && npm run client:lint",
|
||||
"prepare": "husky",
|
||||
@@ -57,13 +58,14 @@
|
||||
},
|
||||
"dependencies": {
|
||||
"concurrently": "^8.2.2",
|
||||
"husky": "^9.0.1",
|
||||
"lint-staged": "^15.2.5"
|
||||
"genversion": "^3.2.0",
|
||||
"husky": "^9.1.6",
|
||||
"lint-staged": "^15.2.10"
|
||||
},
|
||||
"devDependencies": {
|
||||
"eslint": "^8.57.0",
|
||||
"eslint-config-prettier": "^9.1.0",
|
||||
"eslint-plugin-prettier": "^5.1.3",
|
||||
"prettier": "^3.3.0"
|
||||
"eslint-plugin-prettier": "^5.2.1",
|
||||
"prettier": "^3.3.3"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -22,6 +22,8 @@ SECRET_KEY=notsecretkey
|
||||
# DEFAULT_ADMIN_NAME=Demo Demo
|
||||
# DEFAULT_ADMIN_USERNAME=demo
|
||||
|
||||
# SHOW_DETAILED_AUTH_ERRORS=false # Set to true to show more detailed authentication error messages. It should not be enabled without a rate limiter for security reasons.
|
||||
|
||||
# ALLOW_ALL_TO_CREATE_PROJECTS=true
|
||||
|
||||
# OIDC_ISSUER=
|
||||
@@ -33,6 +35,7 @@ SECRET_KEY=notsecretkey
|
||||
# OIDC_RESPONSE_MODE=fragment
|
||||
# OIDC_USE_DEFAULT_RESPONSE_MODE=true
|
||||
# OIDC_ADMIN_ROLES=admin
|
||||
# OIDC_CLAIMS_SOURCE=userinfo
|
||||
# OIDC_EMAIL_ATTRIBUTE=email
|
||||
# OIDC_NAME_ATTRIBUTE=name
|
||||
# OIDC_USERNAME_ATTRIBUTE=preferred_username
|
||||
@@ -59,6 +62,7 @@ SECRET_KEY=notsecretkey
|
||||
|
||||
# SLACK_BOT_TOKEN=
|
||||
# SLACK_CHANNEL_ID=
|
||||
# GOOGLE_CHAT_WEBHOOK_URL=
|
||||
|
||||
## Do not edit this
|
||||
|
||||
|
||||
@@ -1,9 +1,13 @@
|
||||
const bcrypt = require('bcrypt');
|
||||
const validator = require('validator');
|
||||
const { v4: uuid } = require('uuid');
|
||||
|
||||
const { getRemoteAddress } = require('../../../utils/remoteAddress');
|
||||
|
||||
const Errors = {
|
||||
INVALID_CREDENTIALS: {
|
||||
invalidCredentials: 'Invalid credentials',
|
||||
},
|
||||
INVALID_EMAIL_OR_USERNAME: {
|
||||
invalidEmailOrUsername: 'Invalid email or username',
|
||||
},
|
||||
@@ -31,9 +35,16 @@ module.exports = {
|
||||
type: 'string',
|
||||
required: true,
|
||||
},
|
||||
withHttpOnlyToken: {
|
||||
type: 'boolean',
|
||||
defaultsTo: false,
|
||||
},
|
||||
},
|
||||
|
||||
exits: {
|
||||
invalidCredentials: {
|
||||
responseType: 'unauthorized',
|
||||
},
|
||||
invalidEmailOrUsername: {
|
||||
responseType: 'unauthorized',
|
||||
},
|
||||
@@ -57,7 +68,10 @@ module.exports = {
|
||||
sails.log.warn(
|
||||
`Invalid email or username: "${inputs.emailOrUsername}"! (IP: ${remoteAddress})`,
|
||||
);
|
||||
throw Errors.INVALID_EMAIL_OR_USERNAME;
|
||||
|
||||
throw sails.config.custom.showDetailedAuthErrors
|
||||
? Errors.INVALID_EMAIL_OR_USERNAME
|
||||
: Errors.INVALID_CREDENTIALS;
|
||||
}
|
||||
|
||||
if (user.isSso) {
|
||||
@@ -66,18 +80,30 @@ module.exports = {
|
||||
|
||||
if (!bcrypt.compareSync(inputs.password, user.password)) {
|
||||
sails.log.warn(`Invalid password! (IP: ${remoteAddress})`);
|
||||
throw Errors.INVALID_PASSWORD;
|
||||
|
||||
throw sails.config.custom.showDetailedAuthErrors
|
||||
? Errors.INVALID_PASSWORD
|
||||
: Errors.INVALID_CREDENTIALS;
|
||||
}
|
||||
|
||||
const accessToken = sails.helpers.utils.createToken(user.id);
|
||||
const { token: accessToken, payload: accessTokenPayload } = sails.helpers.utils.createJwtToken(
|
||||
user.id,
|
||||
);
|
||||
|
||||
const httpOnlyToken = inputs.withHttpOnlyToken ? uuid() : null;
|
||||
|
||||
await Session.create({
|
||||
accessToken,
|
||||
httpOnlyToken,
|
||||
remoteAddress,
|
||||
userId: user.id,
|
||||
userAgent: this.req.headers['user-agent'],
|
||||
});
|
||||
|
||||
if (httpOnlyToken && !this.req.isSocket) {
|
||||
sails.helpers.utils.setHttpOnlyTokenCookie(httpOnlyToken, accessTokenPayload, this.res);
|
||||
}
|
||||
|
||||
return {
|
||||
item: accessToken,
|
||||
};
|
||||
|
||||
@@ -1,20 +1,22 @@
|
||||
module.exports = {
|
||||
async fn() {
|
||||
const { accessToken } = this.req;
|
||||
const { currentSession } = this.req;
|
||||
|
||||
await Session.updateOne({
|
||||
accessToken,
|
||||
id: currentSession.id,
|
||||
deletedAt: null,
|
||||
}).set({
|
||||
deletedAt: new Date().toISOString(),
|
||||
});
|
||||
|
||||
if (this.req.isSocket) {
|
||||
sails.sockets.leaveAll(`@accessToken:${accessToken}`);
|
||||
sails.sockets.leaveAll(`@accessToken:${currentSession.accessToken}`);
|
||||
|
||||
if (currentSession.httpOnlyToken && !this.req.isSocket) {
|
||||
sails.helpers.utils.clearHttpOnlyTokenCookie(this.res);
|
||||
}
|
||||
|
||||
return {
|
||||
item: accessToken,
|
||||
item: currentSession.accessToken,
|
||||
};
|
||||
},
|
||||
};
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user