Skip to content

Commit

Permalink
perf: trans onefile
Browse files Browse the repository at this point in the history
  • Loading branch information
521xueweihan committed Aug 2, 2024
1 parent 3b77f91 commit ebd23b3
Show file tree
Hide file tree
Showing 10 changed files with 206 additions and 94 deletions.
File renamed without changes.
44 changes: 44 additions & 0 deletions data/onefile_en.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
## I. Introduction

Are you already overwhelmed by the monotonous CRUD business code, and tired of the endless process of installing dependencies and deploying environments just to create a webpage, followed by the never-ending updates of dependency versions?

The OneFile programming challenge with a single file is here to awaken your interest and pleasure in coding!

Write the code you want, with the simplest code in **just one file**, and find back the original joy of programming.

## II. Requirements

When you step away from modern frameworks and libraries, the opportunity to showcase your talent comes! If you have an idea, you should write it down quickly. It may not need to be very complex; perhaps one file is enough.

The **one-file** programming challenge has the following requirements:

- A single file, not compressed, with a size smaller than 1 MB
- Clear code structure, including comments, and fewer than 5000 lines of code
- Any programming language is allowed, but cannot only contain Markdown files
- No external files are introduced (images, videos, CSS, etc.)
- The project function is complete and has learning or usage value
- (Optional) Up to one open-source library or framework may be depended on

The collected works will be promoted through HelloGitHub's accounts across the entire network (more than 200,000 fans), allowing your project to help more people and be loved by more people.

In addition to submitting your own works, you can also share projects collected from the internet, but the author and source of the code must be indicated.

## III. Submission Methods

