AI

12-Factor Agents 정리— 프로덕션에 올릴 만한 LLM 애플리케이션을 만드는 12가지 원칙

이 글은 HumanLayer의 12-Factor Agents(Dex Horthy 외)를 읽고 제 언어로 다시 정리한 글입니다. 원문의 직역이 아니라 요약·재구성 + 개인적인 해석이며, 정확한 원문은 링크를 참고해 주세요. 원문 콘텐츠는 CC BY-SA 4.0 라이선스로 공개되어 있습니다.들어가며에이전트를 만들어 본 사람이라면 대부분 비슷한 경로를 밟습니다.에이전트를 만들기로 한다프레임워크를 하나 고른다 (빨리 가야 하니까)며칠 만에 70~80% 품질에 도달한다고객에게 내보내기엔 80%가 턱없이 부족하다는 걸 깨닫는다나머지 20%를 채우려면 프레임워크의 프롬프트와 제어 흐름을 역공학해야 한다는 걸 깨닫는다처음부터 다시 짠다원문 저자는 100명이 넘는 SaaS 빌더와 이야기하면서 이 패턴이 반복되는 걸 봤다..

웹 보안

CORS preflight, 정확히 무슨 요청이 오가는가

들어가며네트워크 탭을 열어보면 분명 요청 하나만 보낸 것 같은데 OPTIONS 요청이 먼저 하나 더 나가있는 걸 본 적이 있을 겁니다. 어떤 API는 이 과정 없이 바로 본 요청이 나가고, 어떤 API는 항상 OPTIONS가 먼저 나갑니다. 이 차이가 어디서 갈리는지, 그리고 서버가 Access-Control-Allow-Origin: *를 내려줬는데도 왜 로그인이 필요한 요청에서는 브라우저가 여전히 막아버리는지 — 이 두 가지를 정확한 기준으로 정리해봅니다.TL;DR모든 크로스 오리진 요청이 preflight를 거치는 게 아닙니다. "simple request"라는 정해진 조건을 만족하면 preflight 없이 바로 나갑니다.simple request의 기준은 메서드, 헤더 종류, Content-Type..

카테고리 없음

Web Crypto API가 HTTP를 막는 이유

들어가며crypto.subtle.encrypt()를 로컬에서 잘 쓰다가, 배포 환경이 아직 HTTP인 서버에 붙이는 순간 window.crypto.subtle이 undefined가 되는 걸 마주한 적이 있을 것입니다. 급한 대로 jsencrypt 같은 순수 JS RSA 라이브러리로 바꾸면 에러는 사라집니다. 하지만 같은 RSA 암호화인데, 왜 하나는 HTTP에서 막히고 하나는 멀쩡히 동작하는 걸까요?TL;DRcrypto.subtle이 HTTP에서 막히는 건 RSA-OAEP라는 알고리즘이 위험해서가 아니라, SubtleCrypto 인터페이스 전체가 Secure Context 스펙에 걸려있기 때문입니다.jsencrypt가 HTTP에서도 동작하는 건 더 안전해서가 아니라, window.crypto를 거치지 ..

HTML&CSS

aria-describedby

웹 접근성(Accessibility, a11y)에서 ARIA(Accessible Rich Internet Applications)는 스크린리더 등 보조 기술이 페이지 구조와 의미를 올바르게 이해하도록 돕는 역할을 합니다.그중 aria-describedby는 사용자에게 추가 설명(Description)을 제공할 때 가장 핵심적인 ARIA 속성 중 하나입니다. aria-describedby란?정의: 특정 요소가 참조하는 설명 요소(id)를 연결하여, 스크린리더와 같은 보조 기술이 해당 설명을 읽도록 하는 ARIA 속성용도: 단순히 레이블(Label)을 넘어, 보조 설명을 제공할 때 사용.속성 타입: ID 참조 스크린 리더나 다른 보조 기술이 해당 요소에 접근할 때, aria-describedby로 연결된 ..

카테고리 없음

컨텐츠 주소 저장소

