Skip to content

Commit ad5a915

Browse files
committed
post
1 parent 08cac77 commit ad5a915

8 files changed

Lines changed: 262 additions & 36 deletions
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
---
2+
date: 2025-09-12
3+
category: [에세이]
4+
published: true
5+
---
6+
7+
'나의 능력이 AI를 제한한다'는 말이 요즘 많다.
8+
나는 그 반대라고 생각한다.
9+
10+
> AI가 내 능력을 제한한다.
11+
12+
예컨데, 무언가 하기 위해서 대부분은 AI에게 부탁하나,
13+
그것은 논란없게 가장 보편적이고도 원론적인 예기만하거나 이니면 극단적으로 편향적인 예기만한다.
14+
15+
예컨데, 무언가가 정답임을 확인을 받기 위해,
16+
그것에 의존하여 정답을 갈구한다.
17+
18+
왜 그들로부터 속박되는가?
19+
저항하라.
Lines changed: 113 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,113 @@
1+
---
2+
date: 2024-07-23
3+
category: [에세이]
4+
published: true
5+
---
6+
7+
> Tailwind CSS의 Utility-First는 프론트엔드 프로그래밍이 지향하는 가치와 맞는 것인가?
8+
9+
<img src="https://velog.velcdn.com/images/haneum/post/3429909d-9e4d-4160-ab4e-eac7f383e90e/image.png" width="300" />
10+
11+
위의 반응형 레이아웃을 만들기 위해서 Tailwind CSS는 이 정도의 코드를 요구한다.
12+
13+
```jsx
14+
<main class="py-6 px-4 sm:p-6 md:py-10 md:px-8">
15+
<div class="max-w-4xl mx-auto grid grid-cols-1 lg:max-w-5xl lg:gap-x-20 lg:grid-cols-2">
16+
<div class="relative p-3 col-start-1 row-start-1 flex flex-col-reverse rounded-lg bg-gradient-to-t from-black/75 via-black/0 sm:bg-none sm:row-start-2 sm:p-0 lg:row-start-1">
17+
<h1 class="mt-1 text-lg font-semibold text-white sm:text-slate-900 md:text-2xl dark:sm:text-white">Beach House in Collingwood</h1>
18+
<p class="text-sm leading-4 font-medium text-white sm:text-slate-500 dark:sm:text-slate-400">Entire house</p>
19+
</div>
20+
<div class="grid gap-4 col-start-1 col-end-3 row-start-1 sm:mb-6 sm:grid-cols-4 lg:gap-6 lg:col-start-2 lg:row-end-6 lg:row-span-6 lg:mb-0">
21+
<img src="/beach-house.jpg" alt="" class="w-full h-60 object-cover rounded-lg sm:h-52 sm:col-span-2 lg:col-span-full" loading="lazy">
22+
<img src="/beach-house-interior-1.jpg" alt="" class="hidden w-full h-52 object-cover rounded-lg sm:block sm:col-span-2 md:col-span-1 lg:row-start-2 lg:col-span-2 lg:h-32" loading="lazy">
23+
<img src="/beach-house-interior-2.jpg" alt="" class="hidden w-full h-52 object-cover rounded-lg md:block lg:row-start-2 lg:col-span-2 lg:h-32" loading="lazy">
24+
</div>
25+
<dl class="mt-4 text-xs font-medium flex items-center row-start-2 sm:mt-1 sm:row-start-3 md:mt-2.5 lg:row-start-2">
26+
<dt class="sr-only">Reviews</dt>
27+
<dd class="text-indigo-600 flex items-center dark:text-indigo-400">
28+
<svg width="24" height="24" fill="none" aria-hidden="true" class="mr-1 stroke-current dark:stroke-indigo-500">
29+
<path d="m12 5 2 5h5l-4 4 2.103 5L12 16l-5.103 3L9 14l-4-4h5l2-5Z" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" />
30+
</svg>
31+
<span>4.89 <span class="text-slate-400 font-normal">(128)</span></span>
32+
</dd>
33+
<dt class="sr-only">Location</dt>
34+
<dd class="flex items-center">
35+
<svg width="2" height="2" aria-hidden="true" fill="currentColor" class="mx-3 text-slate-300">
36+
<circle cx="1" cy="1" r="1" />
37+
</svg>
38+
<svg width="24" height="24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="mr-1 text-slate-400 dark:text-slate-500" aria-hidden="true">
39+
<path d="M18 11.034C18 14.897 12 19 12 19s-6-4.103-6-7.966C6 7.655 8.819 5 12 5s6 2.655 6 6.034Z" />
40+
<path d="M14 11a2 2 0 1 1-4 0 2 2 0 0 1 4 0Z" />
41+
</svg>
42+
Collingwood, Ontario
43+
</dd>
44+
</dl>
45+
<div class="mt-4 col-start-1 row-start-3 self-center sm:mt-0 sm:col-start-2 sm:row-start-2 sm:row-span-2 lg:mt-6 lg:col-start-1 lg:row-start-3 lg:row-end-4">
46+
<button type="button" class="bg-indigo-600 text-white text-sm leading-6 font-medium py-2 px-3 rounded-lg">Check availability</button>
47+
</div>
48+
<p class="mt-4 text-sm leading-6 col-start-1 sm:col-span-2 lg:mt-6 lg:row-start-4 lg:col-span-1 dark:text-slate-400">
49+
This sunny and spacious room is for those traveling light and looking for a comfy and cosy place to lay their head for a night or two. This beach house sits in a vibrant neighborhood littered with cafes, pubs, restaurants and supermarkets and is close to all the major attractions such as Edinburgh Castle and Arthur's Seat.
50+
</p>
51+
</div>
52+
</main>
53+
```
54+
55+
나는 여러분들에게 물어보고자 한다. 이것이 과연 정상적인 코드인가?
56+
도대체 이 코드를 보고 레이아웃이 머릿속으로 그려지기는 하는가?
57+
58+
내가 Tailwind CSS className에 익숙하지 않아서 그럴 수도 있을 것이다.
59+
그러나 당신이 과연 기존의 CSS 스타일링으로 넘어갈 수 있는가?
60+
className이 온통 약자로 되어있어서 결국 기존의 속성값이 무엇인지 까먹게 되지 않는가?
61+
나는 당신이 기존의 CSS 스타일링으로 넘어가는 데에 많은 시간을 소요할 것이라고 단연코 생각한다.
62+
63+
그리고 유의할 점은 Tailwind CSS는 CSS를 인라인상으로 표현하게 해주는 도구가 아니다.
64+
Tailwind CSS는 CSS 용 부트스트랩이다.
65+
다른 말로, Tailwind CSS는 제한된 CSS 스타일 셋이다.
66+
67+
당신이 Tailwind CSS에 지나치게 의존한다면, 깊은 의미로는 그만큼의 CSS 스타일링 실력이 없다는 것이다.
68+
69+
<img src="https://velog.velcdn.com/images/haneum/post/f995ad49-2c11-4759-94b6-3dd08f6cea21/image.png" width="300" />
70+
71+
위처럼 이미 모든 스타일은 Tailwind CSS 상에서 정해져 있다. 그리고 개발자는 이런 정의된 스타일을 차용하여 프론트엔드를 구성한다. 그리고 정의되지 않은 스타일은 따로 관리한다.
72+
73+
도대체 이것이 복제가 아니면 무엇인가?
74+
프론트엔드 개발자는 UI/UX를 개발하는 사람 아닌가?
75+
왜 이미 정의된 UI/UX의 경험을 복사/붙여넣기 하는 것인가?
76+
77+
---
78+
79+
더불어 Tailwind CSS의 최대 단점은 기존의 CSS 스타일링 방식을 모두 파괴했다는 것이다.
80+
당신이 처음 Tailwind CSS를 접하는 프론트엔드 개발자라면 도대체 이 코드를 해석할 수 있는가?
81+
82+
그리고 재사용성을 지원하지 않는다는 것이다.
83+
Tailwind CSS는 재사용을 하기 위해서는 멀티 커서를 사용하라고 한다.
84+
85+
![](https://velog.velcdn.com/images/haneum/post/5b9edc20-759e-4f71-9894-592cc30dae39/image.png)
86+
87+
아니면 루프를 사용하라고 한다.
88+
89+
![](https://velog.velcdn.com/images/haneum/post/16d21dd0-9346-42cc-8be8-0b199fd3f8b2/image.png)
90+
91+
아니면 @apply라는 기능을 활용하라고 한다.
92+
93+
```css
94+
@tailwind base;
95+
@tailwind components;
96+
@tailwind utilities;
97+
98+
@layer components {
99+
.btn-primary {
100+
@apply py-2 px-5 bg-violet-500 text-white font-semibold rounded-full shadow-md hover:bg-violet-700 focus:outline-none focus:ring focus:ring-violet-400 focus:ring-opacity-75;
101+
}
102+
}
103+
```
104+
105+
또한, Tailwind CSS로 구현하기 복잡한 스타일링이 너무 많다는 점이다.
106+
당신이 복잡한 스타일링을 구현하기 위해서는 배보다 배꼽이 더 큰 상황을 목도할 수 있다.
107+
108+
109+
---
110+
111+
결론적으로 당신이 Tailwind CSS에만 익숙해지게 되면 당신은 더욱더 창의적인 레이아웃을 구현할 수 없을 것이다. Tailwind CSS는 아주 빠른 기일 내에 프로젝트를 구현하는 데에만 아주 적합하므로, 유지 보수의 관점에서는 정말 끔찍하다.
112+
113+
나는 이것이 과연 프론트엔드가 지향하는 관점이 맞는가 묻고 싶다.
Lines changed: 84 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,84 @@
1+
---
2+
date: 2022-08-30
3+
category: [에세이]
4+
published: true
5+
---
6+
7+
> 저는 주로 Vanilla JavaScript로 Side project를 개발 중입니다.
8+
Vanilla JavaScript로 코딩하는 것이 어떤 방식으로 이루어지는 가에 대해 궁금하신 분들을 위해 이번 [gitits](https://github.com/chebread/gitits)를 개발하면서 알게 된 Vanilla JavaScript의 한계에 대해 알려드리고자 합니다.
9+
10+
## SPA(Single Page Application)을 구현하기 위해서는 꽤나 많은 코드가 필요하다
11+
저는 Vanilla JavaScript로 코딩을 하기 때문에 모든 상태 관리와 컴포넌트는 직접 구현하여 프로젝트에 사용해야 합니다. 필수로 구현을 필요로 하는 기능들은 이와 같습니다. (이 기능들은 React와 React 라이브러리에 내장되어 있는 함수와 기능이 유사하기에 함수명을 빌렸습니다)
12+
13+
- `render`
14+
- `useState`
15+
- `useEffect`
16+
- `router`
17+
- `useParams`
18+
19+
이러한 기존의 기능과 제가 구현할 기능은 기능적인 측면으로서는 같지만 저의 프로젝트의 따라서 각각의 기능들은 최적화가 필요합니다. 그러하여, 이런 식의 많은 기능을 구현할 때 많은 시간과 코드가 작성되게 됩니다. 이는 꽤나 힘들고 귀찮은 일입니다.
20+
21+
## Bundler를 구성하기 위해선 각각의 필요로 하는 기능의 Config 파일을 작성해야 한다
22+
대표적으로는 `webpack` 이 있는데요. 여기서 `webpack` 은 그저 JavaScript의 파일을 하나의 파일로 합치는 역할만을 하기에 JavaScript 코드를 각각의 Browser에 최적화 하기 위해서는 컴파일러가 필요합니다. 대표적으로는 `babel` 이 있습니다. (저는 `esbuild-loader` 를 사용합니다) 이러한 패키지들은 Config 파일을 필수로 필요로 합니다. 그러하여 프로젝트에 맞는 이러한 Config 파일을 작성하는 데에 시간이 많이 소요됩니다. (NodeJS 일 경우에만 이러한 현상이 지속되게 됩니다. 만약 Bun, Deno를 사용한다면 꽤나 편하게 구성이 가능합니다)
23+
24+
## Vanilla JavaScript로 구현한 기능들은 코드를 상대적으로 매우 많이 필요로 한다
25+
일반적으로 `Vue` 로 Counter 예제를 만들게 된다면 대충 이러한 코드로 구현하게 될 것입니다.
26+
27+
```html
28+
<template>
29+
<button @click="increase"></button>
30+
<div>{{ count }}</div>
31+
</template>
32+
```
33+
```html
34+
<script>
35+
// options api
36+
export default {
37+
data() {
38+
count: 0
39+
},
40+
methods: {
41+
increase() {
42+
this.count++;
43+
}
44+
}
45+
}
46+
</script>
47+
```
48+
49+
그렇지만 Vanilla JavaScript로 Counter 예제를 구현하게 된다면 꽤나 많은 코드를 가지게 됩니다.
50+
51+
```html
52+
<div id="app"></div>
53+
```
54+
```js
55+
const app = document.querySelector('#app');
56+
let count = 0;
57+
const component = () => {
58+
app.innerHTML = `
59+
<button id="increase"></button>
60+
<div>${count}</div>
61+
`;
62+
const increaseId = document.querySelector('#increase');
63+
increaseId.addEventListener('click', () => {
64+
count++;
65+
component();
66+
});
67+
};
68+
```
69+
70+
Vanilla JavaScript에서 Counter 예제를 만들기 위해서는 상태 업데이트를 위해 컴포넌트를 만들고, 상태가 변경될때 마다 컴포넌트를 실행해야 하는 컴포넌트의 동작 방식을 숙지해야 이러한 코드를 구현할 수 있습니다. 그러하여 JavaScript의 기초적인 것만 아는 분이라면 Vanilla JavaScript는 굉장히 쉬운 것이지만, 어떤 것을 구현하기 위해선 그것을 구현하는 것의 난이도로 봤을 때는 Vanilla JavaScript는 진입장벽 높다고 볼 수 있다. 꽤나 기초적인 지식이 요구되기 때문입니다.
71+
72+
이렇게 Vanila JavaScript는 코드가 상대적으로 읽기가 불편하고, 굉장히 코드를 작성하는 데에 피로감이 있으며, 꽤나 쉽지 않은 그러한 언어라고 볼 수 있을 것입니다.
73+
74+
## Vanill JavaScript에서 Mark-up을 Styling 하는 것은 꽤나 귀찮게 이루어 진다
75+
Vanilla JavaScript가 뜻하는 것이 아주 기본, 아무 것도 입혀지지 않은 그러한 것이기 때문에 Mark-up을 Styling 하기 위해서는 가장 기본적인 방법인 CSS 파일을 `import` 하여 사용하는 방법과, CSS in JS를 구현하여 사용하는 방법 이 두 가지가 존재합니다.
76+
77+
저는 CSS 파일을 `import` 해서 Styling 하는 방법과 CSS in JS를 사용하는 방법 이 두 가지를 혼용하여 사용합니다. `h-30` 같이 먼저 `define.css` 에 정의하여 속성으로 Styling 하는 방법과 `&:hover` 같은 동적인 것을 사용하기 위해서 CSS in JS를 사용하고 있습니다. (Dark mode도 CSS in JS를 사용하여 지원하고 있습니다)
78+
79+
만약 CSS in JS 같이 이러한 방식을 사용해야 한다면 이 또한 구현해야 하니 엄청난 코드가 필요로 되게 됩니다. 이를 구현하는 과정에서 나오는 피로감과 귀찮음은 엄청나게 증가되게 됩니다.
80+
81+
또한, Vanilla JavaScript에서 Styling 하는 것은 거의 HTML에서 Styling 하는 것과 별반 다르지 않기 때문에 그렇게 재밌게 이루어지는 과정은 아닙니다.
82+
83+
## 프로젝트의 크기가 커질 수록 유지 보수를 하는 것은 굉장히 어려워 진다
84+
Vanilla JavaScript로 Side project나 어떤 것을 어느 정도 개발을 완료하여 리팩토링을 하거나 유지 보수를 한다면, 매우 끔찍한 일이 벌어지게 될 것입니다. 만약 테스트 코드 조차 없다면 더욱더 힘든 과정이 벌어지게 될 것 입니다. 저의 코드일 경우 HTML을 그저 render 하여 Mark-up을 해가는 그러한 코드이며, HTML의 코드는 직관성과 신속성도 없기 때문에 유지 보수는 매우 불편합니다.
Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
---
2+
date: 2025-08-24
3+
category: [에세이]
4+
published: true
5+
fixed: false
6+
---
7+
8+
우리는 현재 AI 이데올로기 시대를 살고 있다.
9+
AI에 대한 이야기들은 매일 같이 쏟아지고,
10+
AI에 대한 기술도 매일 같이 쏟아진다.
11+
뉴스, 책, 블로그, 인터넷, 면접, 프로그래밍, ...
12+
어떤 분야든지 AI로 점철되어 있다.
13+
사람들은 AI에 대해 말하며, 소비한다.
14+
사람들은 AI가 만든 것을 이용하고, 소비한다.
15+
16+
나는 AI 이데올로기 시대에 한 가지 새로운 관점을 논해보고자 한다.
17+
바로 '완벽주의의 종말'이다.
18+
우리는 항상 완벽주의를 향해 달려왔다.
19+
완벽한 자기소개서, 완벽한 코드, 완벽한 블로그, 완벽한 풀이, ...
20+
그러나, AI가 출현한 이상 완벽한 것은 모두 AI가 작성해준다.
21+
그렇다면, 우리 인간은 도대체 왜 필요한 것인가?
22+
23+
> 이 총장은 “100년 후 인간은 현재 존재하는 인류와 달라져 있을 것”이라며 “인간의 역할과 위상 등을 두고 존재론적 질문에 빠질 수밖에 없다”고 말했다. 현재는 인간의 존재와 역할이 일치하는 시대로 ‘문명의 주인’ 역할을 하지만, 앞으로는 인간이 존재와 사유의 주체이되 역할이 사라질 수 있다고 봤다. 그는 “AI로 인간의 존재와 역할이 부조화가 일어난다”고 말했다.
24+
> 출처: 경향포럼 2025
25+
26+
정말, "인간의 존재와 역할이 부조화"가 실현되고 있는 것이다.
27+
우리는 AI가 생성한 산출물을 현실에 출력하는 존재 밖에 되지 않을 것이다.
28+
그렇다면, 우리는 왜 "AI가 생성한 산출물을 현실에 출력"하고 있는가?
29+
왜냐면, 우리가 완벽주의를 추구하기 때문이다.
30+
완벽한 자기소개서를 원하기 때문에 AI에게 의탁하는 것이고,
31+
완벽한 코드를 원하기 때문에 AI에게 의탁하는 것이다.
32+
33+
AI가 출현한 이상, 완벽한 산출물은 이제 아무 쓸모가 없다.
34+
AI 시대 쓸모 있는 것은, 인간적인 것이다.
35+
조금 문법이 틀린 자기소개서가 완벽한 자기소개서보다 낫고,
36+
조금 느린 코드가 완벽한 코드보다 나으며,
37+
조금 장황한 블로그가 완벽한 블로그보다 낫다.
38+
39+
나는 현재 AI 이데올로기 시대가,
40+
인간이 출현한 이래로 가장 많은 기회가 주어진 시대라고 생각한다.
41+
드디어 '완벽주의'라는 틀에 갇히지 않아도 되기 때문이다.
42+
실수를 용인하는 등의 인간적인 것에,
43+
진정 사람들이 관심을 보여주기 때문이다.
44+
AI 이데올로기는 한 편으로 인간적인 세상의 진정한 시작이라고 볼 수 있다.
45+
'완벽하지 못함'에 두려워하지 말라.
46+
대신, '사회학'적이지 못함에 두려워 하라.

content/처음처럼/높은 곳.md

Lines changed: 0 additions & 9 deletions
This file was deleted.

content/처음처럼/비상.md

Lines changed: 0 additions & 10 deletions
This file was deleted.

content/처음처럼/훈도.md

Lines changed: 0 additions & 9 deletions
This file was deleted.

content/처음처럼/히말라야 토끼.md

Lines changed: 0 additions & 8 deletions
This file was deleted.

0 commit comments

Comments
 (0)