mirror of
https://github.com/AmruthPillai/Reactive-Resume.git
synced 2025-11-10 04:22:27 +10:00
Compare commits
150 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| b4381a22f3 | |||
| ba6ca4d220 | |||
| 5486906b05 | |||
| 7348b295cb | |||
| 025762fdf6 | |||
| 96411cdb90 | |||
| 9c0c6076b3 | |||
| 36bf729161 | |||
| 3a430ad98c | |||
| 90a8610dd7 | |||
| d62ddab140 | |||
| ca0186bb67 | |||
| 88ac8389ea | |||
| 2f3864fff2 | |||
| 7878e52cc4 | |||
| 08b1967a4e | |||
| b870ca8297 | |||
| 1507c54671 | |||
| 0984ca4daf | |||
| 438798f8de | |||
| 27aadb8948 | |||
| 244a4118cf | |||
| cde320ce46 | |||
| 4772df7618 | |||
| ecb95b35f3 | |||
| 24b09af563 | |||
| 9471fb4169 | |||
| 2f296d6f08 | |||
| cd3d3caa15 | |||
| 440eefe46e | |||
| 5787e2badb | |||
| c235e5ab16 | |||
| f584c70f27 | |||
| 3aa0279519 | |||
| 6830aec2f9 | |||
| 9a3d7af325 | |||
| 52f7e8557f | |||
| 12c17d1c7c | |||
| 67918187a1 | |||
| dcbc0c2b45 | |||
| 26b6a741c2 | |||
| d7064129e8 | |||
| 279dd36a13 | |||
| 49e47b28de | |||
| a782343e0a | |||
| 1e7821a46d | |||
| f7bea5a218 | |||
| 05fa4f3192 | |||
| ed357f0ebc | |||
| 1774832a58 | |||
| 2837befd52 | |||
| 38d866c0c2 | |||
| 87c7acf4f1 | |||
| 1bd68118ce | |||
| 5c34b28c80 | |||
| c550183720 | |||
| 3605579b1b | |||
| fa2e28688f | |||
| 20f1031e28 | |||
| 292cb6d0ed | |||
| 45f2dc1cfc | |||
| e319dd3e3d | |||
| 9678f7a6e5 | |||
| 0cca4e21fb | |||
| f6758f191d | |||
| 983662f877 | |||
| c7fc28a5c5 | |||
| 1f7c33e805 | |||
| 437cc331a8 | |||
| aef51375b8 | |||
| bdd65968e5 | |||
| 061a789c18 | |||
| 68507d0501 | |||
| 1e28c5adfa | |||
| 3b09550ebd | |||
| 16aef9cbec | |||
| b24da90ba7 | |||
| 2aa7dbd3ad | |||
| 9f8f2c4b8b | |||
| 5331ecccc1 | |||
| f2ec86940c | |||
| cd74e707ba | |||
| ff101dbfac | |||
| 5024c19f87 | |||
| c9850b5815 | |||
| 6fe4e7d7e1 | |||
| a5b8b91e82 | |||
| cc7095adc3 | |||
| e2703f55aa | |||
| 8c5849c988 | |||
| 5322ab2420 | |||
| b84e6bcfb1 | |||
| a4ab0174c7 | |||
| 7e93b5a757 | |||
| 044820fa71 | |||
| 322178e8a4 | |||
| 6358fbad30 | |||
| d342c0a9af | |||
| 63084eebb4 | |||
| 3b4ea00db8 | |||
| c8f7bffe7e | |||
| 3ff56f89d9 | |||
| 7fb9f27837 | |||
| c9685d4ce7 | |||
| 4dc987e27d | |||
| f7af06ae9a | |||
| a5c337faa3 | |||
| fc4704f0a6 | |||
| d968334ada | |||
| fea6d23178 | |||
| 3fefc95572 | |||
| b07e7d1213 | |||
| d47b8bfb03 | |||
| 5bf7fbdae1 | |||
| fca766b382 | |||
| feadfb1b67 | |||
| e69000f221 | |||
| 6b4a54465a | |||
| 878659999f | |||
| 1868c47e30 | |||
| 51442efc23 | |||
| 556e962ec5 | |||
| b5ce67f863 | |||
| c3ce89dc3a | |||
| e87930c758 | |||
| 815a693e58 | |||
| 8287fcae96 | |||
| cd7fe6c404 | |||
| d47d5dd819 | |||
| 1919d79e43 | |||
| ab08cd9e34 | |||
| 2522bdd0a2 | |||
| f9b6aefffe | |||
| 2ba6658a0b | |||
| dbc46f27a3 | |||
| f21e1caed1 | |||
| 4ffe2a6330 | |||
| 1bc0438872 | |||
| 57fb9fdaea | |||
| 58ce641f18 | |||
| 5f4e7802e4 | |||
| 42d3109ae1 | |||
| f7ca7b97fa | |||
| f5d8a54134 | |||
| eaec14dc62 | |||
| c93b3264cd | |||
| bf41aa9c6c | |||
| 8af6bfd5ae | |||
| ab08c10874 | |||
| 9af9a0284e |
@ -2,7 +2,6 @@
|
||||
/app
|
||||
|
||||
# Build Artifacts
|
||||
**/.turbo
|
||||
/server/dist
|
||||
/client/.next
|
||||
|
||||
|
||||
13
.env.example
13
.env.example
@ -1,12 +1,3 @@
|
||||
# Turbo Cache (Optional)
|
||||
TURBO_TEAM=
|
||||
TURBO_TOKEN=
|
||||
|
||||
# Sentry Error Logging (Optional)
|
||||
SENTRY_AUTH_TOKEN=
|
||||
SERVER_SENTRY_DSN=
|
||||
PUBLIC_CLIENT_SENTRY_DSN=
|
||||
|
||||
# Server + Client
|
||||
TZ=UTC
|
||||
PUBLIC_URL=http://localhost:3000
|
||||
@ -20,7 +11,7 @@ POSTGRES_PASSWORD=postgres
|
||||
|
||||
# Server
|
||||
SECRET_KEY=
|
||||
POSTGRES_HOST=postgres
|
||||
POSTGRES_HOST=localhost
|
||||
POSTGRES_PORT=5432
|
||||
POSTGRES_SSL_CERT=
|
||||
JWT_SECRET=
|
||||
@ -41,5 +32,5 @@ STORAGE_ACCESS_KEY=
|
||||
STORAGE_SECRET_KEY=
|
||||
PDF_DELETION_TIME=345600000
|
||||
|
||||
# Flags (Client)
|
||||
# Client
|
||||
PUBLIC_FLAG_DISABLE_SIGNUPS=false
|
||||
|
||||
@ -14,6 +14,7 @@
|
||||
// TypeScript ESLint
|
||||
"@typescript-eslint/no-unused-vars": "off",
|
||||
"@typescript-eslint/no-explicit-any": "off",
|
||||
"@typescript-eslint/no-non-null-assertion": "off",
|
||||
"@typescript-eslint/interface-name-prefix": "off",
|
||||
"@typescript-eslint/explicit-function-return-type": "off",
|
||||
"@typescript-eslint/explicit-module-boundary-types": "off"
|
||||
|
||||
2
.github/workflows/digitalocean-deploy.yml
vendored
2
.github/workflows/digitalocean-deploy.yml
vendored
@ -13,7 +13,7 @@ jobs:
|
||||
if: ${{ github.event.workflow_run.conclusion == 'success' }}
|
||||
steps:
|
||||
- name: Install DigitalOcean CLI
|
||||
uses: digitalocean/action-doctl@v2.2.0
|
||||
uses: digitalocean/action-doctl@v2.3.0
|
||||
with:
|
||||
token: ${{ secrets.DIGITALOCEAN_TOKEN }}
|
||||
|
||||
|
||||
25
.github/workflows/docker-build-push.yml
vendored
25
.github/workflows/docker-build-push.yml
vendored
@ -10,18 +10,13 @@ jobs:
|
||||
name: Build and Push Docker Image
|
||||
runs-on: ubuntu-latest
|
||||
|
||||
env:
|
||||
TURBO_TEAM: ${{ secrets.TURBO_TEAM }}
|
||||
TURBO_TOKEN: ${{ secrets.TURBO_TOKEN }}
|
||||
SENTRY_AUTH_TOKEN: ${{ secrets.SENTRY_AUTH_TOKEN }}
|
||||
|
||||
strategy:
|
||||
matrix:
|
||||
image: [client, server]
|
||||
|
||||
steps:
|
||||
- name: Checkout the repository
|
||||
uses: actions/checkout@v3.1.0
|
||||
uses: actions/checkout@v3.5.0
|
||||
|
||||
- id: version
|
||||
name: App Version
|
||||
@ -34,7 +29,7 @@ jobs:
|
||||
|
||||
- id: buildx
|
||||
name: Set up Docker Buildx
|
||||
uses: docker/setup-buildx-action@v2.2.1
|
||||
uses: docker/setup-buildx-action@v2.5.0
|
||||
|
||||
- name: Login to Docker Hub
|
||||
uses: docker/login-action@v2.1.0
|
||||
@ -50,28 +45,14 @@ jobs:
|
||||
password: ${{ secrets.GH_TOKEN }}
|
||||
|
||||
- name: Build and Push Docker Image
|
||||
uses: docker/build-push-action@v3.2.0
|
||||
uses: docker/build-push-action@v4.0.0
|
||||
with:
|
||||
context: .
|
||||
push: true
|
||||
platforms: linux/amd64
|
||||
file: ${{ matrix.image }}/Dockerfile
|
||||
build-args: |
|
||||
TURBO_TEAM=${{ secrets.TURBO_TEAM }}
|
||||
TURBO_TOKEN=${{ secrets.TURBO_TOKEN }}
|
||||
SENTRY_AUTH_TOKEN=${{ secrets.SENTRY_AUTH_TOKEN }}
|
||||
tags: |
|
||||
amruthpillai/reactive-resume:${{ matrix.image }}-latest
|
||||
amruthpillai/reactive-resume:${{ matrix.image }}-${{ steps.version.outputs.current-version }}
|
||||
ghcr.io/amruthpillai/reactive-resume:${{ matrix.image }}-latest
|
||||
ghcr.io/amruthpillai/reactive-resume:${{ matrix.image }}-${{ steps.version.outputs.current-version }}
|
||||
|
||||
- name: Create Sentry Release
|
||||
uses: getsentry/action-release@v1.2.1
|
||||
env:
|
||||
SENTRY_ORG: reactive-resume
|
||||
SENTRY_PROJECT: ${{ matrix.image }}
|
||||
SENTRY_AUTH_TOKEN: ${{ secrets.SENTRY_AUTH_TOKEN }}
|
||||
with:
|
||||
environment: production
|
||||
version: ${{ steps.version.outputs.current-version }}
|
||||
|
||||
4
.gitignore
vendored
4
.gitignore
vendored
@ -1,6 +1,7 @@
|
||||
# Environment Variables
|
||||
.env
|
||||
.env.*
|
||||
!.env.gitpod
|
||||
!.env.example
|
||||
|
||||
# Project Dependencies
|
||||
@ -9,8 +10,5 @@ node_modules
|
||||
# macOS
|
||||
.DS_Store
|
||||
|
||||
# Turbo
|
||||
.turbo
|
||||
|
||||
# Intellij
|
||||
.idea
|
||||
|
||||
41
.gitpod.yml
Normal file
41
.gitpod.yml
Normal file
@ -0,0 +1,41 @@
|
||||
tasks:
|
||||
- name: Run PostgreSQL Database
|
||||
command: docker run --name postgres -p 5432:5432 -e POSTGRES_PASSWORD=postgres -d postgres
|
||||
|
||||
- name: Install Project Dependencies
|
||||
command: |
|
||||
pnpm install
|
||||
pnpm dlx playwright install --with-deps chromium
|
||||
gp sync-done deps
|
||||
|
||||
- name: Generate Environment Variables
|
||||
init: gp sync-await deps
|
||||
command: |
|
||||
if [ -f .env ]; then
|
||||
echo "Found .env in workspace, skipping generation"
|
||||
else
|
||||
pnpm generate-env
|
||||
fi
|
||||
gp sync-done env
|
||||
|
||||
- name: Build and Run Project
|
||||
init: gp sync-await env
|
||||
command: |
|
||||
pnpm build
|
||||
pnpm start
|
||||
|
||||
ports:
|
||||
# PostgreSQL
|
||||
- port: 5432
|
||||
onOpen: ignore
|
||||
visibility: private
|
||||
|
||||
# Client
|
||||
- port: 3100
|
||||
onOpen: ignore
|
||||
visibility: public
|
||||
|
||||
# Client
|
||||
- port: 3000
|
||||
onOpen: open-browser
|
||||
visibility: public
|
||||
13
README.md
13
README.md
@ -6,7 +6,8 @@
|
||||
[](https://github.com/AmruthPillai/Reactive-Resume/blob/main/LICENSE)
|
||||
[](https://translate.rxresu.me)
|
||||
[](https://hub.docker.com/r/amruthpillai/reactive-resume)
|
||||

|
||||

|
||||
[](https://gitpod.io/#https://github.com/AmruthPillai/Reactive-Resume)
|
||||
[](https://app.fossa.com/projects/git%2Bgithub.com%2FAmruthPillai%2FReactive-Resume?ref=badge_shield)
|
||||
|
||||
## [Go to App](https://rxresu.me) | [Docs](https://docs.rxresu.me)
|
||||
@ -18,7 +19,7 @@ You have complete control over what goes into your resume, how it looks, what co
|
||||
## Table of Contents
|
||||
|
||||
- [Reactive Resume](#reactive-resume)
|
||||
- [Go to App Docs](https://docs.rxresu.me)
|
||||
- [Go to App | Docs](#go-to-app--docs)
|
||||
- [Table of Contents](#table-of-contents)
|
||||
- [Features](#features)
|
||||
- [Languages](#languages)
|
||||
@ -104,6 +105,10 @@ The docs include an extensive [Tutorial](https://docs.rxresu.me/tutorial) sectio
|
||||
|
||||
## Build from Source
|
||||
|
||||
[](https://gitpod.io/#https://github.com/AmruthPillai/Reactive-Resume)
|
||||
|
||||
Initially building the image and project on Gitpod will take at least ~10 minutes, so please be patient on first launch.
|
||||
|
||||
For extensive information on how to build the app on your local machine, head over to the docs [Source Code](https://docs.rxresu.me/source-code) section.
|
||||
|
||||
## Contributing
|
||||
@ -129,6 +134,10 @@ Reactive Resume would be nothing without the folks who supported me and kept the
|
||||
### [GitHub Sponsor](https://github.com/sponsors/AmruthPillai)
|
||||
### [PayPal](https://paypal.me/RajaRajanA)
|
||||
|
||||
## GitHub Star History
|
||||
|
||||
[](https://star-history.com/#AmruthPillai/Reactive-Resume&Date)
|
||||
|
||||
## Infrastructure
|
||||
|
||||
- [Next.js](https://nextjs.org/), frontend
|
||||
|
||||
@ -12,8 +12,8 @@ android {
|
||||
targetSdk 32
|
||||
versionCode 3
|
||||
versionName "1.0"
|
||||
resConfigs 'en'
|
||||
|
||||
resConfigs "en"
|
||||
}
|
||||
|
||||
buildTypes {
|
||||
@ -38,6 +38,7 @@ android {
|
||||
buildFeatures {
|
||||
viewBinding true
|
||||
}
|
||||
namespace 'me.rxresu.app'
|
||||
}
|
||||
|
||||
dependencies {
|
||||
|
||||
@ -1,7 +1,6 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<manifest
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
package="me.rxresu.app">
|
||||
xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
|
||||
<uses-permission android:name="android.permission.INTERNET"/>
|
||||
|
||||
|
||||
@ -6,7 +6,6 @@ import android.webkit.WebView
|
||||
import androidx.appcompat.app.AppCompatActivity
|
||||
|
||||
class MainActivity : AppCompatActivity() {
|
||||
|
||||
private lateinit var webView: WebView
|
||||
|
||||
private var url = "https://rxresu.me"
|
||||
|
||||
@ -1,7 +1,7 @@
|
||||
plugins {
|
||||
id 'com.android.application' version '7.1.2' apply false
|
||||
id 'com.android.library' version '7.1.2' apply false
|
||||
id 'org.jetbrains.kotlin.android' version '1.7.21' apply false
|
||||
id 'com.android.application' version '7.4.2' apply false
|
||||
id 'com.android.library' version '7.4.2' apply false
|
||||
id 'org.jetbrains.kotlin.android' version '1.8.20' apply false
|
||||
}
|
||||
|
||||
task clean(type: Delete) {
|
||||
|
||||
2
app/gradle/wrapper/gradle-wrapper.properties
vendored
2
app/gradle/wrapper/gradle-wrapper.properties
vendored
@ -1,6 +1,6 @@
|
||||
#Wed Mar 09 21:34:49 CET 2022
|
||||
distributionBase=GRADLE_USER_HOME
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-7.2-bin.zip
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-7.5-bin.zip
|
||||
distributionPath=wrapper/dists
|
||||
zipStorePath=wrapper/dists
|
||||
zipStoreBase=GRADLE_USER_HOME
|
||||
|
||||
3
client/.gitignore
vendored
3
client/.gitignore
vendored
@ -40,6 +40,3 @@ __ENV.js
|
||||
|
||||
# next-sitemap
|
||||
sitemap*.xml
|
||||
|
||||
# sentry
|
||||
.sentryclirc
|
||||
@ -2,12 +2,12 @@ FROM node:lts-alpine AS base
|
||||
|
||||
WORKDIR /app
|
||||
|
||||
RUN apk add --no-cache g++ git curl make python3 libc6-compat \
|
||||
&& curl -f https://get.pnpm.io/v6.16.js | node - add --global pnpm
|
||||
RUN apk add --no-cache g++ git make curl python3 libc6-compat \
|
||||
&& corepack enable && corepack prepare pnpm@latest --activate
|
||||
|
||||
FROM base as dependencies
|
||||
|
||||
COPY package.json pnpm-*.yaml turbo.json ./
|
||||
COPY package.json pnpm-*.yaml ./
|
||||
COPY ./schema/package.json ./schema/package.json
|
||||
COPY ./client/package.json ./client/package.json
|
||||
|
||||
@ -21,19 +21,12 @@ COPY --from=dependencies /app/node_modules ./node_modules
|
||||
COPY --from=dependencies /app/schema/node_modules ./schema/node_modules
|
||||
COPY --from=dependencies /app/client/node_modules ./client/node_modules
|
||||
|
||||
ARG TURBO_TEAM
|
||||
ARG TURBO_TOKEN
|
||||
ARG SENTRY_AUTH_TOKEN
|
||||
|
||||
ENV TURBO_TEAM $TURBO_TEAM
|
||||
ENV TURBO_TOKEN $TURBO_TOKEN
|
||||
ENV SENTRY_AUTH_TOKEN $SENTRY_AUTH_TOKEN
|
||||
|
||||
RUN pnpm run build --filter client
|
||||
RUN pnpm run --filter schema build \
|
||||
&& pnpm run --filter client build
|
||||
|
||||
FROM base as production
|
||||
|
||||
COPY --from=builder /app/package.json /app/pnpm-*.yaml /app/turbo.json ./
|
||||
COPY --from=builder /app/package.json /app/pnpm-*.yaml ./
|
||||
COPY --from=builder /app/client/package.json ./client/package.json
|
||||
|
||||
RUN pnpm install --filter client --prod --frozen-lockfile --workspace-root
|
||||
@ -50,4 +43,4 @@ ENV PORT 3000
|
||||
HEALTHCHECK --interval=30s --timeout=20s --retries=3 --start-period=15s \
|
||||
CMD curl -fSs localhost:3000 || exit 1
|
||||
|
||||
CMD [ "pnpm", "run", "start", "--filter", "client" ]
|
||||
CMD [ "pnpm", "run", "--filter", "client", "start" ]
|
||||
@ -14,11 +14,11 @@ import {
|
||||
import { ButtonBase, Divider, Tooltip, useMediaQuery, useTheme } from '@mui/material';
|
||||
import clsx from 'clsx';
|
||||
import dayjs from 'dayjs';
|
||||
import { get } from 'lodash';
|
||||
import get from 'lodash/get';
|
||||
import { useTranslation } from 'next-i18next';
|
||||
import toast from 'react-hot-toast';
|
||||
import { useMutation } from 'react-query';
|
||||
import { ReactZoomPanPinchRef } from 'react-zoom-pan-pinch';
|
||||
import { ReactZoomPanPinchHandlers } from 'react-zoom-pan-pinch';
|
||||
import { ActionCreators } from 'redux-undo';
|
||||
|
||||
import { ServerError } from '@/services/axios';
|
||||
@ -29,7 +29,7 @@ import getResumeUrl from '@/utils/getResumeUrl';
|
||||
|
||||
import styles from './ArtboardController.module.scss';
|
||||
|
||||
const ArtboardController: React.FC<ReactZoomPanPinchRef> = ({ zoomIn, zoomOut, centerView }) => {
|
||||
const ArtboardController: React.FC<ReactZoomPanPinchHandlers> = ({ zoomIn, zoomOut, centerView }) => {
|
||||
const { t } = useTranslation();
|
||||
|
||||
const theme = useTheme();
|
||||
|
||||
@ -53,13 +53,12 @@ const Header = () => {
|
||||
|
||||
const [anchorEl, setAnchorEl] = useState<HTMLButtonElement | null>(null);
|
||||
|
||||
const { mutateAsync: duplicateMutation } = useMutation<Resume, ServerError, DuplicateResumeParams>(duplicateResume);
|
||||
|
||||
const { mutateAsync: deleteMutation } = useMutation<void, ServerError, DeleteResumeParams>(deleteResume);
|
||||
|
||||
const resume = useAppSelector((state) => state.resume.present);
|
||||
const { left, right } = useAppSelector((state) => state.build.sidebar);
|
||||
|
||||
const { mutateAsync: deleteMutation } = useMutation<void, ServerError, DeleteResumeParams>(deleteResume);
|
||||
const { mutateAsync: duplicateMutation } = useMutation<Resume, ServerError, DuplicateResumeParams>(duplicateResume);
|
||||
|
||||
const name = useMemo(() => get(resume, 'name'), [resume]);
|
||||
|
||||
useEffect(() => {
|
||||
|
||||
@ -27,6 +27,7 @@ const LeftSidebar = () => {
|
||||
const isDesktop = useMediaQuery(theme.breakpoints.up('lg'));
|
||||
|
||||
const sections = useAppSelector((state) => state.resume.present.sections);
|
||||
|
||||
const { open } = useAppSelector((state) => state.build.sidebar.left);
|
||||
|
||||
const customSections = useMemo(() => getCustomSections(sections), [sections]);
|
||||
@ -108,7 +109,7 @@ const LeftSidebar = () => {
|
||||
variant={isDesktop ? 'persistent' : 'temporary'}
|
||||
>
|
||||
<div className={styles.container}>
|
||||
<nav className="overflow-y-scroll">
|
||||
<nav className="overflow-y-auto">
|
||||
<div>
|
||||
<Link href="/dashboard">
|
||||
<Logo size={40} />
|
||||
@ -122,14 +123,19 @@ const LeftSidebar = () => {
|
||||
arrow
|
||||
key={id}
|
||||
placement="right"
|
||||
title={get(sections, `${id}.name`, t<string>(`builder.leftSidebar.sections.${id}.heading`)) as string}
|
||||
title={t<string>(`builder.leftSidebar.sections.${id}.heading`, get(sections, `${id}.name`))}
|
||||
>
|
||||
<IconButton onClick={() => handleClick(id)}>{icon}</IconButton>
|
||||
</Tooltip>
|
||||
))}
|
||||
|
||||
{customSections.map(({ id }) => (
|
||||
<Tooltip key={id} title={get(sections, `${id}.name`, '') as string} placement="right" arrow>
|
||||
<Tooltip
|
||||
key={id}
|
||||
title={t<string>(`builder.leftSidebar.sections.${id}.heading`, get(sections, `${id}.name`))}
|
||||
placement="right"
|
||||
arrow
|
||||
>
|
||||
<IconButton onClick={() => id && handleClick(id)}>
|
||||
<Star />
|
||||
</IconButton>
|
||||
|
||||
@ -98,7 +98,9 @@ const Section: React.FC<Props> = ({
|
||||
<SectionSettings path={path} />
|
||||
|
||||
<Button variant="outlined" startIcon={<Add />} onClick={handleAdd}>
|
||||
{t<string>('builder.common.actions.add', { token: heading })}
|
||||
{t<string>('builder.common.actions.add', {
|
||||
token: t<string>(`builder.leftSidebar.${path}.heading`, heading),
|
||||
})}
|
||||
</Button>
|
||||
</footer>
|
||||
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
import { Divider, IconButton, SwipeableDrawer, Tooltip, useMediaQuery, useTheme } from '@mui/material';
|
||||
import { capitalize } from 'lodash';
|
||||
import capitalize from 'lodash/capitalize';
|
||||
import { useTranslation } from 'next-i18next';
|
||||
|
||||
import Avatar from '@/components/shared/Avatar';
|
||||
@ -43,7 +43,7 @@ const RightSidebar = () => {
|
||||
variant={isDesktop ? 'persistent' : 'temporary'}
|
||||
>
|
||||
<div className={styles.container}>
|
||||
<nav className="overflow-y-scroll">
|
||||
<nav className="overflow-y-auto">
|
||||
<div>
|
||||
<Avatar size={40} />
|
||||
<Divider />
|
||||
|
||||
@ -3,7 +3,7 @@ import { Button } from '@mui/material';
|
||||
import { useTranslation } from 'next-i18next';
|
||||
|
||||
import Heading from '@/components/shared/Heading';
|
||||
import { DOCS_URL, DONATION_URL, GITHUB_ISSUES_URL, GITHUB_URL } from '@/constants/index';
|
||||
import { DOCS_URL, DONATION_URL, GITHUB_ISSUES_URL, GITHUB_URL, REDDIT_URL } from '@/constants/index';
|
||||
|
||||
import styles from './Links.module.scss';
|
||||
|
||||
@ -50,6 +50,12 @@ const Links = () => {
|
||||
</Button>
|
||||
</a>
|
||||
|
||||
<a href={REDDIT_URL} target="_blank" rel="noreferrer">
|
||||
<Button variant="text" startIcon={<Link />}>
|
||||
{t<string>('builder.rightSidebar.sections.links.reddit')}
|
||||
</Button>
|
||||
</a>
|
||||
|
||||
<a href={DOCS_URL} target="_blank" rel="noreferrer">
|
||||
<Button variant="text" startIcon={<Link />}>
|
||||
{t<string>('builder.rightSidebar.sections.links.docs')}
|
||||
|
||||
@ -51,7 +51,7 @@ const Settings = () => {
|
||||
const pageConfig: PageConfig | undefined = useMemo(() => get(resume, 'metadata.page'), [resume]);
|
||||
|
||||
const isDarkMode = useMemo(() => theme === 'dark', [theme]);
|
||||
const exampleDateString = useMemo(() => `Eg. ${dayjs().utc().format(dateConfig.format)}`, [dateConfig.format]);
|
||||
const exampleDateString = useMemo(() => `Eg. ${dayjs().format(dateConfig.format)}`, [dateConfig.format]);
|
||||
const themeString = useMemo(() => (isDarkMode ? 'Matte Black Everything' : 'As bright as your future'), [isDarkMode]);
|
||||
|
||||
const { mutateAsync: loadSampleDataMutation } = useMutation<Resume, ServerError, LoadSampleDataParams>(
|
||||
|
||||
@ -6,15 +6,17 @@ import { useState } from 'react';
|
||||
|
||||
import { logout } from '@/store/auth/authSlice';
|
||||
import { useAppDispatch, useAppSelector } from '@/store/hooks';
|
||||
import { setModalState } from '@/store/modal/modalSlice';
|
||||
import getGravatarUrl from '@/utils/getGravatarUrl';
|
||||
|
||||
import styles from './Avatar.module.scss';
|
||||
|
||||
type Props = {
|
||||
size?: number;
|
||||
interactive?: boolean;
|
||||
};
|
||||
|
||||
const Avatar: React.FC<Props> = ({ size = 64 }) => {
|
||||
const Avatar: React.FC<Props> = ({ size = 64, interactive = true }) => {
|
||||
const router = useRouter();
|
||||
|
||||
const { t } = useTranslation();
|
||||
@ -34,6 +36,11 @@ const Avatar: React.FC<Props> = ({ size = 64 }) => {
|
||||
setAnchorEl(null);
|
||||
};
|
||||
|
||||
const handleOpenProfile = () => {
|
||||
dispatch(setModalState({ modal: 'auth.profile', state: { open: true } }));
|
||||
handleClose();
|
||||
};
|
||||
|
||||
const handleLogout = () => {
|
||||
dispatch(logout());
|
||||
handleClose();
|
||||
@ -43,7 +50,7 @@ const Avatar: React.FC<Props> = ({ size = 64 }) => {
|
||||
|
||||
return (
|
||||
<>
|
||||
<IconButton onClick={handleOpen}>
|
||||
<IconButton onClick={handleOpen} disabled={!interactive}>
|
||||
<Image
|
||||
width={size}
|
||||
height={size}
|
||||
@ -54,9 +61,9 @@ const Avatar: React.FC<Props> = ({ size = 64 }) => {
|
||||
</IconButton>
|
||||
|
||||
<Menu anchorEl={anchorEl} onClose={handleClose} open={Boolean(anchorEl)}>
|
||||
<MenuItem>
|
||||
<MenuItem onClick={handleOpenProfile}>
|
||||
<div>
|
||||
<span className="text-xs opacity-50">{t<string>('common.avatar.menu.greeting')}</span>
|
||||
<span className="text-xs opacity-50">{t<string>('common.avatar.menu.greeting')},</span>
|
||||
<p>{user?.name}</p>
|
||||
</div>
|
||||
</MenuItem>
|
||||
|
||||
@ -62,7 +62,7 @@ const Heading: React.FC<Props> = ({
|
||||
{editMode ? (
|
||||
<TextField size="small" value={heading} className="w-3/4" onChange={handleChange} />
|
||||
) : (
|
||||
<h1>{heading}</h1>
|
||||
<h1>{t<string>(`builder.leftSidebar.${path}.heading`, heading)}</h1>
|
||||
)}
|
||||
</div>
|
||||
|
||||
|
||||
@ -1,6 +1,9 @@
|
||||
import clsx from 'clsx';
|
||||
import { isEmpty } from 'lodash';
|
||||
import isEmpty from 'lodash/isEmpty';
|
||||
import ReactMarkdown from 'react-markdown';
|
||||
import rehypeKatex from 'rehype-katex';
|
||||
import remarkGfm from 'remark-gfm';
|
||||
import remarkMath from 'remark-math';
|
||||
|
||||
type Props = {
|
||||
children?: string;
|
||||
@ -11,7 +14,11 @@ const Markdown: React.FC<Props> = ({ className, children }) => {
|
||||
if (!children || isEmpty(children)) return null;
|
||||
|
||||
return (
|
||||
<ReactMarkdown remarkPlugins={[]} className={clsx('markdown', className)}>
|
||||
<ReactMarkdown
|
||||
className={clsx('markdown', className)}
|
||||
remarkPlugins={[remarkGfm, remarkMath]}
|
||||
rehypePlugins={[rehypeKatex]}
|
||||
>
|
||||
{children}
|
||||
</ReactMarkdown>
|
||||
);
|
||||
|
||||
@ -1,7 +1,6 @@
|
||||
import { TextField } from '@mui/material';
|
||||
import { DatePicker } from '@mui/x-date-pickers';
|
||||
import { DatePicker } from '@mui/x-date-pickers/DatePicker';
|
||||
import dayjs from 'dayjs';
|
||||
import { isEmpty } from 'lodash';
|
||||
import get from 'lodash/get';
|
||||
import { useEffect, useState } from 'react';
|
||||
|
||||
@ -22,7 +21,6 @@ const ResumeInput: React.FC<Props> = ({ type = 'text', label, path, className, m
|
||||
const dispatch = useAppDispatch();
|
||||
|
||||
const stateValue = useAppSelector((state) => get(state.resume.present, path, ''));
|
||||
const dateFormat = useAppSelector((state) => state.resume.present.metadata.date.format);
|
||||
|
||||
useEffect(() => {
|
||||
setValue(stateValue);
|
||||
@ -57,15 +55,14 @@ const ResumeInput: React.FC<Props> = ({ type = 'text', label, path, className, m
|
||||
if (type === 'date') {
|
||||
return (
|
||||
<DatePicker
|
||||
showToolbar
|
||||
openTo="year"
|
||||
label={label}
|
||||
value={value}
|
||||
toolbarFormat={dateFormat}
|
||||
value={dayjs(value)}
|
||||
views={['year', 'month', 'day']}
|
||||
renderInput={(params) => <TextField {...params} error={false} className={className} />}
|
||||
onChange={(date: Date | null, keyboardInputValue: string | undefined) => {
|
||||
isEmpty(keyboardInputValue) && onChangeValue('');
|
||||
slots={{
|
||||
textField: (params) => <TextField {...params} error={false} className={className} />,
|
||||
}}
|
||||
onChange={(date: dayjs.Dayjs | null) => {
|
||||
date && dayjs(date).isValid() && onChangeValue(dayjs(date).format('YYYY-MM-DD'));
|
||||
}}
|
||||
/>
|
||||
|
||||
@ -37,6 +37,7 @@ export const languages: Language[] = [
|
||||
{ code: 'or', name: 'Odia', localName: 'ଓଡ଼ିଆ' },
|
||||
{ code: 'pl', name: 'Polish', localName: 'Polski' },
|
||||
{ code: 'pt', name: 'Portuguese', localName: 'Português' },
|
||||
{ code: 'pt-BR', name: 'Brazilian Portuguese', localName: 'Brasil' },
|
||||
{ code: 'ro', name: 'Romanian', localName: 'limba română' },
|
||||
{ code: 'ru', name: 'Russian', localName: 'русский' },
|
||||
{ code: 'sr', name: 'Serbian', localName: 'српски језик' },
|
||||
|
||||
@ -13,6 +13,11 @@ export const DOCS_URL = 'https://docs.rxresu.me';
|
||||
export const DONATION_URL = 'https://paypal.me/RajaRajanA';
|
||||
export const TRANSLATE_URL = 'https://translate.rxresu.me/';
|
||||
export const DIGITALOCEAN_URL = 'https://pillai.xyz/digitalocean';
|
||||
export const REDDIT_URL = 'https://www.reddit.com/r/reactiveresume/';
|
||||
export const GITHUB_URL = 'https://github.com/AmruthPillai/Reactive-Resume';
|
||||
export const PRODUCT_HUNT_URL = 'https://www.producthunt.com/posts/reactive-resume-v3';
|
||||
export const GITHUB_ISSUES_URL = 'https://github.com/AmruthPillai/Reactive-Resume/issues/new/choose';
|
||||
|
||||
// Default Error Message
|
||||
export const DEFAULT_ERROR_MESSAGE =
|
||||
'Something went wrong while performing this action, please report this issue on GitHub.';
|
||||
|
||||
@ -4,7 +4,7 @@ import { Login, Visibility, VisibilityOff } from '@mui/icons-material';
|
||||
import { Button, IconButton, InputAdornment, TextField } from '@mui/material';
|
||||
import { CredentialResponse, GoogleLogin } from '@react-oauth/google';
|
||||
import Joi from 'joi';
|
||||
import { isEmpty } from 'lodash';
|
||||
import isEmpty from 'lodash/isEmpty';
|
||||
import { Trans, useTranslation } from 'next-i18next';
|
||||
import { useMemo, useState } from 'react';
|
||||
import { Controller, useForm } from 'react-hook-form';
|
||||
@ -62,14 +62,7 @@ const LoginModal: React.FC = () => {
|
||||
};
|
||||
|
||||
const onSubmit = async ({ identifier, password }: FormData) => {
|
||||
await loginMutation(
|
||||
{ identifier, password },
|
||||
{
|
||||
onError: (error) => {
|
||||
toast.error(error.message);
|
||||
},
|
||||
}
|
||||
);
|
||||
await loginMutation({ identifier, password });
|
||||
|
||||
handleClose();
|
||||
};
|
||||
@ -86,14 +79,14 @@ const LoginModal: React.FC = () => {
|
||||
|
||||
const handleLoginWithGoogle = async (response: CredentialResponse) => {
|
||||
if (response.credential) {
|
||||
await loginWithGoogleMutation({ credential: response.credential }, { onError: handleLoginWithGoogleError });
|
||||
await loginWithGoogleMutation({ credential: response.credential }, { onError: handleGoogleLoginError });
|
||||
|
||||
handleClose();
|
||||
}
|
||||
};
|
||||
|
||||
const handleLoginWithGoogleError = () => {
|
||||
toast("Please try logging in using email/password, or use another browser that supports Google's One Tap API.");
|
||||
const handleGoogleLoginError = () => {
|
||||
toast.error("Google doesn't seem to be responding, please try logging in using email/password instead.");
|
||||
};
|
||||
|
||||
const PasswordVisibility = (): React.ReactElement => {
|
||||
@ -117,7 +110,7 @@ const LoginModal: React.FC = () => {
|
||||
footerChildren={
|
||||
<div className="flex gap-4">
|
||||
{!isEmpty(env('GOOGLE_CLIENT_ID')) && (
|
||||
<GoogleLogin onSuccess={handleLoginWithGoogle} onError={handleLoginWithGoogleError} />
|
||||
<GoogleLogin onSuccess={handleLoginWithGoogle} onError={handleGoogleLoginError} />
|
||||
)}
|
||||
|
||||
<Button type="submit" onClick={handleSubmit(onSubmit)} disabled={isLoading}>
|
||||
|
||||
@ -4,7 +4,7 @@ import { HowToReg } from '@mui/icons-material';
|
||||
import { Button, TextField } from '@mui/material';
|
||||
import { CredentialResponse, GoogleLogin } from '@react-oauth/google';
|
||||
import Joi from 'joi';
|
||||
import { isEmpty } from 'lodash';
|
||||
import isEmpty from 'lodash/isEmpty';
|
||||
import { Trans, useTranslation } from 'next-i18next';
|
||||
import { Controller, useForm } from 'react-hook-form';
|
||||
import toast from 'react-hot-toast';
|
||||
@ -81,14 +81,14 @@ const RegisterModal: React.FC = () => {
|
||||
|
||||
const handleLoginWithGoogle = async (response: CredentialResponse) => {
|
||||
if (response.credential) {
|
||||
await loginWithGoogleMutation({ credential: response.credential }, { onError: handleLoginWithGoogleError });
|
||||
await loginWithGoogleMutation({ credential: response.credential }, { onError: handleGoogleLoginError });
|
||||
|
||||
handleClose();
|
||||
}
|
||||
};
|
||||
|
||||
const handleLoginWithGoogleError = () => {
|
||||
toast("Please try logging in using email/password, or use another browser that supports Google's One Tap API.");
|
||||
const handleGoogleLoginError = () => {
|
||||
toast("Google doesn't seem to be responding, please try logging in using email/password instead.");
|
||||
};
|
||||
|
||||
return (
|
||||
@ -100,7 +100,7 @@ const RegisterModal: React.FC = () => {
|
||||
footerChildren={
|
||||
<div className="flex gap-4">
|
||||
{!isEmpty(env('GOOGLE_CLIENT_ID')) && (
|
||||
<GoogleLogin onSuccess={handleLoginWithGoogle} onError={handleLoginWithGoogleError} />
|
||||
<GoogleLogin onSuccess={handleLoginWithGoogle} onError={handleGoogleLoginError} />
|
||||
)}
|
||||
|
||||
<Button type="submit" onClick={handleSubmit(onSubmit)} disabled={isLoading}>
|
||||
|
||||
159
client/modals/auth/UserProfileModal.tsx
Normal file
159
client/modals/auth/UserProfileModal.tsx
Normal file
@ -0,0 +1,159 @@
|
||||
import { joiResolver } from '@hookform/resolvers/joi';
|
||||
import { CrisisAlert, ManageAccounts } from '@mui/icons-material';
|
||||
import { Button, Divider, TextField } from '@mui/material';
|
||||
import Joi from 'joi';
|
||||
import { useRouter } from 'next/router';
|
||||
import { Trans, useTranslation } from 'next-i18next';
|
||||
import { useEffect, useMemo, useState } from 'react';
|
||||
import { Controller, useForm } from 'react-hook-form';
|
||||
import { useMutation } from 'react-query';
|
||||
|
||||
import Avatar from '@/components/shared/Avatar';
|
||||
import BaseModal from '@/components/shared/BaseModal';
|
||||
import { deleteAccount, updateProfile, UpdateProfileParams } from '@/services/auth';
|
||||
import { ServerError } from '@/services/axios';
|
||||
import { useAppDispatch, useAppSelector } from '@/store/hooks';
|
||||
import { setModalState } from '@/store/modal/modalSlice';
|
||||
|
||||
type FormData = {
|
||||
name: string;
|
||||
email: string;
|
||||
};
|
||||
|
||||
const defaultState: FormData = {
|
||||
name: '',
|
||||
email: '',
|
||||
};
|
||||
|
||||
const schema = Joi.object({
|
||||
name: Joi.string().required(),
|
||||
email: Joi.string()
|
||||
.email({ tlds: { allow: false } })
|
||||
.required(),
|
||||
});
|
||||
|
||||
const UserProfileModal = () => {
|
||||
const router = useRouter();
|
||||
|
||||
const { t } = useTranslation();
|
||||
|
||||
const dispatch = useAppDispatch();
|
||||
|
||||
const [deleteText, setDeleteText] = useState<string>('');
|
||||
const isDeleteTextValid = useMemo(() => deleteText.toLowerCase() === 'delete', [deleteText]);
|
||||
|
||||
const user = useAppSelector((state) => state.auth.user);
|
||||
const { open: isOpen } = useAppSelector((state) => state.modal['auth.profile']);
|
||||
|
||||
const { mutateAsync: deleteAccountMutation } = useMutation<void, ServerError>(deleteAccount);
|
||||
const { mutateAsync: updateProfileMutation } = useMutation<void, ServerError, UpdateProfileParams>(updateProfile);
|
||||
|
||||
const { reset, getFieldState, control, handleSubmit } = useForm<FormData>({
|
||||
defaultValues: defaultState,
|
||||
resolver: joiResolver(schema),
|
||||
});
|
||||
|
||||
useEffect(() => {
|
||||
if (user && !getFieldState('name').isTouched && !getFieldState('email').isTouched) {
|
||||
reset({ name: user.name, email: user.email });
|
||||
}
|
||||
}, [user]);
|
||||
|
||||
const handleClose = () => {
|
||||
dispatch(setModalState({ modal: 'auth.profile', state: { open: false } }));
|
||||
};
|
||||
|
||||
const handleUpdate = handleSubmit(async (data) => {
|
||||
handleClose();
|
||||
await updateProfileMutation({ name: data.name });
|
||||
});
|
||||
|
||||
const handleDelete = async () => {
|
||||
await deleteAccountMutation();
|
||||
handleClose();
|
||||
|
||||
router.push('/');
|
||||
};
|
||||
|
||||
return (
|
||||
<BaseModal isOpen={isOpen} handleClose={handleClose} heading="Your Account" icon={<ManageAccounts />}>
|
||||
<div className="grid gap-4">
|
||||
<form className="grid gap-4 xl:w-2/3">
|
||||
<div className="flex items-center gap-4">
|
||||
<Avatar interactive={false} />
|
||||
|
||||
<div className="grid flex-1 gap-1.5">
|
||||
<Controller
|
||||
name="name"
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<TextField
|
||||
autoFocus
|
||||
label={t('modals.auth.profile.form.name.label')}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message}
|
||||
{...field}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
|
||||
<p className="pl-4 text-[10.25px] opacity-50">
|
||||
<Trans t={t} i18nKey="modals.auth.profile.form.avatar.help-text">
|
||||
You can update your profile picture on{' '}
|
||||
<a href="https://gravatar.com/" target="_blank" rel="noreferrer">
|
||||
Gravatar
|
||||
</a>
|
||||
</Trans>
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<Controller
|
||||
name="email"
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<TextField
|
||||
disabled
|
||||
label={t('modals.auth.profile.form.email.label')}
|
||||
error={!!fieldState.error}
|
||||
helperText={t('modals.auth.profile.form.email.help-text')}
|
||||
{...field}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
|
||||
<div>
|
||||
<Button onClick={handleUpdate}>{t('modals.auth.profile.actions.save')}</Button>
|
||||
</div>
|
||||
</form>
|
||||
|
||||
<div className="my-2">
|
||||
<Divider />
|
||||
</div>
|
||||
|
||||
<div className="flex items-center gap-2">
|
||||
<CrisisAlert />
|
||||
<h5 className="font-medium">{t('modals.auth.profile.delete-account.heading')}</h5>
|
||||
</div>
|
||||
|
||||
<p className="text-xs opacity-75">{t('modals.auth.profile.delete-account.body', { keyword: 'delete' })}</p>
|
||||
|
||||
<div className="flex max-w-xs flex-col gap-4">
|
||||
<TextField
|
||||
value={deleteText}
|
||||
placeholder="Type 'delete' to confirm"
|
||||
onChange={(e) => setDeleteText(e.target.value)}
|
||||
/>
|
||||
|
||||
<div>
|
||||
<Button variant="contained" color="error" disabled={!isDeleteTextValid} onClick={handleDelete}>
|
||||
{t('modals.auth.profile.delete-account.actions.delete')}
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</BaseModal>
|
||||
);
|
||||
};
|
||||
|
||||
export default UserProfileModal;
|
||||
@ -1,7 +1,7 @@
|
||||
import { joiResolver } from '@hookform/resolvers/joi';
|
||||
import { Add, DriveFileRenameOutline } from '@mui/icons-material';
|
||||
import { Button, TextField } from '@mui/material';
|
||||
import { DatePicker } from '@mui/x-date-pickers';
|
||||
import { DatePicker } from '@mui/x-date-pickers/DatePicker';
|
||||
import { Award, SectionPath } from '@reactive-resume/schema';
|
||||
import dayjs from 'dayjs';
|
||||
import Joi from 'joi';
|
||||
@ -128,21 +128,23 @@ const AwardModal: React.FC = () => {
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<DatePicker
|
||||
{...field}
|
||||
openTo="year"
|
||||
inputRef={field.ref}
|
||||
label={t<string>('builder.common.form.date.label')}
|
||||
value={dayjs(field.value)}
|
||||
views={['year', 'month', 'day']}
|
||||
onChange={(date: Date | null, keyboardInputValue: string | undefined) => {
|
||||
isEmpty(keyboardInputValue) && field.onChange('');
|
||||
date && dayjs(date).utc().isValid() && field.onChange(dayjs(date).utc().toISOString());
|
||||
slots={{
|
||||
textField: (params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
),
|
||||
}}
|
||||
onChange={(date: dayjs.Dayjs | null) => {
|
||||
date && dayjs(date).isValid() && field.onChange(dayjs(date).format('YYYY-MM-DD'));
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
|
||||
@ -1,7 +1,7 @@
|
||||
import { joiResolver } from '@hookform/resolvers/joi';
|
||||
import { Add, DriveFileRenameOutline } from '@mui/icons-material';
|
||||
import { Button, TextField } from '@mui/material';
|
||||
import { DatePicker } from '@mui/x-date-pickers';
|
||||
import { DatePicker } from '@mui/x-date-pickers/DatePicker';
|
||||
import { Certificate, SectionPath } from '@reactive-resume/schema';
|
||||
import dayjs from 'dayjs';
|
||||
import Joi from 'joi';
|
||||
@ -128,21 +128,23 @@ const CertificateModal: React.FC = () => {
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<DatePicker
|
||||
{...field}
|
||||
openTo="year"
|
||||
inputRef={field.ref}
|
||||
label={t<string>('builder.common.form.date.label')}
|
||||
value={dayjs(field.value)}
|
||||
views={['year', 'month', 'day']}
|
||||
onChange={(date: Date | null, keyboardInputValue: string | undefined) => {
|
||||
isEmpty(keyboardInputValue) && field.onChange('');
|
||||
date && dayjs(date).utc().isValid() && field.onChange(dayjs(date).utc().toISOString());
|
||||
slots={{
|
||||
textField: (params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
),
|
||||
}}
|
||||
onChange={(date: dayjs.Dayjs | null) => {
|
||||
date && dayjs(date).isValid() && field.onChange(dayjs(date).format('YYYY-MM-DD'));
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
|
||||
@ -1,7 +1,7 @@
|
||||
import { joiResolver } from '@hookform/resolvers/joi';
|
||||
import { Add, DriveFileRenameOutline } from '@mui/icons-material';
|
||||
import { Button, Slider, TextField } from '@mui/material';
|
||||
import { DatePicker } from '@mui/x-date-pickers';
|
||||
import { DatePicker } from '@mui/x-date-pickers/DatePicker';
|
||||
import { Custom } from '@reactive-resume/schema';
|
||||
import dayjs from 'dayjs';
|
||||
import Joi from 'joi';
|
||||
@ -145,21 +145,23 @@ const CustomModal: React.FC = () => {
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<DatePicker
|
||||
{...field}
|
||||
openTo="year"
|
||||
inputRef={field.ref}
|
||||
label={t<string>('builder.common.form.start-date.label')}
|
||||
value={dayjs(field.value)}
|
||||
views={['year', 'month', 'day']}
|
||||
onChange={(date: Date | null, keyboardInputValue: string | undefined) => {
|
||||
isEmpty(keyboardInputValue) && field.onChange('');
|
||||
date && dayjs(date).utc().isValid() && field.onChange(dayjs(date).utc().toISOString());
|
||||
slots={{
|
||||
textField: (params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
),
|
||||
}}
|
||||
onChange={(date: dayjs.Dayjs | null) => {
|
||||
date && dayjs(date).isValid() && field.onChange(dayjs(date).format('YYYY-MM-DD'));
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
@ -169,21 +171,23 @@ const CustomModal: React.FC = () => {
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<DatePicker
|
||||
{...field}
|
||||
openTo="year"
|
||||
inputRef={field.ref}
|
||||
label={t<string>('builder.common.form.end-date.label')}
|
||||
value={dayjs(field.value)}
|
||||
views={['year', 'month', 'day']}
|
||||
onChange={(date: Date | null, keyboardInputValue: string | undefined) => {
|
||||
isEmpty(keyboardInputValue) && field.onChange('');
|
||||
date && dayjs(date).utc().isValid() && field.onChange(dayjs(date).utc().toISOString());
|
||||
slots={{
|
||||
textField: (params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || t<string>('builder.common.form.end-date.help-text')}
|
||||
/>
|
||||
),
|
||||
}}
|
||||
onChange={(date: dayjs.Dayjs | null) => {
|
||||
date && dayjs(date).isValid() && field.onChange(dayjs(date).format('YYYY-MM-DD'));
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || 'Leave this field blank, if still present'}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
|
||||
@ -1,7 +1,7 @@
|
||||
import { joiResolver } from '@hookform/resolvers/joi';
|
||||
import { Add, DriveFileRenameOutline } from '@mui/icons-material';
|
||||
import { Button, TextField } from '@mui/material';
|
||||
import { DatePicker } from '@mui/x-date-pickers';
|
||||
import { DatePicker } from '@mui/x-date-pickers/DatePicker';
|
||||
import { Education, SectionPath } from '@reactive-resume/schema';
|
||||
import dayjs from 'dayjs';
|
||||
import Joi from 'joi';
|
||||
@ -167,21 +167,23 @@ const EducationModal: React.FC = () => {
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<DatePicker
|
||||
{...field}
|
||||
openTo="year"
|
||||
inputRef={field.ref}
|
||||
label={t<string>('builder.common.form.start-date.label')}
|
||||
value={dayjs(field.value)}
|
||||
views={['year', 'month', 'day']}
|
||||
onChange={(date: Date | null, keyboardInputValue: string | undefined) => {
|
||||
isEmpty(keyboardInputValue) && field.onChange('');
|
||||
date && dayjs(date).utc().isValid() && field.onChange(dayjs(date).utc().toISOString());
|
||||
slots={{
|
||||
textField: (params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
),
|
||||
}}
|
||||
onChange={(date: dayjs.Dayjs | null) => {
|
||||
date && dayjs(date).isValid() && field.onChange(dayjs(date).format('YYYY-MM-DD'));
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
@ -191,21 +193,23 @@ const EducationModal: React.FC = () => {
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<DatePicker
|
||||
{...field}
|
||||
openTo="year"
|
||||
inputRef={field.ref}
|
||||
label={t<string>('builder.common.form.end-date.label')}
|
||||
value={dayjs(field.value)}
|
||||
views={['year', 'month', 'day']}
|
||||
onChange={(date: Date | null, keyboardInputValue: string | undefined) => {
|
||||
isEmpty(keyboardInputValue) && field.onChange('');
|
||||
date && dayjs(date).utc().isValid() && field.onChange(dayjs(date).utc().toISOString());
|
||||
slots={{
|
||||
textField: (params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || t<string>('builder.common.form.end-date.help-text')}
|
||||
/>
|
||||
),
|
||||
}}
|
||||
onChange={(date: dayjs.Dayjs | null) => {
|
||||
date && dayjs(date).isValid() && field.onChange(dayjs(date).format('YYYY-MM-DD'));
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || t<string>('builder.common.form.end-date.help-text')}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
|
||||
@ -1,7 +1,7 @@
|
||||
import { joiResolver } from '@hookform/resolvers/joi';
|
||||
import { Add, DriveFileRenameOutline } from '@mui/icons-material';
|
||||
import { Button, TextField } from '@mui/material';
|
||||
import { DatePicker } from '@mui/x-date-pickers';
|
||||
import { DatePicker } from '@mui/x-date-pickers/DatePicker';
|
||||
import { Project, SectionPath } from '@reactive-resume/schema';
|
||||
import dayjs from 'dayjs';
|
||||
import Joi from 'joi';
|
||||
@ -137,21 +137,23 @@ const ProjectModal: React.FC = () => {
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<DatePicker
|
||||
{...field}
|
||||
openTo="year"
|
||||
inputRef={field.ref}
|
||||
label={t<string>('builder.common.form.start-date.label')}
|
||||
value={dayjs(field.value)}
|
||||
views={['year', 'month', 'day']}
|
||||
onChange={(date: Date | null, keyboardInputValue: string | undefined) => {
|
||||
isEmpty(keyboardInputValue) && field.onChange('');
|
||||
date && dayjs(date).utc().isValid() && field.onChange(dayjs(date).utc().toISOString());
|
||||
slots={{
|
||||
textField: (params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
),
|
||||
}}
|
||||
onChange={(date: dayjs.Dayjs | null) => {
|
||||
date && dayjs(date).isValid() && field.onChange(dayjs(date).format('YYYY-MM-DD'));
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
@ -161,21 +163,23 @@ const ProjectModal: React.FC = () => {
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<DatePicker
|
||||
{...field}
|
||||
openTo="year"
|
||||
inputRef={field.ref}
|
||||
label={t<string>('builder.common.form.end-date.label')}
|
||||
value={dayjs(field.value)}
|
||||
views={['year', 'month', 'day']}
|
||||
onChange={(date: Date | null, keyboardInputValue: string | undefined) => {
|
||||
isEmpty(keyboardInputValue) && field.onChange('');
|
||||
date && dayjs(date).utc().isValid() && field.onChange(dayjs(date).utc().toISOString());
|
||||
slots={{
|
||||
textField: (params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || t<string>('builder.common.form.end-date.help-text')}
|
||||
/>
|
||||
),
|
||||
}}
|
||||
onChange={(date: dayjs.Dayjs | null) => {
|
||||
date && dayjs(date).isValid() && field.onChange(dayjs(date).format('YYYY-MM-DD'));
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || 'Leave this field blank, if still present'}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
|
||||
@ -1,7 +1,7 @@
|
||||
import { joiResolver } from '@hookform/resolvers/joi';
|
||||
import { Add, DriveFileRenameOutline } from '@mui/icons-material';
|
||||
import { Button, TextField } from '@mui/material';
|
||||
import { DatePicker } from '@mui/x-date-pickers';
|
||||
import { DatePicker } from '@mui/x-date-pickers/DatePicker';
|
||||
import { Publication, SectionPath } from '@reactive-resume/schema';
|
||||
import dayjs from 'dayjs';
|
||||
import Joi from 'joi';
|
||||
@ -128,21 +128,23 @@ const PublicationModal: React.FC = () => {
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<DatePicker
|
||||
{...field}
|
||||
openTo="year"
|
||||
inputRef={field.ref}
|
||||
label={t<string>('builder.common.form.date.label')}
|
||||
value={dayjs(field.value)}
|
||||
views={['year', 'month', 'day']}
|
||||
onChange={(date: Date | null, keyboardInputValue: string | undefined) => {
|
||||
isEmpty(keyboardInputValue) && field.onChange('');
|
||||
date && dayjs(date).utc().isValid() && field.onChange(dayjs(date).utc().toISOString());
|
||||
slots={{
|
||||
textField: (params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
),
|
||||
}}
|
||||
onChange={(date: dayjs.Dayjs | null) => {
|
||||
date && dayjs(date).isValid() && field.onChange(dayjs(date).format('YYYY-MM-DD'));
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
|
||||
@ -1,7 +1,7 @@
|
||||
import { joiResolver } from '@hookform/resolvers/joi';
|
||||
import { Add, DriveFileRenameOutline } from '@mui/icons-material';
|
||||
import { Button, TextField } from '@mui/material';
|
||||
import { DatePicker } from '@mui/x-date-pickers';
|
||||
import { DatePicker } from '@mui/x-date-pickers/DatePicker';
|
||||
import { SectionPath, Volunteer } from '@reactive-resume/schema';
|
||||
import dayjs from 'dayjs';
|
||||
import Joi from 'joi';
|
||||
@ -134,21 +134,23 @@ const VolunteerModal: React.FC = () => {
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<DatePicker
|
||||
{...field}
|
||||
openTo="year"
|
||||
inputRef={field.ref}
|
||||
label={t<string>('builder.common.form.start-date.label')}
|
||||
value={dayjs(field.value)}
|
||||
views={['year', 'month', 'day']}
|
||||
onChange={(date: Date | null, keyboardInputValue: string | undefined) => {
|
||||
isEmpty(keyboardInputValue) && field.onChange('');
|
||||
date && dayjs(date).utc().isValid() && field.onChange(dayjs(date).utc().toISOString());
|
||||
slots={{
|
||||
textField: (params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
),
|
||||
}}
|
||||
onChange={(date: dayjs.Dayjs | null) => {
|
||||
date && dayjs(date).isValid() && field.onChange(dayjs(date).format('YYYY-MM-DD'));
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
@ -158,21 +160,23 @@ const VolunteerModal: React.FC = () => {
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<DatePicker
|
||||
{...field}
|
||||
openTo="year"
|
||||
inputRef={field.ref}
|
||||
label={t<string>('builder.common.form.end-date.label')}
|
||||
value={dayjs(field.value)}
|
||||
views={['year', 'month', 'day']}
|
||||
onChange={(date: Date | null, keyboardInputValue: string | undefined) => {
|
||||
isEmpty(keyboardInputValue) && field.onChange('');
|
||||
date && dayjs(date).utc().isValid() && field.onChange(dayjs(date).utc().toISOString());
|
||||
slots={{
|
||||
textField: (params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || t<string>('builder.common.form.end-date.help-text')}
|
||||
/>
|
||||
),
|
||||
}}
|
||||
onChange={(date: dayjs.Dayjs | null) => {
|
||||
date && dayjs(date).isValid() && field.onChange(dayjs(date).format('YYYY-MM-DD'));
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || 'Leave this field blank, if still present'}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
|
||||
@ -1,7 +1,7 @@
|
||||
import { joiResolver } from '@hookform/resolvers/joi';
|
||||
import { Add, DriveFileRenameOutline } from '@mui/icons-material';
|
||||
import { Button, TextField } from '@mui/material';
|
||||
import { DatePicker } from '@mui/x-date-pickers';
|
||||
import { DatePicker } from '@mui/x-date-pickers/DatePicker';
|
||||
import { WorkExperience } from '@reactive-resume/schema';
|
||||
import dayjs from 'dayjs';
|
||||
import Joi from 'joi';
|
||||
@ -56,8 +56,15 @@ const WorkModal: React.FC = () => {
|
||||
|
||||
const isEditMode = useMemo(() => !!item, [item]);
|
||||
|
||||
const addText = useMemo(() => t<string>('builder.common.actions.add', { token: heading }), [t, heading]);
|
||||
const editText = useMemo(() => t<string>('builder.common.actions.edit', { token: heading }), [t, heading]);
|
||||
const addText = useMemo(
|
||||
() => t<string>('builder.common.actions.add', { token: t<string>(`builder.leftSidebar.${path}.heading`, heading) }),
|
||||
[t, heading]
|
||||
);
|
||||
const editText = useMemo(
|
||||
() =>
|
||||
t<string>('builder.common.actions.edit', { token: t<string>(`builder.leftSidebar.${path}.heading`, heading) }),
|
||||
[t, heading]
|
||||
);
|
||||
|
||||
const { reset, control, handleSubmit } = useForm<FormData>({
|
||||
defaultValues: defaultState,
|
||||
@ -134,21 +141,23 @@ const WorkModal: React.FC = () => {
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<DatePicker
|
||||
{...field}
|
||||
openTo="year"
|
||||
inputRef={field.ref}
|
||||
label={t<string>('builder.common.form.start-date.label')}
|
||||
value={dayjs(field.value)}
|
||||
views={['year', 'month', 'day']}
|
||||
onChange={(date: Date | null, keyboardInputValue: string | undefined) => {
|
||||
isEmpty(keyboardInputValue) && field.onChange('');
|
||||
date && dayjs(date).utc().isValid() && field.onChange(dayjs(date).utc().toISOString());
|
||||
slots={{
|
||||
textField: (params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
),
|
||||
}}
|
||||
onChange={(date: dayjs.Dayjs | null) => {
|
||||
date && dayjs(date).isValid() && field.onChange(dayjs(date).format('YYYY-MM-DD'));
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || params.inputProps?.placeholder}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
@ -158,21 +167,23 @@ const WorkModal: React.FC = () => {
|
||||
control={control}
|
||||
render={({ field, fieldState }) => (
|
||||
<DatePicker
|
||||
{...field}
|
||||
openTo="year"
|
||||
inputRef={field.ref}
|
||||
label={t<string>('builder.common.form.end-date.label')}
|
||||
value={dayjs(field.value)}
|
||||
views={['year', 'month', 'day']}
|
||||
onChange={(date: Date | null, keyboardInputValue: string | undefined) => {
|
||||
isEmpty(keyboardInputValue) && field.onChange('');
|
||||
date && dayjs(date).utc().isValid() && field.onChange(dayjs(date).utc().toISOString());
|
||||
slots={{
|
||||
textField: (params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || t<string>('builder.common.form.end-date.help-text')}
|
||||
/>
|
||||
),
|
||||
}}
|
||||
onChange={(date: dayjs.Dayjs | null) => {
|
||||
date && dayjs(date).isValid() && field.onChange(dayjs(date).format('YYYY-MM-DD'));
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
error={!!fieldState.error}
|
||||
helperText={fieldState.error?.message || t<string>('builder.common.form.end-date.help-text')}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
|
||||
@ -6,7 +6,6 @@ import Joi from 'joi';
|
||||
import { useTranslation } from 'next-i18next';
|
||||
import { useEffect } from 'react';
|
||||
import { Controller, useForm } from 'react-hook-form';
|
||||
import toast from 'react-hot-toast';
|
||||
import { useMutation } from 'react-query';
|
||||
|
||||
import BaseModal from '@/components/shared/BaseModal';
|
||||
@ -66,15 +65,10 @@ const CreateResumeModal: React.FC = () => {
|
||||
}, [name, setValue]);
|
||||
|
||||
const onSubmit = async ({ name, slug, isPublic }: FormData) => {
|
||||
try {
|
||||
await mutateAsync({ name, slug, public: isPublic });
|
||||
await mutateAsync({ name, slug, public: isPublic });
|
||||
await queryClient.invalidateQueries(RESUMES_QUERY);
|
||||
|
||||
await queryClient.invalidateQueries(RESUMES_QUERY);
|
||||
|
||||
handleClose();
|
||||
} catch (error: any) {
|
||||
toast.error(error.message);
|
||||
}
|
||||
handleClose();
|
||||
};
|
||||
|
||||
const handleClose = () => {
|
||||
|
||||
@ -68,8 +68,8 @@ const ImportExternalModal: React.FC = () => {
|
||||
}
|
||||
|
||||
await mutateAsync({ integration, file });
|
||||
|
||||
queryClient.invalidateQueries(RESUMES_QUERY);
|
||||
|
||||
handleClose();
|
||||
}
|
||||
};
|
||||
|
||||
@ -8,6 +8,7 @@ import ForgotPasswordModal from './auth/ForgotPasswordModal';
|
||||
import LoginModal from './auth/LoginModal';
|
||||
import RegisterModal from './auth/RegisterModal';
|
||||
import ResetPasswordModal from './auth/ResetPasswordModal';
|
||||
import UserProfileModal from './auth/UserProfileModal';
|
||||
import AwardModal from './builder/sections/AwardModal';
|
||||
import CertificateModal from './builder/sections/CertificateModal';
|
||||
import CustomModal from './builder/sections/CustomModal';
|
||||
@ -49,6 +50,7 @@ const ModalWrapper: React.FC = () => {
|
||||
<RegisterModal />
|
||||
<ForgotPasswordModal />
|
||||
<ResetPasswordModal />
|
||||
<UserProfileModal />
|
||||
|
||||
{/* Dashboard */}
|
||||
<CreateResumeModal />
|
||||
|
||||
@ -35,6 +35,7 @@ const i18nConfig = {
|
||||
'or',
|
||||
'pl',
|
||||
'pt',
|
||||
'pt-BR',
|
||||
'ro',
|
||||
'ru',
|
||||
'sr',
|
||||
|
||||
@ -1,6 +1,5 @@
|
||||
const { version } = require('../package.json');
|
||||
const { i18n } = require('./next-i18next.config');
|
||||
const { withSentryConfig } = require('@sentry/nextjs');
|
||||
|
||||
/** @type {import('next').NextConfig} */
|
||||
const nextConfig = {
|
||||
@ -16,11 +15,6 @@ const nextConfig = {
|
||||
domains: ['cdn.rxresu.me', 'www.gravatar.com'],
|
||||
},
|
||||
|
||||
sentry: {
|
||||
hideSourceMaps: true,
|
||||
widenClientFileUpload: true,
|
||||
},
|
||||
|
||||
// Hack to make Tailwind darkMode 'class' strategy with CSS Modules
|
||||
// Ref: https://github.com/tailwindlabs/tailwindcss/issues/3258#issuecomment-968368156
|
||||
webpack: (config) => {
|
||||
@ -53,11 +47,4 @@ const nextConfig = {
|
||||
},
|
||||
};
|
||||
|
||||
/** @type {import('@sentry/nextjs').SentryWebpackPluginOptions} */
|
||||
const sentryConfig = {
|
||||
silent: true,
|
||||
project: 'client',
|
||||
dryRun: process.env.NODE_ENV !== 'production',
|
||||
};
|
||||
|
||||
module.exports = withSentryConfig(nextConfig, sentryConfig);
|
||||
module.exports = nextConfig;
|
||||
|
||||
@ -9,76 +9,74 @@
|
||||
},
|
||||
"dependencies": {
|
||||
"@beam-australia/react-env": "^3.1.1",
|
||||
"@date-io/dayjs": "^2.16.0",
|
||||
"@emotion/css": "^11.10.5",
|
||||
"@emotion/react": "^11.10.5",
|
||||
"@emotion/styled": "^11.10.5",
|
||||
"@hello-pangea/dnd": "^16.0.1",
|
||||
"@hookform/resolvers": "2.9.10",
|
||||
"@emotion/css": "^11.10.6",
|
||||
"@emotion/react": "^11.10.6",
|
||||
"@emotion/styled": "^11.10.6",
|
||||
"@hello-pangea/dnd": "^16.2.0",
|
||||
"@hookform/resolvers": "3.0.1",
|
||||
"@monaco-editor/react": "^4.4.6",
|
||||
"@mui/icons-material": "^5.10.15",
|
||||
"@mui/lab": "^5.0.0-alpha.109",
|
||||
"@mui/material": "^5.10.15",
|
||||
"@mui/system": "^5.10.15",
|
||||
"@mui/x-date-pickers": "5.0.8",
|
||||
"@next/env": "^13.0.5",
|
||||
"@react-oauth/google": "^0.5.0",
|
||||
"@reduxjs/toolkit": "^1.9.0",
|
||||
"@sentry/nextjs": "^7.21.1",
|
||||
"axios": "^1.2.0",
|
||||
"@mui/icons-material": "^5.11.16",
|
||||
"@mui/lab": "^5.0.0-alpha.125",
|
||||
"@mui/material": "^5.11.16",
|
||||
"@mui/system": "^5.11.16",
|
||||
"@mui/x-date-pickers": "6.0.4",
|
||||
"@react-oauth/google": "^0.9.0",
|
||||
"@reduxjs/toolkit": "^1.9.3",
|
||||
"axios": "^1.3.5",
|
||||
"clsx": "^1.2.1",
|
||||
"dayjs": "^1.11.6",
|
||||
"dayjs": "^1.11.7",
|
||||
"downloadjs": "^1.4.7",
|
||||
"joi": "^17.7.0",
|
||||
"joi": "^17.9.1",
|
||||
"lodash": "^4.17.21",
|
||||
"md5-hex": "^4.0.0",
|
||||
"monaco-editor": "^0.34.1",
|
||||
"nanoid": "^3.3.4",
|
||||
"next": "13.0.5",
|
||||
"next-i18next": "^13.0.0",
|
||||
"monaco-editor": "^0.37.0",
|
||||
"nanoid": "3.3.4",
|
||||
"next": "13.2.4",
|
||||
"next-i18next": "^13.2.2",
|
||||
"react": "^18.2.0",
|
||||
"react-colorful": "^5.6.1",
|
||||
"react-dnd": "16.0.1",
|
||||
"react-dnd-html5-backend": "16.0.1",
|
||||
"react-dom": "^18.2.0",
|
||||
"react-hook-form": "^7.39.5",
|
||||
"react-hook-form": "^7.43.9",
|
||||
"react-hot-toast": "2.4.0",
|
||||
"react-icons": "^4.6.0",
|
||||
"react-markdown": "^8.0.3",
|
||||
"react-query": "^3.39.2",
|
||||
"react-icons": "^4.8.0",
|
||||
"react-markdown": "^8.0.6",
|
||||
"react-query": "^3.39.3",
|
||||
"react-redux": "^8.0.5",
|
||||
"react-zoom-pan-pinch": "^2.1.3",
|
||||
"redux": "^4.2.0",
|
||||
"react-zoom-pan-pinch": "^3.0.6",
|
||||
"redux": "^4.2.1",
|
||||
"redux-persist": "^6.0.0",
|
||||
"redux-saga": "^1.2.1",
|
||||
"redux-saga": "^1.2.3",
|
||||
"redux-undo": "^1.0.1",
|
||||
"rehype-katex": "^6.0.2",
|
||||
"remark-gfm": "^3.0.1",
|
||||
"sharp": "^0.31.2",
|
||||
"remark-math": "^5.1.1",
|
||||
"sharp": "^0.32.0",
|
||||
"uuid": "^9.0.0",
|
||||
"webfontloader": "^1.6.28"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@babel/core": "^7.20.2",
|
||||
"@babel/core": "^7.21.4",
|
||||
"@reactive-resume/schema": "workspace:*",
|
||||
"@tailwindcss/typography": "^0.5.8",
|
||||
"@tailwindcss/typography": "^0.5.9",
|
||||
"@types/downloadjs": "^1.4.3",
|
||||
"@types/lodash": "^4.14.190",
|
||||
"@types/node": "^18.11.9",
|
||||
"@types/react": "^18.0.25",
|
||||
"@types/react-dom": "^18.0.9",
|
||||
"@types/react-redux": "^7.1.24",
|
||||
"@types/tailwindcss": "^3.0.11",
|
||||
"@types/uuid": "^8.3.4",
|
||||
"@types/lodash": "^4.14.192",
|
||||
"@types/node": "^18.15.11",
|
||||
"@types/react": "^18.0.33",
|
||||
"@types/react-dom": "^18.0.11",
|
||||
"@types/react-redux": "^7.1.25",
|
||||
"@types/uuid": "^9.0.1",
|
||||
"@types/webfontloader": "^1.6.35",
|
||||
"autoprefixer": "^10.4.13",
|
||||
"csstype": "^3.1.1",
|
||||
"eslint-config-next": "^13.0.5",
|
||||
"eslint-plugin-tailwindcss": "^3.7.0",
|
||||
"autoprefixer": "^10.4.14",
|
||||
"csstype": "^3.1.2",
|
||||
"eslint-config-next": "^13.2.4",
|
||||
"eslint-plugin-tailwindcss": "^3.11.0",
|
||||
"eslint-plugin-unused-imports": "^2.0.0",
|
||||
"next-sitemap": "^3.1.32",
|
||||
"postcss": "^8.4.19",
|
||||
"sass": "^1.56.1",
|
||||
"tailwindcss": "^3.2.4",
|
||||
"typescript": "^4.9.3"
|
||||
"next-sitemap": "^4.0.6",
|
||||
"postcss": "^8.4.21",
|
||||
"sass": "^1.60.0",
|
||||
"tailwindcss": "^3.3.1",
|
||||
"typescript": "^5.0.3"
|
||||
}
|
||||
}
|
||||
|
||||
@ -15,6 +15,7 @@ import toast from 'react-hot-toast';
|
||||
import { useMutation, useQuery } from 'react-query';
|
||||
|
||||
import Page from '@/components/build/Center/Page';
|
||||
import { DEFAULT_ERROR_MESSAGE } from '@/constants/index';
|
||||
import { ServerError } from '@/services/axios';
|
||||
import { printResumeAsPdf, PrintResumeAsPdfParams } from '@/services/printer';
|
||||
import { fetchResumeByIdentifier } from '@/services/resume';
|
||||
@ -105,7 +106,7 @@ const Preview: NextPage<Props> = ({ username, slug, resume: initialData }) => {
|
||||
|
||||
download(url);
|
||||
} catch {
|
||||
toast.error('Something went wrong, please try again later.');
|
||||
toast.error(DEFAULT_ERROR_MESSAGE);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@ -1,8 +1,8 @@
|
||||
import '@/styles/globals.scss';
|
||||
|
||||
import env from '@beam-australia/react-env';
|
||||
import DayjsAdapter from '@date-io/dayjs';
|
||||
import { LocalizationProvider } from '@mui/x-date-pickers';
|
||||
import { AdapterDayjs } from '@mui/x-date-pickers/AdapterDayjs';
|
||||
import { LocalizationProvider } from '@mui/x-date-pickers/LocalizationProvider';
|
||||
import { GoogleOAuthProvider } from '@react-oauth/google';
|
||||
import type { AppProps } from 'next/app';
|
||||
import Head from 'next/head';
|
||||
@ -32,7 +32,7 @@ const App = ({ Component, pageProps }: AppProps): JSX.Element => (
|
||||
</Head>
|
||||
|
||||
<ReduxProvider store={store}>
|
||||
<LocalizationProvider dateAdapter={DayjsAdapter}>
|
||||
<LocalizationProvider dateAdapter={AdapterDayjs}>
|
||||
<PersistGate loading={null} persistor={persistor}>
|
||||
<GoogleOAuthProvider clientId={env('GOOGLE_CLIENT_ID')}>
|
||||
<QueryClientProvider client={queryClient}>
|
||||
|
||||
@ -1,15 +1,69 @@
|
||||
import { NextPage } from 'next';
|
||||
import NextDocument, { DocumentContext, Head, Html, Main, NextScript } from 'next/document';
|
||||
import Script from 'next/script';
|
||||
|
||||
const Document: NextPage = () => (
|
||||
<Html lang="en">
|
||||
<Head />
|
||||
<Head>
|
||||
<Script
|
||||
id="google-tag-manager"
|
||||
type="text/javascript"
|
||||
strategy="afterInteractive"
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: `(function(w,d,s,l,i){w[l]=w[l]||[];w[l].push({'gtm.start':new Date().getTime(),event:'gtm.js'});var f=d.getElementsByTagName(s)[0],j=d.createElement(s),dl=l!='dataLayer'?'&l='+l:'';j.async=true;j.src='https://www.googletagmanager.com/gtm.js?id='+i+dl;f.parentNode.insertBefore(j,f);})(window,document,'script','dataLayer','GTM-M9DK4S4');`,
|
||||
}}
|
||||
/>
|
||||
|
||||
<Script
|
||||
id="logo-schema"
|
||||
type="application/ld+json"
|
||||
strategy="afterInteractive"
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: `{
|
||||
"@context": "https://schema.org",
|
||||
"@type": "Organization",
|
||||
"url": "https://rxresu.me",
|
||||
"logo": "https://rxresu.me/images/logos/logo.svg"
|
||||
}`,
|
||||
}}
|
||||
/>
|
||||
|
||||
<Script
|
||||
id="software-application-schema"
|
||||
type="application/ld+json"
|
||||
strategy="afterInteractive"
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: `{
|
||||
"@context": "https://schema.org",
|
||||
"@type": "SoftwareApplication",
|
||||
"name": "Reactive Resume",
|
||||
"operatingSystem": "Windows, macOS, Linux, Android, iOS",
|
||||
"applicationCategory": "BrowserApplication",
|
||||
"aggregateRating": {
|
||||
"@type": "AggregateRating",
|
||||
"ratingValue": "5",
|
||||
"ratingCount": "11394"
|
||||
},
|
||||
"offers": {
|
||||
"@type": "Offer",
|
||||
"price": "0"
|
||||
}
|
||||
}`,
|
||||
}}
|
||||
/>
|
||||
</Head>
|
||||
|
||||
<body>
|
||||
<Main />
|
||||
<NextScript />
|
||||
|
||||
<script src="/__ENV.js" />
|
||||
|
||||
<noscript
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: `<iframe src="https://www.googletagmanager.com/ns.html?id=GTM-M9DK4S4" height="0" width="0" style="display:none;visibility:hidden"></iframe>`,
|
||||
}}
|
||||
/>
|
||||
</body>
|
||||
</Html>
|
||||
);
|
||||
|
||||
@ -1,14 +0,0 @@
|
||||
import * as Sentry from '@sentry/nextjs';
|
||||
import type { NextPage } from 'next';
|
||||
import type { ErrorProps } from 'next/error';
|
||||
import NextErrorComponent from 'next/error';
|
||||
|
||||
const CustomErrorComponent: NextPage<ErrorProps> = (props) => <NextErrorComponent statusCode={props.statusCode} />;
|
||||
|
||||
CustomErrorComponent.getInitialProps = async (contextData) => {
|
||||
await Sentry.captureUnderscoreErrorException(contextData);
|
||||
|
||||
return NextErrorComponent.getInitialProps(contextData);
|
||||
};
|
||||
|
||||
export default CustomErrorComponent;
|
||||
@ -20,7 +20,7 @@ import { useAppDispatch, useAppSelector } from '@/store/hooks';
|
||||
import { setModalState } from '@/store/modal/modalSlice';
|
||||
import styles from '@/styles/pages/Home.module.scss';
|
||||
|
||||
import { DIGITALOCEAN_URL, DOCS_URL, DONATION_URL, GITHUB_URL } from '../constants';
|
||||
import { DIGITALOCEAN_URL, DOCS_URL, DONATION_URL, GITHUB_URL, REDDIT_URL } from '../constants';
|
||||
|
||||
export const getStaticProps: GetStaticProps = async ({ locale = 'en' }) => ({
|
||||
props: {
|
||||
@ -177,6 +177,12 @@ const Home: NextPage = () => {
|
||||
</Button>
|
||||
</a>
|
||||
|
||||
<a href={REDDIT_URL} target="_blank" rel="noreferrer">
|
||||
<Button variant="text" startIcon={<LinkIcon />}>
|
||||
{t<string>('landing.links.links.reddit')}
|
||||
</Button>
|
||||
</a>
|
||||
|
||||
<a href={DONATION_URL} target="_blank" rel="noreferrer">
|
||||
<Button variant="text" startIcon={<LinkIcon />}>
|
||||
{t<string>('landing.links.links.donate')}
|
||||
|
||||
@ -11,7 +11,6 @@ import Link from 'next/link';
|
||||
import { useRouter } from 'next/router';
|
||||
import { serverSideTranslations } from 'next-i18next/serverSideTranslations';
|
||||
import { useEffect } from 'react';
|
||||
import toast from 'react-hot-toast';
|
||||
import { useMutation, useQuery } from 'react-query';
|
||||
|
||||
import Page from '@/components/build/Center/Page';
|
||||
@ -69,17 +68,13 @@ const Preview: NextPage<Props> = ({ shortId }) => {
|
||||
const layout: string[][][] = get(resume, 'metadata.layout', []);
|
||||
|
||||
const handleDownload = async () => {
|
||||
try {
|
||||
const url = await mutateAsync({
|
||||
username: resume.user.username,
|
||||
slug: resume.slug,
|
||||
lastUpdated: dayjs(resume.updatedAt).unix().toString(),
|
||||
});
|
||||
const url = await mutateAsync({
|
||||
username: resume.user.username,
|
||||
slug: resume.slug,
|
||||
lastUpdated: dayjs(resume.updatedAt).unix().toString(),
|
||||
});
|
||||
|
||||
download(url);
|
||||
} catch {
|
||||
toast.error('Something went wrong, please try again later.');
|
||||
}
|
||||
download(url);
|
||||
};
|
||||
|
||||
return (
|
||||
|
||||
@ -3,6 +3,7 @@
|
||||
"actions": {
|
||||
"add": "Tilføj ny {{token}}",
|
||||
"delete": "Slet {{token}}",
|
||||
"duplicate": "Dublet afsnit",
|
||||
"edit": "Rediger {{token}}"
|
||||
},
|
||||
"columns": {
|
||||
@ -80,13 +81,13 @@
|
||||
"center-artboard": "Centrer tegnebræt",
|
||||
"copy-link": "Kopier link til CV",
|
||||
"export-pdf": "Eksporter PDF",
|
||||
"redo": "Redo",
|
||||
"toggle-orientation": "Skift sideorientering",
|
||||
"toggle-page-break-line": "Skift sideskiftlinje",
|
||||
"toggle-sidebars": "Sidebjælke til/fra",
|
||||
"zoom-in": "Zoom ind",
|
||||
"zoom-out": "Zoom ud",
|
||||
"undo": "Fortryd",
|
||||
"redo": "Redo"
|
||||
"zoom-in": "Zoom ind",
|
||||
"zoom-out": "Zoom ud"
|
||||
}
|
||||
},
|
||||
"header": {
|
||||
@ -114,6 +115,9 @@
|
||||
"actions": {
|
||||
"photo-filters": "Fotofiltre"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Fødselsdato"
|
||||
},
|
||||
"heading": "Grundlæggende",
|
||||
"headline": {
|
||||
"label": "Overskrift"
|
||||
@ -121,9 +125,6 @@
|
||||
"name": {
|
||||
"label": "Fulde navn"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Fødselsdato"
|
||||
},
|
||||
"photo-filters": {
|
||||
"effects": {
|
||||
"border": {
|
||||
@ -264,14 +265,15 @@
|
||||
"button": "GitHub-problemer",
|
||||
"heading": "Fejl? Ønsker til en ny funktion?"
|
||||
},
|
||||
"docs": "Dokumentation",
|
||||
"donate": {
|
||||
"body": "Hvis du kunne lide at bruge Reactive Resume, bedes du overveje at donere så meget som muligt til formålet med at holde appen oppe og køre, uden annoncer og gratis for evigt.",
|
||||
"button": "Købe mig en kop kaffe",
|
||||
"heading": "Donér til Reactive Resume"
|
||||
},
|
||||
"github": "Kildekode",
|
||||
"docs": "Dokumentation",
|
||||
"heading": "Links"
|
||||
"heading": "Links",
|
||||
"reddit": "Reddit"
|
||||
},
|
||||
"settings": {
|
||||
"global": {
|
||||
@ -290,14 +292,14 @@
|
||||
},
|
||||
"heading": "Indstillinger",
|
||||
"page": {
|
||||
"format": {
|
||||
"primary": "Papirstørrelse",
|
||||
"secondary": "Bestemmer dimensionerne på dine CV-sider"
|
||||
},
|
||||
"break-line": {
|
||||
"primary": "Brudlinje",
|
||||
"secondary": "Vis en streg på alle sider for at markere højden på en A4-side"
|
||||
},
|
||||
"format": {
|
||||
"primary": "Papirstørrelse",
|
||||
"secondary": "Bestemmer dimensionerne på dine CV-sider"
|
||||
},
|
||||
"heading": "Side",
|
||||
"orientation": {
|
||||
"disabled": "Har ingen effekt, når der kun er én side",
|
||||
|
||||
@ -8,35 +8,36 @@
|
||||
"features": {
|
||||
"heading": "Funktioner",
|
||||
"list": {
|
||||
"ads": "Ingen reklamer.",
|
||||
"ads": "Ingen reklamer",
|
||||
"export": "Eksporter dit CV til JSON- eller PDF-format",
|
||||
"free": "Gratis for evigt",
|
||||
"import": "Importer data fra LinkedIn, JSON CV",
|
||||
"languages": "Tilgængelig på flere sprog",
|
||||
"more": "Og meget flere spændende funktioner, <1>læs alt om det her</1>",
|
||||
"more": "Og mange flere spændende funktioner, <1>læs alt om det her</1>",
|
||||
"tracking": "Ingen brugersporing"
|
||||
}
|
||||
},
|
||||
"links": {
|
||||
"heading": "Links",
|
||||
"links": {
|
||||
"docs": "Dokumentation",
|
||||
"donate": "Donér",
|
||||
"github": "Kildekode",
|
||||
"docs": "Dokumentation",
|
||||
"privacy": "Fortrolighedspolitik",
|
||||
"reddit": "Reddit",
|
||||
"service": "Servicevilkår"
|
||||
}
|
||||
},
|
||||
"screenshots": {
|
||||
"heading": "Skærmbilleder"
|
||||
},
|
||||
"testimonials": {
|
||||
"heading": "Udtalelser",
|
||||
"body": "Godt eller dårligt, jeg ville elske at høre din mening om Reactive Resume og hvordan oplevelsen har været for dig.<br/>Her er nogle af de beskeder, der er sendt af brugere over hele verden.",
|
||||
"contact": "Du kan kontakte mig via <1>min e-mail</1> eller gennem kontaktformularen på <3>min hjemmeside</3> ."
|
||||
},
|
||||
"summary": {
|
||||
"body": "Reactive Resume er en gratis og open source CV-bygger, der er bygget til at gøre de hverdagsagtige opgaver med at oprette, opdatere og dele dit CV så lette som 1, 2, 3. Med denne app kan du oprette flere CV'er, dele dem med rekrutterere eller venner gennem et unikt link og udskriv det som en PDF, helt gratis, ingen annoncer, ingen sporing, uden at miste integriteten og fortroligheden af dine data.",
|
||||
"heading": "Opsummering"
|
||||
},
|
||||
"testimonials": {
|
||||
"body": "Godt eller dårligt, jeg ville elske at høre din mening om Reactive Resume og hvordan oplevelsen har været for dig.<br/>Her er nogle af de beskeder, der er sendt af brugere over hele verden.",
|
||||
"contact": "Du kan kontakte mig via <1>min e-mail</1> eller gennem kontaktformularen på <3>min hjemmeside</3> .",
|
||||
"heading": "Udtalelser"
|
||||
}
|
||||
}
|
||||
|
||||
@ -3,8 +3,8 @@
|
||||
"actions": {
|
||||
"add": "{{token}} hinzufügen",
|
||||
"delete": "{{token}} löschen",
|
||||
"edit": "{{token}} bearbeiten",
|
||||
"duplicate": "Abschnitt duplizieren"
|
||||
"duplicate": "Abschnitt duplizieren",
|
||||
"edit": "{{token}} bearbeiten"
|
||||
},
|
||||
"columns": {
|
||||
"heading": "Spalten",
|
||||
@ -81,13 +81,13 @@
|
||||
"center-artboard": "Artboard zentrieren",
|
||||
"copy-link": "Link zum Lebenslauf kopieren",
|
||||
"export-pdf": "PDF exportieren",
|
||||
"redo": "Wiederholen",
|
||||
"toggle-orientation": "Seitenausrichtung umschalten",
|
||||
"toggle-page-break-line": "Pausenzeile umschalten",
|
||||
"toggle-sidebars": "Seitenleisten umschalten",
|
||||
"zoom-in": "Vergrößern",
|
||||
"zoom-out": "Verkleinern",
|
||||
"undo": "Rückgängig machen",
|
||||
"redo": "Wiederholen"
|
||||
"zoom-in": "Vergrößern",
|
||||
"zoom-out": "Verkleinern"
|
||||
}
|
||||
},
|
||||
"header": {
|
||||
@ -115,6 +115,9 @@
|
||||
"actions": {
|
||||
"photo-filters": "Fotofilter"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Geburtsdatum"
|
||||
},
|
||||
"heading": "Grundlagen",
|
||||
"headline": {
|
||||
"label": "Überschrift"
|
||||
@ -122,9 +125,6 @@
|
||||
"name": {
|
||||
"label": "Vollständiger Name"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Geburtsdatum"
|
||||
},
|
||||
"photo-filters": {
|
||||
"effects": {
|
||||
"border": {
|
||||
@ -257,33 +257,31 @@
|
||||
"heading": "Layout",
|
||||
"tooltip": {
|
||||
"reset-layout": "Layout zurücksetzen"
|
||||
},
|
||||
"main": "Hauptteil",
|
||||
"sidebar": "Seitenleiste"
|
||||
}
|
||||
},
|
||||
"links": {
|
||||
"bugs-features": {
|
||||
"body": "Sind Sie bei der Erstellung Ihres Lebenslaufs auf ein Problem gestoßen? Oder haben Sie eine tolle Idee, die Sie hinzufügen möchten? Erstellen Sie ein Ticket auf GitHub.",
|
||||
"button": "GitHub Issues",
|
||||
"button": "GitHub Themen",
|
||||
"heading": "Fehler? Verbesserungsvorschläge?"
|
||||
},
|
||||
"docs": "Dokumentation",
|
||||
"donate": {
|
||||
"body": "Sollte Ihnen Reactive Resume gefallen, möchte ich Sie bitten, etwas zu spenden, damit die App für immer kostenlos und werbefrei bleibt.",
|
||||
"button": "Kaufe mir einen Kaffee",
|
||||
"heading": "Spenden Sie an Reactive Resume."
|
||||
},
|
||||
"github": "Quellcode",
|
||||
"docs": "Dokumentation",
|
||||
"heading": "Links"
|
||||
"heading": "Links",
|
||||
"reddit": "Reddit"
|
||||
},
|
||||
"settings": {
|
||||
"global": {
|
||||
"date": {
|
||||
"primary": "Datum",
|
||||
"secondary": "Datumsformat für die gesamte App.",
|
||||
"prefix": "Z.B."
|
||||
"secondary": "Datumsformat für die gesamte App."
|
||||
},
|
||||
"heading": "Global",
|
||||
"heading": "Globale",
|
||||
"language": {
|
||||
"primary": "Sprache",
|
||||
"secondary": "Anzeigesprache, die in der gesamten App verwendet wird."
|
||||
@ -294,14 +292,14 @@
|
||||
},
|
||||
"heading": "Einstellungen",
|
||||
"page": {
|
||||
"format": {
|
||||
"primary": "Papiergröße",
|
||||
"secondary": "Legt die Seitenabmessungen Ihres Lebenslaufs fest."
|
||||
},
|
||||
"break-line": {
|
||||
"primary": "Seitenumbruch anzeigen",
|
||||
"secondary": "Zeigt den Seitenumbruch als Linie auf allen Seiten an."
|
||||
},
|
||||
"format": {
|
||||
"primary": "Papiergröße",
|
||||
"secondary": "Legt die Seitenabmessungen Ihres Lebenslaufs fest."
|
||||
},
|
||||
"heading": "Seite",
|
||||
"orientation": {
|
||||
"disabled": "Hat keine Auswirkung, wenn nur eine Seite vorhanden ist.",
|
||||
|
||||
@ -18,25 +18,26 @@
|
||||
}
|
||||
},
|
||||
"links": {
|
||||
"heading": "Links",
|
||||
"heading": "Verknüpfungen",
|
||||
"links": {
|
||||
"docs": "Dokumentation",
|
||||
"donate": "Spenden",
|
||||
"github": "Quellcode",
|
||||
"docs": "Dokumentation",
|
||||
"privacy": "Datenschutzerklärung",
|
||||
"reddit": "Reddit",
|
||||
"service": "Nutzungsbedingungen"
|
||||
}
|
||||
},
|
||||
"screenshots": {
|
||||
"heading": "Screenshots"
|
||||
},
|
||||
"testimonials": {
|
||||
"heading": "Referenzen",
|
||||
"body": "Egal ob gut oder schlecht - ich würde gerne Ihre Meinung über Reactive Resume hören und welche Erfahrungen Sie gemacht haben.<br/>Hier sind einige der Nachrichten, die mir von Benutzern auf der ganzen Welt zugesandt wurden.",
|
||||
"contact": "Sie können mich über <1>meine E-Mail</1> oder über das Kontaktformular auf <3>meiner Website</3> erreichen."
|
||||
},
|
||||
"summary": {
|
||||
"body": "Reactive Resume ist ein kostenloser Open Source Lebenslauf-Builder, der gebaut wurde, um die langweilige Aufgabe einen Lebenslauf zu erstellen, aktuell zu halten und zu teilen so einfach wie möglich zu machen. Mit dieser App können Sie mehrere Lebensläufe erstellen, sie mit Recruitern oder Freunden über einen einzigartigen Link teilen und als PDF exportieren. Kostenlos, ohne Werbung, kein Tracking, ohne die Integrität und Privatsphäre Ihrer Daten zu verlieren.",
|
||||
"heading": "Zusammenfassung"
|
||||
},
|
||||
"testimonials": {
|
||||
"body": "Egal ob gut oder schlecht - ich würde gerne Ihre Meinung über Reactive Resume hören und welche Erfahrungen Sie gemacht haben.<br/>Hier sind einige der Nachrichten, die mir von Benutzern auf der ganzen Welt zugesandt wurden.",
|
||||
"contact": "Sie können mich über <1>meine E-Mail</1> oder über das Kontaktformular auf <3>meiner Website</3> erreichen.",
|
||||
"heading": "Referenzen"
|
||||
}
|
||||
}
|
||||
|
||||
@ -7,7 +7,7 @@
|
||||
"body": "Geben Sie die E-Mail-Adresse des Benutzerkontos ein, dass Sie wiederherstellen möchten.",
|
||||
"form": {
|
||||
"email": {
|
||||
"label": "E-Mail-Addresse"
|
||||
"label": "E-Mail-Adresse"
|
||||
}
|
||||
},
|
||||
"heading": "Passwort vergessen?",
|
||||
@ -42,7 +42,7 @@
|
||||
"label": "Passwort bestätigen"
|
||||
},
|
||||
"email": {
|
||||
"label": "E-Mail-Addresse"
|
||||
"label": "E-Mail-Adresse"
|
||||
},
|
||||
"name": {
|
||||
"label": "Vollständiger Name"
|
||||
@ -71,6 +71,31 @@
|
||||
}
|
||||
},
|
||||
"heading": "Passwort zurücksetzen"
|
||||
},
|
||||
"profile": {
|
||||
"heading": "Ihr Benutzerkonto",
|
||||
"form": {
|
||||
"avatar": {
|
||||
"help-text": "Sie können Ihr Profilbild auf <1>Gravatar</1> aktualisieren"
|
||||
},
|
||||
"name": {
|
||||
"label": "Vollständiger Name"
|
||||
},
|
||||
"email": {
|
||||
"label": "E-Mail-Adresse",
|
||||
"help-text": "Im Moment ist es nicht möglich, Ihre E-Mail-Adresse zu aktualisieren. Bitte erstellen Sie stattdessen ein neues Konto."
|
||||
}
|
||||
},
|
||||
"delete-account": {
|
||||
"heading": "Konto und Daten löschen",
|
||||
"body": "Um Ihr Konto, Ihre Daten und alle Ihre Lebensläufe zu löschen, geben Sie „{{keyword}}“ in das Textfeld ein und klicken Sie auf die Schaltfläche. Bitte beachten Sie, dass dies ein irreversibler Vorgang ist und Ihre Daten nicht wiederhergestellt werden können.",
|
||||
"actions": {
|
||||
"delete": "Account löschen"
|
||||
}
|
||||
},
|
||||
"actions": {
|
||||
"save": "Änderungen speichern"
|
||||
}
|
||||
}
|
||||
},
|
||||
"dashboard": {
|
||||
@ -87,7 +112,7 @@
|
||||
"label": "Ist öffentlich zugänglich?"
|
||||
},
|
||||
"slug": {
|
||||
"label": "Slug"
|
||||
"label": "URL-Segment"
|
||||
}
|
||||
},
|
||||
"heading": "Neuen Lebenslauf erstellen"
|
||||
@ -98,14 +123,14 @@
|
||||
"actions": {
|
||||
"upload-json": "JSON hochladen"
|
||||
},
|
||||
"body": "Wenn du einen <1>validierten JSON Resume</1> bereit hast, kannst du damit deine Entwicklung auf reaktiven Resume beschleunigen. Klicken Sie auf den Button unten und laden Sie eine gültige JSON-Datei hoch, um zu beginnen.",
|
||||
"body": "Wenn du einen <1>validierten JSON Lebenslauf</1> bereit hast, kannst du damit deine Entwicklung auf Reactive Resume beschleunigen. Klicken Sie auf den Button unten und laden Sie eine gültige JSON-Datei hoch, um zu beginnen.",
|
||||
"heading": "Import vom JSON-Lebenslauf"
|
||||
},
|
||||
"linkedin": {
|
||||
"actions": {
|
||||
"upload-archive": "ZIP-Archiv hochladen"
|
||||
},
|
||||
"body": "Sie können Zeit sparen, indem Sie Ihre Daten aus LinkedIn exportieren und sie zum automatischen Ausfüllen von Feldern auf Reaktives Lebenslauf verwenden. Gehen Sie zum Abschnitt <1>Datenschutz </1> auf LinkedIn und fordern Sie ein Archiv Ihrer Daten an. Sobald diese verfügbar sind, laden Sie die ZIP-Datei unten hoch.",
|
||||
"body": "Sie können Zeit sparen, indem Sie Ihre Daten aus LinkedIn exportieren und sie zum automatischen Ausfüllen von Feldern auf Reactive Resume verwenden. Gehen Sie zum Abschnitt <1>Datenschutz </1> auf LinkedIn und fordern Sie ein Archiv Ihrer Daten an. Sobald diese verfügbar sind, laden Sie die ZIP-Datei unten hoch.",
|
||||
"heading": "Aus LinkedIn importieren"
|
||||
},
|
||||
"reactive-resume": {
|
||||
@ -114,7 +139,7 @@
|
||||
"upload-json-v2": "Laden Sie JSON von v2 hoch"
|
||||
},
|
||||
"body": "Wenn Sie eine JSON haben, die mit der aktuellen Version von Reactive Resume exportiert wurde, können Sie sie hier wieder importieren, um wieder eine bearbeitbare Version zu erhalten.",
|
||||
"heading": "Import vom Reaktives Lebenslauf"
|
||||
"heading": "Import von Reactive Resume"
|
||||
}
|
||||
},
|
||||
"rename-resume": {
|
||||
@ -126,7 +151,7 @@
|
||||
"label": "Name"
|
||||
},
|
||||
"slug": {
|
||||
"label": "Slug"
|
||||
"label": "URL-Segment"
|
||||
}
|
||||
},
|
||||
"heading": "Lebenslauf umbenennen"
|
||||
|
||||
@ -3,8 +3,8 @@
|
||||
"actions": {
|
||||
"add": "Add New {{token}}",
|
||||
"delete": "Delete {{token}}",
|
||||
"edit": "Edit {{token}}",
|
||||
"duplicate": "Duplicate Section"
|
||||
"duplicate": "Duplicate Section",
|
||||
"edit": "Edit {{token}}"
|
||||
},
|
||||
"columns": {
|
||||
"heading": "Columns",
|
||||
@ -81,13 +81,13 @@
|
||||
"center-artboard": "Center Artboard",
|
||||
"copy-link": "Copy Link to Resume",
|
||||
"export-pdf": "Export PDF",
|
||||
"redo": "Redo",
|
||||
"toggle-orientation": "Toggle Page Orientation",
|
||||
"toggle-page-break-line": "Toggle Page Break Line",
|
||||
"toggle-sidebars": "Toggle Sidebars",
|
||||
"zoom-in": "Zoom In",
|
||||
"zoom-out": "Zoom Out",
|
||||
"undo": "Undo",
|
||||
"redo": "Redo"
|
||||
"zoom-in": "Zoom In",
|
||||
"zoom-out": "Zoom Out"
|
||||
}
|
||||
},
|
||||
"header": {
|
||||
@ -115,6 +115,9 @@
|
||||
"actions": {
|
||||
"photo-filters": "Photo Filters"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Date of Birth"
|
||||
},
|
||||
"heading": "Basics",
|
||||
"headline": {
|
||||
"label": "Headline"
|
||||
@ -122,9 +125,6 @@
|
||||
"name": {
|
||||
"label": "Full Name"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Date of Birth"
|
||||
},
|
||||
"photo-filters": {
|
||||
"effects": {
|
||||
"border": {
|
||||
@ -265,14 +265,15 @@
|
||||
"button": "GitHub Issues",
|
||||
"heading": "Bugs? Feature Requests?"
|
||||
},
|
||||
"docs": "Documentation",
|
||||
"donate": {
|
||||
"body": "If you liked using Reactive Resume, please consider donating as much as you can to the cause of keeping the app up and running, without ads and free forever.",
|
||||
"button": "Buy me a coffee",
|
||||
"heading": "Donate to Reactive Resume"
|
||||
},
|
||||
"github": "Source Code",
|
||||
"docs": "Documentation",
|
||||
"heading": "Links"
|
||||
"heading": "Links",
|
||||
"reddit": "Reddit"
|
||||
},
|
||||
"settings": {
|
||||
"global": {
|
||||
@ -291,14 +292,14 @@
|
||||
},
|
||||
"heading": "Settings",
|
||||
"page": {
|
||||
"format": {
|
||||
"primary": "Paper Size",
|
||||
"secondary": "Determines the dimensions of your resume pages"
|
||||
},
|
||||
"break-line": {
|
||||
"primary": "Break Line",
|
||||
"secondary": "Show a line on all pages to mark the height of an A4 page"
|
||||
},
|
||||
"format": {
|
||||
"primary": "Paper Size",
|
||||
"secondary": "Determines the dimensions of your resume pages"
|
||||
},
|
||||
"heading": "Page",
|
||||
"orientation": {
|
||||
"disabled": "Has no effect when there is only one page",
|
||||
|
||||
@ -20,23 +20,24 @@
|
||||
"links": {
|
||||
"heading": "Links",
|
||||
"links": {
|
||||
"docs": "Documentation",
|
||||
"donate": "Donate",
|
||||
"github": "Source Code",
|
||||
"docs": "Documentation",
|
||||
"privacy": "Privacy Policy",
|
||||
"reddit": "Reddit",
|
||||
"service": "Terms of Service"
|
||||
}
|
||||
},
|
||||
"screenshots": {
|
||||
"heading": "Screenshots"
|
||||
},
|
||||
"testimonials": {
|
||||
"heading": "Testimonials",
|
||||
"body": "Good or bad, I would love to hear your opinion on Reactive Resume and how the experience has been for you.<br/>Here are some of the messages sent in by users across the world.",
|
||||
"contact": "You can reach out to me through <1>my email</1> or through the contact form on <3>my website</3>."
|
||||
},
|
||||
"summary": {
|
||||
"body": "Reactive Resume is a free and open source resume builder that's built to make the mundane tasks of creating, updating and sharing your resume as easy as 1, 2, 3. With this app, you can create multiple resumes, share them with recruiters or friends through a unique link and print it as a PDF, all for free, no ads, no tracking, without losing the integrity and privacy of your data.",
|
||||
"heading": "Summary"
|
||||
},
|
||||
"testimonials": {
|
||||
"body": "Good or bad, I would love to hear your opinion on Reactive Resume and how the experience has been for you.<br/>Here are some of the messages sent in by users across the world.",
|
||||
"contact": "You can reach out to me through <1>my email</1> or through the contact form on <3>my website</3>.",
|
||||
"heading": "Testimonials"
|
||||
}
|
||||
}
|
||||
|
||||
@ -71,6 +71,31 @@
|
||||
}
|
||||
},
|
||||
"heading": "Reset your password"
|
||||
},
|
||||
"profile": {
|
||||
"heading": "Your Account",
|
||||
"form": {
|
||||
"avatar": {
|
||||
"help-text": "You can update your profile picture on <1>Gravatar</1>"
|
||||
},
|
||||
"name": {
|
||||
"label": "Full Name"
|
||||
},
|
||||
"email": {
|
||||
"label": "Email Address",
|
||||
"help-text": "It is not possible to update your email address at the moment, please create a new account instead."
|
||||
}
|
||||
},
|
||||
"delete-account": {
|
||||
"heading": "Delete Account and Data",
|
||||
"body": "To delete your account, your data and all your resumes, type \"{{keyword}}\" into the textbox and click on the button. Please note that this is an irreversible action and your data cannot be retrieved again.",
|
||||
"actions": {
|
||||
"delete": "Delete Account"
|
||||
}
|
||||
},
|
||||
"actions": {
|
||||
"save": "Save Changes"
|
||||
}
|
||||
}
|
||||
},
|
||||
"dashboard": {
|
||||
|
||||
@ -3,6 +3,7 @@
|
||||
"actions": {
|
||||
"add": "Agregar nuevo {{token}}",
|
||||
"delete": "Eliminar {{token}}",
|
||||
"duplicate": "Duplicar sección",
|
||||
"edit": "Editar {{token}}"
|
||||
},
|
||||
"columns": {
|
||||
@ -80,13 +81,13 @@
|
||||
"center-artboard": "Centrar Tablero",
|
||||
"copy-link": "Copiar enlace al currículum",
|
||||
"export-pdf": "Exportar PDF",
|
||||
"redo": "Rehacer",
|
||||
"toggle-orientation": "Cambiar la orientación de la página",
|
||||
"toggle-page-break-line": "Alternar línea de salto de página",
|
||||
"toggle-sidebars": "Ocultar/mostrar barra lateral",
|
||||
"zoom-in": "Acercar",
|
||||
"zoom-out": "Alejar",
|
||||
"undo": "Deshacer",
|
||||
"redo": "Rehacer"
|
||||
"zoom-in": "Acercar",
|
||||
"zoom-out": "Alejar"
|
||||
}
|
||||
},
|
||||
"header": {
|
||||
@ -114,6 +115,9 @@
|
||||
"actions": {
|
||||
"photo-filters": "Filtro de fotos"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Fecha de cumpleaños"
|
||||
},
|
||||
"heading": "Información básica",
|
||||
"headline": {
|
||||
"label": "Titular"
|
||||
@ -121,9 +125,6 @@
|
||||
"name": {
|
||||
"label": "Nombre Completo"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Fecha de cumpleaños"
|
||||
},
|
||||
"photo-filters": {
|
||||
"effects": {
|
||||
"border": {
|
||||
@ -264,14 +265,15 @@
|
||||
"button": "Propuesta de GitHub",
|
||||
"heading": "¿Errores? ¿Solicitud de características?"
|
||||
},
|
||||
"docs": "Documentación",
|
||||
"donate": {
|
||||
"body": "Si le gustó usar Reactive Resume, considere donar lo que pueda a la causa de mantener la aplicación en funcionamiento, sin anuncios y gratis para siempre.",
|
||||
"button": "Invítame a un café",
|
||||
"heading": "Donar a Reactive Resume"
|
||||
},
|
||||
"github": "Código Fuente",
|
||||
"docs": "Documentación",
|
||||
"heading": "Enlaces"
|
||||
"heading": "Enlaces",
|
||||
"reddit": "Reddit"
|
||||
},
|
||||
"settings": {
|
||||
"global": {
|
||||
@ -290,14 +292,14 @@
|
||||
},
|
||||
"heading": "Preferencias",
|
||||
"page": {
|
||||
"format": {
|
||||
"primary": "Tamaño de papel",
|
||||
"secondary": "Determina las dimensiones de las páginas de tu currículum."
|
||||
},
|
||||
"break-line": {
|
||||
"primary": "Linea de separación",
|
||||
"secondary": "Mostrar una línea en todas las páginas para marcar la altura de una página A4"
|
||||
},
|
||||
"format": {
|
||||
"primary": "Tamaño de papel",
|
||||
"secondary": "Determina las dimensiones de las páginas de tu currículum."
|
||||
},
|
||||
"heading": "Página",
|
||||
"orientation": {
|
||||
"disabled": "No tiene efecto cuando solo hay una página",
|
||||
|
||||
@ -12,7 +12,7 @@
|
||||
"delete": "Borrar",
|
||||
"duplicate": "Duplicar",
|
||||
"open": "Abrir",
|
||||
"rename": "Rebautizar",
|
||||
"rename": "Renombrar",
|
||||
"share-link": "Compartir enlace",
|
||||
"tooltips": {
|
||||
"delete": "¿Está seguro de que desea eliminar este currículum? Esta es una acción irreversible.",
|
||||
|
||||
@ -20,23 +20,24 @@
|
||||
"links": {
|
||||
"heading": "Enlaces",
|
||||
"links": {
|
||||
"docs": "Documentación",
|
||||
"donate": "Donar",
|
||||
"github": "Código fuente",
|
||||
"docs": "Documentación",
|
||||
"privacy": "Política de Privacidad",
|
||||
"reddit": "Reddit",
|
||||
"service": "Términos de Servicio"
|
||||
}
|
||||
},
|
||||
"screenshots": {
|
||||
"heading": "Capturas de pantalla"
|
||||
},
|
||||
"testimonials": {
|
||||
"heading": "Opiniones",
|
||||
"body": "Bueno o malo, me encantaría saber tu opinión sobre Reactive Resume y cómo ha sido la experiencia para ti.<br/>Estos son algunos de los mensajes enviados por usuarios de todo el mundo.",
|
||||
"contact": "Puedes comunicarte conmigo a través de <1>mi correo electrónico</1> o a través del formulario de contacto en <3>mi sitio web</3>."
|
||||
},
|
||||
"summary": {
|
||||
"body": "Reactive Resume es un generador de currículums gratuito y de código abierto que está diseñado para hacer que las tareas mundanas de crear, actualizar y compartir su currículum sean tan fáciles como 1, 2, 3. Con esta aplicación, puede crear múltiples currículums, compartirlos con reclutadores o amigos a través de un enlace único e imprímalo como PDF, todo gratis, sin anuncios, sin seguimiento, sin perder la integridad y privacidad de sus datos.",
|
||||
"heading": "Resumen"
|
||||
},
|
||||
"testimonials": {
|
||||
"body": "Bueno o malo, me encantaría saber tu opinión sobre Reactive Resume y cómo ha sido la experiencia para ti.<br/>Estos son algunos de los mensajes enviados por usuarios de todo el mundo.",
|
||||
"contact": "Puedes comunicarte conmigo a través de <1>mi correo electrónico</1> o a través del formulario de contacto en <3>mi sitio web</3>.",
|
||||
"heading": "Opiniones"
|
||||
}
|
||||
}
|
||||
|
||||
@ -71,6 +71,31 @@
|
||||
}
|
||||
},
|
||||
"heading": "Restablecer tu contraseña"
|
||||
},
|
||||
"profile": {
|
||||
"heading": "Tu cuenta",
|
||||
"form": {
|
||||
"avatar": {
|
||||
"help-text": "Puedes actualizar tu foto de perfil en <1>Gravatar</1>"
|
||||
},
|
||||
"name": {
|
||||
"label": "Nombre Completo"
|
||||
},
|
||||
"email": {
|
||||
"label": "Correo electrónico",
|
||||
"help-text": "No es posible actualizar tu dirección de correo electrónico en este momento, por favor crea una nueva cuenta en su lugar."
|
||||
}
|
||||
},
|
||||
"delete-account": {
|
||||
"heading": "Eliminar cuenta y datos",
|
||||
"body": "Para eliminar su cuenta, sus datos y todos sus currículums, escriba \"{{keyword}}\" en el cuadro de texto y haga clic en el botón. Tenga en cuenta que esta es una acción irreversible y sus datos no se pueden recuperar nuevamente.",
|
||||
"actions": {
|
||||
"delete": "Eliminar Cuenta"
|
||||
}
|
||||
},
|
||||
"actions": {
|
||||
"save": "Guardar cambios"
|
||||
}
|
||||
}
|
||||
},
|
||||
"dashboard": {
|
||||
|
||||
@ -3,6 +3,7 @@
|
||||
"actions": {
|
||||
"add": "{{token}} جدید اضافه کنید",
|
||||
"delete": "حذف {{token}}",
|
||||
"duplicate": "بخش تکراری",
|
||||
"edit": "ویرایش {{token}}"
|
||||
},
|
||||
"columns": {
|
||||
@ -80,13 +81,13 @@
|
||||
"center-artboard": "قرار دادن صفحه در مرکز",
|
||||
"copy-link": "کپی کردن لینک رزومه",
|
||||
"export-pdf": "خروجی PDF",
|
||||
"redo": "دوباره انجام دهید",
|
||||
"toggle-orientation": "تغییر وضعیت جهتگیری صفحه",
|
||||
"toggle-page-break-line": "تغییر وضعیت خط شکست صفحه",
|
||||
"toggle-sidebars": "باز/بسته کردن نوار کنار صفحه",
|
||||
"zoom-in": "بزرگنمایی",
|
||||
"zoom-out": "کوچکنمایی",
|
||||
"undo": "واگرد",
|
||||
"redo": "دوباره انجام دهید"
|
||||
"zoom-in": "بزرگنمایی",
|
||||
"zoom-out": "کوچکنمایی"
|
||||
}
|
||||
},
|
||||
"header": {
|
||||
@ -114,6 +115,9 @@
|
||||
"actions": {
|
||||
"photo-filters": "فیلترهای تصویر"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "تاریخ تولد"
|
||||
},
|
||||
"heading": "موارد پایه",
|
||||
"headline": {
|
||||
"label": "سرصفحه"
|
||||
@ -121,9 +125,6 @@
|
||||
"name": {
|
||||
"label": "نام کامل"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "تاریخ تولد"
|
||||
},
|
||||
"photo-filters": {
|
||||
"effects": {
|
||||
"border": {
|
||||
@ -264,14 +265,15 @@
|
||||
"button": "GitHub Issues",
|
||||
"heading": "باگها؟ درخواست ویژگی جدید؟"
|
||||
},
|
||||
"docs": "مستندات",
|
||||
"donate": {
|
||||
"body": "اگر استفاده از Reactive Resume را دوست داشتید، لطفاً تا جایی که می توانید کمک مالی کنید تا برنامه را بدون تبلیغات و برای همیشه رایگان نگه دارید.",
|
||||
"button": "برای من یک قهوه بخر",
|
||||
"heading": "کمک مالی به Reactive Resume"
|
||||
},
|
||||
"github": "کد منبع",
|
||||
"docs": "مستندات",
|
||||
"heading": "لینکها"
|
||||
"heading": "لینکها",
|
||||
"reddit": "ردیت"
|
||||
},
|
||||
"settings": {
|
||||
"global": {
|
||||
@ -290,14 +292,14 @@
|
||||
},
|
||||
"heading": "تنظیمات",
|
||||
"page": {
|
||||
"format": {
|
||||
"primary": "اندازه کاغذ",
|
||||
"secondary": "ابعاد صفحات رزومه شما را تعیین می کند"
|
||||
},
|
||||
"break-line": {
|
||||
"primary": "خط شکست",
|
||||
"secondary": "برای مشخص کردن ارتفاع صفحه A4 یک خط در همه صفحات نشان داده شود"
|
||||
},
|
||||
"format": {
|
||||
"primary": "اندازه کاغذ",
|
||||
"secondary": "ابعاد صفحات رزومه شما را تعیین می کند"
|
||||
},
|
||||
"heading": "صفحه",
|
||||
"orientation": {
|
||||
"disabled": "زمانی که تنها یک صفحه وجود دارد، تاثیری ندارد",
|
||||
|
||||
@ -20,23 +20,24 @@
|
||||
"links": {
|
||||
"heading": "لینکها",
|
||||
"links": {
|
||||
"docs": "مستندات",
|
||||
"donate": "حمایت مالی",
|
||||
"github": "کد منبع",
|
||||
"docs": "مستندات",
|
||||
"privacy": "حریم خصوصی",
|
||||
"reddit": "ردیت",
|
||||
"service": "شرایط سرویسدهی"
|
||||
}
|
||||
},
|
||||
"screenshots": {
|
||||
"heading": "اسکرینشاتها"
|
||||
},
|
||||
"testimonials": {
|
||||
"heading": "نظرات کاربران",
|
||||
"body": "خوب یا بد، من دوست دارم نظر شما را در مورد Reactive Resume و اینکه تجربه کار با آن برای شما چگونه بوده است را بدانم.<br/>تعدادی از پیام های ارسال شده توسط کاربران در سراسر جهان را اینجا میبینید.",
|
||||
"contact": "میتوانید از طریق <1>ایمیل من</1> یا فرم تماس در <3>وبسایت من</3> با من در ارتباط باشید."
|
||||
},
|
||||
"summary": {
|
||||
"body": "Reactive Resume یک رزومه ساز رایگان و متنباز است که برای ایجاد، به روز رسانی و به اشتراک گذاری رزومه شما به آسانی شمردن ۱، ۲، ۳ ساخته شده است. با این برنامه، می توانید چندین رزومه ایجاد کنید و آنها را با کارفرماها یا دوستان از طریق یک لینک منحصر به فرد و چاپ آن به صورت PDF، همه به صورت رایگان، بدون تبلیغات، بدون ردیابی، بدون از دست دادن امنیت و حریم خصوصی داده های شما، به اشتراک بگذارید.",
|
||||
"heading": "درباره من"
|
||||
},
|
||||
"testimonials": {
|
||||
"body": "خوب یا بد، من دوست دارم نظر شما را در مورد Reactive Resume و اینکه تجربه کار با آن برای شما چگونه بوده است را بدانم.<br/>تعدادی از پیام های ارسال شده توسط کاربران در سراسر جهان را اینجا میبینید.",
|
||||
"contact": "میتوانید از طریق <1>ایمیل من</1> یا فرم تماس در <3>وبسایت من</3> با من در ارتباط باشید.",
|
||||
"heading": "نظرات کاربران"
|
||||
}
|
||||
}
|
||||
|
||||
@ -3,6 +3,7 @@
|
||||
"actions": {
|
||||
"add": "Ajouter un/une {{token}}",
|
||||
"delete": "Supprimer {{token}}",
|
||||
"duplicate": "Dupliquer la section",
|
||||
"edit": "Éditer {{token}}"
|
||||
},
|
||||
"columns": {
|
||||
@ -63,7 +64,7 @@
|
||||
"list": {
|
||||
"actions": {
|
||||
"delete": "Supprimer",
|
||||
"duplicate": "Dédoubler",
|
||||
"duplicate": "Dupliquer",
|
||||
"edit": "Éditer"
|
||||
},
|
||||
"empty-text": "Cette liste est vide."
|
||||
@ -80,19 +81,19 @@
|
||||
"center-artboard": "Centrer l'affichage",
|
||||
"copy-link": "Copier le lien vers le CV",
|
||||
"export-pdf": "Exporter en PDF",
|
||||
"redo": "Refaire",
|
||||
"toggle-orientation": "Basculer l'orientation de la page",
|
||||
"toggle-page-break-line": "Afficher/cacher l'indicateur de saut de page",
|
||||
"toggle-sidebars": "Afficher/cacher les barres latérales",
|
||||
"zoom-in": "Zoomer",
|
||||
"zoom-out": "Dézoomer",
|
||||
"undo": "Défaire",
|
||||
"redo": "Refaire"
|
||||
"zoom-in": "Zoomer",
|
||||
"zoom-out": "Dézoomer"
|
||||
}
|
||||
},
|
||||
"header": {
|
||||
"menu": {
|
||||
"delete": "Supprimer",
|
||||
"duplicate": "Dédoubler",
|
||||
"duplicate": "Dupliquer",
|
||||
"rename": "Renommer",
|
||||
"share-link": "Partager un lien",
|
||||
"tooltips": {
|
||||
@ -112,7 +113,10 @@
|
||||
},
|
||||
"basics": {
|
||||
"actions": {
|
||||
"photo-filters": "Filtres pour la photo"
|
||||
"photo-filters": "Filtres photo"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Date de naissance"
|
||||
},
|
||||
"heading": "Informations de base",
|
||||
"headline": {
|
||||
@ -121,9 +125,6 @@
|
||||
"name": {
|
||||
"label": "Nom complet"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Date de naissance"
|
||||
},
|
||||
"photo-filters": {
|
||||
"effects": {
|
||||
"border": {
|
||||
@ -244,11 +245,11 @@
|
||||
"pdf": {
|
||||
"loading": {
|
||||
"primary": "Génération du PDF",
|
||||
"secondary": "Veuillez patienter pendant que votre PDF est généré, cela peut prendre jusqu'à 15 secondes."
|
||||
"secondary": "Merci de patienter que votre PDF soit généré, cela peut prendre jusqu'à 15 secondes."
|
||||
},
|
||||
"normal": {
|
||||
"primary": "PDF",
|
||||
"secondary": "Téléchargez un PDF de votre CV que vous pourrez imprimer et envoyer à l'emploi de vos rêves. Ce fichier ne peut pas être réimporté pour être modifié ultérieurement."
|
||||
"secondary": "Télécharger au format PDF votre CV, à imprimer et envoyer à l'offre d'emploi de vos rêves. Ce fichier ne peut pas être réimporté pour être modifié ultérieurement."
|
||||
}
|
||||
}
|
||||
},
|
||||
@ -260,18 +261,19 @@
|
||||
},
|
||||
"links": {
|
||||
"bugs-features": {
|
||||
"body": "Quelque chose vous a empêché de rédiger un CV ? Ou vous avez une idée géniale à ajouter ? Créez une issue sur GitHub pour commencer.",
|
||||
"body": "Quelque chose vous a empêché de faire un CV ? Vous avez une idée géniale à ajouter ? Créez une issue sur GitHub dès maintenant.",
|
||||
"button": "Issues GitHub",
|
||||
"heading": "Bogues ? Demandes de fonctionnalités ?"
|
||||
},
|
||||
"docs": "Documentation",
|
||||
"donate": {
|
||||
"body": "Si vous avez aimé utiliser Reactive Resume, pensez à donner comme vous le pouvez pour que l'application reste disponible, gratuite et sans publicité pour toujours.",
|
||||
"body": "Si vous avez aimé utiliser Reactive Resume, merci d'envisager de faire un don pour que l'application puisse rester disponible, gratuite et sans publicité pour toujours.",
|
||||
"button": "Offrez-moi un café",
|
||||
"heading": "Faire un don à Reactive Resume"
|
||||
},
|
||||
"github": "Code source",
|
||||
"docs": "Documentation",
|
||||
"heading": "Liens"
|
||||
"heading": "Liens",
|
||||
"reddit": "Reddit"
|
||||
},
|
||||
"settings": {
|
||||
"global": {
|
||||
@ -290,17 +292,17 @@
|
||||
},
|
||||
"heading": "Paramètres",
|
||||
"page": {
|
||||
"break-line": {
|
||||
"primary": "Indicateur de changement de page",
|
||||
"secondary": "Affiche une ligne sur toutes les pages pour marquer la hauteur d'une feuille A4"
|
||||
},
|
||||
"format": {
|
||||
"primary": "Taille de papier",
|
||||
"secondary": "Détermine les dimensions de vos pages de CV"
|
||||
},
|
||||
"break-line": {
|
||||
"primary": "Indicateur de changement de page",
|
||||
"secondary": "Afficher une ligne sur toutes les pages pour marquer la hauteur d'une feuille A4"
|
||||
},
|
||||
"heading": "Page",
|
||||
"orientation": {
|
||||
"disabled": "N'a aucun effet lorsqu'il n'y a qu'une seule page",
|
||||
"disabled": "Aucun effet lorsqu'il n'y a qu'une seule page",
|
||||
"primary": "Orientation",
|
||||
"secondary": "Afficher les pages horizontalement ou verticalement"
|
||||
}
|
||||
@ -308,22 +310,22 @@
|
||||
"resume": {
|
||||
"heading": "CV",
|
||||
"reset": {
|
||||
"primary": "Tout remettre à zéro",
|
||||
"primary": "Remise à zéro",
|
||||
"secondary": "Vous avez fait trop d'erreurs ? Cliquez ici pour réinitialiser toutes les modifications et repartir de zéro. Attention, cette action ne peut pas être annulée."
|
||||
},
|
||||
"sample": {
|
||||
"primary": "Charger les données de démo",
|
||||
"secondary": "Vous ne savez pas par où commencer ? Cliquez ici pour charger quelques exemples de données afin de voir à quoi ressemble un CV complet."
|
||||
"primary": "Charger un exemple de données",
|
||||
"secondary": "Vous ne savez pas par où commencer ? Cliquez-ici pour charger un exemple de données afin de voir à quoi ressemble un CV complet."
|
||||
}
|
||||
}
|
||||
},
|
||||
"sharing": {
|
||||
"heading": "Partage",
|
||||
"heading": "Partager",
|
||||
"short-url": {
|
||||
"label": "Préférer une URL courte"
|
||||
"label": "URL courte préférée"
|
||||
},
|
||||
"visibility": {
|
||||
"subtitle": "Permettre à toute personne ayant un lien de consulter votre CV",
|
||||
"subtitle": "Permettre de consulter votre CV à toute personne ayant un lien",
|
||||
"title": "Public"
|
||||
}
|
||||
},
|
||||
@ -353,7 +355,7 @@
|
||||
"label": "Taille de la police"
|
||||
}
|
||||
},
|
||||
"heading": "Typographie",
|
||||
"heading": "Polices",
|
||||
"widgets": {
|
||||
"body": {
|
||||
"label": "Contenu"
|
||||
|
||||
@ -15,7 +15,7 @@
|
||||
"date": {
|
||||
"present": "Présent"
|
||||
},
|
||||
"subtitle": "Un constructeur de CV gratuit et open source.",
|
||||
"subtitle": "Un créateur de CV gratuit et open source.",
|
||||
"title": "Reactive Resume",
|
||||
"toast": {
|
||||
"error": {
|
||||
|
||||
@ -5,12 +5,12 @@
|
||||
},
|
||||
"import-external": {
|
||||
"subtitle": "LinkedIn, JSON Resume, Reactive Resume",
|
||||
"title": "Importer de sources externes"
|
||||
"title": "Importer à partir de sources externes"
|
||||
},
|
||||
"resume": {
|
||||
"menu": {
|
||||
"delete": "Supprimer",
|
||||
"duplicate": "Dédoubler",
|
||||
"duplicate": "Dupliquer",
|
||||
"open": "Ouvrir",
|
||||
"rename": "Renommer",
|
||||
"share-link": "Partager un lien",
|
||||
|
||||
@ -20,23 +20,24 @@
|
||||
"links": {
|
||||
"heading": "Liens",
|
||||
"links": {
|
||||
"docs": "Documentation",
|
||||
"donate": "Faire un don",
|
||||
"github": "Code source",
|
||||
"docs": "Documentation",
|
||||
"privacy": "Politique de confidentialité",
|
||||
"reddit": "Reddit",
|
||||
"service": "Conditions d'utilisation"
|
||||
}
|
||||
},
|
||||
"screenshots": {
|
||||
"heading": "Captures d'écran"
|
||||
},
|
||||
"testimonials": {
|
||||
"heading": "Témoignages",
|
||||
"body": "Bonne ou mauvaiss, j'aimerais entendre votre opinion sur Reactive Resume et comment l'expérience a été pour vous.<br/>Voici quelques-uns des messages envoyés par des utilisateurs du monde entier.",
|
||||
"contact": "Vous pouvez me contacter via <1>mon e-mail</1> ou via le formulaire de contact de <3>mon site web</3>."
|
||||
},
|
||||
"summary": {
|
||||
"body": "Reactive Resume est un générateur de CV gratuit et open source, conçu pour rendre les tâches banales de création, de mise à jour et de partage de votre CV aussi faciles que de compter jusqu'à 3. Avec cette application, vous pouvez créer plusieurs CVs, les partager avec des recruteurs ou des amis par le biais d'un lien unique et les imprimer au format PDF, le tout gratuitement, sans publicité, sans pistage, et sans perdre l'intégrité et la confidentialité de vos données.",
|
||||
"heading": "Résumé"
|
||||
},
|
||||
"testimonials": {
|
||||
"body": "Bon ou mauvais, je souhaiterais avoir votre avis sur Reactive Resume et l'expérience que vous en avez-eu.<br/>Voici quelques-uns des messages envoyés par des utilisateurs du monde entier.",
|
||||
"contact": "Vous pouvez me contacter via <1>mon e-mail</1> ou via le formulaire de contact de <3>mon site web</3>.",
|
||||
"heading": "Témoignages"
|
||||
}
|
||||
}
|
||||
|
||||
@ -71,6 +71,31 @@
|
||||
}
|
||||
},
|
||||
"heading": "Réinitialiser votre mot de passe"
|
||||
},
|
||||
"profile": {
|
||||
"heading": "Votre compte",
|
||||
"form": {
|
||||
"avatar": {
|
||||
"help-text": "Vous pouvez mettre à jour votre photo de profil sur <1>Gravatar</1>"
|
||||
},
|
||||
"name": {
|
||||
"label": "Nom complet"
|
||||
},
|
||||
"email": {
|
||||
"label": "Email",
|
||||
"help-text": "Il n'est pas possible de mettre à jour votre adresse e-mail pour le moment, merci de créer un nouveau compte à la place."
|
||||
}
|
||||
},
|
||||
"delete-account": {
|
||||
"heading": "Supprimer le compte et effacer les données",
|
||||
"body": "Pour supprimer votre compte, vos données et tous vos CV, tapez \"{{keyword}}\" dans la zone de texte et cliquez sur le bouton. Veuillez noter qu'il s'agit d'une action irréversible et que vos données ne pourront plus être récupérées.",
|
||||
"actions": {
|
||||
"delete": "Supprimer le compte"
|
||||
}
|
||||
},
|
||||
"actions": {
|
||||
"save": "Enregistrer les Modifications"
|
||||
}
|
||||
}
|
||||
},
|
||||
"dashboard": {
|
||||
@ -110,10 +135,10 @@
|
||||
},
|
||||
"reactive-resume": {
|
||||
"actions": {
|
||||
"upload-json": "Mettre en ligne un JSON",
|
||||
"upload-json-v2": "Télécharger JSON à partir de la v2"
|
||||
"upload-json": "Importer un JSON",
|
||||
"upload-json-v2": "Importer un JSON v2 ou plus"
|
||||
},
|
||||
"body": "Si vous avez un JSON qui a été exporté avec la version actuelle de Reactive Resume, vous pouvez le réimporter ici pour obtenir à nouveau une version modifiable.",
|
||||
"body": "Si vous avez un JSON qui a été exporté avec la version actuelle de Reactive Resume, vous pouvez le réimporter ici pour l'éditer à nouveau.",
|
||||
"heading": "Importer depuis Reactive Resume"
|
||||
}
|
||||
},
|
||||
|
||||
@ -1,13 +1,14 @@
|
||||
{
|
||||
"common": {
|
||||
"actions": {
|
||||
"add": "הוסף חדש{{token}}",
|
||||
"delete": "מחק{{token}}",
|
||||
"edit": "ערוך{{token}}"
|
||||
"add": "הוספת {{token}} חדש",
|
||||
"delete": "מחיקת {{token}}",
|
||||
"duplicate": "שכפול מקטע",
|
||||
"edit": "עריכת {{token}}"
|
||||
},
|
||||
"columns": {
|
||||
"heading": "טורים",
|
||||
"tooltip": "שנה את מספר הטורים"
|
||||
"heading": "עמודות",
|
||||
"tooltip": "החלפת כמות העמודות"
|
||||
},
|
||||
"form": {
|
||||
"date": {
|
||||
@ -17,10 +18,10 @@
|
||||
"label": "תיאור"
|
||||
},
|
||||
"email": {
|
||||
"label": "כתובת דוא\"ל"
|
||||
"label": "כתובת דוא״ל"
|
||||
},
|
||||
"end-date": {
|
||||
"help-text": "השאר שדה זה ריק, אם אתה עדיין נמצא שם",
|
||||
"help-text": "יש להשאיר שדה זה ריק, אם זה המקום הנוכחי",
|
||||
"label": "תאריך סיום"
|
||||
},
|
||||
"keywords": {
|
||||
@ -39,16 +40,16 @@
|
||||
"label": "מספר טלפון"
|
||||
},
|
||||
"position": {
|
||||
"label": "תפקיד בעבודה"
|
||||
"label": "תפקיד"
|
||||
},
|
||||
"start-date": {
|
||||
"label": "תאריך התחלה"
|
||||
},
|
||||
"subtitle": {
|
||||
"label": "תת כותרת"
|
||||
"label": "תת־כותרת"
|
||||
},
|
||||
"summary": {
|
||||
"label": "סיכום"
|
||||
"label": "תקציר"
|
||||
},
|
||||
"title": {
|
||||
"label": "כותרת"
|
||||
@ -58,7 +59,7 @@
|
||||
}
|
||||
},
|
||||
"glossary": {
|
||||
"page": "דף"
|
||||
"page": "עמוד"
|
||||
},
|
||||
"list": {
|
||||
"actions": {
|
||||
@ -66,38 +67,38 @@
|
||||
"duplicate": "שכפול",
|
||||
"edit": "עריכה"
|
||||
},
|
||||
"empty-text": "הרשימה ריקה!"
|
||||
"empty-text": "הרשימה ריקה."
|
||||
},
|
||||
"tooltip": {
|
||||
"delete-item": "האם אתה בטוח שברצונך להסיר פריט זה? זה בלתי הפיך.",
|
||||
"delete-section": "מחיקת קטע",
|
||||
"rename-section": "שנה את שם הקטע",
|
||||
"toggle-visibility": "שנה מצב נראות"
|
||||
"delete-item": "למחוק את הפריט? זו פעולה בלתי הפיכה.",
|
||||
"delete-section": "מחיקת מקטע",
|
||||
"rename-section": "שינוי שם המקטע",
|
||||
"toggle-visibility": "החלפת מצב חשיפה"
|
||||
}
|
||||
},
|
||||
"controller": {
|
||||
"tooltip": {
|
||||
"center-artboard": "משטח יצירה מרכזי",
|
||||
"copy-link": "העתק קישור לקורות חיים",
|
||||
"export-pdf": "ייצא PDF",
|
||||
"toggle-orientation": "כיוון דף הבית",
|
||||
"toggle-page-break-line": "החלף את קו מעבר עמוד",
|
||||
"toggle-sidebars": "החלף את סרגלי הצד",
|
||||
"zoom-in": "הגדל",
|
||||
"zoom-out": "הקטן",
|
||||
"undo": "לבטל",
|
||||
"redo": "לַעֲשׂוֹת שׁוּב"
|
||||
"center-artboard": "מרכוז משטח היצירה",
|
||||
"copy-link": "העתקת קישור לקורות חיים",
|
||||
"export-pdf": "ייצוא PDF",
|
||||
"redo": "ביצוע חוזר",
|
||||
"toggle-orientation": "החלפת כיוון הדף",
|
||||
"toggle-page-break-line": "החלפת קו מעבר עמוד",
|
||||
"toggle-sidebars": "החלפת מצב סרגלי הצד",
|
||||
"undo": "ביטול",
|
||||
"zoom-in": "הגדלה",
|
||||
"zoom-out": "הקטנה"
|
||||
}
|
||||
},
|
||||
"header": {
|
||||
"menu": {
|
||||
"delete": "מחיקה",
|
||||
"duplicate": "שכפל",
|
||||
"rename": "שנה שם",
|
||||
"share-link": "שתף קישור",
|
||||
"duplicate": "שכפול",
|
||||
"rename": "שינוי שם",
|
||||
"share-link": "שיתוף קישור",
|
||||
"tooltips": {
|
||||
"delete": "האם אתה בטוח שברצונך להסיר תכונה זו? זה בלתי הפיך.",
|
||||
"share-link": "עליך לשנות את החשיפה של קורות החיים שלך לציבור כדי להפוך אותם לגלויים לאחרים."
|
||||
"delete": "להסיר קורות חיים אלה? זה בלתי הפיך.",
|
||||
"share-link": "עליך לשנות את החשיפה של קורות החיים שלך לציבורית כדי שיהיו זמינים לאחרים."
|
||||
}
|
||||
}
|
||||
},
|
||||
@ -114,16 +115,16 @@
|
||||
"actions": {
|
||||
"photo-filters": "מסנן תמונות"
|
||||
},
|
||||
"heading": "בסיסי",
|
||||
"birthdate": {
|
||||
"label": "תאריך לידה"
|
||||
},
|
||||
"heading": "יסודות",
|
||||
"headline": {
|
||||
"label": "כותרת"
|
||||
"label": "כותרת ראשית"
|
||||
},
|
||||
"name": {
|
||||
"label": "שם מלא"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "תאריך לידה"
|
||||
},
|
||||
"photo-filters": {
|
||||
"effects": {
|
||||
"border": {
|
||||
@ -135,7 +136,7 @@
|
||||
"heading": "אפקטים"
|
||||
},
|
||||
"shape": {
|
||||
"heading": "צוּרָה"
|
||||
"heading": "צורה"
|
||||
},
|
||||
"size": {
|
||||
"heading": "גודל (בפיקסלים)"
|
||||
@ -143,8 +144,8 @@
|
||||
},
|
||||
"photo-upload": {
|
||||
"tooltip": {
|
||||
"remove": "הסר תמונה",
|
||||
"upload": "העלה תמונה"
|
||||
"remove": "הסרת תמונה",
|
||||
"upload": "העלאת תמונה"
|
||||
}
|
||||
}
|
||||
},
|
||||
@ -158,19 +159,19 @@
|
||||
"education": {
|
||||
"form": {
|
||||
"area-study": {
|
||||
"label": "תחום לימוד"
|
||||
"label": "תחום לימודים"
|
||||
},
|
||||
"courses": {
|
||||
"label": "קורסים"
|
||||
},
|
||||
"degree": {
|
||||
"label": "תוֹאַר"
|
||||
"label": "תואר"
|
||||
},
|
||||
"grade": {
|
||||
"label": "כיתה"
|
||||
"label": "ציון"
|
||||
},
|
||||
"institution": {
|
||||
"label": "מוֹסָד"
|
||||
"label": "מוסד"
|
||||
}
|
||||
}
|
||||
},
|
||||
@ -179,7 +180,7 @@
|
||||
"label": "כתובת"
|
||||
},
|
||||
"city": {
|
||||
"label": "עִיר"
|
||||
"label": "עיר"
|
||||
},
|
||||
"country": {
|
||||
"label": "מדינה"
|
||||
@ -195,19 +196,19 @@
|
||||
"profiles": {
|
||||
"form": {
|
||||
"network": {
|
||||
"label": "רֶשֶׁת"
|
||||
"label": "רשת"
|
||||
},
|
||||
"username": {
|
||||
"label": "שם משתמש"
|
||||
}
|
||||
},
|
||||
"heading": "פרופילים",
|
||||
"heading_one": "פּרוֹפִיל"
|
||||
"heading_one": "פרופיל"
|
||||
},
|
||||
"publications": {
|
||||
"form": {
|
||||
"publisher": {
|
||||
"label": "מוֹצִיא לָאוֹר"
|
||||
"label": "הוצאה לאור"
|
||||
}
|
||||
}
|
||||
},
|
||||
@ -219,12 +220,12 @@
|
||||
}
|
||||
},
|
||||
"section": {
|
||||
"heading": "סָעִיף"
|
||||
"heading": "מקטע"
|
||||
},
|
||||
"volunteer": {
|
||||
"form": {
|
||||
"organization": {
|
||||
"label": "אִרגוּן"
|
||||
"label": "ארגון"
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -236,69 +237,70 @@
|
||||
"heading": "CSS מותאם אישית"
|
||||
},
|
||||
"export": {
|
||||
"heading": "יְצוּא",
|
||||
"heading": "ייצוא",
|
||||
"json": {
|
||||
"primary": "JSON",
|
||||
"secondary": "הורד גירסת JSON של קורות החיים שלך שניתן לייבא חזרה אל קורות חיים ריאקטיביים."
|
||||
"secondary": "הורדת גרסת JSON של קורות החיים שלך שניתן לייבא בחזרה לקורות חיים מסתגלים."
|
||||
},
|
||||
"pdf": {
|
||||
"loading": {
|
||||
"primary": "יצירת PDF",
|
||||
"secondary": "המתן עם יצירת ה-PDF שלך, זה עשוי להימשך עד 15 שניות."
|
||||
"primary": "נוצר PDF",
|
||||
"secondary": "נא להמתין בזמן יצירת ה־PDF שלך, הפעולה עשויה לארוך עד 15 שניות."
|
||||
},
|
||||
"normal": {
|
||||
"primary": "PDF",
|
||||
"secondary": "הורד קובץ PDF של קורות החיים שלך שתוכל להדפיס ולשלוח לעבודת החלומות שלך. לא ניתן לייבא קובץ זה בחזרה לעריכה נוספת."
|
||||
"secondary": "הורדת PDF של קורות החיים שלך שניתן להדפיס ולשלוח לטובת משרת החלומות שלך. אי אפשר לייבא את הקובץ הזה בחזרה להמשך עריכה."
|
||||
}
|
||||
}
|
||||
},
|
||||
"layout": {
|
||||
"heading": "מַעֲרָך",
|
||||
"heading": "פריסה",
|
||||
"tooltip": {
|
||||
"reset-layout": "אפס פריסה"
|
||||
"reset-layout": "איפוס פריסה"
|
||||
}
|
||||
},
|
||||
"links": {
|
||||
"bugs-features": {
|
||||
"body": "משהו מונע ממך לעשות קורות חיים? או שיש לכם רעיון מדהים להוסיף? העלה בעיה ב-GitHub כדי להתחיל.",
|
||||
"button": "בעיות GitHub",
|
||||
"heading": "באגים? בקשות לתכונה?"
|
||||
"body": "משהו מונע ממך ליצור קורות חיים? או שיש לך רעיון מדהים להוסיף? צריך רק לתעד בעיה ב־GitHub כדי להתחיל.",
|
||||
"button": "בעיות ב־GitHub",
|
||||
"heading": "תקלות? בקשות ליכולות?"
|
||||
},
|
||||
"docs": "תיעוד",
|
||||
"donate": {
|
||||
"body": "אם אהבתם להשתמש בקורות חיים ריאקטיביים, אנא שקול לתרום ככל שתוכל למען שמירה על האפליקציה ופועלת, ללא פרסומות ובחינם לנצח.",
|
||||
"button": "תקנה לי קפה",
|
||||
"heading": "תרומה לקורות חיים ריאקטיביים"
|
||||
"body": "אם אהבת להשתמש בקורות חיים מסתגלים, נא לשקול לתרום ככל שניתן כדי לשמור על היישום חי ובועט, ללא פרסומות ובחינם לנצח.",
|
||||
"button": "קנו לי קפה",
|
||||
"heading": "תרומה לקורות חיים מסתגלים"
|
||||
},
|
||||
"github": "קוד מקור",
|
||||
"docs": "תיעוד",
|
||||
"heading": "קישורים"
|
||||
"heading": "קישורים",
|
||||
"reddit": "רדיט"
|
||||
},
|
||||
"settings": {
|
||||
"global": {
|
||||
"date": {
|
||||
"primary": "תַאֲרִיך",
|
||||
"secondary": "פורמט תאריך לשימוש בכל האפליקציה"
|
||||
"primary": "תאריך",
|
||||
"secondary": "תבנית תאריך לשימוש בכל היישום"
|
||||
},
|
||||
"heading": "גלוֹבָּלִי",
|
||||
"heading": "גלובלית",
|
||||
"language": {
|
||||
"primary": "שפה",
|
||||
"secondary": "שפת תצוגה לשימוש בכל האפליקציה"
|
||||
"secondary": "שפת התצוגה של היישום"
|
||||
},
|
||||
"theme": {
|
||||
"primary": "ערכת נושא"
|
||||
"primary": "ערכת עיצוב"
|
||||
}
|
||||
},
|
||||
"heading": "הגדרות",
|
||||
"page": {
|
||||
"break-line": {
|
||||
"primary": "קו מעבר",
|
||||
"secondary": "להציג קו בכל הדפים כדי לסמן את גובהו של דף A4"
|
||||
},
|
||||
"format": {
|
||||
"primary": "גודל נייר",
|
||||
"secondary": "קובע את הממדים של דפי קורות החיים שלך"
|
||||
},
|
||||
"break-line": {
|
||||
"primary": "קו עצירה",
|
||||
"secondary": "הצג קו בכל הדפים כדי לסמן את גובהו של דף A4"
|
||||
},
|
||||
"heading": "דף",
|
||||
"heading": "עמוד",
|
||||
"orientation": {
|
||||
"disabled": "אין השפעה כשיש רק עמוד אחד",
|
||||
"primary": "כיוון",
|
||||
@ -308,23 +310,23 @@
|
||||
"resume": {
|
||||
"heading": "קורות חיים",
|
||||
"reset": {
|
||||
"primary": "אפס הכל",
|
||||
"secondary": "עשית יותר מדי טעויות? לחץ כאן כדי לאפס את כל השינויים ולהתחיל מאפס. היזהר, פעולה זו לא ניתנת לביטול."
|
||||
"primary": "איפוס של הכול",
|
||||
"secondary": "עשית יותר מדי טעויות? לחיצה כאן תאפס את כל השינויים ותאפשר לך להתחיל מחדש. כדאי לשים לב, זאת פעולה בלתי הפיכה."
|
||||
},
|
||||
"sample": {
|
||||
"primary": "טען נתונים לדוגמה",
|
||||
"secondary": "לא בטוחים מאיפה להתחיל? לחץ כאן כדי לטעון כמה נתונים לדוגמה כדי לראות איך קורות חיים מלאים נראים."
|
||||
"primary": "טעינת נתונים לדוגמה",
|
||||
"secondary": "לא ברור לך מאיפה להתחיל? לחיצה כאן תטען נתונים לדוגמה כדי לראות איך נראים קורות חיים שלמים."
|
||||
}
|
||||
}
|
||||
},
|
||||
"sharing": {
|
||||
"heading": "שיתוף",
|
||||
"short-url": {
|
||||
"label": "העדף כתובת URL קצרה"
|
||||
"label": "להעדיף כתובת מקוצרת"
|
||||
},
|
||||
"visibility": {
|
||||
"subtitle": "אפשר לכל מי שיש לו קישור לראות את קורות החיים שלך",
|
||||
"title": "גלוי לכול"
|
||||
"subtitle": "לאפשר לכל מי שיש קישור לראות את קורות החיים שלך",
|
||||
"title": "ציבורי"
|
||||
}
|
||||
},
|
||||
"templates": {
|
||||
@ -342,15 +344,15 @@
|
||||
"label": "טקסט"
|
||||
}
|
||||
},
|
||||
"heading": "ערכת נושא"
|
||||
"heading": "ערכת עיצוב"
|
||||
},
|
||||
"typography": {
|
||||
"form": {
|
||||
"font-family": {
|
||||
"label": "משפחת גופן"
|
||||
"label": "משפחת גופנים"
|
||||
},
|
||||
"font-size": {
|
||||
"label": "גודל גופן"
|
||||
"label": "גודל כתב"
|
||||
}
|
||||
},
|
||||
"heading": "טיפוגרפיה",
|
||||
@ -359,7 +361,7 @@
|
||||
"label": "גוף"
|
||||
},
|
||||
"headings": {
|
||||
"label": "כותרת"
|
||||
"label": "כותרות"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -2,28 +2,28 @@
|
||||
"avatar": {
|
||||
"menu": {
|
||||
"greeting": "שלום",
|
||||
"logout": "התנתק/י"
|
||||
"logout": "יציאה"
|
||||
}
|
||||
},
|
||||
"footer": {
|
||||
"credit": "פרויקט תשוקה מאת <1>אמרות פילאי</1>",
|
||||
"credit": "מיזם שהוא התשוקה של <1>אמרות פילאי</1>",
|
||||
"license": "על ידי הקהילה, עבור הקהילה."
|
||||
},
|
||||
"markdown": {
|
||||
"help-text": "סעיף זה תומך ב-<1>markdown</1> עיצוב."
|
||||
"help-text": "סעיף זה תומך בעיצוב <1>Markdown</1>."
|
||||
},
|
||||
"date": {
|
||||
"present": "הווה"
|
||||
},
|
||||
"subtitle": "בונה קורות חיים חינמי ובקוד פתוח.",
|
||||
"title": "קורות חיים תגובתיים",
|
||||
"title": "קורות חיים מסתגלים",
|
||||
"toast": {
|
||||
"error": {
|
||||
"upload-file-size": "נא להעלות רק קבצים מתחת ל-2 מגה בייט.",
|
||||
"upload-photo-size": "נא להעלות רק תמונות מתחת ל-2 מגה בייט, רצוי מרובע."
|
||||
"upload-file-size": "נא להעלות רק קבצים קטנים מ־2 מגהבתים.",
|
||||
"upload-photo-size": "נא להעלות רק תמונות מתחת ל־2 מגהבתים, רצוי מרובעות."
|
||||
},
|
||||
"success": {
|
||||
"resume-link-copied": "קישור לקורות החיים שלך הועתק ללוח."
|
||||
"resume-link-copied": "הקישור לקורות החיים שלך הועתק ללוח הגזירים."
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -1,25 +1,25 @@
|
||||
{
|
||||
"create-resume": {
|
||||
"subtitle": "להתחיל מאפס",
|
||||
"title": "צור קורות חיים חדשים"
|
||||
"subtitle": "התחלה מאפס",
|
||||
"title": "יצירת קורות חיים חדשים"
|
||||
},
|
||||
"import-external": {
|
||||
"subtitle": "לינקדאין, קורות חיים של JSON, קורות חיים ריאקטיביים",
|
||||
"subtitle": "לינקדאין, קורות חיים ב־JSON, קורות חיים מסתגלים",
|
||||
"title": "ייבוא ממקורות חיצוניים"
|
||||
},
|
||||
"resume": {
|
||||
"menu": {
|
||||
"delete": "מחיקה",
|
||||
"duplicate": "שכפל",
|
||||
"open": "פתוח",
|
||||
"rename": "שנה שם",
|
||||
"share-link": "שתף קישור",
|
||||
"duplicate": "שכפול",
|
||||
"open": "פתיחה",
|
||||
"rename": "שינוי שם",
|
||||
"share-link": "שיתוף קישור",
|
||||
"tooltips": {
|
||||
"delete": "האם אתה בטוח שברצונך להסיר תכונה זו? זה בלתי הפיך.",
|
||||
"share-link": "עליך לשנות את החשיפה של קורות החיים שלך לציבורי כדי להפוך אותם לגלויים לאחרים."
|
||||
"delete": "להסיר קורות חיים אלה? זה בלתי הפיך.",
|
||||
"share-link": "עליך לשנות את החשיפה של קורות החיים שלך לציבורית כדי שיהיו זמינים לאחרים."
|
||||
}
|
||||
},
|
||||
"timestamp": "עודכן לאחרונה {{timestamp}}"
|
||||
"timestamp": "עודכן לאחרונה לפני {{timestamp}}"
|
||||
},
|
||||
"title": "לוּחַ מַחווָנִים"
|
||||
"title": "לוח בקרה"
|
||||
}
|
||||
|
||||
@ -1,42 +1,43 @@
|
||||
{
|
||||
"actions": {
|
||||
"app": "עבור לאפליקציה",
|
||||
"login": "התחברות",
|
||||
"logout": "להתנתק",
|
||||
"register": "הירשם"
|
||||
"app": "מעבר ליישום",
|
||||
"login": "כניסה",
|
||||
"logout": "יציאה",
|
||||
"register": "הרשמה"
|
||||
},
|
||||
"features": {
|
||||
"heading": "תכונות",
|
||||
"heading": "יכולות",
|
||||
"list": {
|
||||
"ads": "אין פרסום",
|
||||
"export": "ייצא את קורות החיים שלך לפורמט JSON או PDF",
|
||||
"free": "חופשי לנצח",
|
||||
"import": "יבא נתונים מ-LinkedIn, קורות חיים של JSON",
|
||||
"ads": "אין פרסומות",
|
||||
"export": "ייצוא קורות החיים שלך ל־JSON או ל־PDF",
|
||||
"free": "חופשי, לנצח",
|
||||
"import": "ייבוא נתונים מלינקדאין, קורות חיים ב־JSON",
|
||||
"languages": "נגיש במספר שפות",
|
||||
"more": "ותכונות מרגשות הרבה יותר, <1>קרא הכל כאן</1>",
|
||||
"more": "ועוד המון יכולות מפתיעות, <1>כאן יש יותר מידע על זה</1>",
|
||||
"tracking": "אין מעקב אחר משתמשים"
|
||||
}
|
||||
},
|
||||
"links": {
|
||||
"heading": "קישורים",
|
||||
"links": {
|
||||
"donate": "לִתְרוֹם",
|
||||
"github": "קוד מקור",
|
||||
"docs": "תיעוד",
|
||||
"donate": "תרומה",
|
||||
"github": "קוד מקור",
|
||||
"privacy": "מדיניות פרטיות",
|
||||
"reddit": "רדיט",
|
||||
"service": "תנאי השירות"
|
||||
}
|
||||
},
|
||||
"screenshots": {
|
||||
"heading": "צילומי מסך"
|
||||
},
|
||||
"testimonials": {
|
||||
"heading": "המלצות",
|
||||
"body": "טוב או רע, אשמח לשמוע את דעתכם על קורות חיים ריאקטיביים ואיך הייתה החוויה עבורכם.<br/>הנה כמה מההודעות שנשלחו על ידי משתמשים ברחבי העולם.",
|
||||
"contact": "אתה יכול ליצור איתי קשר דרך <1>המייל שלי</1> או דרך טופס יצירת הקשר ב<3>אתר האינטרנט שלי</3> ."
|
||||
},
|
||||
"summary": {
|
||||
"body": "Reactive Resume הוא בונה קורות חיים חינמי וקוד פתוח שנבנה כדי להפוך את המשימות השגרתיות של יצירה, עדכון ושיתוף של קורות החיים שלך לקלות כמו 1, 2, 3. עם האפליקציה הזו, אתה יכול ליצור מספר קורות חיים, לשתף אותם עם מגייסים או חברים דרך קישור ייחודי והדפיס אותו כקובץ PDF, הכל בחינם, ללא פרסומות, ללא מעקב, מבלי לאבד את השלמות והפרטיות של הנתונים שלך.",
|
||||
"heading": "סיכום"
|
||||
"body": "קורות חיים מסתגלים הוא בונה קורות חיים בחינם ובקוד פתוח שנבנה כדי להקל על המשימות המשמימות של יצירה, עדכון ושיתוף קורות החיים שלך. עם היישום הזה אפשר ליצור מספר גיליונות של קורות חיים, לשתף אותם עם מגייסים או חברים דרך קישור ייחודי ולהדפיס אותם כ־PDF, הכול בחינם, ללא פרסומות, ללא מעקב, מבלי לאבד את שלמות או את פרטיות הנתונים שלך.",
|
||||
"heading": "תקציר"
|
||||
},
|
||||
"testimonials": {
|
||||
"body": "לטוב ולרע, אשמח לשמוע את הדעה שלך על קורות חיים מסתגלים ואיך הייתה החוויה שלך.<br/>הנה כמה מההודעות שנשלחו על ידי משתמשים מכל רחבי העולם.",
|
||||
"contact": "אפשר יכול ליצור איתי קשר דרך ה<1>דוא״ל שלי</1> או דרך טופס יצירת הקשר ב<3>אתר שלי</3> .",
|
||||
"heading": "המלצות"
|
||||
}
|
||||
}
|
||||
|
||||
@ -2,47 +2,47 @@
|
||||
"auth": {
|
||||
"forgot-password": {
|
||||
"actions": {
|
||||
"send-email": "שלח אימייל איפוס סיסמה"
|
||||
"send-email": "שליחת דוא״ל לאיפוס סיסמה"
|
||||
},
|
||||
"body": "פשוט הזן את כתובת האימייל המשויכת לחשבון שברצונך לשחזר.",
|
||||
"body": "צריך פשוט למלא את כתובת הדוא״ל שמשויכת לחשבון שמיועד לשחזור.",
|
||||
"form": {
|
||||
"email": {
|
||||
"label": "כתובת דוא\"ל"
|
||||
"label": "כתובת דוא״ל"
|
||||
}
|
||||
},
|
||||
"heading": "שכחת ססמה?",
|
||||
"help-text": "אם החשבון קיים, תקבל אימייל עם קישור לאיפוס הסיסמה שלך."
|
||||
"heading": "שכחת סיסמה?",
|
||||
"help-text": "אם החשבון קיים, תישלח הודעה עם קישור לאיפוס הסיסמה שלך בדוא״ל."
|
||||
},
|
||||
"login": {
|
||||
"actions": {
|
||||
"login": "התחברות"
|
||||
"login": "כניסה"
|
||||
},
|
||||
"body": "אנא הזן את שם המשתמש והסיסמה המשויכים לחשבונך כדי להתחבר ולגשת, לנהל ולשתף את קורות החיים שלך.",
|
||||
"body": "נא למלא את שם המשתמש והסיסמה המשויכים לחשבונך כדי להתחבר ולגשת, לנהל ולשתף את קורות החיים שלך.",
|
||||
"form": {
|
||||
"password": {
|
||||
"label": "סיסמה"
|
||||
},
|
||||
"username": {
|
||||
"help-text": "אתה יכול גם להזין את כתובת הדוא\"ל שלך",
|
||||
"help-text": "אפשר גם למלא את כתובת הדוא״ל שלך",
|
||||
"label": "שם משתמש"
|
||||
}
|
||||
},
|
||||
"heading": "התחבר לחשבונך",
|
||||
"recover-text": "במקרה ששכחת את הסיסמה שלך, תוכל <1>לשחזר את חשבונך</1> כאן.",
|
||||
"register-text": "אם אין לך אחד, אתה יכול <1>ליצור חשבון</1> כאן."
|
||||
"heading": "כניסה לחשבונך",
|
||||
"recover-text": "אם שכחת את הסיסמה שלך, אפשר <1>לשחזר את החשבון שלך</1> דרך כאן.",
|
||||
"register-text": "אם אין לך חשבון, אפשר <1>ליצור אחד</1> כאן."
|
||||
},
|
||||
"register": {
|
||||
"actions": {
|
||||
"register": "הירשם",
|
||||
"google": "הירשם בגוגל"
|
||||
"register": "הרשמה",
|
||||
"google": "הרשמה עם Google"
|
||||
},
|
||||
"body": "אנא הזן את המידע האישי שלך כדי ליצור חשבון.",
|
||||
"body": "נא למלא את הפרטים האישיים שלך כדי ליצור חשבון.",
|
||||
"form": {
|
||||
"confirm-password": {
|
||||
"label": "אשר סיסמה"
|
||||
"label": "אישור סיסמה"
|
||||
},
|
||||
"email": {
|
||||
"label": "כתובת דוא\"ל"
|
||||
"label": "כתובת דוא״ל"
|
||||
},
|
||||
"name": {
|
||||
"label": "שם מלא"
|
||||
@ -54,31 +54,56 @@
|
||||
"label": "שם משתמש"
|
||||
}
|
||||
},
|
||||
"heading": "צור חשבון",
|
||||
"loginText": "אם כבר יש לך חשבון, אתה יכול <1>להתחבר כאן</1> ."
|
||||
"heading": "יצירת חשבון",
|
||||
"loginText": "אם כבר יש לך חשבון, אפשר <1>להיכנס כאן</1> ."
|
||||
},
|
||||
"reset-password": {
|
||||
"actions": {
|
||||
"set-password": "הגדר סיסמה חדשה"
|
||||
"set-password": "הגדרת סיסמה חדשה"
|
||||
},
|
||||
"body": "הזן סיסמה חדשה לחשבון שלך.",
|
||||
"body": "מילוי סיסמה חדשה לחשבון שלך.",
|
||||
"form": {
|
||||
"confirm-password": {
|
||||
"label": "אשר סיסמה"
|
||||
"label": "אימות סיסמה"
|
||||
},
|
||||
"password": {
|
||||
"label": "סיסמה"
|
||||
}
|
||||
},
|
||||
"heading": "אפס את הסיסמה שלך"
|
||||
"heading": "איפוס הסיסמה שלך"
|
||||
},
|
||||
"profile": {
|
||||
"heading": "החשבון שלך",
|
||||
"form": {
|
||||
"avatar": {
|
||||
"help-text": "אפשר לעדכן את תמונת הפרופיל שלך ב־<1>Gravatar</1>"
|
||||
},
|
||||
"name": {
|
||||
"label": "שם מלא"
|
||||
},
|
||||
"email": {
|
||||
"label": "כתובת דוא״ל",
|
||||
"help-text": "אי אפשר לעדכן את כתובת הדוא״ל שלך כרגע, נא ליצור חשבון חדש במקום."
|
||||
}
|
||||
},
|
||||
"delete-account": {
|
||||
"heading": "מחיקת חשבון ונתונים",
|
||||
"body": "כדי למחוק את החשבון שלך ואת כל קורות החיים שלך, יש להקליד את „{{keyword}}” לתיבת טקסט וללחוץ על הכפתור. נא לשים לב שזאת פעולה בלתי הפיכה ושלא ניתן יהיה להשיג את הנתונים שלך עוד.",
|
||||
"actions": {
|
||||
"delete": "מחיקת חשבון"
|
||||
}
|
||||
},
|
||||
"actions": {
|
||||
"save": "שמירת השינויים"
|
||||
}
|
||||
}
|
||||
},
|
||||
"dashboard": {
|
||||
"create-resume": {
|
||||
"actions": {
|
||||
"create-resume": "צור קורות חיים"
|
||||
"create-resume": "יצירת קורות חיים"
|
||||
},
|
||||
"body": "התחל לבנות את קורות החיים שלך על ידי מתן שם לקובץ. זה יכול להיות בהתייחסות לתפקיד שאתה מגיש מועמדות אליו, או רק החטיף האהוב עליך.",
|
||||
"body": "התחלה בבניית קורות החיים שלך עוברת דרך מתן שם. זה יכול להיות תואם לתפקיד המיועד או סתם החטיף האהוב עליך.",
|
||||
"form": {
|
||||
"name": {
|
||||
"label": "שם"
|
||||
@ -87,49 +112,49 @@
|
||||
"label": "האם נגיש לציבור?"
|
||||
},
|
||||
"slug": {
|
||||
"label": "סלאג"
|
||||
"label": "שם ייצוגי"
|
||||
}
|
||||
},
|
||||
"heading": "צור קורות חיים חדשים"
|
||||
"heading": "יצירת קורות חיים חדשים"
|
||||
},
|
||||
"import-external": {
|
||||
"heading": "ייבוא ממקורות חיצוניים",
|
||||
"json-resume": {
|
||||
"actions": {
|
||||
"upload-json": "העלה JSON"
|
||||
"upload-json": "העלאת JSON"
|
||||
},
|
||||
"body": "אם יש לך <1>קורות חיים של JSON מאומת</1> מוכן לפעולה, אתה יכול להשתמש בו כדי לעקוב במהירות את הפיתוח שלך בקורות חיים ריאקטיביים. לחץ על הכפתור למטה והעלה קובץ JSON חוקי כדי להתחיל.",
|
||||
"heading": "ייבוא מ-JSON קורות חיים"
|
||||
"body": "אם יש לך <1>קורות חיים ב־JSON תקף</1> בהישג יד, אפשר להשתמש בהם כדי לעקוב במהירות אחר ההתפתחות שלך בקורות חיים מסתגלים. יש ללחוץ על הכפתור להלן ולהעלות קובץ JSON תקף כדי להתחיל.",
|
||||
"heading": "ייבוא מקורות חיים ב־JSON"
|
||||
},
|
||||
"linkedin": {
|
||||
"actions": {
|
||||
"upload-archive": "העלה ארכיון ZIP"
|
||||
"upload-archive": "העלאת ארכיון ZIP"
|
||||
},
|
||||
"body": "אתה יכול לחסוך זמן על ידי ייצוא הנתונים שלך מ-LinkedIn ושימוש בהם למילוי אוטומטי של שדות בקורות חיים תגובתיים. עבור אל <1>פרטיות נתונים</1> מדור בלינקדאין ובקש ארכיון של הנתונים שלך. ברגע שהוא זמין, העלה את קובץ ה-ZIP למטה.",
|
||||
"heading": "ייבוא מ-LinkedIn"
|
||||
"body": "אפשר לחסוך זמן על ידי ייצוא הנתונים שלך מלינקדאין ושימוש בהם למילוי אוטומטי של כל השדות בקורות חיים מסתגלים. יש לגשת לסעיף <1>פרטיות נתונים</1> בלינקדאין ולבקש ארכיון של הנתונים שלך. לאחר שהשגת אותו, יש להעלות את קובץ ה־ZIP להלן.",
|
||||
"heading": "ייבוא מלינקדאין"
|
||||
},
|
||||
"reactive-resume": {
|
||||
"actions": {
|
||||
"upload-json": "העלה JSON",
|
||||
"upload-json-v2": "העלה JSON מגרסה 2"
|
||||
"upload-json": "העלאת JSON",
|
||||
"upload-json-v2": "העלאת JSON מגרסה 2"
|
||||
},
|
||||
"body": "אם יש לך JSON שיוצא עם הגרסה הנוכחית של Reactive Resume, תוכל לייבא אותו בחזרה לכאן כדי לקבל שוב גרסה הניתנת לעריכה.",
|
||||
"heading": "ייבא מ- Reactive Resume"
|
||||
"body": "אם יש לך JSON שייוצא עם הגרסה הנוכחית של קורות חיים מסתגלים, אפשר לייבא אותם בחזרה לכאן כדי לקבל שוב גרסה שניתן לערוך.",
|
||||
"heading": "ייבוא מקורות חיים מסתגלים"
|
||||
}
|
||||
},
|
||||
"rename-resume": {
|
||||
"actions": {
|
||||
"rename-resume": "שנה את שם קורות החיים"
|
||||
"rename-resume": "שינוי שם קורות החיים"
|
||||
},
|
||||
"form": {
|
||||
"name": {
|
||||
"label": "שם"
|
||||
},
|
||||
"slug": {
|
||||
"label": "סלאג"
|
||||
"label": "שם ייצוגי"
|
||||
}
|
||||
},
|
||||
"heading": "שנה את שם קורות החיים שלך"
|
||||
"heading": "שינוי שם קורות החיים שלך"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -3,6 +3,7 @@
|
||||
"actions": {
|
||||
"add": "새 {{token}} 추가",
|
||||
"delete": "{{token}} 삭제",
|
||||
"duplicate": "중복 섹션",
|
||||
"edit": "{{token}} 수정"
|
||||
},
|
||||
"columns": {
|
||||
@ -63,8 +64,8 @@
|
||||
"list": {
|
||||
"actions": {
|
||||
"delete": "삭제",
|
||||
"duplicate": "복제하다",
|
||||
"edit": "편집하다"
|
||||
"duplicate": "복제",
|
||||
"edit": "편집"
|
||||
},
|
||||
"empty-text": "이 목록은 비어 있습니다."
|
||||
},
|
||||
@ -72,7 +73,7 @@
|
||||
"delete-item": "이 항목을 삭제하시겠습니까? 이것은 되돌릴 수 없는 조치입니다.",
|
||||
"delete-section": "섹션 삭제",
|
||||
"rename-section": "섹션 이름 바꾸기",
|
||||
"toggle-visibility": "가시성 전환"
|
||||
"toggle-visibility": "표시 전환"
|
||||
}
|
||||
},
|
||||
"controller": {
|
||||
@ -80,23 +81,23 @@
|
||||
"center-artboard": "중앙 대지",
|
||||
"copy-link": "이력서 링크 복사",
|
||||
"export-pdf": "PDF 내보내기",
|
||||
"redo": "다시 실행",
|
||||
"toggle-orientation": "페이지 방향 전환",
|
||||
"toggle-page-break-line": "페이지 나누기 줄 전환",
|
||||
"toggle-sidebars": "사이드바 토글",
|
||||
"zoom-in": "확대",
|
||||
"zoom-out": "축소",
|
||||
"toggle-page-break-line": "페이지 구분선 전환",
|
||||
"toggle-sidebars": "사이드바 전환",
|
||||
"undo": "실행 취소",
|
||||
"redo": "다시 하다"
|
||||
"zoom-in": "확대",
|
||||
"zoom-out": "축소"
|
||||
}
|
||||
},
|
||||
"header": {
|
||||
"menu": {
|
||||
"delete": "삭제",
|
||||
"duplicate": "복제하다",
|
||||
"duplicate": "복제",
|
||||
"rename": "이름 바꾸기",
|
||||
"share-link": "링크 공유",
|
||||
"tooltips": {
|
||||
"delete": "이 이력서를 삭제하시겠습니까? 이것은 되돌릴 수 없는 조치입니다.",
|
||||
"delete": "이 이력서를 삭제하시겠습니까? 삭제는 되돌릴 수 없는 작업입니다.",
|
||||
"share-link": "다른 사람이 볼 수 있도록 이력서의 공개 상태를 변경해야 합니다."
|
||||
}
|
||||
}
|
||||
@ -114,6 +115,9 @@
|
||||
"actions": {
|
||||
"photo-filters": "사진 필터"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "생일"
|
||||
},
|
||||
"heading": "기초",
|
||||
"headline": {
|
||||
"label": "표제"
|
||||
@ -121,9 +125,6 @@
|
||||
"name": {
|
||||
"label": "성명"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "생일"
|
||||
},
|
||||
"photo-filters": {
|
||||
"effects": {
|
||||
"border": {
|
||||
@ -264,14 +265,15 @@
|
||||
"button": "GitHub 문제",
|
||||
"heading": "버그? 기능 요청?"
|
||||
},
|
||||
"docs": "선적 서류 비치",
|
||||
"donate": {
|
||||
"body": "Reactive Resume 사용이 마음에 드셨다면, 광고 없이 영원히 무료로 앱을 계속 운영할 수 있도록 가능한 한 많은 기부를 고려하십시오.",
|
||||
"button": "커피 사줘",
|
||||
"heading": "Reactive Resume에 기부"
|
||||
},
|
||||
"github": "소스 코드",
|
||||
"docs": "선적 서류 비치",
|
||||
"heading": "연결"
|
||||
"heading": "연결",
|
||||
"reddit": "Reddit"
|
||||
},
|
||||
"settings": {
|
||||
"global": {
|
||||
@ -290,14 +292,14 @@
|
||||
},
|
||||
"heading": "설정",
|
||||
"page": {
|
||||
"format": {
|
||||
"primary": "용지 크기",
|
||||
"secondary": "이력서 페이지의 크기를 결정합니다."
|
||||
},
|
||||
"break-line": {
|
||||
"primary": "브레이크 라인",
|
||||
"secondary": "A4 페이지의 높이를 표시하기 위해 모든 페이지에 선 표시"
|
||||
},
|
||||
"format": {
|
||||
"primary": "용지 크기",
|
||||
"secondary": "이력서 페이지의 크기를 결정합니다."
|
||||
},
|
||||
"heading": "페이지",
|
||||
"orientation": {
|
||||
"disabled": "한 페이지만 있는 경우에는 효과가 없습니다.",
|
||||
|
||||
@ -1,7 +1,7 @@
|
||||
{
|
||||
"avatar": {
|
||||
"menu": {
|
||||
"greeting": "안녕하십니까",
|
||||
"greeting": "안녕하세요",
|
||||
"logout": "로그 아웃"
|
||||
}
|
||||
},
|
||||
@ -10,13 +10,13 @@
|
||||
"license": "커뮤니티에 의한, 커뮤니티를 위한."
|
||||
},
|
||||
"markdown": {
|
||||
"help-text": "이 섹션은 <1>마크다운을 지원합니다.</1> 포맷."
|
||||
"help-text": "이 섹션은 <1>markdown</1> 서식을 지원합니다."
|
||||
},
|
||||
"date": {
|
||||
"present": "현재의"
|
||||
"present": "현재"
|
||||
},
|
||||
"subtitle": "무료 오픈 소스 이력서 작성기.",
|
||||
"title": "반응적인 이력서",
|
||||
"title": "리액티브 레쥬메",
|
||||
"toast": {
|
||||
"error": {
|
||||
"upload-file-size": "2MB 미만의 파일만 업로드하십시오.",
|
||||
|
||||
@ -10,16 +10,16 @@
|
||||
"resume": {
|
||||
"menu": {
|
||||
"delete": "삭제",
|
||||
"duplicate": "복제하다",
|
||||
"open": "열려 있는",
|
||||
"duplicate": "복제",
|
||||
"open": "열기",
|
||||
"rename": "이름 바꾸기",
|
||||
"share-link": "링크 공유",
|
||||
"tooltips": {
|
||||
"delete": "이 이력서를 삭제하시겠습니까? 이것은 되돌릴 수 없는 조치입니다.",
|
||||
"delete": "이 이력서를 삭제하시겠습니까? 삭제는 되돌릴 수 없는 작업입니다.",
|
||||
"share-link": "다른 사람이 볼 수 있도록 이력서의 공개 상태를 변경해야 합니다."
|
||||
}
|
||||
},
|
||||
"timestamp": "{{timestamp}} 전에 마지막으로 업데이트됨"
|
||||
},
|
||||
"title": "계기반"
|
||||
"title": "대시보드"
|
||||
}
|
||||
|
||||
@ -3,40 +3,41 @@
|
||||
"app": "앱으로 이동",
|
||||
"login": "로그인",
|
||||
"logout": "로그 아웃",
|
||||
"register": "등록하다"
|
||||
"register": "등록"
|
||||
},
|
||||
"features": {
|
||||
"heading": "특징",
|
||||
"list": {
|
||||
"ads": "광고 없음",
|
||||
"export": "이력서를 JSON 또는 PDF 형식으로 내보내기",
|
||||
"free": "무료, 영원히",
|
||||
"free": "평생 무료",
|
||||
"import": "LinkedIn, JSON 이력서에서 데이터 가져오기",
|
||||
"languages": "여러 언어로 액세스 가능",
|
||||
"more": "훨씬 더 흥미로운 기능은 <1>여기에서 자세히 읽어보십시오.</1>",
|
||||
"more": "훨씬 더 흥미로운 기능에 대한 자세한 <1>내용은 여기에서</1> 확인하세요.",
|
||||
"tracking": "사용자 추적 없음"
|
||||
}
|
||||
},
|
||||
"links": {
|
||||
"heading": "연결",
|
||||
"heading": "링크",
|
||||
"links": {
|
||||
"donate": "기부",
|
||||
"docs": "문서",
|
||||
"donate": "후원하기",
|
||||
"github": "소스 코드",
|
||||
"docs": "선적 서류 비치",
|
||||
"privacy": "개인 정보 정책",
|
||||
"reddit": "Reddit",
|
||||
"service": "서비스 약관"
|
||||
}
|
||||
},
|
||||
"screenshots": {
|
||||
"heading": "스크린샷"
|
||||
},
|
||||
"testimonials": {
|
||||
"heading": "사용후기",
|
||||
"body": "좋든 나쁘든 Reactive Resume에 대한 귀하의 의견과 경험이 어떠했는지 듣고 싶습니다.<br/>다음은 전 세계 사용자가 보낸 메시지 중 일부입니다.",
|
||||
"contact": "<1>내 이메일을 통해 저에게 연락하실 수 있습니다.</1> 또는 <3>내 웹사이트의 문의 양식을 통해</3> ."
|
||||
},
|
||||
"summary": {
|
||||
"body": "Reactive Resume은 이력서를 1, 2, 3처럼 쉽게 생성, 업데이트 및 공유하는 일상적인 작업을 수행할 수 있도록 구축된 무료 오픈 소스 이력서 작성기입니다. 이 앱을 사용하면 여러 이력서를 만들고 채용 담당자 또는 친구와 공유할 수 있습니다. 고유 링크를 통해 데이터의 무결성과 개인 정보를 잃지 않고 PDF로 인쇄할 수 있습니다.",
|
||||
"body": "Reactive Resume는 이력서를 만들고, 업데이트하고, 공유하는 일상적인 작업을 1, 2, 3처럼 쉽게 할 수 있도록 만들어진 무료 오픈 소스 이력서 작성기입니다. 이 앱을 사용하면 여러 개의 이력서를 작성하고, 고유한 링크를 통해 채용 담당자 또는 친구와 공유하고, PDF로 인쇄할 수 있으며, 데이터의 무결성과 개인 정보 보호를 유지하면서 광고나 추적 없이 모두 무료로 이용할 수 있습니다.",
|
||||
"heading": "요약"
|
||||
},
|
||||
"testimonials": {
|
||||
"body": "좋든 나쁘든 Reactive Resume에 대한 귀하의 의견과 경험이 어떠했는지 듣고 싶습니다.<br/>다음은 전 세계 사용자가 보낸 메시지 중 일부입니다.",
|
||||
"contact": "<1>제 이메일이나</1> <3>웹사이트의</3> 문의 양식을 통해 저에게 연락하실 수 있습니다.",
|
||||
"heading": "사용후기"
|
||||
}
|
||||
}
|
||||
|
||||
@ -28,13 +28,13 @@
|
||||
}
|
||||
},
|
||||
"heading": "계정에 로그인",
|
||||
"recover-text": "비밀번호를 잊어버린 경우 <1>계정을 복구할 수 있습니다.</1> 여기.",
|
||||
"register-text": "계정이 없으면 <1>계정을 만들 수 있습니다.</1> 여기."
|
||||
"recover-text": "비밀번호를 잊어버린 경우 여기에서 <1>계정을 복구</1>할 수 있습니다.",
|
||||
"register-text": "계정이 없으면 여기에서 <1>계정을 생성</1>할 수 있습니다."
|
||||
},
|
||||
"register": {
|
||||
"actions": {
|
||||
"register": "등록하다",
|
||||
"google": "Google에 등록"
|
||||
"register": "등록하기",
|
||||
"google": "Google 계정으로 등록"
|
||||
},
|
||||
"body": "계정 생성을 위해 개인정보를 입력해주세요.",
|
||||
"form": {
|
||||
@ -71,12 +71,37 @@
|
||||
}
|
||||
},
|
||||
"heading": "비밀번호를 재설정"
|
||||
},
|
||||
"profile": {
|
||||
"heading": "사용자 계정",
|
||||
"form": {
|
||||
"avatar": {
|
||||
"help-text": "<1>Gravatar에서 프로필 사진을 업데이트할 수 있습니다.</1>"
|
||||
},
|
||||
"name": {
|
||||
"label": "성명"
|
||||
},
|
||||
"email": {
|
||||
"label": "이메일 주소",
|
||||
"help-text": "지금은 이메일 주소를 업데이트할 수 없습니다. 대신 새 계정을 만드십시오."
|
||||
}
|
||||
},
|
||||
"delete-account": {
|
||||
"heading": "계정 및 데이터 삭제",
|
||||
"body": "계정, 데이터 및 모든 이력서를 삭제하려면 텍스트 상자에 \"{{keyword}}\"을 입력하고 버튼을 클릭하십시오. 이는 되돌릴 수 없는 작업이며 데이터를 다시 검색할 수 없습니다.",
|
||||
"actions": {
|
||||
"delete": "계정 삭제"
|
||||
}
|
||||
},
|
||||
"actions": {
|
||||
"save": "변경 사항 저장"
|
||||
}
|
||||
}
|
||||
},
|
||||
"dashboard": {
|
||||
"create-resume": {
|
||||
"actions": {
|
||||
"create-resume": "이력서 작성"
|
||||
"create-resume": "이력서 만들기"
|
||||
},
|
||||
"body": "이름을 지정하여 이력서 작성을 시작하십시오. 지원하는 역할이나 좋아하는 간식을 참조할 수 있습니다.",
|
||||
"form": {
|
||||
@ -103,7 +128,7 @@
|
||||
},
|
||||
"linkedin": {
|
||||
"actions": {
|
||||
"upload-archive": "ZIP 아카이브 업로드"
|
||||
"upload-archive": "ZIP 압축파일 업로드"
|
||||
},
|
||||
"body": "LinkedIn에서 데이터를 내보내고 Reactive Resume의 필드를 자동으로 채우는 데 사용하여 시간을 절약할 수 있습니다. <1>데이터 개인정보 보호로 이동</1> LinkedIn에서 섹션을 방문하여 데이터 아카이브를 요청하십시오. 사용할 수 있게 되면 아래 ZIP 파일을 업로드하세요.",
|
||||
"heading": "LinkedIn에서 가져오기"
|
||||
@ -114,7 +139,7 @@
|
||||
"upload-json-v2": "v2에서 JSON 업로드"
|
||||
},
|
||||
"body": "Reactive Resume의 현재 버전으로 내보낸 JSON이 있는 경우 여기에서 다시 가져와서 편집 가능한 버전을 다시 얻을 수 있습니다.",
|
||||
"heading": "반응적인 이력서에서 가져오기"
|
||||
"heading": "Reactive Resume에서 가져오기"
|
||||
}
|
||||
},
|
||||
"rename-resume": {
|
||||
|
||||
@ -2,7 +2,7 @@
|
||||
"avatar": {
|
||||
"menu": {
|
||||
"greeting": "Hallo",
|
||||
"logout": "Afmelden"
|
||||
"logout": "Uitloggen"
|
||||
}
|
||||
},
|
||||
"footer": {
|
||||
@ -10,7 +10,7 @@
|
||||
"license": "Door de gemeenschap, voor de gemeenschap."
|
||||
},
|
||||
"markdown": {
|
||||
"help-text": "Deze sectie ondersteunt <1>markdown</1> opmaak."
|
||||
"help-text": "Deze sectie ondersteunt <1>html</1> opmaak."
|
||||
},
|
||||
"date": {
|
||||
"present": "Heden"
|
||||
|
||||
401
client/public/locales/pt-BR/builder.json
Normal file
401
client/public/locales/pt-BR/builder.json
Normal file
@ -0,0 +1,401 @@
|
||||
{
|
||||
"common": {
|
||||
"actions": {
|
||||
"add": "Adicionar {{token}}",
|
||||
"delete": "Remover {{token}}",
|
||||
"edit": "Editar {{token}}",
|
||||
"duplicate": "Duplicar sessão"
|
||||
},
|
||||
"columns": {
|
||||
"heading": "Colunas",
|
||||
"tooltip": "Alterar o número de colunas"
|
||||
},
|
||||
"form": {
|
||||
"date": {
|
||||
"label": "Data"
|
||||
},
|
||||
"description": {
|
||||
"label": "Descrição"
|
||||
},
|
||||
"email": {
|
||||
"label": "Endereço de e-mail"
|
||||
},
|
||||
"end-date": {
|
||||
"help-text": "Deixe este campo em branco se for até o presente",
|
||||
"label": "Data de Término"
|
||||
},
|
||||
"keywords": {
|
||||
"label": "Palavras-chave"
|
||||
},
|
||||
"level": {
|
||||
"label": "Nível"
|
||||
},
|
||||
"levelNum": {
|
||||
"label": "Nível (Número)"
|
||||
},
|
||||
"name": {
|
||||
"label": "Nome"
|
||||
},
|
||||
"phone": {
|
||||
"label": "Número de telefone"
|
||||
},
|
||||
"position": {
|
||||
"label": "Cargo"
|
||||
},
|
||||
"start-date": {
|
||||
"label": "Data de Início"
|
||||
},
|
||||
"subtitle": {
|
||||
"label": "Subtítulo"
|
||||
},
|
||||
"summary": {
|
||||
"label": "Resumo"
|
||||
},
|
||||
"title": {
|
||||
"label": "Título"
|
||||
},
|
||||
"url": {
|
||||
"label": "Site"
|
||||
}
|
||||
},
|
||||
"glossary": {
|
||||
"page": "Página"
|
||||
},
|
||||
"list": {
|
||||
"actions": {
|
||||
"delete": "Excluir",
|
||||
"duplicate": "Duplicar",
|
||||
"edit": "Editar"
|
||||
},
|
||||
"empty-text": "Essa lista está vazia."
|
||||
},
|
||||
"tooltip": {
|
||||
"delete-item": "Tem certeza de que deseja excluir este item? Esta ação é irreversível.",
|
||||
"delete-section": "Excluir Seção",
|
||||
"rename-section": "Renomear Seção",
|
||||
"toggle-visibility": "Alternar Visibilidade"
|
||||
}
|
||||
},
|
||||
"controller": {
|
||||
"tooltip": {
|
||||
"center-artboard": "Prancheta central",
|
||||
"copy-link": "Copiar link do currículo",
|
||||
"export-pdf": "Exportar PDF",
|
||||
"toggle-orientation": "Alternar orientação da página",
|
||||
"toggle-page-break-line": "Alternar linha de quebra de página",
|
||||
"toggle-sidebars": "Alternar barra lateral",
|
||||
"zoom-in": "Mais Zoom",
|
||||
"zoom-out": "Menos Zoom",
|
||||
"undo": "Desfazer",
|
||||
"redo": "Redo"
|
||||
}
|
||||
},
|
||||
"header": {
|
||||
"menu": {
|
||||
"delete": "Deletar",
|
||||
"duplicate": "Duplicar",
|
||||
"rename": "Renomear",
|
||||
"share-link": "Compartilhar Link",
|
||||
"tooltips": {
|
||||
"delete": "Tem certeza de que deseja excluir este currículo? Esta ação é irreversível.",
|
||||
"share-link": "Você precisa alterar a visibilidade do seu currículo para público para torná-lo visível para outras pessoas."
|
||||
}
|
||||
}
|
||||
},
|
||||
"leftSidebar": {
|
||||
"sections": {
|
||||
"awards": {
|
||||
"form": {
|
||||
"awarder": {
|
||||
"label": "Concedente"
|
||||
}
|
||||
},
|
||||
"heading": "Títulos",
|
||||
"heading_one": "Título"
|
||||
},
|
||||
"work": {
|
||||
"heading": "Experiências de Trabalho",
|
||||
"heading_one": "Experiência de Trabalho"
|
||||
},
|
||||
"basics": {
|
||||
"actions": {
|
||||
"photo-filters": "Filtros da foto"
|
||||
},
|
||||
"heading": "Informações básicas",
|
||||
"headline": {
|
||||
"label": "Título"
|
||||
},
|
||||
"name": {
|
||||
"label": "Nome Completo"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Data de nascimento"
|
||||
},
|
||||
"photo-filters": {
|
||||
"effects": {
|
||||
"border": {
|
||||
"label": "Borda"
|
||||
},
|
||||
"grayscale": {
|
||||
"label": "Escala de cinza"
|
||||
},
|
||||
"heading": "Efeitos"
|
||||
},
|
||||
"shape": {
|
||||
"heading": "Forma"
|
||||
},
|
||||
"size": {
|
||||
"heading": "Tamanho (em px)"
|
||||
}
|
||||
},
|
||||
"photo-upload": {
|
||||
"tooltip": {
|
||||
"remove": "Excluir Foto",
|
||||
"upload": "Enviar Foto"
|
||||
}
|
||||
}
|
||||
},
|
||||
"certifications": {
|
||||
"form": {
|
||||
"issuer": {
|
||||
"label": "Emissor"
|
||||
}
|
||||
},
|
||||
"heading": "Certificações",
|
||||
"heading_one": "Certificação"
|
||||
},
|
||||
"education": {
|
||||
"form": {
|
||||
"area-study": {
|
||||
"label": "Área de estudo"
|
||||
},
|
||||
"courses": {
|
||||
"label": "Cursos"
|
||||
},
|
||||
"degree": {
|
||||
"label": "Grau"
|
||||
},
|
||||
"grade": {
|
||||
"label": "Nota"
|
||||
},
|
||||
"institution": {
|
||||
"label": "Instituição"
|
||||
}
|
||||
},
|
||||
"heading": "Formação Acadêmica",
|
||||
"heading_one": "Formação Acadêmica"
|
||||
},
|
||||
"location": {
|
||||
"address": {
|
||||
"label": "Endereço"
|
||||
},
|
||||
"city": {
|
||||
"label": "Cidade"
|
||||
},
|
||||
"country": {
|
||||
"label": "País"
|
||||
},
|
||||
"heading": "Localização",
|
||||
"postal-code": {
|
||||
"label": "Código Postal"
|
||||
},
|
||||
"region": {
|
||||
"label": "Região"
|
||||
}
|
||||
},
|
||||
"profiles": {
|
||||
"form": {
|
||||
"network": {
|
||||
"label": "Rede Social"
|
||||
},
|
||||
"username": {
|
||||
"label": "Nome de Usuário"
|
||||
}
|
||||
},
|
||||
"heading": "Perfis",
|
||||
"heading_one": "Perfil"
|
||||
},
|
||||
"publications": {
|
||||
"form": {
|
||||
"publisher": {
|
||||
"label": "Editor"
|
||||
}
|
||||
},
|
||||
"heading": "Publicações",
|
||||
"heading_one": "Publicação"
|
||||
},
|
||||
"references": {
|
||||
"form": {
|
||||
"relationship": {
|
||||
"label": "Relação"
|
||||
}
|
||||
},
|
||||
"heading": "Referências",
|
||||
"heading_one": "Referência"
|
||||
},
|
||||
"skills": {
|
||||
"heading": "Habilidades",
|
||||
"heading_one": "Habilidade"
|
||||
},
|
||||
"languages": {
|
||||
"heading": "Idiomas",
|
||||
"heading_one": "Idioma"
|
||||
},
|
||||
"interests": {
|
||||
"heading": "Interesses",
|
||||
"heading_one": "Interesse"
|
||||
},
|
||||
"projects": {
|
||||
"heading": "Projetos",
|
||||
"heading_one": "Projeto"
|
||||
},
|
||||
"section": {
|
||||
"heading": "Seção"
|
||||
},
|
||||
"volunteer": {
|
||||
"form": {
|
||||
"organization": {
|
||||
"label": "Organização"
|
||||
}
|
||||
},
|
||||
"heading": "Trabalhos Voluntários",
|
||||
"heading_one": "Trabalho Voluntário"
|
||||
}
|
||||
}
|
||||
},
|
||||
"rightSidebar": {
|
||||
"sections": {
|
||||
"css": {
|
||||
"heading": "CSS Personalizado"
|
||||
},
|
||||
"export": {
|
||||
"heading": "Exportar",
|
||||
"json": {
|
||||
"primary": "JSON",
|
||||
"secondary": "Baixe uma versão JSON do seu currículo que poderá ser importada de volta ao Reactive Resume."
|
||||
},
|
||||
"pdf": {
|
||||
"loading": {
|
||||
"primary": "Gerando PDF",
|
||||
"secondary": "Por favor aguarde enquanto o seu PDF é gerado, isso pode levar até 15 segundos."
|
||||
},
|
||||
"normal": {
|
||||
"primary": "PDF",
|
||||
"secondary": "Baixe um PDF do seu currículo que você pode imprimir e enviar para o emprego dos seus sonhos. Este arquivo não pode ser importado de volta para edição posterior."
|
||||
}
|
||||
}
|
||||
},
|
||||
"layout": {
|
||||
"heading": "Layout",
|
||||
"tooltip": {
|
||||
"reset-layout": "Redefinir Layout"
|
||||
}
|
||||
},
|
||||
"links": {
|
||||
"bugs-features": {
|
||||
"body": "Alguma coisa te impede de fazer um currículo? Ou você tem uma ideia incrível para adicionar? Crie uma issue no GitHub para começar.",
|
||||
"button": "GitHub Issues",
|
||||
"heading": "Bugs? Sugestões de recursos?"
|
||||
},
|
||||
"donate": {
|
||||
"body": "Se você gostou de usar o Reactive Resume, considere doar o máximo possível para manter o aplicativo em funcionamento, sem anúncios e gratuito para sempre.",
|
||||
"button": "Pague-me um café",
|
||||
"heading": "Faça uma doação ao Reactive Resume"
|
||||
},
|
||||
"github": "Código Fonte",
|
||||
"docs": "Documentação",
|
||||
"heading": "Links"
|
||||
},
|
||||
"settings": {
|
||||
"global": {
|
||||
"date": {
|
||||
"primary": "Data",
|
||||
"secondary": "Formato de data usado em todo o aplicativo"
|
||||
},
|
||||
"heading": "Global",
|
||||
"language": {
|
||||
"primary": "Idioma",
|
||||
"secondary": "Idioma de exibição usado em todo o aplicativo"
|
||||
},
|
||||
"theme": {
|
||||
"primary": "Tema"
|
||||
}
|
||||
},
|
||||
"heading": "Configurações",
|
||||
"page": {
|
||||
"format": {
|
||||
"primary": "Tamanho do papel",
|
||||
"secondary": "Determina as dimensões das suas páginas de currículo"
|
||||
},
|
||||
"break-line": {
|
||||
"primary": "Linha de quebra",
|
||||
"secondary": "Mostrar uma linha em todas as páginas para marcar a altura de uma página A4"
|
||||
},
|
||||
"heading": "Página",
|
||||
"orientation": {
|
||||
"disabled": "Não tem efeito quando há somente uma página",
|
||||
"primary": "Orientação",
|
||||
"secondary": "Se as páginas devem ser exibidas horizontalmente ou verticalmente"
|
||||
}
|
||||
},
|
||||
"resume": {
|
||||
"heading": "Currículo",
|
||||
"reset": {
|
||||
"primary": "Limpar Tudo",
|
||||
"secondary": "Cometeu muitos erros? Clique aqui para redefinir todas as alterações e começar do zero. Tenha cuidado, esta ação não pode ser revertida."
|
||||
},
|
||||
"sample": {
|
||||
"primary": "Carregar dados de exemplo",
|
||||
"secondary": "Não sabe por onde começar? Clique aqui para carregar alguns dados de exemplo para ver como é um currículo completo."
|
||||
}
|
||||
}
|
||||
},
|
||||
"sharing": {
|
||||
"heading": "Compartilhamento",
|
||||
"short-url": {
|
||||
"label": "Prefiro um URL curto"
|
||||
},
|
||||
"visibility": {
|
||||
"subtitle": "Permitir que qualquer um com um link veja seu currículo",
|
||||
"title": "Público"
|
||||
}
|
||||
},
|
||||
"templates": {
|
||||
"heading": "Modelos"
|
||||
},
|
||||
"theme": {
|
||||
"form": {
|
||||
"background": {
|
||||
"label": "Plano de fundo"
|
||||
},
|
||||
"primary": {
|
||||
"label": "Primário"
|
||||
},
|
||||
"text": {
|
||||
"label": "Texto"
|
||||
}
|
||||
},
|
||||
"heading": "Tema"
|
||||
},
|
||||
"typography": {
|
||||
"form": {
|
||||
"font-family": {
|
||||
"label": "Família da fonte"
|
||||
},
|
||||
"font-size": {
|
||||
"label": "Tamanho da fonte"
|
||||
}
|
||||
},
|
||||
"heading": "Tipografia",
|
||||
"widgets": {
|
||||
"body": {
|
||||
"label": "Corpo"
|
||||
},
|
||||
"headings": {
|
||||
"label": "Cabeçalho"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
29
client/public/locales/pt-BR/common.json
Normal file
29
client/public/locales/pt-BR/common.json
Normal file
@ -0,0 +1,29 @@
|
||||
{
|
||||
"avatar": {
|
||||
"menu": {
|
||||
"greeting": "Olá",
|
||||
"logout": "Sair"
|
||||
}
|
||||
},
|
||||
"footer": {
|
||||
"credit": "Um projeto apaixonado de <1>Amruth Pillai</1>",
|
||||
"license": "Pela comunidade, para a comunidade."
|
||||
},
|
||||
"markdown": {
|
||||
"help-text": "Esta seção suporta formatação <1>markdown</1>."
|
||||
},
|
||||
"date": {
|
||||
"present": "Presente"
|
||||
},
|
||||
"subtitle": "Gerador de currículos gratuito e de código aberto.",
|
||||
"title": "Reactive Resume",
|
||||
"toast": {
|
||||
"error": {
|
||||
"upload-file-size": "Carregue apenas arquivos com menos de 2 megabytes.",
|
||||
"upload-photo-size": "Carregue apenas fotos com menos de 2 megabytes, preferencialmente quadradas."
|
||||
},
|
||||
"success": {
|
||||
"resume-link-copied": "Um link para o seu currículo foi copiado para a área de transferência."
|
||||
}
|
||||
}
|
||||
}
|
||||
25
client/public/locales/pt-BR/dashboard.json
Normal file
25
client/public/locales/pt-BR/dashboard.json
Normal file
@ -0,0 +1,25 @@
|
||||
{
|
||||
"create-resume": {
|
||||
"subtitle": "Começar do zero",
|
||||
"title": "Criar Novo Currículo"
|
||||
},
|
||||
"import-external": {
|
||||
"subtitle": "LinkedIn, currículo em JSON, Reactive Resume",
|
||||
"title": "Importar de fontes externas"
|
||||
},
|
||||
"resume": {
|
||||
"menu": {
|
||||
"delete": "Deletar",
|
||||
"duplicate": "Duplicar",
|
||||
"open": "Abrir",
|
||||
"rename": "Renomear",
|
||||
"share-link": "Compartilhar Link",
|
||||
"tooltips": {
|
||||
"delete": "Tem certeza de que deseja excluir este currículo? Esta ação é irreversível.",
|
||||
"share-link": "Você precisa alterar a visibilidade do seu currículo para público para torná-lo visível para outras pessoas."
|
||||
}
|
||||
},
|
||||
"timestamp": "Última atualização há {{timestamp}}"
|
||||
},
|
||||
"title": "Painel de Controle"
|
||||
}
|
||||
42
client/public/locales/pt-BR/landing.json
Normal file
42
client/public/locales/pt-BR/landing.json
Normal file
@ -0,0 +1,42 @@
|
||||
{
|
||||
"actions": {
|
||||
"app": "Ir para aplicativo",
|
||||
"login": "Entrar",
|
||||
"logout": "Sair",
|
||||
"register": "Registrar"
|
||||
},
|
||||
"features": {
|
||||
"heading": "Características",
|
||||
"list": {
|
||||
"ads": "Sem publicidade",
|
||||
"export": "Exporte seu currículo para o formato JSON ou PDF",
|
||||
"free": "Gratuito, para sempre",
|
||||
"import": "Importe dados do LinkedIn, ou de um currículo em JSON",
|
||||
"languages": "Disponível em vários idiomas",
|
||||
"more": "E outros recursos interessantes, <1>veja todos aqui</1>",
|
||||
"tracking": "Sem rastreamento de usuários"
|
||||
}
|
||||
},
|
||||
"links": {
|
||||
"heading": "Links",
|
||||
"links": {
|
||||
"donate": "Fazer doação",
|
||||
"github": "Código Fonte",
|
||||
"docs": "Documentação",
|
||||
"privacy": "Política de privacidade",
|
||||
"service": "Termos de serviço"
|
||||
}
|
||||
},
|
||||
"screenshots": {
|
||||
"heading": "Imagens"
|
||||
},
|
||||
"testimonials": {
|
||||
"heading": "Depoimentos",
|
||||
"body": "Considero importante a sua opinião, positiva ou negativa, a respeito do Reactive Resume, bem como a sua experiência ao usá-lo.<br/>Confira algumas das mensagens enviadas por pessoas de todo o mundo.",
|
||||
"contact": "Envie a sua mensagem por <1>e-mail</1> ou pelo formulário disponível <3>aqui</3>."
|
||||
},
|
||||
"summary": {
|
||||
"body": "O Reactive Resume é um gerador de currículos, gratuito e de código aberto, desenvolvido para facilitar as tarefas tediosas de criação, atualização e divulgação de seu currículo. Este aplicativo possibilita a criação de múltiplos currículos, que podem ser compartilhados com recrutadores ou amigos com um link exclusivo ou impressos como PDF. Tudo isso de graça, sem anúncios, sem rastreamento, mantendo a integridade e privacidade dos seus dados.",
|
||||
"heading": "Resumo"
|
||||
}
|
||||
}
|
||||
135
client/public/locales/pt-BR/modals.json
Normal file
135
client/public/locales/pt-BR/modals.json
Normal file
@ -0,0 +1,135 @@
|
||||
{
|
||||
"auth": {
|
||||
"forgot-password": {
|
||||
"actions": {
|
||||
"send-email": "Enviar e-mail de redefinição de senha"
|
||||
},
|
||||
"body": "Basta inserir o endereço de e-mail associado à conta que você gostaria de recuperar.",
|
||||
"form": {
|
||||
"email": {
|
||||
"label": "Endereço de e-mail"
|
||||
}
|
||||
},
|
||||
"heading": "Esqueceu sua senha?",
|
||||
"help-text": "Se a conta existir, você receberá um e-mail com um link para redefinir sua senha."
|
||||
},
|
||||
"login": {
|
||||
"actions": {
|
||||
"login": "Entrar"
|
||||
},
|
||||
"body": "Por favor, digite seu nome de usuário e senha associados à sua conta para fazer login e acessar, gerenciar e compartilhar seus currículos.",
|
||||
"form": {
|
||||
"password": {
|
||||
"label": "Senha"
|
||||
},
|
||||
"username": {
|
||||
"help-text": "Você também pode inserir seu endereço de e-mail",
|
||||
"label": "Nome de Usuário"
|
||||
}
|
||||
},
|
||||
"heading": "Acesse a sua conta",
|
||||
"recover-text": "Caso tenha esquecido sua senha, você pode <1>recuperar sua conta</1> aqui.",
|
||||
"register-text": "Se não tiver, você pode <1>criar uma conta</1> aqui."
|
||||
},
|
||||
"register": {
|
||||
"actions": {
|
||||
"register": "Registre-se",
|
||||
"google": "Registre-se com o Google"
|
||||
},
|
||||
"body": "Por favor, insira suas informações pessoais para criar uma conta.",
|
||||
"form": {
|
||||
"confirm-password": {
|
||||
"label": "Confirme a senha"
|
||||
},
|
||||
"email": {
|
||||
"label": "Endereço de e-mail"
|
||||
},
|
||||
"name": {
|
||||
"label": "Nome completo"
|
||||
},
|
||||
"password": {
|
||||
"label": "Senha"
|
||||
},
|
||||
"username": {
|
||||
"label": "Nome de usuário"
|
||||
}
|
||||
},
|
||||
"heading": "Criar uma conta",
|
||||
"loginText": "Se já tem uma conta, você pode <1>entrar aqui</1>."
|
||||
},
|
||||
"reset-password": {
|
||||
"actions": {
|
||||
"set-password": "Definir nova senha"
|
||||
},
|
||||
"body": "Digite uma nova senha para sua conta.",
|
||||
"form": {
|
||||
"confirm-password": {
|
||||
"label": "Confirme a senha"
|
||||
},
|
||||
"password": {
|
||||
"label": "Senha"
|
||||
}
|
||||
},
|
||||
"heading": "Redefinir sua senha"
|
||||
}
|
||||
},
|
||||
"dashboard": {
|
||||
"create-resume": {
|
||||
"actions": {
|
||||
"create-resume": "Criar Currículo"
|
||||
},
|
||||
"body": "Comece a construir seu currículo dando-lhe um nome. Pode ser em referência ao cargo para o qual você está se candidatando ou apenas ao seu lanche favorito.",
|
||||
"form": {
|
||||
"name": {
|
||||
"label": "Nome"
|
||||
},
|
||||
"public": {
|
||||
"label": "É publicamente acessível?"
|
||||
},
|
||||
"slug": {
|
||||
"label": "Endereço amigável"
|
||||
}
|
||||
},
|
||||
"heading": "Criar um novo currículo"
|
||||
},
|
||||
"import-external": {
|
||||
"heading": "Importar de fontes externas",
|
||||
"json-resume": {
|
||||
"actions": {
|
||||
"upload-json": "Carregar JSON"
|
||||
},
|
||||
"body": "Se você possui um <1>currículo JSON válido</1>, poderá usá-lo para acelerar seu desenvolvimento no Reactive Resume. Clique no botão abaixo e carregue um arquivo JSON válido para começar.",
|
||||
"heading": "Importar de um currículo JSON"
|
||||
},
|
||||
"linkedin": {
|
||||
"actions": {
|
||||
"upload-archive": "Carregar arquivo ZIP"
|
||||
},
|
||||
"body": "Você pode economizar tempo exportando seus dados do LinkedIn e usando-os para preencher automaticamente os campos no Reactive Resume. Vá para a seção <1>Privacidade dos Dados</1> no LinkedIn e solicite um arquivo com seus dados. Assim que estiver disponível, faça upload do arquivo ZIP abaixo.",
|
||||
"heading": "Importar do LinkedIn"
|
||||
},
|
||||
"reactive-resume": {
|
||||
"actions": {
|
||||
"upload-json": "Carregar JSON",
|
||||
"upload-json-v2": "Carregar JSON do v2"
|
||||
},
|
||||
"body": "Se você possuir um JSON que foi exportado com a versão atual do Reactive Resume, poderá importá-lo de volta aqui para obter uma versão editável novamente.",
|
||||
"heading": "Importe do Reactive Resume"
|
||||
}
|
||||
},
|
||||
"rename-resume": {
|
||||
"actions": {
|
||||
"rename-resume": "Renomear currículo"
|
||||
},
|
||||
"form": {
|
||||
"name": {
|
||||
"label": "Nome"
|
||||
},
|
||||
"slug": {
|
||||
"label": "Endereço amigável"
|
||||
}
|
||||
},
|
||||
"heading": "Renomear o seu currículo"
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -3,6 +3,7 @@
|
||||
"actions": {
|
||||
"add": "Adicionar {{token}}",
|
||||
"delete": "Remover {{token}}",
|
||||
"duplicate": "Seção Duplicada",
|
||||
"edit": "Editar {{token}}"
|
||||
},
|
||||
"columns": {
|
||||
@ -80,13 +81,13 @@
|
||||
"center-artboard": "Prancheta central",
|
||||
"copy-link": "Copiar link do currículo",
|
||||
"export-pdf": "Exportar PDF",
|
||||
"redo": "Redo",
|
||||
"toggle-orientation": "Alternar orientação da página",
|
||||
"toggle-page-break-line": "Alternar linha de quebra de página",
|
||||
"toggle-sidebars": "Alternar barra lateral",
|
||||
"zoom-in": "Mais Zoom",
|
||||
"zoom-out": "Menos Zoom",
|
||||
"undo": "Desfazer",
|
||||
"redo": "Redo"
|
||||
"zoom-in": "Mais Zoom",
|
||||
"zoom-out": "Menos Zoom"
|
||||
}
|
||||
},
|
||||
"header": {
|
||||
@ -114,6 +115,9 @@
|
||||
"actions": {
|
||||
"photo-filters": "Filtros da foto"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Data de nascimento"
|
||||
},
|
||||
"heading": "Informações básicas",
|
||||
"headline": {
|
||||
"label": "Título"
|
||||
@ -121,9 +125,6 @@
|
||||
"name": {
|
||||
"label": "Nome Completo"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Data de nascimento"
|
||||
},
|
||||
"photo-filters": {
|
||||
"effects": {
|
||||
"border": {
|
||||
@ -264,14 +265,15 @@
|
||||
"button": "GitHub Issues",
|
||||
"heading": "Bugs? Sugestões de recursos?"
|
||||
},
|
||||
"docs": "Documentação",
|
||||
"donate": {
|
||||
"body": "Se você gostou de usar o Reactive Resume, considere doar o máximo possível para manter o aplicativo em funcionamento, sem anúncios e gratuito para sempre.",
|
||||
"button": "Pague-me um café",
|
||||
"heading": "Faça uma doação ao Reactive Resume"
|
||||
},
|
||||
"github": "Código Fonte",
|
||||
"docs": "Documentação",
|
||||
"heading": "Links"
|
||||
"heading": "Links",
|
||||
"reddit": "Reddit"
|
||||
},
|
||||
"settings": {
|
||||
"global": {
|
||||
@ -290,14 +292,14 @@
|
||||
},
|
||||
"heading": "Configurações",
|
||||
"page": {
|
||||
"format": {
|
||||
"primary": "Tamanho do papel",
|
||||
"secondary": "Determina as dimensões das suas páginas de currículo"
|
||||
},
|
||||
"break-line": {
|
||||
"primary": "Linha de quebra",
|
||||
"secondary": "Mostrar uma linha em todas as páginas para marcar a altura de uma página A4"
|
||||
},
|
||||
"format": {
|
||||
"primary": "Tamanho do papel",
|
||||
"secondary": "Determina as dimensões das suas páginas de currículo"
|
||||
},
|
||||
"heading": "Página",
|
||||
"orientation": {
|
||||
"disabled": "Não tem efeito quando há somente uma página",
|
||||
|
||||
@ -20,23 +20,24 @@
|
||||
"links": {
|
||||
"heading": "Links",
|
||||
"links": {
|
||||
"docs": "Documentação",
|
||||
"donate": "Fazer doação",
|
||||
"github": "Código Fonte",
|
||||
"docs": "Documentação",
|
||||
"privacy": "Política de privacidade",
|
||||
"reddit": "Reddit",
|
||||
"service": "Termos de serviço"
|
||||
}
|
||||
},
|
||||
"screenshots": {
|
||||
"heading": "Imagens"
|
||||
},
|
||||
"testimonials": {
|
||||
"heading": "Depoimentos",
|
||||
"body": "Considero importante a sua opinião, positiva ou negativa, a respeito do Reactive Resume, bem como a sua experiência ao usá-lo.<br/>Confira algumas das mensagens enviadas por pessoas de todo o mundo.",
|
||||
"contact": "Envie a sua mensagem por <1>e-mail</1> ou pelo formulário disponível <3>aqui</3>."
|
||||
},
|
||||
"summary": {
|
||||
"body": "O Reactive Resume é um gerador de currículos, gratuito e de código aberto, desenvolvido para facilitar as tarefas tediosas de criação, atualização e divulgação de seu currículo. Este aplicativo possibilita a criação de múltiplos currículos, que podem ser compartilhados com recrutadores ou amigos com um link exclusivo ou impressos como PDF. Tudo isso de graça, sem anúncios, sem rastreamento, mantendo a integridade e privacidade dos seus dados.",
|
||||
"heading": "Resumo"
|
||||
},
|
||||
"testimonials": {
|
||||
"body": "Considero importante a sua opinião, positiva ou negativa, a respeito do Reactive Resume, bem como a sua experiência ao usá-lo.<br/>Confira algumas das mensagens enviadas por pessoas de todo o mundo.",
|
||||
"contact": "Envie a sua mensagem por <1>e-mail</1> ou pelo formulário disponível <3>aqui</3>.",
|
||||
"heading": "Depoimentos"
|
||||
}
|
||||
}
|
||||
|
||||
@ -71,6 +71,31 @@
|
||||
}
|
||||
},
|
||||
"heading": "Redefinir sua senha"
|
||||
},
|
||||
"profile": {
|
||||
"heading": "Sua conta",
|
||||
"form": {
|
||||
"avatar": {
|
||||
"help-text": "Você pode atualizar a sua foto de perfil no <1>Gravatar</1>"
|
||||
},
|
||||
"name": {
|
||||
"label": "Nome Completo"
|
||||
},
|
||||
"email": {
|
||||
"label": "Endereço de e-mail",
|
||||
"help-text": "Não é possível atualizar o seu endereço de e-mail no momento, por favor crie uma nova conta."
|
||||
}
|
||||
},
|
||||
"delete-account": {
|
||||
"heading": "Excluir Conta e Dados",
|
||||
"body": "Para excluir a sua conta, seus dados e todos os seus currículos, digite \"{{keyword}}\" na caixa de texto e clique no botão. Observe que esta é uma ação irreversível e os seus dados não podem ser recuperados novamente.",
|
||||
"actions": {
|
||||
"delete": "Deletar Conta"
|
||||
}
|
||||
},
|
||||
"actions": {
|
||||
"save": "Salvar Alterações"
|
||||
}
|
||||
}
|
||||
},
|
||||
"dashboard": {
|
||||
|
||||
@ -3,6 +3,7 @@
|
||||
"actions": {
|
||||
"add": "Adăugați un nou {{token}}",
|
||||
"delete": "Ștergeți {{token}}",
|
||||
"duplicate": "Secțiune duplicat",
|
||||
"edit": "Editați {{token}}"
|
||||
},
|
||||
"columns": {
|
||||
@ -80,13 +81,13 @@
|
||||
"center-artboard": "Centrul Artboard",
|
||||
"copy-link": "Copiați link-ul în CV",
|
||||
"export-pdf": "Export PDF",
|
||||
"redo": "Refaceți",
|
||||
"toggle-orientation": "Schimbă orientarea paginii",
|
||||
"toggle-page-break-line": "Alternează linia de întrerupere a paginii",
|
||||
"toggle-sidebars": "Comutați bare laterale",
|
||||
"zoom-in": "Zoom In",
|
||||
"zoom-out": "Zoom Out",
|
||||
"undo": "Desfaceți",
|
||||
"redo": "Refaceți"
|
||||
"zoom-in": "Zoom In",
|
||||
"zoom-out": "Zoom Out"
|
||||
}
|
||||
},
|
||||
"header": {
|
||||
@ -114,6 +115,9 @@
|
||||
"actions": {
|
||||
"photo-filters": "Filtre foto"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Data nașterii"
|
||||
},
|
||||
"heading": "Noțiuni de bază",
|
||||
"headline": {
|
||||
"label": "Titlul"
|
||||
@ -121,9 +125,6 @@
|
||||
"name": {
|
||||
"label": "Nume și prenume"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Data nașterii"
|
||||
},
|
||||
"photo-filters": {
|
||||
"effects": {
|
||||
"border": {
|
||||
@ -264,14 +265,15 @@
|
||||
"button": "Probleme GitHub",
|
||||
"heading": "Gândaci? Solicitări de caracteristici?"
|
||||
},
|
||||
"docs": "Documentație",
|
||||
"donate": {
|
||||
"body": "Dacă ți-a plăcut să folosești Reactive Resume, te rugăm să te gândești să donezi cât de mult poți pentru a menține aplicația în funcțiune, fără reclame și gratuită pentru totdeauna.",
|
||||
"button": "Cumpără-mi o cafea.",
|
||||
"heading": "Donează pentru Reactive Resume"
|
||||
},
|
||||
"github": "Codul sursă",
|
||||
"docs": "Documentație",
|
||||
"heading": "Legături"
|
||||
"heading": "Legături",
|
||||
"reddit": "Reddit"
|
||||
},
|
||||
"settings": {
|
||||
"global": {
|
||||
@ -290,14 +292,14 @@
|
||||
},
|
||||
"heading": "Setări",
|
||||
"page": {
|
||||
"format": {
|
||||
"primary": "Dimensiunea hartiei",
|
||||
"secondary": "Determină dimensiunile paginilor de CV"
|
||||
},
|
||||
"break-line": {
|
||||
"primary": "Linia de pauză",
|
||||
"secondary": "Afișați o linie pe toate paginile pentru a marca înălțimea unei pagini A4"
|
||||
},
|
||||
"format": {
|
||||
"primary": "Dimensiunea hartiei",
|
||||
"secondary": "Determină dimensiunile paginilor de CV"
|
||||
},
|
||||
"heading": "Pagina",
|
||||
"orientation": {
|
||||
"disabled": "Nu are niciun efect atunci când există doar o singură pagină",
|
||||
|
||||
@ -20,23 +20,24 @@
|
||||
"links": {
|
||||
"heading": "Legături",
|
||||
"links": {
|
||||
"docs": "Documentație",
|
||||
"donate": "Donează",
|
||||
"github": "Codul sursă",
|
||||
"docs": "Documentație",
|
||||
"privacy": "Politica de confidențialitate",
|
||||
"reddit": "Reddit",
|
||||
"service": "Termeni și condiții de utilizare"
|
||||
}
|
||||
},
|
||||
"screenshots": {
|
||||
"heading": "Capturi de ecran"
|
||||
},
|
||||
"testimonials": {
|
||||
"heading": "Mărturii",
|
||||
"body": "Bună sau rea, mi-ar plăcea să aflu părerea ta despre Reactive Resume și cum a fost experiența pentru tine.<br/>Iată câteva dintre mesajele trimise de utilizatori din întreaga lume.",
|
||||
"contact": "Puteți să mă contactați prin <1>e-mail</1> sau prin formularul de contact de pe <3>site-ul meu</3>."
|
||||
},
|
||||
"summary": {
|
||||
"body": "Reactive Resume este un constructor de CV-uri gratuit și open source care a fost creat pentru a face ca sarcinile banale de creare, actualizare și partajare a CV-ului să fie la fel de simple ca 1, 2, 3. Cu această aplicație, puteți crea mai multe CV-uri, le puteți partaja cu recrutorii sau prietenii printr-un link unic și le puteți imprima în format PDF, totul gratuit, fără reclame, fără urmărire, fără a pierde integritatea și confidențialitatea datelor dvs.",
|
||||
"heading": "Rezumat"
|
||||
},
|
||||
"testimonials": {
|
||||
"body": "Bună sau rea, mi-ar plăcea să aflu părerea ta despre Reactive Resume și cum a fost experiența pentru tine.<br/>Iată câteva dintre mesajele trimise de utilizatori din întreaga lume.",
|
||||
"contact": "Puteți să mă contactați prin <1>e-mail</1> sau prin formularul de contact de pe <3>site-ul meu</3>.",
|
||||
"heading": "Mărturii"
|
||||
}
|
||||
}
|
||||
|
||||
@ -2,7 +2,7 @@
|
||||
"auth": {
|
||||
"forgot-password": {
|
||||
"actions": {
|
||||
"send-email": "Trimiteți e-mail de resetare a parolei"
|
||||
"send-email": "Trimite e-mail pentru resetarea parolei"
|
||||
},
|
||||
"body": "Introduceți doar adresa de e-mail asociată contului pe care doriți să îl recuperați.",
|
||||
"form": {
|
||||
@ -71,6 +71,31 @@
|
||||
}
|
||||
},
|
||||
"heading": "Resetați-vă parola"
|
||||
},
|
||||
"profile": {
|
||||
"heading": "Your account",
|
||||
"form": {
|
||||
"avatar": {
|
||||
"help-text": "Vă puteți actualiza imaginea de profil pe <1>Gravatar</1>"
|
||||
},
|
||||
"name": {
|
||||
"label": "Nume Complet"
|
||||
},
|
||||
"email": {
|
||||
"label": "Adresa de e-mail",
|
||||
"help-text": "Nu este posibil să vă actualizați adresa de e-mail în acest moment, vă rugăm să creați un cont nou."
|
||||
}
|
||||
},
|
||||
"delete-account": {
|
||||
"heading": "Șterge Datele Contului",
|
||||
"body": "Pentru a vă șterge contul, datele și toate CV-urile, tastați \"{{keyword}}\" în caseta de text și faceți clic pe buton. Vă rugăm să rețineți că aceasta este o acțiune ireversibilă și că datele dumneavoastră nu mai pot fi recuperate.",
|
||||
"actions": {
|
||||
"delete": "Ștergere cont"
|
||||
}
|
||||
},
|
||||
"actions": {
|
||||
"save": "Salvează modificările"
|
||||
}
|
||||
}
|
||||
},
|
||||
"dashboard": {
|
||||
|
||||
@ -3,6 +3,7 @@
|
||||
"actions": {
|
||||
"add": "Lägg till {{token}}",
|
||||
"delete": "Ta bort {{token}}",
|
||||
"duplicate": "Duplicera avsnitt",
|
||||
"edit": "Redigera {{token}}"
|
||||
},
|
||||
"columns": {
|
||||
@ -80,13 +81,13 @@
|
||||
"center-artboard": "Centrera Artboard",
|
||||
"copy-link": "Kopiera länken till CV:et",
|
||||
"export-pdf": "Exportera som PDF",
|
||||
"redo": "Gör om",
|
||||
"toggle-orientation": "Byt sidans orientering",
|
||||
"toggle-page-break-line": "Visa/dölj Sidbrytningslinjer",
|
||||
"toggle-sidebars": "Visa/dölj Sidpanelen",
|
||||
"zoom-in": "Zooma in",
|
||||
"zoom-out": "Zooma Ut",
|
||||
"undo": "Ångra",
|
||||
"redo": "Gör om"
|
||||
"zoom-in": "Zooma in",
|
||||
"zoom-out": "Zooma Ut"
|
||||
}
|
||||
},
|
||||
"header": {
|
||||
@ -114,6 +115,9 @@
|
||||
"actions": {
|
||||
"photo-filters": "Fotofilter"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Födelsedatum"
|
||||
},
|
||||
"heading": "Grunder",
|
||||
"headline": {
|
||||
"label": "Rubrik"
|
||||
@ -121,9 +125,6 @@
|
||||
"name": {
|
||||
"label": "Fullständigt namn"
|
||||
},
|
||||
"birthdate": {
|
||||
"label": "Födelsedatum"
|
||||
},
|
||||
"photo-filters": {
|
||||
"effects": {
|
||||
"border": {
|
||||
@ -264,14 +265,15 @@
|
||||
"button": "GitHub Issues",
|
||||
"heading": "Buggar? Funktionsförslag?"
|
||||
},
|
||||
"docs": "Dokumentation",
|
||||
"donate": {
|
||||
"body": "Om du gillade att använda Reactive Resume, överväg att donera så mycket som möjligt för att hålla appen igång utan annonser och gratis för alltid.",
|
||||
"button": "Köp mig en kaffe",
|
||||
"heading": "Donera till Reactive Resume"
|
||||
},
|
||||
"github": "Källkod",
|
||||
"docs": "Dokumentation",
|
||||
"heading": "Länkar"
|
||||
"heading": "Länkar",
|
||||
"reddit": "Reddit"
|
||||
},
|
||||
"settings": {
|
||||
"global": {
|
||||
@ -290,14 +292,14 @@
|
||||
},
|
||||
"heading": "Inställningar",
|
||||
"page": {
|
||||
"format": {
|
||||
"primary": "Pappersformat",
|
||||
"secondary": "Bestämmer måtten på dina CV-sidor"
|
||||
},
|
||||
"break-line": {
|
||||
"primary": "Radbrytning",
|
||||
"secondary": "Visa en linje på alla sidor för att markera höjden på en A4-sida"
|
||||
},
|
||||
"format": {
|
||||
"primary": "Pappersformat",
|
||||
"secondary": "Bestämmer måtten på dina CV-sidor"
|
||||
},
|
||||
"heading": "Sida",
|
||||
"orientation": {
|
||||
"disabled": "Har ingen effekt när det bara finns en sida",
|
||||
|
||||
@ -20,23 +20,24 @@
|
||||
"links": {
|
||||
"heading": "Länkar",
|
||||
"links": {
|
||||
"docs": "Dokumentation",
|
||||
"donate": "Donera",
|
||||
"github": "Källkod",
|
||||
"docs": "Dokumentation",
|
||||
"privacy": "Sekretesspolicy",
|
||||
"reddit": "Reddit",
|
||||
"service": "Användarvillkor"
|
||||
}
|
||||
},
|
||||
"screenshots": {
|
||||
"heading": "Skärmdumpar"
|
||||
},
|
||||
"testimonials": {
|
||||
"heading": "Rekommendationer",
|
||||
"body": "Bra eller dåligt, jag skulle älska att höra din åsikt om Reactive Resume och hur upplevelsen har varit för dig.<br/>Här är några av de meddelanden som skickas in av användare över hela världen.",
|
||||
"contact": "Du kan nå mig via <1>min e-post</1> eller genom kontaktformuläret på <3>min hemsida</3> ."
|
||||
},
|
||||
"summary": {
|
||||
"body": "Reactive Resume är en gratis och öppen källkodsbyggare för CV som är gjord för att göra de vardagliga uppgifterna som att skapa, uppdatera och dela ditt CV så enkelt som 1, 2, 3. Med den här appen kan du skapa flera CV, dela dem med rekryterare eller vänner genom en unik länk och skriva ut den som en PDF, helt gratis, inga annonser, ingen spårning och utan att förlora integriteten för dina data.",
|
||||
"heading": "Sammanfattning"
|
||||
},
|
||||
"testimonials": {
|
||||
"body": "Bra eller dåligt, jag skulle älska att höra din åsikt om Reactive Resume och hur upplevelsen har varit för dig.<br/>Här är några av de meddelanden som skickas in av användare över hela världen.",
|
||||
"contact": "Du kan nå mig via <1>min e-post</1> eller genom kontaktformuläret på <3>min hemsida</3> .",
|
||||
"heading": "Rekommendationer"
|
||||
}
|
||||
}
|
||||
|
||||
@ -71,6 +71,31 @@
|
||||
}
|
||||
},
|
||||
"heading": "Återställ ditt lösenord"
|
||||
},
|
||||
"profile": {
|
||||
"heading": "Ditt konto",
|
||||
"form": {
|
||||
"avatar": {
|
||||
"help-text": "Du kan ändra din profilbild på <1>Gravatar</1>"
|
||||
},
|
||||
"name": {
|
||||
"label": "Fullständigt namn"
|
||||
},
|
||||
"email": {
|
||||
"label": "E-postadress",
|
||||
"help-text": "Det är inte möjligt att uppdatera din e-postadress för tillfället, skapa ett nytt konto istället."
|
||||
}
|
||||
},
|
||||
"delete-account": {
|
||||
"heading": "Ta bort konto och data",
|
||||
"body": "För att radera ditt konto, din data och alla dina CV, skriv \"{{keyword}}\" i textrutan och klicka på knappen. Observera att detta är en oåterkallelig åtgärd och din data kan inte hämtas igen.",
|
||||
"actions": {
|
||||
"delete": "Radera konto"
|
||||
}
|
||||
},
|
||||
"actions": {
|
||||
"save": "Spara ändringar"
|
||||
}
|
||||
}
|
||||
},
|
||||
"dashboard": {
|
||||
|
||||
@ -1,15 +0,0 @@
|
||||
import env from '@beam-australia/react-env';
|
||||
import * as Sentry from '@sentry/nextjs';
|
||||
|
||||
import packageJSON from '../package.json';
|
||||
|
||||
const SENTRY_DSN = env('CLIENT_SENTRY_DSN');
|
||||
|
||||
if (SENTRY_DSN) {
|
||||
Sentry.init({
|
||||
dsn: SENTRY_DSN,
|
||||
tracesSampleRate: 1.0,
|
||||
release: packageJSON.version,
|
||||
enabled: process.env.NODE_ENV === 'production',
|
||||
});
|
||||
}
|
||||
@ -1,3 +0,0 @@
|
||||
defaults.url=https://sentry.io/
|
||||
defaults.org=reactive-resume
|
||||
defaults.project=client
|
||||
@ -1,15 +0,0 @@
|
||||
import env from '@beam-australia/react-env';
|
||||
import * as Sentry from '@sentry/nextjs';
|
||||
|
||||
import packageJSON from '../package.json';
|
||||
|
||||
const SENTRY_DSN = env('CLIENT_SENTRY_DSN');
|
||||
|
||||
if (SENTRY_DSN) {
|
||||
Sentry.init({
|
||||
dsn: SENTRY_DSN,
|
||||
tracesSampleRate: 1.0,
|
||||
release: packageJSON.version,
|
||||
enabled: process.env.NODE_ENV === 'production',
|
||||
});
|
||||
}
|
||||
@ -2,7 +2,7 @@ import { User } from '@reactive-resume/schema';
|
||||
import { AxiosResponse } from 'axios';
|
||||
import toast from 'react-hot-toast';
|
||||
|
||||
import { setAccessToken, setUser } from '@/store/auth/authSlice';
|
||||
import { logout, setAccessToken, setUser } from '@/store/auth/authSlice';
|
||||
|
||||
import store from '../store';
|
||||
import axios from './axios';
|
||||
@ -37,6 +37,10 @@ export type ResetPasswordParams = {
|
||||
password: string;
|
||||
};
|
||||
|
||||
export type UpdateProfileParams = {
|
||||
name: string;
|
||||
};
|
||||
|
||||
export const login = async (loginParams: LoginParams) => {
|
||||
const {
|
||||
data: { user, accessToken },
|
||||
@ -75,3 +79,23 @@ export const resetPassword = async (resetPasswordParams: ResetPasswordParams) =>
|
||||
|
||||
toast.success('Your password has been changed successfully, please login again.');
|
||||
};
|
||||
|
||||
export const updateProfile = async (updateProfileParams: UpdateProfileParams) => {
|
||||
const { data: user } = await axios.patch<User, AxiosResponse<User>, UpdateProfileParams>(
|
||||
'/auth/update-profile',
|
||||
updateProfileParams
|
||||
);
|
||||
|
||||
store.dispatch(setUser(user));
|
||||
|
||||
toast.success('Your profile has been successfully updated.');
|
||||
};
|
||||
|
||||
export const deleteAccount = async () => {
|
||||
await axios.delete('/resume/all');
|
||||
await axios.delete('/auth');
|
||||
|
||||
store.dispatch(logout());
|
||||
|
||||
toast.success('Your account has been deleted, hope to see you again soon.');
|
||||
};
|
||||
|
||||
@ -1,6 +1,7 @@
|
||||
import env from '@beam-australia/react-env';
|
||||
import _axios from 'axios';
|
||||
import _axios, { AxiosError } from 'axios';
|
||||
import Router from 'next/router';
|
||||
import { toast } from 'react-hot-toast';
|
||||
|
||||
import { logout } from '@/store/auth/authSlice';
|
||||
|
||||
@ -19,22 +20,22 @@ const axios = _axios.create({ baseURL });
|
||||
axios.interceptors.request.use((config) => {
|
||||
const { accessToken } = store.getState().auth;
|
||||
|
||||
config.headers = {
|
||||
...config.headers,
|
||||
Authorization: `Bearer ${accessToken}`,
|
||||
};
|
||||
config.headers.set('Authorization', `Bearer ${accessToken}`);
|
||||
|
||||
return config;
|
||||
});
|
||||
|
||||
axios.interceptors.response.use(
|
||||
(response) => response,
|
||||
(error) => {
|
||||
(error: AxiosError<ServerError>) => {
|
||||
const { response } = error;
|
||||
|
||||
if (response) {
|
||||
const errorObject: ServerError = response.data;
|
||||
const errorObject = response.data;
|
||||
const code = errorObject.statusCode;
|
||||
const message = errorObject.message;
|
||||
|
||||
toast.error(message);
|
||||
|
||||
if (code === 401 || code === 404) {
|
||||
store.dispatch(logout());
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user