**First Method**: Submit through the form: [Click Here](https://hellogithub.yuque.com/forms/share/4f0bf06b-2991-4f7e-a860-5b76337b7b5b)

**Second Method**: Submit through GitHub Pull Request steps:

1. Fork this project
2. Categorize the work according to the language and put it in the `src/appropriate directory`
3. Submit PR
4. Fill in the relevant information in the PR description area
5. You will receive a reply on whether to include it within three days

Tips: [Click Here](https://docs.github.com/cn/pull-requests/collaborating-with-pull-requests/proposing-changes-to-your-work-with-pull-requests/creating-a-pull-request-from-a-fork) to view the PR method

## IV. Final Thoughts

Every project starts with a single file and becomes what you see today through continuous iteration. The one file you submit today is a seed.

> The best time to plant a tree is twenty years ago. The second-best time is now.
4 changes: 2 additions & 2 deletions public/locales/en/common.json
Original file line number Diff line number Diff line change
Expand Up @@ -27,12 +27,12 @@
"login": "Sign In"
},
"advert": {
"desc": "Server expires by",
"desc": "expire in",
"desc2": "Buy me a coffee",
"next": "Need to gold",
"next2": "Next target by",
"day": "D",
"year": ""
"year": "Y"
},
"site_stats": {
"user": "#Users",
Expand Down
26 changes: 26 additions & 0 deletions public/locales/en/onefile.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
{
"title": "Single-File Open Source Projects",
"description": "A collection of single-file, copy-to-run open source projects",
"click": "Click",
"p_text": "OneFile gathers open source projects that are single-file, easy to run, and straightforward to understand. Including games, compilers, servers, tools, utility libraries, and other interesting open source projects that you can <strong>run just by copying the code</strong>. Click to view the source code and try it online.",
"p_text2": "<strong>OneFile</strong> is an open source project where you can find interesting and easy-to-run programs. It's also a programming challenge where you can submit a single file to take on the challenge.",
"p_text3": "Join the OneFile programming challenge and write some interesting code with just one file!",
"code": {
"copy_success": "Source code copied, paste it into a file to run",
"copy_fail": "Copy failed",
"title": "OneFile: {{name}} Source Code",
"nav": "Code",
"author": "Author: {{author}}",
"language": "Language: {{language}}",
"package": "Deps",
"nopackage": "No Deps",
"read": "{{num}} views",
"play": "Play",
"vite": "Visit",
"copy": "Copy"
},
"join": {
"title": "Join the OneFile Programming Challenge",
"nav": "Join"
}
}
26 changes: 26 additions & 0 deletions public/locales/zh/onefile.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
{
"title": "仅一个文件的开源项目",
"description": "仅一个文件、复制即可运行的开源项目集合",
"click": "点击",
"p_text": "OneFile 是汇集了仅一个文件、运行简单、一看就懂的开源项目。包括:游戏、编译器、服务器、工具、实用库等有趣的开源项目,而且<strong>复制代码就能跑</strong>,点击即可在线查看源码和试玩。",
"p_text2": "<strong>「OneFile」</strong>是一个开源项目,在这里你可以找到有趣运行简单的程序。同时它也是一个编程挑战,你也可以提交一个文件接受挑战。",
"p_text3": "加入 OneFile 编程挑战,一个文件而已就写点有趣的代码吧!",
"code": {
"copy_success": "源码已复制,粘贴到文件中即可运行",
"copy_fail": "复制失败",
"title": "OneFile: {{name}} 源码",
"nav": "源码",
"author": "作者 {{author}}",
"language": "主语言 {{language}}",
"package": "有依赖",
"nopackage": "无依赖",
"read": "{{num}} 次查看",
"play": "试玩",
"vite": "访问",
"copy": "复制"
},
"join": {
"title": "加入 OneFile 编程挑战",
"nav": "加入"
}
}
4 changes: 2 additions & 2 deletions src/components/buttons/LanguageSwitcher.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ const LanguageSwitcher = (props: LanguageSwitchProps) => {
};

if (props.type === 'text') {
const isChinese = locale == 'en' ? false : true;
const isChinese = locale == 'zh' ? true : false;
const buttonText = isChinese ? 'English' : '简体中文';
return (
<span onClick={() => changeLanguage(isChinese ? 'en' : 'zh')}>
Expand Down Expand Up @@ -74,7 +74,7 @@ const LanguageSwitcher = (props: LanguageSwitchProps) => {
aria-haspopup='true'
aria-expanded={isHovered ? 'true' : 'false'}
>
{selectedLocale === 'en' ? 'EN' : '中文'}
{selectedLocale === 'zh' ? '中文' : 'EN'}
</button>
</div>

Expand Down
13 changes: 8 additions & 5 deletions src/components/side/Ad.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import Link from 'next/link';
import { MouseEventHandler, useState } from 'react';
import { GoServer } from 'react-icons/go';
import { VscClose } from 'react-icons/vsc';

import { redirectRecord } from '@/services/home';
Expand All @@ -19,6 +20,7 @@ interface Props {
interface AdContentProps {
t: (key: string) => string;
data: AdvertItem;
i18n_lang?: string;
}

interface ImageAdContentProps {
Expand Down Expand Up @@ -71,11 +73,12 @@ export default function Ad({ data, className, t, i18n_lang }: Props) {
</div>
);

const AdServerInfo = ({ data, t }: AdContentProps) => (
const AdServerInfo = ({ data, t, i18n_lang }: AdContentProps) => (
<div className='mt-1.5 mb-1 text-xs text-gray-500'>
<span>
<span className=' inline-flex items-center'>
{i18n_lang != 'zh' && <GoServer size={11} className='mr-0.5' />}
{t('advert.desc')}
<strong className='mx-1'>{data.day}</strong>
<strong className='mx-0.5'>{data.day}</strong>
{t('advert.day')}
</span>
<div className='relative left-0.5 bottom-1 inline-flex w-fit'>
Expand All @@ -92,7 +95,7 @@ export default function Ad({ data, className, t, i18n_lang }: Props) {
<div className='group flex flex-row p-3'>
<img
className='h-[55px] w-[55px]'
src={i18n_lang == 'en' ? ImageURL : data.image_url}
src={i18n_lang != 'zh' ? ImageURL : data.image_url}
alt='ad'
/>
<div className='ml-3'>
Expand All @@ -101,7 +104,7 @@ export default function Ad({ data, className, t, i18n_lang }: Props) {
</div>
<div className='hidden lg:block'>
<div className='group-hover:hidden'>
<AdServerInfo data={data} t={t} />
<AdServerInfo data={data} t={t} i18n_lang={i18n_lang} />
</div>
<div className='hidden group-hover:block'>
<AdTargetInfo data={data} t={t} />
Expand Down
69 changes: 33 additions & 36 deletions src/pages/onefile/code/[oid].tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
import copy from 'copy-to-clipboard';
import { GetServerSideProps, NextPage } from 'next';
import Link from 'next/link';
import { useTranslation } from 'next-i18next';
import { serverSideTranslations } from 'next-i18next/serverSideTranslations';
import { GoClippy, GoLink, GoPlay } from 'react-icons/go';

import { CodeRender } from '@/components/mdRender/MDRender';
Expand All @@ -10,23 +12,24 @@ import Seo from '@/components/Seo';
import ToTop from '@/components/toTop/ToTop';

import { getOnefileContent } from '@/services/article';
import { numFormat } from '@/utils/util';
import { getClientIP, numFormat } from '@/utils/util';

import { OneFileProps, OneItem } from '@/types/article';

const OneFileDetailPage: NextPage<OneFileProps> = ({ onefile }) => {
const { t } = useTranslation('onefile');
const handleCopy = (onefile: OneItem) => {
const text = onefile.source_code;
if (copy(text)) {
message.success('源码已复制,粘贴到文件中即可运行!');
} else message.error('复制失败');
message.success(t('code.copy_success'));
} else message.error(t('code.copy_fail'));
};

return (
<>
<Seo title={`OneFile: ${onefile.name} 源码`} />
<Seo title={t('code.title', { name: onefile.name })} />
<div className='relative pb-6'>
<Navbar middleText='OneFile' endText='源码'></Navbar>
<Navbar middleText='OneFile' endText={t('code.nav')} />

<div className='my-2 bg-white p-5 dark:bg-gray-800 md:rounded-lg'>
<div className='text-normal mb-4 dark:bg-gray-800 dark:text-gray-300'>
Expand All @@ -39,30 +42,30 @@ const OneFileDetailPage: NextPage<OneFileProps> = ({ onefile }) => {
<div className='truncate pt-1 text-sm text-gray-400'></div>
<div className='flex items-center pt-2'>
<div className='flex shrink grow flex-wrap items-center overflow-x-hidden text-sm text-gray-400'>
<span>作者 {onefile.author}</span>
<span>{t('code.author', { author: onefile.author })}</span>
<span className='px-1'>·</span>
<span>主语言 {onefile.language}</span>
<span>
{t('code.language', { language: onefile.language })}
</span>
<span className='px-1'>·</span>
{onefile.package ? (
<span>有依赖</span>
) : (
<span>无依赖</span>
)}
<span>
{onefile.package ? t('code.package') : t('code.package')}
</span>
<span className='px-1'>·</span>
{numFormat(onefile.uv_count, 1, 1000)} 次查看
<div className='flex gap-1 pl-2 md:hidden'>
{onefile.demo_url ? (
{t('code.read', {
num: numFormat(onefile.uv_count, 1, 1000),
})}
<div className='flex gap-1 pl-2 md:hidden'>
{onefile.demo_url && (
<a
className='flex cursor-pointer items-center justify-center rounded-md border py-0.5 px-1 hover:border-blue-500 hover:text-current active:!text-gray-400 dark:border-gray-700 md:hover:text-blue-500'
href={onefile.demo_url}
target='_blank'
rel='noreferrer'
>
<GoPlay className='mr-1' size={14} />
试玩
{t('code.play')}
</a>
) : (
<></>
)}

<a
Expand All @@ -72,31 +75,29 @@ const OneFileDetailPage: NextPage<OneFileProps> = ({ onefile }) => {
rel='noreferrer'
>
<GoLink className='mr-1' size={14} />
访问
{t('code.vite')}
</a>
<span
className='flex cursor-pointer items-center justify-center rounded-md border py-0.5 px-1 hover:border-blue-500 hover:text-current active:!text-gray-400 dark:border-gray-700 md:hover:text-blue-500'
onClick={() => handleCopy(onefile)}
>
<GoClippy className='mr-1' size={14} />
复制
{t('code.copy')}
</span>
</div>
</div>
<div className='hidden gap-2 text-sm text-gray-400 md:flex'>
{onefile.demo_url ? (
{onefile.demo_url && (
<Link href={onefile.demo_url}>
<a
className='flex cursor-pointer items-center justify-center rounded-md border py-0.5 px-1 hover:border-blue-500 hover:text-current active:!text-gray-400 dark:border-gray-700 md:hover:text-blue-500'
target='_blank'
rel='noreferrer'
>
<GoPlay className='mr-1' size={14} />
试玩
{t('code.play')}
</a>
</Link>
) : (
<></>
)}
<Link href={onefile.repo_url}>
<a
Expand All @@ -105,15 +106,15 @@ const OneFileDetailPage: NextPage<OneFileProps> = ({ onefile }) => {
rel='noreferrer'
>
<GoLink className='mr-1' size={14} />
访问
{t('code.vite')}
</a>
</Link>
<span
className='flex cursor-pointer items-center justify-center rounded-md border py-0.5 px-1 hover:border-blue-500 hover:text-current active:!text-gray-400 dark:border-gray-700 md:hover:text-blue-500'
onClick={() => handleCopy(onefile)}
>
<GoClippy className='mr-1' size={14} />
复制
{t('code.copy')}
</span>
</div>
</div>
Expand All @@ -136,17 +137,9 @@ export default OneFileDetailPage;
export const getServerSideProps: GetServerSideProps = async ({
query,
req,
locale,
}) => {
let ip;
if (req.headers['x-forwarded-for']) {
ip = req.headers['x-forwarded-for'] as string;
ip = ip.split(',')[0] as string;
} else if (req.headers['x-real-ip']) {
ip = req.headers['x-real-ip'] as string;
} else {
ip = req.socket.remoteAddress as string;
}

const ip = getClientIP(req);
const oid = query['oid'] as string;
const data = await getOnefileContent(ip, oid);
if (!data.success) {
Expand All @@ -157,6 +150,10 @@ export const getServerSideProps: GetServerSideProps = async ({
return {
props: {
onefile: data.data,
...(await serverSideTranslations(locale as string, [
'common',
'onefile',
])),
},
};
}
Expand Down
Loading

0 comments on commit ebd23b3

Please sign in to comment.