단순하게 파일 이름으로 해당 파일을 접근하는 것이 아니라각각의 의존성 파일에 hash id 를 부여하고 관리이 과정에서 중복되는 패키지는 동일한 hash id를 얻게 된다.개념저장되는 컨텐츠의 해시값을 주소로 사용동일한 컨텐츠는 항상 동일한 주소내용 기반으로 파일을 식별하고 저장위치(URL)가 아닌 컨텐츠를 기반으로 검색할 수 있도록 정보를 저장하는 방법기존의 데이터는 중앙화된 서버에 보관되어 주소(URL)를 통해 접근하여 데이터를 볼 수 있었음이런 방법을 위치 주소라고 함*ex) https://n.news.naver.com/article/032*네이버 뉴스 페이지에서 기사 032를 가져오라는 URL이다. 말 그대로 네이버 뉴스 페이지라는 위치에서 기사 032라는 데이터를 가지고 오는 방식이다. 이러한 ..

카테고리 없음

토큰 저장소 공격

들어가며"토큰은 localStorage에 저장하면 안 되고 httpOnly 쿠키에 저장해야 한다"는 말은 프론트엔드 개발자라면 한 번쯤 들어봤을 겁니다. 그런데 왜 안 되는지, httpOnly 쿠키는 정확히 무엇을 막아주고 무엇은 못 막는지, 메모리에 저장하면 정말 안전한지를 물으면 대답이 애매해지는 경우가 많습니다.이 글은 저장소 선택 논쟁을 "어디가 안전한가"가 아니라 **"각 저장소가 어떤 공격 벡터에 노출되는가"**라는 질문으로 바꿔서, 공격 표면 단위로 하나씩 뜯어봅니다.TL;DR저장소 선택은 안전/위험의 이분법이 아니라 어떤 공격을 막고 어떤 공격에는 여전히 노출되는지의 트레이드오프입니다.localStorage/sessionStorage는 XSS가 발생하는 순간 전체 노출됩니다. 스크립트 실행..

카테고리 없음

커스텀 에러 만들기

Error 클래스 구조// 자바스크립트 자체 내장 에러 클래스 Error의 '슈도 코드'class Error { constructor(message) { this.message = message; // 에러 메시지 this.name = "Error"; // 에러로 표시될 이름 this.stack = [call stack]; // stack은 표준은 아니지만, 대다수 환경이 지원함 }}message: 에러 객체안에 들어있는 에러 메시지를 갖는 프로퍼티name: 에러가 발생할 때 ReferenceError와 같이 에러의 이름을 표시해 주는 프로퍼티stack: 에러 전에 있는 call stack들을 갖는 프로퍼티class ValidationError extends Error { const..

카테고리 없음

ComponentType, ComponentProps

ComponentType컴포넌트 자체의 타입을 정의컴포넌트의 전체 구조를 나타냄함수형 또는 클래스형 컴포넌트 전체를 의미type ComponentType = | React.ComponentClass | React.FunctionComponent// 사용 예시const MyComponent: ComponentType = (props) => { return {props.name};}ComponentProps특정 컴포넌트의 Props 타입을 추출컴포넌트에 전달되는 속성들의 타입을 얻을 때 사용컴포넌트의 props 구조만을 나타냄type ComponentProps = T extends React.ComponentType ? P : never;// 사용 예시type ButtonProps = Componen..

카테고리 없음

npm import 안됨(feat. 커스텀)

https://velog.io/@kcj_dev96/내가-만든-npm-패키지가-import가-안되는-이슈-feat.-tsconfig.json-pacakge.json문제의 원인은 types 필드가 exports 필드에 포함되어 있지 않아서였다.TypeScript는 exports 필드가 있다면 exports 필드를 참조하여 모듈의 파일을 찾기 때문에, 선언 파일(.d.ts)이 exports 필드에 포함되어 있지 않으면 TypeScript는 선언 파일을 찾지 못하고 오류를 발생시킬 수 있다고 한다.https://thebook.io/080334/0254/수정하고나서 npm을 다시 버전 업을 해야하나?git stash(작업물이 있는 경우)npm version pathgit stash popgit publish→ 버..

카테고리 없음

Outlet

React의 Outlet은 주로 React Router에서 사용되는 컴포넌트로, 중첩된 라우트에서 자식 라우트를 렌더링하기 위해 사용됩니다. Outlet을 사용하면 부모 컴포넌트 내에서 자식 컴포넌트를 표시할 위치를 정의할 수 있어, 중첩 라우팅 구조를 간편하게 관리할 수 있습니다.기본 사용 예시Outlet은 부모 라우트 컴포넌트에 배치되고, 자식 라우트가 활성화될 때 해당 위치에 렌더링됩니다.// App.jsimport { BrowserRouter, Routes, Route } from "react-router-dom";import Layout from "./Layout";import Home from "./Home";import About from "./About";function App() { r..

놀이터주인장
우당탕탕 개발놀이터