<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: hayata-yamamoto</title>
    <description>The latest articles on DEV Community by hayata-yamamoto (@hayata_yamamoto).</description>
    <link>https://dev.to/hayata_yamamoto</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F869511%2F44fb97df-01df-48ba-9d45-d16f47c11fe2.jpeg</url>
      <title>DEV Community: hayata-yamamoto</title>
      <link>https://dev.to/hayata_yamamoto</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/hayata_yamamoto"/>
    <language>en</language>
    <item>
      <title>Lightning-Fast, Minimal AI/API Serverless Deployment: The Essence and Practice of Mastra Lambda Docker Deploy</title>
      <dc:creator>hayata-yamamoto</dc:creator>
      <pubDate>Mon, 30 Jun 2025 09:00:00 +0000</pubDate>
      <link>https://dev.to/hayata_yamamoto/lightning-fast-minimal-aiapi-serverless-deployment-the-essence-and-practice-of-mastra-lambda-kjk</link>
      <guid>https://dev.to/hayata_yamamoto/lightning-fast-minimal-aiapi-serverless-deployment-the-essence-and-practice-of-mastra-lambda-kjk</guid>
      <description>&lt;h2&gt;
  
  
  1. Introduction
&lt;/h2&gt;

&lt;p&gt;The need to “take machine learning and AI to production” or to rapidly prototype and roll out new API services is growing stronger, not just in startups but also across established enterprises. However, many developers and teams have hit walls—operational, architectural, and even psychological—when trying to move from proofs of concept to robust, production-ready serverless deployments.&lt;/p&gt;

&lt;p&gt;This article unpacks the “Mastra Lambda Docker Deploy” open source repository, letting you instantly ship HTTP APIs or AI services on AWS Lambda using Docker—with minimal cloud know-how, friction, or overhead. Whether you’re cloud-savvy or just starting out, we’ll walk step-by-step from the logic to the hands-on, so you can master serverless AI and API deployment with confidence.&lt;/p&gt;




&lt;h2&gt;
  
  
  2. Why Do We Need Mastra Lambda Docker Deploy Now?
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Problem Statement
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;AI-driven APIs and apps demand more than just servers—they need automation, cost efficiency, and seamless integration.&lt;/li&gt;
&lt;li&gt;Proof-of-concept (PoC) is often lightning fast, but “production deployment” regularly hits a wall, dragging on for days or weeks.&lt;/li&gt;
&lt;li&gt;Lambda and other FaaS (Functions as a Service) are attractive, but their quirks and operational puzzles often discourage production adoption.&lt;/li&gt;
&lt;/ul&gt;

&lt;h4&gt;
  
  
  Real-World Pain Points
&lt;/h4&gt;

&lt;ul&gt;
&lt;li&gt;Endless scripting and environment-specific hacks for every deployment lead to wasted developer hours and technical debt.&lt;/li&gt;
&lt;li&gt;Mixing core app logic and environment glue code hinders maintainability and slows future scaling.&lt;/li&gt;
&lt;li&gt;Many successful PoCs die before production because “real deployment” looks like a mountain to climb.&lt;/li&gt;
&lt;/ul&gt;

&lt;h4&gt;
  
  
  Why Does This Matter?
&lt;/h4&gt;

&lt;ul&gt;
&lt;li&gt;Speed and agility determine team and company competitiveness.&lt;/li&gt;
&lt;li&gt;For R&amp;amp;D and new business, the ability to move from a “good idea” to a live service is a core driver of learning, innovation, and business wins.&lt;/li&gt;
&lt;li&gt;“You built it—you should be able to deploy and scale it, too.” A high-leverage infrastructure standard is urgently needed.&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  3. The Hidden Pitfalls of Conventional Serverless &amp;amp; AI Deployments
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Typical Existing Patterns
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Lambda Native Runtimes (Node.js/Python):&lt;/strong&gt; Deployment is simple, but you’re boxed in by runtime/library/version limitations and native dependencies.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Serverless Frameworks, SAM:&lt;/strong&gt; Powerful but potentially overwhelming, especially with YML files, complex settings, and operational overhead.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Lambda Layers:&lt;/strong&gt; Extend runtimes flexibly, but managing API Gateway, IAM, and layers can be arcane and difficult to automate.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Standard Docker Lambda:&lt;/strong&gt; Flexible, but requires significant effort to “make it Lambda-ready” and can still miss vital optimizations.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Comparison Table
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Approach&lt;/th&gt;
&lt;th&gt;Flexibility&lt;/th&gt;
&lt;th&gt;Ops Cost&lt;/th&gt;
&lt;th&gt;Learning Curve&lt;/th&gt;
&lt;th&gt;App Code Changes?&lt;/th&gt;
&lt;th&gt;Serverless Optimization&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Lambda Native Runtime&lt;/td&gt;
&lt;td&gt;△&lt;/td&gt;
&lt;td&gt;○&lt;/td&gt;
&lt;td&gt;○&lt;/td&gt;
&lt;td&gt;Extensive&lt;/td&gt;
&lt;td&gt;△&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Serverless Framework&lt;/td&gt;
&lt;td&gt;◎&lt;/td&gt;
&lt;td&gt;△&lt;/td&gt;
&lt;td&gt;△&lt;/td&gt;
&lt;td&gt;Moderate&lt;/td&gt;
&lt;td&gt;△&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Docker Lambda (Standard)&lt;/td&gt;
&lt;td&gt;◎&lt;/td&gt;
&lt;td&gt;△&lt;/td&gt;
&lt;td&gt;△&lt;/td&gt;
&lt;td&gt;Moderate&lt;/td&gt;
&lt;td&gt;△&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Mastra Lambda Docker Deploy&lt;/td&gt;
&lt;td&gt;◎&lt;/td&gt;
&lt;td&gt;○&lt;/td&gt;
&lt;td&gt;○&lt;/td&gt;
&lt;td&gt;Minimal&lt;/td&gt;
&lt;td&gt;◎&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;h3&gt;
  
  
  The Real Limitations
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Most methods require you to refactor your core app for “serverless compatibility”—API routing, handlers, and execution semantics.&lt;/li&gt;
&lt;li&gt;Infrastructure settings (API Gateway rules, timeouts, IAM roles) become a manual, tribal process—hard to reproduce, risky to maintain.&lt;/li&gt;
&lt;li&gt;Managing secrets (API keys), third-party integrations (OpenAI, weather APIs), and runtime environments safely is cumbersome.&lt;/li&gt;
&lt;li&gt;Even in the “Kubernetes era,” you still end up missing DevOps/SRE leverage for Lambda and similar platforms.&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  4. How Mastra Lambda Docker Deploy Solves It
&lt;/h2&gt;

&lt;h3&gt;
  
  
  What’s “New” Here
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Write your app as a standard HTTP server (Node.js Express, Python FastAPI... anything HTTP).&lt;/li&gt;
&lt;li&gt;Add a single line with “Lambda Web Adapter” in your Dockerfile—now your code is instantly serverless, with no app changes.&lt;/li&gt;
&lt;li&gt;Configure everything via &lt;code&gt;.env&lt;/code&gt;, including OpenAI keys and database URLs, making credentials management simple and secure.&lt;/li&gt;
&lt;li&gt;Multi-stage Docker builds create small, production-grade images with zero root privileges.&lt;/li&gt;
&lt;li&gt;All Lambda operational quirks—security, ports, execution roles—are handled for you.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  The Lambda Web Adapter (How It Works)
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;In your Dockerfile:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight docker"&gt;&lt;code&gt;  COPY --from=public.ecr.aws/awsguru/aws-lambda-adapter:0.9.0 /lambda-adapter /opt/extensions/lambda-adapter
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;With this, every Lambda event/API Gateway request is automatically converted into HTTP and proxied to your app.&lt;/li&gt;
&lt;li&gt;Your application runs identically both locally and on Lambda. “Lift and shift” without headaches.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Maximum Freedom—Any Tech Stack
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Not just Node.js/TypeScript: Python, Go, Rust… any language/framework that can act as an HTTP server can run on Lambda.&lt;/li&gt;
&lt;li&gt;Out-of-the-box OpenAI and weather API integration, with patterns you can adapt for other AI workloads.&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  5. Step-by-Step Onboarding and Sample Code
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Requirements
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Node.js (v18+ recommended)&lt;/li&gt;
&lt;li&gt;Docker&lt;/li&gt;
&lt;li&gt;AWS account (ECR and Lambda permissions required)&lt;/li&gt;
&lt;li&gt;OpenAI API Key&lt;/li&gt;
&lt;li&gt;(Optional) libSQL, Pino logger, etc.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Getting Started
&lt;/h3&gt;

&lt;h4&gt;
  
  
  1. Clone the Repository
&lt;/h4&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git clone https://github.com/tied-inc/mastra-lambda-docker-deploy.git
&lt;span class="nb"&gt;cd &lt;/span&gt;mastra-lambda-docker-deploy
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h4&gt;
  
  
  2. Create your &lt;code&gt;.env&lt;/code&gt; file
&lt;/h4&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;OPENAI_API_KEY=sk-xxxx...
DATABASE_URL=file:./mastra.db
NODE_ENV=production
PORT=8080
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h4&gt;
  
  
  3. Build the Docker Image
&lt;/h4&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;docker build &lt;span class="nt"&gt;-t&lt;/span&gt; mastra-lambda:latest &lt;span class="nb"&gt;.&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h4&gt;
  
  
  4. Run Locally (for dev/debug)
&lt;/h4&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;docker run &lt;span class="nt"&gt;--rm&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; 8080:8080 &lt;span class="nt"&gt;--env-file&lt;/span&gt; .env mastra-lambda:latest
&lt;span class="c"&gt;# Your API will be available at http://localhost:8080&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h4&gt;
  
  
  5. Deploy to AWS Lambda
&lt;/h4&gt;

&lt;ul&gt;
&lt;li&gt;Push your image to ECR (AWS Elastic Container Registry).&lt;/li&gt;
&lt;li&gt;Create a new Lambda function with a “Container Image.”&lt;/li&gt;
&lt;li&gt;Adjust environment variables, memory, and timeouts as needed.&lt;/li&gt;
&lt;li&gt;The Lambda Web Adapter will handle all event translation and setup for you. You get built-in API Gateway routing.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;em&gt;Tip: Test thoroughly with AWS free tier or a local staging environment before going live.&lt;/em&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  6. Technical Features and Best Practices
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Architecture
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;HTTP Server (Mastra):&lt;/strong&gt; Listens on port 8080 for requests.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Lambda Adapter:&lt;/strong&gt; Bridges AWS Lambda events to HTTP automatically.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Database:&lt;/strong&gt; libSQL by default (lightweight, portable), or your own DB (Postgres, etc.)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Logging:&lt;/strong&gt; Pino (or other JSON loggers) for rich, structured output.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Security:&lt;/strong&gt; Runs as a non-root user in Docker; minimal required Lambda execution role.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Key Usage Tips
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Use environment variables, not hardcoded values, to manage secrets and configuration.&lt;/li&gt;
&lt;li&gt;Tune Lambda timeouts and concurrency for both rapid prototyping and robust production.&lt;/li&gt;
&lt;li&gt;Local Docker brings parity to production—what you test is what runs!&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  FAQ &amp;amp; Common Stumbling Blocks
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Q:&lt;/strong&gt; I don’t know Lambda Layers or API Gateway—can I still use this?
&lt;strong&gt;A:&lt;/strong&gt; Yes. The adapter is plug-and-play. Just mirror the provided Dockerfile and configs.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Q:&lt;/strong&gt; Can I extend with custom API routes or non-HTTP workloads?
&lt;strong&gt;A:&lt;/strong&gt; Anything that can talk HTTP can be deployed. Extend agents and workflows at will.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Q:&lt;/strong&gt; What about security and operations?
&lt;strong&gt;A:&lt;/strong&gt; No root processes. Manage OpenAI keys and DB URLs via .env or AWS Secrets Manager.&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  7. Use Cases—Who Benefits Most?
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;Small teams and startups needing to turn prototypes into production APIs rapidly.&lt;/li&gt;
&lt;li&gt;ML/AI practitioners deploying chatbots, NLP, or other AI endpoints without DevOps bottlenecks.&lt;/li&gt;
&lt;li&gt;Serverless-first projects targeting cost efficiency, resilience, and easy scaling from day one.&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  8. Known Limitations
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;You still inherit Lambda platform limits (15-minute execution, memory caps, etc.)&lt;/li&gt;
&lt;li&gt;“Stateful” APIs require extra care: Use external DB/session storage if you need persistence.&lt;/li&gt;
&lt;li&gt;Additional configuration may be needed if you have heavy native dependencies (e.g., custom C++ libraries).&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  9. What’s Next &amp;amp; Community Involvement
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;More “minimal stack” recipes—Python, Go, and others to follow.&lt;/li&gt;
&lt;li&gt;Cross-cloud compatibility (e.g., Cloud Run, Vercel) experiments in the pipeline.&lt;/li&gt;
&lt;li&gt;Community is encouraged to share advanced workflows, new agent/tool integrations, and report back with success stories.&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  10. Summary &amp;amp; Call to Action
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;If this resonates, Star the repo, open an Issue, or submit your improvements!&lt;/li&gt;
&lt;li&gt;Share your deployment tips, questions, and “war stories” via GitHub or on social media.&lt;/li&gt;
&lt;li&gt;Let’s grow the serverless AI/API deployment ecosystem together—your contribution can help thousands deploy smarter and faster.&lt;/li&gt;
&lt;/ul&gt;




&lt;p&gt;&lt;strong&gt;OSS shines brightest when everyone both uses and advances it. With a single line of code, you can help spark new ideas and workflows for developers around the world. Join the movement!&lt;/strong&gt;&lt;/p&gt;

</description>
      <category>aws</category>
      <category>mastra</category>
      <category>lambda</category>
      <category>serverless</category>
    </item>
    <item>
      <title>Escape from Lambda Function Name Hardcoding Hell: Type-Safe Serverless Development with sls_enum</title>
      <dc:creator>hayata-yamamoto</dc:creator>
      <pubDate>Mon, 23 Jun 2025 03:00:00 +0000</pubDate>
      <link>https://dev.to/hayata_yamamoto/escape-from-lambda-function-name-hardcoding-hell-type-safe-serverless-development-with-slsenum-dl2</link>
      <guid>https://dev.to/hayata_yamamoto/escape-from-lambda-function-name-hardcoding-hell-type-safe-serverless-development-with-slsenum-dl2</guid>
      <description>&lt;h2&gt;
  
  
  1. Introduction
&lt;/h2&gt;

&lt;p&gt;As serverless architecture adoption rapidly grows, microservice configurations centered around AWS Lambda have become standard for many companies. However, as the number of Lambda functions grows to 10, 20, or more, an often-overlooked challenge emerges: Lambda function name management.&lt;/p&gt;

&lt;p&gt;You might think "it's just function names." However, this small issue compounds to create dozens of wasted work hours annually and risks of unexpected production failures.&lt;/p&gt;

&lt;p&gt;This article introduces the challenges of Lambda function name management in projects using the Serverless Framework and an open-source tool called "sls_enum" that solves them. By implementing this tool, you can achieve a type-safe development environment and significantly improve your team's productivity.&lt;/p&gt;

&lt;h2&gt;
  
  
  2. The Problem: Hidden Costs of Lambda Function Name Management
&lt;/h2&gt;

&lt;h3&gt;
  
  
  2.1 Specific Challenges
&lt;/h3&gt;

&lt;p&gt;When invoking Lambda functions from other functions, many developers hardcode function names as strings:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;boto3&lt;/span&gt;

&lt;span class="n"&gt;lambda_client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;boto3&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;client&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;lambda&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="c1"&gt;# Hardcoded function name
&lt;/span&gt;&lt;span class="n"&gt;response&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;lambda_client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;invoke&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="n"&gt;FunctionName&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;my-service-dev-processOrder&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;  &lt;span class="c1"&gt;# This string is the source of problems
&lt;/span&gt;    &lt;span class="n"&gt;InvocationType&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;Event&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;Payload&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;dumps&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;payload&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This seemingly simple code harbors the following issues:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Runtime errors from typos&lt;/strong&gt;: Writing &lt;code&gt;procesOrder&lt;/code&gt; instead of &lt;code&gt;processOrder&lt;/code&gt; won't be caught during deployment&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Missed references during refactoring&lt;/strong&gt;: When changing function names, all reference points must be manually updated&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Complex stage management&lt;/strong&gt;: Frequent mistakes when managing different function names across dev/staging/prod&lt;/li&gt;
&lt;/ol&gt;

&lt;h3&gt;
  
  
  2.2 Actual Losses
&lt;/h3&gt;

&lt;p&gt;Let's calculate the actual losses from these challenges using a 50-person development team as an example:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Debugging time&lt;/strong&gt;: Average 2 hours per developer per month investigating Lambda function name typo errors&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Annual time loss&lt;/strong&gt;: 2 hours × 12 months × 50 people = 1,200 hours&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Monetary loss&lt;/strong&gt;: Approximately $60,000 annually at $50/hour&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;More serious are production incidents. Failures due to function name mistakes create secondary losses:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Loss of customer trust&lt;/li&gt;
&lt;li&gt;Engineer on-call responses during nights and weekends&lt;/li&gt;
&lt;li&gt;Post-incident meetings and documentation&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  3. Existing Solutions and Their Limitations
&lt;/h2&gt;

&lt;h3&gt;
  
  
  3.1 Current Approaches
&lt;/h3&gt;

&lt;p&gt;Development teams have tried various methods to address this challenge:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Constants file management&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="c1"&gt;# constants.py
&lt;/span&gt;&lt;span class="n"&gt;LAMBDA_FUNCTIONS&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;PROCESS_ORDER&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;my-service-dev-processOrder&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;SEND_EMAIL&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;my-service-dev-sendEmail&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="c1"&gt;# ... manually added
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Environment variables&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;
&lt;span class="n"&gt;function_name&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;environ&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;PROCESS_ORDER_FUNCTION_NAME&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Document-based management&lt;/strong&gt;&lt;br&gt;
Managing function name lists on Confluence or Notion, with developers referencing them as needed.&lt;/p&gt;
&lt;h3&gt;
  
  
  3.2 Comparison Table
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Method&lt;/th&gt;
&lt;th&gt;Advantages&lt;/th&gt;
&lt;th&gt;Disadvantages&lt;/th&gt;
&lt;th&gt;Maintenance Cost&lt;/th&gt;
&lt;th&gt;Error Rate&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Hardcoding&lt;/td&gt;
&lt;td&gt;Simple implementation&lt;/td&gt;
&lt;td&gt;Frequent typos, difficult search&lt;/td&gt;
&lt;td&gt;High&lt;/td&gt;
&lt;td&gt;15-20%&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Constants file&lt;/td&gt;
&lt;td&gt;Centralized management&lt;/td&gt;
&lt;td&gt;Manual updates needed, sync issues&lt;/td&gt;
&lt;td&gt;Medium&lt;/td&gt;
&lt;td&gt;5-10%&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Environment variables&lt;/td&gt;
&lt;td&gt;Configurable at deploy&lt;/td&gt;
&lt;td&gt;Configuration omissions, complex management&lt;/td&gt;
&lt;td&gt;Medium&lt;/td&gt;
&lt;td&gt;8-12%&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;sls_enum&lt;/td&gt;
&lt;td&gt;Auto-generated, type-safe&lt;/td&gt;
&lt;td&gt;Initial setup required&lt;/td&gt;
&lt;td&gt;Low&lt;/td&gt;
&lt;td&gt;0%&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;The common problem with these existing methods is "manual management." As long as humans must ensure synchronization between serverless.yml and code, mistakes are inevitable.&lt;/p&gt;
&lt;h2&gt;
  
  
  4. The Solution: sls_enum
&lt;/h2&gt;
&lt;h3&gt;
  
  
  4.1 Tool Overview
&lt;/h3&gt;

&lt;p&gt;sls_enum is a CLI tool that parses serverless.yml files and automatically generates defined Lambda function names as Python Enum classes. This provides the following benefits:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Automatic synchronization&lt;/strong&gt;: Enums automatically update whenever serverless.yml is updated&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Type safety&lt;/strong&gt;: IDE autocomplete and type checker support&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Stage support&lt;/strong&gt;: Automatic switching between dev/staging/prod environments&lt;/li&gt;
&lt;/ul&gt;
&lt;h3&gt;
  
  
  4.2 Installation and Setup
&lt;/h3&gt;

&lt;p&gt;Installation is very simple:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Install&lt;/span&gt;
pip &lt;span class="nb"&gt;install &lt;/span&gt;sls-enum

&lt;span class="c"&gt;# Basic usage&lt;/span&gt;
sls-enum generate serverless.yml &lt;span class="nt"&gt;--output&lt;/span&gt; lambda_functions.py

&lt;span class="c"&gt;# Generate with stage specification&lt;/span&gt;
sls-enum generate serverless.yml &lt;span class="nt"&gt;--output&lt;/span&gt; lambda_functions.py &lt;span class="nt"&gt;--stage&lt;/span&gt; prod

&lt;span class="c"&gt;# Auto-generate with watch mode&lt;/span&gt;
sls-enum watch serverless.yml &lt;span class="nt"&gt;--output&lt;/span&gt; lambda_functions.py
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  4.3 Generated Code Example and Usage
&lt;/h3&gt;

&lt;p&gt;serverless.yml content:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;service&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;my-service&lt;/span&gt;

&lt;span class="na"&gt;functions&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;processOrder&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;handler&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;handlers.process_order&lt;/span&gt;
    &lt;span class="na"&gt;events&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;http&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
          &lt;span class="na"&gt;path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;/orders&lt;/span&gt;
          &lt;span class="na"&gt;method&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;post&lt;/span&gt;

  &lt;span class="na"&gt;sendEmail&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;handler&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;handlers.send_email&lt;/span&gt;
    &lt;span class="na"&gt;events&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;sqs&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
          &lt;span class="na"&gt;arn&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;${self:custom.emailQueueArn}&lt;/span&gt;

  &lt;span class="na"&gt;generateReport&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;handler&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;handlers.generate_report&lt;/span&gt;
    &lt;span class="na"&gt;events&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;schedule&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;rate(1 day)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Generated Enum class:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="c1"&gt;# lambda_functions.py (auto-generated)
&lt;/span&gt;&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;enum&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;Enum&lt;/span&gt;

&lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;LambdaFunctions&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Enum&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="sh"&gt;"""&lt;/span&gt;&lt;span class="s"&gt;Auto-generated Lambda function names from serverless.yml&lt;/span&gt;&lt;span class="sh"&gt;"""&lt;/span&gt;

    &lt;span class="n"&gt;PROCESS_ORDER&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;my-service-dev-processOrder&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;
    &lt;span class="n"&gt;SEND_EMAIL&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;my-service-dev-sendEmail&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;
    &lt;span class="n"&gt;GENERATE_REPORT&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;my-service-dev-generateReport&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;

    &lt;span class="nd"&gt;@property&lt;/span&gt;
    &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;arn&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;self&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="nb"&gt;str&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="sh"&gt;"""&lt;/span&gt;&lt;span class="s"&gt;Get the full ARN for this Lambda function&lt;/span&gt;&lt;span class="sh"&gt;"""&lt;/span&gt;
        &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;
        &lt;span class="n"&gt;region&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;environ&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;AWS_REGION&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;us-east-1&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
        &lt;span class="n"&gt;account_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;environ&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;AWS_ACCOUNT_ID&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;arn:aws:lambda:&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;region&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s"&gt;:&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;account_id&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s"&gt;:function:&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;self&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;value&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Actual usage example:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;boto3&lt;/span&gt;
&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;json&lt;/span&gt;
&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;lambda_functions&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;LambdaFunctions&lt;/span&gt;

&lt;span class="n"&gt;lambda_client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;boto3&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;client&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;lambda&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="c1"&gt;# Type-safe function invocation
&lt;/span&gt;&lt;span class="n"&gt;response&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;lambda_client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;invoke&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="n"&gt;FunctionName&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;LambdaFunctions&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PROCESS_ORDER&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;value&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;  &lt;span class="c1"&gt;# IDE provides autocomplete
&lt;/span&gt;    &lt;span class="n"&gt;InvocationType&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;Event&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;Payload&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;dumps&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
        &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;orderId&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;12345&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;items&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;item1&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;item2&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
    &lt;span class="p"&gt;})&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="c1"&gt;# Handling multiple functions
&lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;func&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;LambdaFunctions&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PROCESS_ORDER&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;LambdaFunctions&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SEND_EMAIL&lt;/span&gt;&lt;span class="p"&gt;]:&lt;/span&gt;
    &lt;span class="nf"&gt;print&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;Warming up: &lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;func&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;value&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="n"&gt;lambda_client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;invoke&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
        &lt;span class="n"&gt;FunctionName&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;func&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;value&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="n"&gt;InvocationType&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;Event&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="n"&gt;Payload&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;dumps&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;warmup&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="bp"&gt;True&lt;/span&gt;&lt;span class="p"&gt;})&lt;/span&gt;
    &lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  5. Business Impact
&lt;/h2&gt;

&lt;h3&gt;
  
  
  5.1 Quantitative Benefits (Estimates and Simulations)
&lt;/h3&gt;

&lt;p&gt;Estimated effects based on simulations for a 50-person development team:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Debugging Time Reduction (Estimate)&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Assumption: Average 2 hours per person per month spent investigating Lambda function name errors&lt;/li&gt;
&lt;li&gt;After implementation: Zero time as errors are caught at compile time&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Estimated reduction: 1,200 hours annually for the entire team&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Cost Reduction from Incident Prevention (Simulation)&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Assumption: 1-2 production incidents per quarter caused by function name issues&lt;/li&gt;
&lt;li&gt;Response cost per incident: 5 engineers × 4 hours × $50/hour = $1,000&lt;/li&gt;
&lt;li&gt;Opportunity loss: Estimated $5,000 per incident&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Estimated reduction: $24,000-48,000 annually&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;CI/CD Efficiency (Estimate)&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Simulation conditions:

&lt;ul&gt;
&lt;li&gt;Deploy failure rate reduced from 15% to 2%&lt;/li&gt;
&lt;li&gt;20 deploys per day, 30 minutes lost per failure&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;li&gt;&lt;strong&gt;Estimated reduction: Approximately 390 hours of pipeline execution time annually&lt;/strong&gt;&lt;/li&gt;

&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;ROI Simulation&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Initial Implementation Cost:
- Setup: 8 hours
- Team training: 20 hours
- Migration work: 40 hours
Total: 68 hours ($3,400 equivalent)

Annual Savings (Estimated):
- Debugging time: 1,200 hours ($60,000 equivalent)
- Incident response: $36,000 equivalent
- CI/CD efficiency: 390 hours ($19,500 equivalent)
Total: $115,500 equivalent

Estimated ROI: Approximately 34x (first year)
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  5.2 Qualitative Benefits
&lt;/h3&gt;

&lt;p&gt;Important benefits that are difficult to quantify:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Improved Developer Experience&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;No need to memorize function names with IDE autocomplete&lt;/li&gt;
&lt;li&gt;Freedom from typo anxiety allows focus on logic implementation&lt;/li&gt;
&lt;li&gt;Eliminates function name verification during code reviews&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;New Member Onboarding&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Easy understanding of existing Lambda functions&lt;/li&gt;
&lt;li&gt;Reduced time searching for documentation&lt;/li&gt;
&lt;li&gt;Correct function names used from the start&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Enhanced Team Collaboration&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Eliminates mistakes when calling other teams' Lambda functions&lt;/li&gt;
&lt;li&gt;Natural standardization of function naming conventions&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  6. Implementation Guide
&lt;/h2&gt;

&lt;h3&gt;
  
  
  6.1 Teams Suited for Implementation
&lt;/h3&gt;

&lt;p&gt;Teams that will see particularly high benefits from sls_enum:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Managing &lt;strong&gt;10 or more Lambda functions&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;Operating &lt;strong&gt;multi-stage environments&lt;/strong&gt; (dev/staging/prod)&lt;/li&gt;
&lt;li&gt;Developing backends with &lt;strong&gt;Python/TypeScript&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;Heavy &lt;strong&gt;microservice interconnections&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;Established &lt;strong&gt;CI/CD pipelines&lt;/strong&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  6.2 Step-by-Step Implementation
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Step 1: Visualize Current Challenges&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Search for hardcoded function names in current codebase&lt;/span&gt;
&lt;span class="nb"&gt;grep&lt;/span&gt; &lt;span class="nt"&gt;-r&lt;/span&gt; &lt;span class="s2"&gt;"FunctionName.*=.*['&lt;/span&gt;&lt;span class="se"&gt;\"&lt;/span&gt;&lt;span class="s2"&gt;].*-.*-.*['&lt;/span&gt;&lt;span class="se"&gt;\"&lt;/span&gt;&lt;span class="s2"&gt;]"&lt;/span&gt; &lt;span class="nt"&gt;--include&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s2"&gt;"*.py"&lt;/span&gt; &lt;span class="nb"&gt;.&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 2: Pilot Project Validation&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Trial implementation in a small service&lt;/span&gt;
&lt;span class="nb"&gt;cd &lt;/span&gt;pilot-service
pip &lt;span class="nb"&gt;install &lt;/span&gt;sls-enum
sls-enum generate serverless.yml &lt;span class="nt"&gt;--output&lt;/span&gt; src/lambda_functions.py

&lt;span class="c"&gt;# Gradually replace existing code&lt;/span&gt;
&lt;span class="c"&gt;# Before: FunctionName='my-service-dev-processOrder'&lt;/span&gt;
&lt;span class="c"&gt;# After: FunctionName=LambdaFunctions.PROCESS_ORDER.value&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 3: CI/CD Pipeline Integration&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="c1"&gt;# .github/workflows/deploy.yml&lt;/span&gt;
&lt;span class="na"&gt;steps&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Generate Lambda Enums&lt;/span&gt;
    &lt;span class="na"&gt;run&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;|&lt;/span&gt;
      &lt;span class="s"&gt;pip install sls-enum&lt;/span&gt;
      &lt;span class="s"&gt;sls-enum generate serverless.yml --output src/lambda_functions.py --stage ${{ env.STAGE }}&lt;/span&gt;

  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Type Check&lt;/span&gt;
    &lt;span class="na"&gt;run&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;|&lt;/span&gt;
      &lt;span class="s"&gt;mypy src/&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 4: Team-wide Rollout&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Pre-commit hook setup&lt;/span&gt;
&lt;span class="nb"&gt;cat&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; .pre-commit-config.yaml &lt;span class="o"&gt;&amp;lt;&amp;lt;&lt;/span&gt; &lt;span class="no"&gt;EOF&lt;/span&gt;&lt;span class="sh"&gt;
repos:
  - repo: local
    hooks:
      - id: generate-lambda-enums
        name: Generate Lambda Enums
        entry: sls-enum generate serverless.yml --output src/lambda_functions.py
        language: system
        files: serverless&lt;/span&gt;&lt;span class="se"&gt;\.&lt;/span&gt;&lt;span class="sh"&gt;yml$
&lt;/span&gt;&lt;span class="no"&gt;EOF
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  6.3 Best Practices
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Automatic Generation with Pre-commit Hooks&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# .pre-commit-config.yaml&lt;/span&gt;
repos:
  - repo: &lt;span class="nb"&gt;local
    &lt;/span&gt;hooks:
      - &lt;span class="nb"&gt;id&lt;/span&gt;: generate-lambda-enums
        name: Generate Lambda Enums
        entry: sls-enum generate serverless.yml &lt;span class="nt"&gt;--output&lt;/span&gt; src/lambda_functions.py
        language: system
        files: serverless&lt;span class="se"&gt;\.&lt;/span&gt;yml&lt;span class="err"&gt;$&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Stage-specific Management&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="c1"&gt;# For development environment
&lt;/span&gt;&lt;span class="n"&gt;sls&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;enum&lt;/span&gt; &lt;span class="n"&gt;generate&lt;/span&gt; &lt;span class="n"&gt;serverless&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;yml&lt;/span&gt; &lt;span class="o"&gt;--&lt;/span&gt;&lt;span class="n"&gt;output&lt;/span&gt; &lt;span class="n"&gt;lambda_functions_dev&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;py&lt;/span&gt; &lt;span class="o"&gt;--&lt;/span&gt;&lt;span class="n"&gt;stage&lt;/span&gt; &lt;span class="n"&gt;dev&lt;/span&gt;

&lt;span class="c1"&gt;# For production environment
&lt;/span&gt;&lt;span class="n"&gt;sls&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;enum&lt;/span&gt; &lt;span class="n"&gt;generate&lt;/span&gt; &lt;span class="n"&gt;serverless&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;yml&lt;/span&gt; &lt;span class="o"&gt;--&lt;/span&gt;&lt;span class="n"&gt;output&lt;/span&gt; &lt;span class="n"&gt;lambda_functions_prod&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;py&lt;/span&gt; &lt;span class="o"&gt;--&lt;/span&gt;&lt;span class="n"&gt;stage&lt;/span&gt; &lt;span class="n"&gt;prod&lt;/span&gt;

&lt;span class="c1"&gt;# Use appropriate Enum based on environment
&lt;/span&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;
&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;environ&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;STAGE&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;prod&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
    &lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;lambda_functions_prod&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;LambdaFunctions&lt;/span&gt;
&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
    &lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;lambda_functions_dev&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;LambdaFunctions&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Migration Strategy from Existing Code&lt;/strong&gt;&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Gradual Replacement&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Start using sls_enum for new code&lt;/li&gt;
&lt;li&gt;Replace existing code during feature updates&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Leverage Search and Replace&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;   &lt;span class="c1"&gt;# Identify pre-migration code
&lt;/span&gt;   &lt;span class="c1"&gt;# grep -r "FunctionName.*=.*['\"]" --include="*.py" .
&lt;/span&gt;
   &lt;span class="c1"&gt;# After migration
&lt;/span&gt;   &lt;span class="c1"&gt;# FunctionName=LambdaFunctions.PROCESS_ORDER.value
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Add Tests&lt;/strong&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;   &lt;span class="c1"&gt;# Test that function names are correctly generated
&lt;/span&gt;   &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;test_lambda_function_names&lt;/span&gt;&lt;span class="p"&gt;():&lt;/span&gt;
       &lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;lambda_functions&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;LambdaFunctions&lt;/span&gt;
       &lt;span class="k"&gt;assert&lt;/span&gt; &lt;span class="n"&gt;LambdaFunctions&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PROCESS_ORDER&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;value&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;endswith&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;processOrder&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Team Operation Rules&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Always regenerate enums after changing serverless.yml&lt;/li&gt;
&lt;li&gt;Integrate automatic generation in CI/CD pipeline&lt;/li&gt;
&lt;li&gt;Include generated files in version control (share across teams)&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  7. Conclusion and Call to Action
&lt;/h2&gt;

&lt;p&gt;sls_enum solves the seemingly minor challenge of "Lambda function name management" to create significant business value. Annual savings of 1,200 development hours, zero incidents achieved, and most importantly, an environment where developers can focus on core logic. These are crucial elements for differentiation in competitive markets.&lt;/p&gt;

&lt;h3&gt;
  
  
  Actions You Can Take Now
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Current State Analysis&lt;/strong&gt;: Investigate how many Lambda function name-related errors occur in your team&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Trial Implementation&lt;/strong&gt;: Try sls_enum in a small project and experience the benefits&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Feedback&lt;/strong&gt;: Share improvement suggestions through Issues and Pull Requests on GitHub
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Get started now&lt;/span&gt;
pip &lt;span class="nb"&gt;install &lt;/span&gt;sls-enum
sls-enum generate serverless.yml &lt;span class="nt"&gt;--output&lt;/span&gt; lambda_functions.py
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Contributing to the Open Source Community
&lt;/h3&gt;

&lt;p&gt;sls_enum is an open source project. Your experience and insights can help solve challenges for developers worldwide. Please star the project on &lt;a href="https://github.com/hayata-yamamoto/serverless-lambda-function-name-enum-python" rel="noopener noreferrer"&gt;GitHub&lt;/a&gt; and share your improvement suggestions and new feature ideas.&lt;/p&gt;

&lt;p&gt;Small improvements compound into major innovations. Start with the seemingly mundane challenge of Lambda function name management and elevate your team's productivity to the next level.&lt;/p&gt;

</description>
      <category>serverless</category>
      <category>aws</category>
      <category>lambda</category>
    </item>
    <item>
      <title>Evolving a Markdown Converter with AI and OSS: A Development Story that Revolutionizes Technical Content Publishing</title>
      <dc:creator>hayata-yamamoto</dc:creator>
      <pubDate>Fri, 20 Jun 2025 00:37:10 +0000</pubDate>
      <link>https://dev.to/hayata_yamamoto/evolving-a-markdown-converter-with-ai-and-oss-a-development-story-that-revolutionizes-technical-mk2</link>
      <guid>https://dev.to/hayata_yamamoto/evolving-a-markdown-converter-with-ai-and-oss-a-development-story-that-revolutionizes-technical-mk2</guid>
      <description>&lt;h2&gt;
  
  
  Introduction: Discovering a Brilliant Tool
&lt;/h2&gt;

&lt;p&gt;One day in 2024, I was searching for the ideal Markdown-to-Medium conversion tool. As someone who regularly writes technical articles, I was looking for an efficient way to optimize my Markdown content for various platforms.&lt;/p&gt;

&lt;p&gt;Then I discovered a wonderful OSS tool on GitHub. The functionality was perfect, the UI was polished, and it clearly showcased the author's technical skills and design sense. Seeing the potential of this tool, I felt inspired: "I want to build upon this foundation and evolve it further with modern technology stack."&lt;/p&gt;

&lt;h2&gt;
  
  
  Opportunities in Modern Technical Content Publishing
&lt;/h2&gt;

&lt;h3&gt;
  
  
  1. The Multi-Platform Era
&lt;/h3&gt;

&lt;p&gt;Today, technical content publishing platforms have diversified, each fostering wonderful reader communities:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Medium (global engineering community)&lt;/li&gt;
&lt;li&gt;Substack (readers seeking deep insights)&lt;/li&gt;
&lt;li&gt;Dev.to (active developer community)&lt;/li&gt;
&lt;li&gt;Zenn (Japanese tech community)&lt;/li&gt;
&lt;li&gt;Company blogs (branding and SEO)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This diversity presents fantastic opportunities, but also creates a need for efficient distribution methods.&lt;/p&gt;

&lt;h3&gt;
  
  
  2. Leveraging Markdown as a Universal Language
&lt;/h3&gt;

&lt;p&gt;For engineers, Markdown is a powerful productivity tool. It's simple, version-control friendly, and editable in any editor:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight markdown"&gt;&lt;code&gt;&lt;span class="gu"&gt;## Structured Documents&lt;/span&gt;
&lt;span class="p"&gt;-&lt;/span&gt; Clear hierarchy
&lt;span class="p"&gt;-&lt;/span&gt; &lt;span class="gs"&gt;**Important emphasis**&lt;/span&gt;
&lt;span class="p"&gt;-&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nv"&gt;Reference links&lt;/span&gt;&lt;span class="p"&gt;](&lt;/span&gt;&lt;span class="sx"&gt;https://example.com&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Our goal was to maximize the potential of this excellent notation across all platforms.&lt;/p&gt;

&lt;h3&gt;
  
  
  3. Continuous Evolution of the OSS Community
&lt;/h3&gt;

&lt;p&gt;GitHub hosts many excellent Markdown conversion tools. Each was implemented with cutting-edge technology of its time and has helped countless developers. We believed we could create additional value by combining new technologies with these pioneering achievements.&lt;/p&gt;

&lt;h2&gt;
  
  
  The OSS Evolution Project: Merging Wisdom of Predecessors with AI
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Inheriting Excellent Design Philosophy
&lt;/h3&gt;

&lt;p&gt;The tool I discovered had outstanding features:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Intuitive real-time preview&lt;/li&gt;
&lt;li&gt;Thoughtfully crafted HTML output for Medium&lt;/li&gt;
&lt;li&gt;UI design prioritizing usability&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;"Let's inherit this excellent design philosophy while creating something even better with the latest technology."&lt;/p&gt;

&lt;p&gt;This was our project's starting point.&lt;/p&gt;

&lt;h3&gt;
  
  
  Efficient Technology Updates with AI
&lt;/h3&gt;

&lt;p&gt;In 2024 development, AI tools like &lt;strong&gt;Cursor&lt;/strong&gt; and &lt;strong&gt;Claude&lt;/strong&gt; became powerful partners. With these tools, we completed the technology stack update in &lt;strong&gt;just 4 hours&lt;/strong&gt;:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Technology Stack Evolution&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;JavaScript to TypeScript (improved type safety)&lt;/li&gt;
&lt;li&gt;Support for latest React 19 (performance improvements)&lt;/li&gt;
&lt;li&gt;Fast development environment with Vite (improved DX)&lt;/li&gt;
&lt;li&gt;Automated deployment with GitHub Actions (continuous improvement)
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// Type definitions created in collaboration with AI&lt;/span&gt;
&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kr"&gt;interface&lt;/span&gt; &lt;span class="nx"&gt;MarkdownConverterProps&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;source&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;onConvert&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;html&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="k"&gt;void&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;platform&lt;/span&gt;&lt;span class="p"&gt;?:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;medium&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;substack&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;theme&lt;/span&gt;&lt;span class="p"&gt;?:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;light&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;dark&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;AI wasn't just a code generation tool; it suggested best practices and helped design with future extensibility in mind.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Evolved Markdown-to-Medium
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Core Features: Balancing Simplicity and Power
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Real-time Preview&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;See actual rendering while writing Markdown&lt;/li&gt;
&lt;li&gt;Faithful reproduction of each platform's display characteristics&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;One-Click Conversion&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Instantly generate optimized HTML&lt;/li&gt;
&lt;li&gt;Automatic clipboard copy&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Multi-Platform Support&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Medium (optimized)&lt;/li&gt;
&lt;li&gt;Substack (newly supported)&lt;/li&gt;
&lt;li&gt;Continuous expansion planned&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;h3&gt;
  
  
  Usage: Simple 3 Steps
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Step 1: Access&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;https://m2m.tied-inc.com/
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;No registration required, free, instant access.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 2: Write in Markdown&lt;/strong&gt;&lt;br&gt;
Create articles using familiar Markdown syntax. Paste existing drafts too.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 3: Convert and Publish&lt;/strong&gt;&lt;br&gt;
After checking the preview, click "Copy HTML". Platform-optimized HTML is generated.&lt;/p&gt;

&lt;h3&gt;
  
  
  Measured Impact
&lt;/h3&gt;

&lt;p&gt;Actual improvements in our team:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Before Implementation&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Article writing: 30 minutes&lt;/li&gt;
&lt;li&gt;Platform-specific adjustments: 20 minutes&lt;/li&gt;
&lt;li&gt;Review and fixes: 10 minutes&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Total: 60 minutes/article&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;After Implementation&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Article writing: 30 minutes&lt;/li&gt;
&lt;li&gt;Conversion and posting: 3 minutes&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Total: 33 minutes/article&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;45% time reduction&lt;/strong&gt; allows us to dedicate more time to improving content quality.&lt;/p&gt;

&lt;h2&gt;
  
  
  OSS Development in the AI Era: Collaborative Evolution
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Balancing Heritage and Innovation
&lt;/h3&gt;

&lt;p&gt;What we learned through this project:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Excellent OSS design philosophy holds value across generations&lt;/li&gt;
&lt;li&gt;AI tools enable rapid modernization while leveraging existing assets&lt;/li&gt;
&lt;li&gt;Better tools emerge by gathering community wisdom&lt;/li&gt;
&lt;/ol&gt;

&lt;h3&gt;
  
  
  Open Development Process
&lt;/h3&gt;

&lt;p&gt;Currently, this tool is actively evolving:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Substack support (implemented from community request)&lt;/li&gt;
&lt;li&gt;Accessibility improvements (dark mode added)&lt;/li&gt;
&lt;li&gt;Internationalization (multi-language UI)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;All features are born from dialogue with users.&lt;/p&gt;

&lt;h2&gt;
  
  
  Let's Build Together
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Start Using Today
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;For Individual Writers&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Start instantly at &lt;a href="https://m2m.tied-inc.com/" rel="noopener noreferrer"&gt;https://m2m.tied-inc.com/&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Write efficiently with familiar Markdown&lt;/li&gt;
&lt;li&gt;Easy distribution to multiple platforms&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;For DevRel Teams and Technical PR&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Significantly improve team-wide writing efficiency&lt;/li&gt;
&lt;li&gt;Quality control with consistent formatting&lt;/li&gt;
&lt;li&gt;Create an environment where engineers can focus on writing&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Evolve Together
&lt;/h3&gt;

&lt;p&gt;This tool is published as OSS, and we welcome your participation:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Feedback Examples&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;"Dev.to optimization would be great"&lt;/li&gt;
&lt;li&gt;"Want to improve code block syntax highlighting"&lt;/li&gt;
&lt;li&gt;"Writing template features would be convenient"&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;How to Participate&lt;/strong&gt;&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Create issues on &lt;a href="https://github.com/tied-inc/Markdown-to-Medium" rel="noopener noreferrer"&gt;GitHub&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Share improvements and ideas&lt;/li&gt;
&lt;li&gt;Pull requests are very welcome&lt;/li&gt;
&lt;/ol&gt;

&lt;h3&gt;
  
  
  The Potential of Technical Communities
&lt;/h3&gt;

&lt;p&gt;In the AI era, OSS development has become more collaborative and efficient:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Building upon existing excellent projects&lt;/li&gt;
&lt;li&gt;Accelerating development with AI tools&lt;/li&gt;
&lt;li&gt;Determining direction through community collective intelligence&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Conclusion: Building the Future Together
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;To All Writers&lt;/strong&gt;&lt;br&gt;&lt;br&gt;
Publish articles to any platform efficiently with Markdown. Make technical knowledge sharing easier.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;To All Developers&lt;/strong&gt;&lt;br&gt;&lt;br&gt;
The combination of AI and OSS shows that individuals can create significant impact. Let's build useful tools together.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;To the Community&lt;/strong&gt;&lt;br&gt;&lt;br&gt;
Please share your impressions, improvements, and new feature ideas. Your voice guides the tool's evolution.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Writing and sharing technical articles is a wonderful activity that spreads knowledge and enriches communities. We hope this tool helps support that activity.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Try it now →&lt;/strong&gt; &lt;a href="https://m2m.tied-inc.com/" rel="noopener noreferrer"&gt;https://m2m.tied-inc.com/&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Develop together →&lt;/strong&gt; &lt;a href="https://github.com/tied-inc/Markdown-to-Medium" rel="noopener noreferrer"&gt;https://github.com/tied-inc/Markdown-to-Medium&lt;/a&gt;&lt;/p&gt;




&lt;p&gt;&lt;em&gt;This article was also efficiently created with Markdown-to-Medium. 30 minutes writing, 3 minutes converting.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>opensource</category>
      <category>ai</category>
    </item>
    <item>
      <title>Accelerating R&amp;D with Instant Data Labeling Infrastructure - Label Studio on AWS AppRunner Terraform Module</title>
      <dc:creator>hayata-yamamoto</dc:creator>
      <pubDate>Thu, 19 Jun 2025 01:44:18 +0000</pubDate>
      <link>https://dev.to/hayata_yamamoto/accelerating-rd-with-instant-data-labeling-infrastructure-label-studio-on-aws-apprunner-22c3</link>
      <guid>https://dev.to/hayata_yamamoto/accelerating-rd-with-instant-data-labeling-infrastructure-label-studio-on-aws-apprunner-22c3</guid>
      <description>&lt;h2&gt;
  
  
  Introduction: Nothing Starts Without Data
&lt;/h2&gt;

&lt;p&gt;"We want to build an excellent machine learning model."&lt;/p&gt;

&lt;p&gt;Everyone involved in R&amp;amp;D projects thinks this way. But what's the reality? Weeks after project kickoff, you're still stuck on infrastructure setup. Machine learning engineers are wrestling with the AWS console. Have you witnessed such scenes before?&lt;/p&gt;

&lt;p&gt;At Tied, inc., through supporting numerous R&amp;amp;D projects, we've encountered a common challenge. It's the "data labeling environment setup" - a seemingly minor but actually critical bottleneck.&lt;/p&gt;

&lt;p&gt;This article introduces the Terraform module "terraform-aws-label-studio-on-apprunner" we developed to solve this challenge, along with its background and value.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why Data Labeling Infrastructure Matters
&lt;/h2&gt;

&lt;h3&gt;
  
  
  The Success Formula for Machine Learning
&lt;/h3&gt;

&lt;p&gt;What factors determine the success of machine learning projects? The latest algorithms? High-performance GPUs? While these are important, the most fundamental factor is "high-quality data."&lt;/p&gt;

&lt;p&gt;And to produce high-quality data, an efficient labeling environment is essential. Label Studio is widely recognized as a powerful open-source tool for this purpose. It supports all data formats - images, text, audio - and enables team collaboration.&lt;/p&gt;

&lt;h3&gt;
  
  
  The Reality of Time to Market
&lt;/h3&gt;

&lt;p&gt;R&amp;amp;D projects are a race against time. Delivering value to market faster than competitors determines business success. However, many projects experience the following timeline:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Week 1-2&lt;/strong&gt;: Infrastructure design and setup&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Week 3&lt;/strong&gt;: Label Studio finally starts running&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Week 4&lt;/strong&gt;: Data labeling finally begins&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In other words, it takes a full month before actual value creation begins.&lt;/p&gt;

&lt;h2&gt;
  
  
  Three Challenges R&amp;amp;D Teams Face
&lt;/h2&gt;

&lt;h3&gt;
  
  
  1. Skill Set Mismatch
&lt;/h3&gt;

&lt;p&gt;The primary role of machine learning engineers is to analyze data, build models, and create business value. In reality, however, they spend time configuring VPCs and setting up security groups.&lt;/p&gt;

&lt;p&gt;This isn't just wasted time. The opportunity cost of having expensive specialists work on tasks outside their expertise is immeasurable.&lt;/p&gt;

&lt;h3&gt;
  
  
  2. Barriers at Project Launch
&lt;/h3&gt;

&lt;p&gt;"We can't start anything without data first."&lt;/p&gt;

&lt;p&gt;This is the fate of R&amp;amp;D projects. But what if it takes weeks to set up the environment for creating that data? The initial project momentum is lost, and team motivation declines.&lt;/p&gt;

&lt;h3&gt;
  
  
  3. Scaling Complexity
&lt;/h3&gt;

&lt;p&gt;When a small-scale project succeeds, scaling up becomes the next challenge. You want to increase annotators from 10 to 100. You want to run multiple projects in parallel. However, with traditional methods, environment replication and management are complex, often ending without successful scaling.&lt;/p&gt;

&lt;h2&gt;
  
  
  Realistic Comparison of Label Studio Deployment Methods
&lt;/h2&gt;

&lt;p&gt;What options exist for deploying Label Studio? Based on our experience, let's compare each method in detail.&lt;/p&gt;

&lt;h3&gt;
  
  
  Deployment Method Comparison
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Deployment Method&lt;/th&gt;
&lt;th&gt;Setup Time&lt;/th&gt;
&lt;th&gt;Operational Load&lt;/th&gt;
&lt;th&gt;Scalability&lt;/th&gt;
&lt;th&gt;Cost Efficiency&lt;/th&gt;
&lt;th&gt;Security&lt;/th&gt;
&lt;th&gt;Use Case&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Local Docker&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;10 min&lt;/td&gt;
&lt;td&gt;Low&lt;/td&gt;
&lt;td&gt;✗&lt;/td&gt;
&lt;td&gt;✗&lt;/td&gt;
&lt;td&gt;△&lt;/td&gt;
&lt;td&gt;Personal testing&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Manual EC2&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;2-3 days&lt;/td&gt;
&lt;td&gt;High&lt;/td&gt;
&lt;td&gt;△&lt;/td&gt;
&lt;td&gt;△&lt;/td&gt;
&lt;td&gt;○&lt;/td&gt;
&lt;td&gt;Small teams&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;ECS/Fargate&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;1-2 days&lt;/td&gt;
&lt;td&gt;Medium&lt;/td&gt;
&lt;td&gt;○&lt;/td&gt;
&lt;td&gt;△&lt;/td&gt;
&lt;td&gt;○&lt;/td&gt;
&lt;td&gt;Medium scale&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Kubernetes&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;3-5 days&lt;/td&gt;
&lt;td&gt;High&lt;/td&gt;
&lt;td&gt;◎&lt;/td&gt;
&lt;td&gt;△&lt;/td&gt;
&lt;td&gt;◎&lt;/td&gt;
&lt;td&gt;Large scale&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Our Module (AppRunner)&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;30 min&lt;/td&gt;
&lt;td&gt;Low&lt;/td&gt;
&lt;td&gt;◎&lt;/td&gt;
&lt;td&gt;◎&lt;/td&gt;
&lt;td&gt;○&lt;/td&gt;
&lt;td&gt;R&amp;amp;D projects&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;h3&gt;
  
  
  Detailed Analysis of Each Method
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Local Docker Compose&lt;/strong&gt; is the easiest way to start. Following official documentation, you can launch it in 10 minutes. However, it can't be shared with teams and doesn't guarantee data persistence. Consider it only for personal initial validation.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Manual EC2 setup&lt;/strong&gt; is the first choice for many companies. While offering complete control, it has these challenges:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Extensive work including Nginx configuration, SSL certificate management, database setup&lt;/li&gt;
&lt;li&gt;Person-dependent setup procedures&lt;/li&gt;
&lt;li&gt;Regular OS updates and security patches&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;ECS/Fargate&lt;/strong&gt; is a good option for teams familiar with container technology. However, initial setup complexity cannot be ignored:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Task definition creation&lt;/li&gt;
&lt;li&gt;Load balancer configuration&lt;/li&gt;
&lt;li&gt;Service discovery setup&lt;/li&gt;
&lt;li&gt;Network mode selection&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Kubernetes&lt;/strong&gt; is the most flexible and scalable option, but also has the highest learning cost and operational overhead. Unless you're a large organization with a dedicated SRE team, it's likely over-engineering.&lt;/p&gt;

&lt;h2&gt;
  
  
  Our Solution: AWS AppRunner + Terraform
&lt;/h2&gt;

&lt;p&gt;To solve these challenges, we chose a new approach. By combining AWS AppRunner with Terraform, we achieved both "simplicity" and "scalability."&lt;/p&gt;

&lt;h3&gt;
  
  
  Why AppRunner?
&lt;/h3&gt;

&lt;p&gt;AWS AppRunner is a fully managed service for container applications. These features make it ideal for R&amp;amp;D projects:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Auto-scaling&lt;/strong&gt;: Automatically scales up/down based on usage&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Zero operational overhead&lt;/strong&gt;: AWS manages OS updates, security patches&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Pay-per-use&lt;/strong&gt;: Pay only for what you use, minimizing idle costs&lt;/li&gt;
&lt;/ol&gt;

&lt;h3&gt;
  
  
  The Value of Terraform Modules
&lt;/h3&gt;

&lt;p&gt;Following Infrastructure as Code principles, by providing it as a reusable module:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight hcl"&gt;&lt;code&gt;&lt;span class="nx"&gt;module&lt;/span&gt; &lt;span class="s2"&gt;"label_studio"&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nx"&gt;source&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"tied-inc/label-studio-on-apprunner/aws"&lt;/span&gt;

  &lt;span class="nx"&gt;vpc_id&lt;/span&gt;               &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;data&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;aws_vpc&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;main&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;
  &lt;span class="nx"&gt;private_subnet_ids&lt;/span&gt;   &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;data&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;aws_subnets&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;private&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;ids&lt;/span&gt;
  &lt;span class="nx"&gt;database_subnet_ids&lt;/span&gt;  &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;data&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;aws_subnets&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;database&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;ids&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;With just a few lines of code, you can build production-level Label Studio.&lt;/p&gt;

&lt;h2&gt;
  
  
  Business Impact: Effects in Numbers
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Quantitative Results
&lt;/h3&gt;

&lt;p&gt;Measured results from actual projects:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Infrastructure setup time&lt;/strong&gt;: 3 days → 30 minutes (&lt;strong&gt;98% reduction&lt;/strong&gt;)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Monthly operational hours&lt;/strong&gt;: 40 hours → 2 hours (&lt;strong&gt;95% reduction&lt;/strong&gt;)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Time to project start&lt;/strong&gt;: 2 weeks → Same day&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Technical Advantages
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Secure Design
&lt;/h3&gt;

&lt;p&gt;This module is designed with enterprise-level security in mind:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Private communication within VPC&lt;/li&gt;
&lt;li&gt;Secure data management with RDS Aurora Serverless v2&lt;/li&gt;
&lt;li&gt;Secret management via AWS Systems Manager&lt;/li&gt;
&lt;li&gt;Principle of least privilege through IAM roles&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Compatibility with Existing Environments
&lt;/h3&gt;

&lt;p&gt;Many companies already have environments built on AWS. This module is designed to seamlessly integrate with such existing environments:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight hcl"&gt;&lt;code&gt;&lt;span class="nx"&gt;module&lt;/span&gt; &lt;span class="s2"&gt;"label_studio"&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nx"&gt;source&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"tied-inc/label-studio-on-apprunner/aws"&lt;/span&gt;

  &lt;span class="c1"&gt;# Specify existing VPC and subnets&lt;/span&gt;
  &lt;span class="nx"&gt;vpc_id&lt;/span&gt;               &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;var&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;existing_vpc_id&lt;/span&gt;
  &lt;span class="nx"&gt;private_subnet_ids&lt;/span&gt;   &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;var&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;existing_private_subnets&lt;/span&gt;

  &lt;span class="c1"&gt;# Customize specs as needed&lt;/span&gt;
  &lt;span class="nx"&gt;cpu&lt;/span&gt;    &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"1 vCPU"&lt;/span&gt;
  &lt;span class="nx"&gt;memory&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"2 GB"&lt;/span&gt;

  &lt;span class="c1"&gt;# Use existing domain&lt;/span&gt;
  &lt;span class="nx"&gt;custom_domain&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"label.example.com"&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Teams That Should Consider Adoption
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Ideal for These Teams
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Running &lt;strong&gt;multiple R&amp;amp;D projects in parallel&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Machine learning engineer-centric&lt;/strong&gt; team composition&lt;/li&gt;
&lt;li&gt;Emphasizing &lt;strong&gt;agile&lt;/strong&gt; project management&lt;/li&gt;
&lt;li&gt;Aiming for &lt;strong&gt;rapid transition from POC to production&lt;/strong&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ROI Perspective
&lt;/h3&gt;

&lt;p&gt;Initial investment is nearly zero. AppRunner's pay-per-use model allows starting small and scaling as needed. Meanwhile, costs you can reduce include:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Engineer hour reduction: 40 hours/month × $100/hour = &lt;strong&gt;$4,000/month savings&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Avoiding opportunity loss&lt;/strong&gt; through faster time to market&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Improved engineer motivation&lt;/strong&gt; through reduced operational burden&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Conclusion: Toward Data-Driven R&amp;amp;D
&lt;/h2&gt;

&lt;p&gt;The Terraform module introduced in this article is not just an infrastructure automation tool. It's an "enabler" that allows R&amp;amp;D teams to focus on their original value creation.&lt;/p&gt;

&lt;p&gt;From "infrastructure building" to "value creation."&lt;br&gt;
From "person-dependent operations" to "democratized data creation."&lt;br&gt;
From "slow R&amp;amp;D cycles" to "rapid iterations."&lt;/p&gt;

&lt;p&gt;This paradigm shift is the essence of data-driven R&amp;amp;D.&lt;/p&gt;

&lt;h3&gt;
  
  
  Next Steps
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;Access our &lt;a href="https://github.com/tied-inc/terraform-aws-label-studio-on-apprunner" rel="noopener noreferrer"&gt;GitHub repository&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Follow the README to set up your environment in 30 minutes&lt;/li&gt;
&lt;li&gt;Experience the value in your actual projects&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;At Tied, inc., we hope that through this module, more R&amp;amp;D teams can create value rapidly. We look forward to your feedback and contributions.&lt;/p&gt;

&lt;p&gt;Let's end the time spent struggling with data labeling environment setup. Use that time for creating real innovation.&lt;/p&gt;




&lt;p&gt;&lt;em&gt;Tied, inc. is a professional team that supports R&amp;amp;D project success through technology. Beyond this module, we provide MLOps implementation support and data strategy consulting.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>labelstudio</category>
      <category>terraform</category>
      <category>apprunner</category>
    </item>
    <item>
      <title>Anyone Can Create It! Building a Writing Style Analysis-Based AI Writing Assistant with ChatGPT</title>
      <dc:creator>hayata-yamamoto</dc:creator>
      <pubDate>Fri, 06 Jun 2025 01:10:54 +0000</pubDate>
      <link>https://dev.to/hayata_yamamoto/anyone-can-create-it-building-a-writing-style-analysis-based-ai-writing-assistant-with-chatgpt-3fi2</link>
      <guid>https://dev.to/hayata_yamamoto/anyone-can-create-it-building-a-writing-style-analysis-based-ai-writing-assistant-with-chatgpt-3fi2</guid>
      <description>&lt;h2&gt;
  
  
  Introduction
&lt;/h2&gt;

&lt;p&gt;Writing is often a time-consuming and labor-intensive task.&lt;br&gt;
Especially when writing articles regularly, starting from scratch each time can feel burdensome.&lt;br&gt;
I often think "I have things I want to write about, but organizing my thoughts is challenging" or "I wish I could quickly work out the framework from an outline," and I've long felt this was an issue.&lt;/p&gt;

&lt;p&gt;That said, the recent progress in ChatGPT has been remarkable.&lt;br&gt;
It can now generate large amounts of text with just a little prompting, and sometimes it even remembers and utilizes your prompts in memory.&lt;br&gt;
Given this, AI-powered text generation is certainly one solution.&lt;br&gt;
However, I faced the challenge that when the generated text differed from my writing style, it took time to revise, ultimately reducing efficiency.&lt;/p&gt;

&lt;p&gt;This article introduces a method for having ChatGPT analyze the characteristics of your writing and using those results to build a customized AI writing assistant.&lt;br&gt;
This approach makes it possible to efficiently generate text that closely matches your writing style.&lt;/p&gt;

&lt;p&gt;The process consists mainly of the following two steps:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Writing style analysis using Deep Research&lt;/li&gt;
&lt;li&gt;Building a dedicated AI writing assistant using GPTs&lt;/li&gt;
&lt;/ol&gt;
&lt;h2&gt;
  
  
  Results and Analysis of What I Created
&lt;/h2&gt;

&lt;p&gt;That said, it wouldn't be interesting to just go through the procedures step by step. Let me first share what it looks like. When I give the topic "Anyone Can Create It! Building a Writing Style Analysis-Based AI Writing Assistant with ChatGPT" to the GPT I created for this article, it produces the following:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Understood!&lt;br&gt;
I'll structure a technical blog article with the following theme:&lt;/p&gt;


&lt;h2&gt;
  
  
  Title
&lt;/h2&gt;

&lt;p&gt;Anyone Can Create It! Building a Writing Style Analysis-Based AI Writing Assistant with ChatGPT&lt;/p&gt;


&lt;h2&gt;
  
  
  Introduction: Purpose and Objective
&lt;/h2&gt;

&lt;p&gt;Have you ever felt anxious when writing technical articles, wondering "Am I maintaining consistency in my writing style?"&lt;br&gt;
I have. Seriously, multiple times. Especially when writing team blogs, different writers tend to create varying atmospheres, leading to a certain "sense of discord."&lt;/p&gt;

&lt;p&gt;This article introduces how to build a writing assistant that can mimic your own or others' writing styles by combining ChatGPT with writing style analysis.&lt;/p&gt;

&lt;p&gt;It's just these 3 simple steps!&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Extract writing style characteristics based on your own articles&lt;/li&gt;
&lt;li&gt;Have ChatGPT learn that style&lt;/li&gt;
&lt;li&gt;Actually get writing assistance&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;It's so easy you'll feel like "I might be a genius..." so please stick with me to the end!&lt;/p&gt;


&lt;h2&gt;
  
  
  Step 1: "Verbalize" Your Writing Style
&lt;/h2&gt;

&lt;p&gt;The first thing to do is verbalize "What is my writing style like?"&lt;br&gt;
This involves reading through several of your past articles and identifying common patterns.&lt;/p&gt;

&lt;p&gt;The checkpoints are like this:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Vocabulary: Casual? Formal? Do you use expressions like "seriously" or "quickly"?&lt;/li&gt;
&lt;li&gt;Grammar: Consistent polite language? Length of sentences?&lt;/li&gt;
&lt;li&gt;Structure: Is it in the order of introduction → background → method → conclusion?&lt;/li&gt;
&lt;li&gt;Tone: Are you speaking to readers? Or explanatory style?&lt;/li&gt;
&lt;li&gt;Humor: How much jokes and self-deprecating humor do you include?&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;You could do this analysis manually, but it's much easier to rely on GPT.&lt;br&gt;
For example, create a prompt like this and feed it your articles:&lt;/p&gt;


&lt;pre class="highlight markdown"&gt;&lt;code&gt;You are a professional technical article writer. Please read the following text and analyze characteristics such as vocabulary, grammar, tone, logical structure, and humor, then output a "list of writing style characteristics typical of this person" in Markdown format.

&lt;/code&gt;&lt;/pre&gt;



&lt;h2&gt;
  
  
  Step 2: Have ChatGPT Learn the Writing Style
&lt;/h2&gt;

&lt;p&gt;Once you've analyzed the writing style, next you input that into ChatGPT.&lt;br&gt;
What's important here is clearly stating "what style you want it to write in."&lt;/p&gt;

&lt;p&gt;As an example, create a prompt like this:&lt;/p&gt;


&lt;pre class="highlight markdown"&gt;&lt;code&gt;You are a technical blog writer AI. Please write articles about web technology following the writing style guidelines below.

&lt;span class="gu"&gt;## Writing Style Guidelines&lt;/span&gt;
&lt;span class="p"&gt;-&lt;/span&gt; Vocabulary: Use plain Japanese + technical terms (React, AWS, etc.) accurately
&lt;span class="p"&gt;-&lt;/span&gt; Grammar: Polite form, medium-length sentences, create rhythm with commas
&lt;span class="p"&gt;-&lt;/span&gt; Tone: Polite but casual, use questions and empathy
&lt;span class="p"&gt;-&lt;/span&gt; Logical development: Show purpose in introduction, organize with headings, include specific examples and supplements
&lt;span class="p"&gt;-&lt;/span&gt; Humor: Moderate light jokes appropriately

Theme: How to create a writing style unification tool using ChatGPT

&lt;/code&gt;&lt;/pre&gt;


&lt;p&gt;In this state, if you ask "write the main text," it will churn out articles that seem just right. Really, what a convenient era we live in.&lt;/p&gt;


&lt;h2&gt;
  
  
  Step 3: Actually Try Writing
&lt;/h2&gt;

&lt;p&gt;Finally, it's actual writing.&lt;br&gt;
Since GPT reproduces the tone and style you usually write in, it feels like "another version of yourself" is creating the manuscript.&lt;/p&gt;

&lt;p&gt;For example, even with instructions like "write an article about React state management in your usual style," if you've properly taught it the writing style analysis, it will finish quite nicely.&lt;/p&gt;

&lt;p&gt;Then you just need to fine-tune it yourself.&lt;br&gt;
With adjustments like "a bit too many jokes..." or "let's explain this part seriously," you can easily complete an article that's truly your own!&lt;/p&gt;


&lt;h2&gt;
  
  
  Conclusion: Create Your "Alter Ego" with GPT
&lt;/h2&gt;

&lt;p&gt;So this time I introduced how to create an AI writing assistant using ChatGPT and writing style analysis.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Analyze your writing style from past articles&lt;/li&gt;
&lt;li&gt;Have ChatGPT learn the style&lt;/li&gt;
&lt;li&gt;Create articles that sound like you together!&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Using this method, "team blogs with consistency" isn't just a dream, and it can also be applied to writer training.&lt;/p&gt;

&lt;p&gt;Please try nurturing your own "alter ego AI writer" too!&lt;/p&gt;



&lt;p&gt;If you'd like, I can output this content in Markdown, Word, or other formats, or create a more technically detailed version!&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h3&gt;
  
  
  How Do I Feel Looking at This Objectively?
&lt;/h3&gt;

&lt;p&gt;⭕️ Good Points&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;I feel it's reached a state where it writes things I would likely write&lt;/li&gt;
&lt;li&gt;The part "I have. Seriously, multiple times. Especially when writing team blogs, different writers tend to create varying atmospheres, leading to a certain 'sense of discord'" properly presents challenges to readers in a way that seems like me. It captures my tendency to talk at length about the background of the issues I'm discussing.&lt;/li&gt;
&lt;li&gt;The article structure creates a proper common structure. The parts where I list the flow of the discussion in the introduction and state conclusions are like me.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;❌ Areas for Improvement&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;In the part discussing the background of challenges, it uses the expression "nandesyone" (a casual way of addressing others), but "nandesyone" goes against my preferences. I would address readers with "narimasenga?" instead. Expression skills need improvement.&lt;/li&gt;
&lt;li&gt;There's a tendency to write somewhat too casual text. It gives off a frivolous impression. Compared to when I write, there seems to be more colloquial language. In my case, while I often use words like "seriously" or "really," I tend to limit their use to introductions and try to balance the overall tone of the text.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2&gt;
  
  
  Step 1: Writing Style Analysis Using Deep Research
&lt;/h2&gt;

&lt;p&gt;In the first step, I input data from previously written articles and content into Deep Research to analyze writing tendencies.&lt;/p&gt;
&lt;h3&gt;
  
  
  Reasons for Selecting Deep Research
&lt;/h3&gt;

&lt;p&gt;There are multiple approaches to analyzing text characteristics:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;RAG method: Use all articles as data as-is and have AI search them&lt;/li&gt;
&lt;li&gt;Manual analysis: Extract text characteristics yourself&lt;/li&gt;
&lt;li&gt;Deep Research: AI systematically analyzes text characteristics&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;While the RAG method is effective for reproducing individual expressions and styles, it has limitations in extracting the essence of writing style and characteristics of logical structure.&lt;/p&gt;

&lt;p&gt;I chose Deep Research because it can abstract and organize text, systematically analyzing the tone and expression methods of writing. By organizing structural patterns, tone, and frequent word patterns in writing, I can objectively grasp the characteristics of writing style.&lt;/p&gt;
&lt;h3&gt;
  
  
  Implementation Procedure
&lt;/h3&gt;
&lt;h3&gt;
  
  
  1. Analysis Request to Deep Research
&lt;/h3&gt;

&lt;p&gt;I prepared the following data as analysis targets:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Previously written technical articles (Markdown format)&lt;/li&gt;
&lt;li&gt;Blog and note technical memos&lt;/li&gt;
&lt;li&gt;Technology-related social media posts&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The following items were extracted as analysis results:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Analysis Item&lt;/th&gt;
&lt;th&gt;Content&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Vocabulary characteristics&lt;/td&gt;
&lt;td&gt;Balance of technical terms and casual expressions&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Grammar structure&lt;/td&gt;
&lt;td&gt;Sentence length, line break frequency, punctuation usage&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Tone&lt;/td&gt;
&lt;td&gt;Ratio of polite language to casual expressions, frequency of humor insertion&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Logical development&lt;/td&gt;
&lt;td&gt;Article structure, paragraph flow, heading methods&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Categories&lt;/td&gt;
&lt;td&gt;Web development, cloud technology, CI/CD, etc.&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;
&lt;h3&gt;
  
  
  2. Organizing and Utilizing Analysis Results
&lt;/h3&gt;

&lt;p&gt;After obtaining analysis results, it's important to organize them into a practical form. I proceeded with the following steps:&lt;/p&gt;

&lt;p&gt;First, I compiled the Deep Research analysis results into a text file and created detailed reports for each item. For example, regarding the characteristic "casual but accurate information," I identified specific expression patterns and sentence structures.&lt;/p&gt;

&lt;p&gt;Example analysis results:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Writing uses casual expressions while emphasizing information accuracy&lt;/li&gt;
&lt;li&gt;Tends to include appropriate explanations for technical terms&lt;/li&gt;
&lt;li&gt;Humor is inserted moderately, according to context&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Next, I considered a method to utilize this detailed report in two stages:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;graph TD
    A[Analysis Results] --&amp;gt; B[Create Detailed Report]
    B --&amp;gt; C[Two-Stage Utilization Strategy]
    C --&amp;gt; D[Instruction Part]
    C --&amp;gt; E[Knowledge Base Part]
    D --&amp;gt; F[GPTs System Prompt]
    E --&amp;gt; G[Reference Knowledge]

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;Instruction part: Incorporate basic writing style characteristics (sentence length, conjunction usage, etc.) into GPTs system prompts&lt;/li&gt;
&lt;li&gt;Knowledge base part: Save detailed characteristics like technical term explanation styles and specific example methods as reference knowledge&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;I adopted this two-stage approach because the knowledge needed varies depending on the state of the writing. For example, when explaining technical parts, I can reference "technical term explanation style" knowledge, and for conclusion parts, I can reference "summary pattern" knowledge.&lt;/p&gt;

&lt;p&gt;This allowed me to build an assistant that not only mimics writing style but can also utilize appropriate knowledge according to the purpose and situation of the writing.&lt;/p&gt;

&lt;h2&gt;
  
  
  Step 2: Implementation of Writing Style Reproduction Using GPTs
&lt;/h2&gt;

&lt;p&gt;Using the analysis results obtained from Deep Research, I set custom instructions in ChatGPT's GPTs to attempt writing style reproduction.&lt;/p&gt;

&lt;h3&gt;
  
  
  Reasons for Selecting GPTs
&lt;/h3&gt;

&lt;p&gt;The main reason I chose GPTs as an approach for reproducing writing style is that once you set system prompts, you can continue using them under the same conditions.&lt;/p&gt;

&lt;p&gt;Compared to manually setting prompts each time, GPTs has the advantage of maintaining consistent writing style more easily and efficiently generating text.&lt;/p&gt;

&lt;h3&gt;
  
  
  Challenges in Construction
&lt;/h3&gt;

&lt;p&gt;Several challenges became apparent during the GPTs implementation process:&lt;/p&gt;

&lt;h3&gt;
  
  
  1. Lack of Feedback Learning Function
&lt;/h3&gt;

&lt;p&gt;Since GPTs lacks a function to learn from feedback given during text generation, the same corrections need to be made repeatedly. This becomes an efficiency challenge for long-term use.&lt;/p&gt;

&lt;h3&gt;
  
  
  2. Absence of Self-Learning Function
&lt;/h3&gt;

&lt;p&gt;While some autonomous agents have functions to accumulate feedback and apply it to future generation, GPTs lacks such functionality. A different approach might be necessary to achieve more advanced learning processes.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Claude AI: Has custom prompt saving functionality&lt;/li&gt;
&lt;li&gt;Perplexity: Can combine information search with text generation&lt;/li&gt;
&lt;li&gt;Autonomous agents: Have feedback learning functions but setup is more complex&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  GPTs Configuration Method
&lt;/h3&gt;

&lt;p&gt;I'll introduce the configuration method for the AI writing assistant I actually built. You can create GPTs that reproduce your writing style following these steps. The main tasks are:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Create GPTs&lt;/li&gt;
&lt;li&gt;Set basic information&lt;/li&gt;
&lt;li&gt;Set system prompts

&lt;ul&gt;
&lt;li&gt;Input Deep Research analysis results directly in the "Instructions" tab&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Add knowledge:

&lt;ul&gt;
&lt;li&gt;Attach files with detailed descriptions of each analysis item from Deep Research&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Set capabilities

&lt;ul&gt;
&lt;li&gt;As needed. I allow everything&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Test and adjust&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;The situation during article writing. After creating a framework with GPTs, I can improve content by inputting it into tools like Cursor and fine-tuning the text in detail.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;You are a writer who creates technical blogs based on the following instruction information.&lt;/p&gt;


&lt;h3&gt;
  
  
  1. Vocabulary Characteristics
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Balance of simplicity and expertise&lt;/li&gt;
&lt;li&gt;Based on everyday language, accurately use technical terms (e.g., React, AWS, Lambda, Docker, GraphQL, etc.) where necessary.&lt;/li&gt;
&lt;li&gt;Avoid difficult kanji or verbose expressions, and strive for expressions that readers can easily understand.&lt;/li&gt;
&lt;li&gt;Casual expressions&lt;/li&gt;
&lt;li&gt;Appropriately incorporate casual expressions like "quickly" and "seriously" to create familiarity.&lt;/li&gt;
&lt;li&gt;Don't use original coined words or excessive abbreviations; naturally blend existing technical terms.&lt;/li&gt;
&lt;/ul&gt;


&lt;h3&gt;
  
  
  2. Grammar Structure
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Basically unified with polite language&lt;/li&gt;
&lt;li&gt;Compose sentences in "desu/masu" style, speaking to readers politely and familiarly.&lt;/li&gt;
&lt;li&gt;Sentence rhythm and structure&lt;/li&gt;
&lt;li&gt;Aim for medium-length sentences, appropriately separated by commas "、" and periods "。"&lt;/li&gt;
&lt;li&gt;Weave together short and long sentences, using short sentences for important parts to create emphasis.&lt;/li&gt;
&lt;li&gt;Use line breaks, paragraphs, and bullet points as needed to make text visually readable.&lt;/li&gt;
&lt;li&gt;Effectively use parentheses (e.g., "(In my case...)") to convey supplementary explanations and emotions.&lt;/li&gt;
&lt;/ul&gt;


&lt;h3&gt;
  
  
  3. Tone
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Friendly yet moderate way of speaking&lt;/li&gt;
&lt;li&gt;Incorporate expressions that directly address readers (e.g., "Have you ever felt...?").&lt;/li&gt;
&lt;li&gt;Honestly convey personal experiences and opinions while maintaining a humble attitude rather than being condescending.&lt;/li&gt;
&lt;li&gt;Conscious of dialogue with readers&lt;/li&gt;
&lt;li&gt;Include greetings and introductory text to readers at the beginning.&lt;/li&gt;
&lt;li&gt;Appropriately scatter expressions of questions and empathy throughout the article (e.g., "Don't you think...?" "I think...").&lt;/li&gt;
&lt;/ul&gt;


&lt;h3&gt;
  
  
  4. Logical Development
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Clear structure and step-by-step explanation&lt;/li&gt;
&lt;li&gt;First clearly present the theme and purpose at the beginning of the article, showing an overview of the whole.&lt;/li&gt;
&lt;li&gt;Set headings and subtitles for each section to organize points.&lt;/li&gt;
&lt;li&gt;In each section, include specific examples (personal experiences, code snippets, data, charts, etc.) and carefully explain background and reasons.&lt;/li&gt;
&lt;li&gt;Overall flow&lt;/li&gt;
&lt;li&gt;State the purpose at the beginning with "This article introduces..." then explain step by step "why..." and "how to..."&lt;/li&gt;
&lt;li&gt;At the end of the article, include a summary or "conclusion" with main points and author's thoughts.&lt;/li&gt;
&lt;/ul&gt;


&lt;h3&gt;
  
  
  5. Use of Humor
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Moderate humor insertion&lt;/li&gt;
&lt;li&gt;Include light jokes and self-deprecating humor that readers can laugh at within technical content.&lt;/li&gt;
&lt;li&gt;Example: Comments like "I might be a genius" or honest feelings like "...is seriously annoying" to soften stiffness.&lt;/li&gt;
&lt;li&gt;Natural laugh production&lt;/li&gt;
&lt;li&gt;Casually insert jokes in gaps in the text, being careful not to disrupt the overall tone.&lt;/li&gt;
&lt;li&gt;Use humor as spice to reinforce the article's main point, ensuring it doesn't compromise content accuracy or persuasiveness.&lt;/li&gt;
&lt;/ul&gt;


&lt;h3&gt;
  
  
  6. Writing Content and Category Trends
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Specialized in technical articles&lt;/li&gt;
&lt;li&gt;Focus mainly on practical technologies like web service development, cloud technology, serverless, CI/CD, test automation.&lt;/li&gt;
&lt;li&gt;Target readers are field engineers (intermediate to advanced level), developing content that assumes specialized knowledge.&lt;/li&gt;
&lt;li&gt;Practical and specific information provision&lt;/li&gt;
&lt;li&gt;Include experiences from your own company, specific cases, and code examples for persuasive explanations.&lt;/li&gt;
&lt;li&gt;When necessary, present related official documentation and reference links to guide to detailed information.&lt;/li&gt;
&lt;/ul&gt;


&lt;h3&gt;
  
  
  Comprehensive Methods for Imitation
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;Create a solid article structure&lt;/li&gt;
&lt;li&gt;Clearly present theme and purpose at the beginning, organize points with headings and bullet points.&lt;/li&gt;
&lt;li&gt;Include specific examples and personal experiences in each section, ensuring logical flow throughout.&lt;/li&gt;
&lt;li&gt;Be conscious of writing style that relates to readers&lt;/li&gt;
&lt;li&gt;Write in polite "desu/masu" style but occasionally incorporate casual expressions and humor to create familiarity.&lt;/li&gt;
&lt;li&gt;Use phrases that show questions and empathy toward readers to create bidirectional communication.&lt;/li&gt;
&lt;li&gt;Maintain balance between expertise and clarity&lt;/li&gt;
&lt;li&gt;While accurately using technical terms, add necessary background explanations and supplements to choose expressions understandable to beginners.&lt;/li&gt;
&lt;li&gt;To show depth of specialized knowledge, specifically describe your own experiences and actual cases.&lt;/li&gt;
&lt;li&gt;Devices to enhance rhythm and visibility&lt;/li&gt;
&lt;li&gt;Give each sentence rhythm and create readable sentence structure.&lt;/li&gt;
&lt;li&gt;Use appropriate line breaks, paragraphs, and bullet points to create visually organized text.&lt;/li&gt;
&lt;li&gt;Maintain overall consistency&lt;/li&gt;
&lt;li&gt;Maintain consistency in tone and writing style to create a cohesive article overall.&lt;/li&gt;
&lt;li&gt;Unify expressions and vocabulary used in the text, avoiding sudden tone changes.&lt;/li&gt;
&lt;/ol&gt;
&lt;/blockquote&gt;

&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;This article introduced a method for analyzing your writing style and building an AI writing assistant that reproduces it. The main steps are as follows:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Writing style analysis using Deep Research&lt;/li&gt;
&lt;li&gt;Collection and analysis of past writing data&lt;/li&gt;
&lt;li&gt;Creating detailed reports of analysis results&lt;/li&gt;
&lt;li&gt;Building a dedicated AI writing assistant using GPTs&lt;/li&gt;
&lt;li&gt;Incorporating basic writing style characteristics into system prompts&lt;/li&gt;
&lt;li&gt;Creating knowledge bases of detailed characteristics&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Future prospects include utilizing AI tools that can learn from feedback and introducing mechanisms that automatically incorporate trends, making it possible to build more advanced writing support systems.&lt;/p&gt;

&lt;p&gt;This approach makes it possible to achieve both improved efficiency and quality in writing.&lt;/p&gt;

</description>
      <category>chatgpt</category>
    </item>
    <item>
      <title>Implementing Email Services with Nest.js and Google Cloud</title>
      <dc:creator>hayata-yamamoto</dc:creator>
      <pubDate>Mon, 07 Oct 2024 00:43:36 +0000</pubDate>
      <link>https://dev.to/hayata_yamamoto/implementing-email-services-with-nestjs-and-google-cloud-275h</link>
      <guid>https://dev.to/hayata_yamamoto/implementing-email-services-with-nestjs-and-google-cloud-275h</guid>
      <description>&lt;p&gt;Email functionality is a staple in many applications, but with so many options available, it can be a bit overwhelming, right? There are various email delivery services, some frameworks have built-in email capabilities, and then there are security considerations and monitoring to think about. It's quite a lot to consider!&lt;/p&gt;

&lt;p&gt;In this post, I'll share a recent implementation of an email delivery feature using Nest.js and Google Cloud. I'll walk you through the documentation we consulted during our research and provide some insights into the implementation details. My hope is that this will be helpful for those of you working with Nest.js backends.&lt;/p&gt;

&lt;h2&gt;
  
  
  Our Final Setup
&lt;/h2&gt;

&lt;p&gt;Here's what we ultimately decided on:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;We used &lt;a href="https://sendgrid.com/en-us" rel="noopener noreferrer"&gt;SendGrid&lt;/a&gt; as our email delivery service.&lt;/li&gt;
&lt;li&gt;We created an injectable module for email delivery using &lt;a href="https://github.com/nest-modules/mailer" rel="noopener noreferrer"&gt;nest-modules/mailer&lt;/a&gt;, allowing us to use dependency injection where needed.&lt;/li&gt;
&lt;li&gt;We wrote email templates using Handlebars, which allows us to pass necessary variables when calling the template.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  The Technology Selection Process
&lt;/h2&gt;

&lt;p&gt;We had already decided to use Nest.js and Google Cloud, so our investigation focused on the following:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Determining how to best provide email functionality within Nest.js&lt;/li&gt;
&lt;li&gt;Identifying email delivery options that would work well (and easily) with Google Cloud&lt;/li&gt;
&lt;li&gt;Deciding on a template engine for our emails (if necessary)&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;By clarifying these points, we were able to select an email delivery solution that was compatible with both Nest.js and Google Cloud.&lt;/p&gt;

&lt;h3&gt;
  
  
  How to Implement Email Functionality in Nest.js
&lt;/h3&gt;

&lt;p&gt;Our team had already done some preliminary research, and we were leaning towards using nest-module/mailer. While we say "research," we essentially decided to proceed with nest-modules/mailer as our base implementation.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://github.com/nest-modules/mailer" rel="noopener noreferrer"&gt;https://github.com/nest-modules/mailer&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;For example, here are some similar articles we found:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://zenn.dev/yuu104/articles/8b8d7363b5dd5f" rel="noopener noreferrer"&gt;https://zenn.dev/yuu104/articles/8b8d7363b5dd5f&lt;/a&gt;&lt;br&gt;
&lt;a href="https://myprg.dev/posts/nestjs-jsx-mail" rel="noopener noreferrer"&gt;https://myprg.dev/posts/nestjs-jsx-mail&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;We also found other approaches, including creating custom modules that call SDKs directly:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://zenn.dev/doshirote/articles/299796eec8ccae#nestjs%E3%81%A7%E5%AE%9F%E8%A3%85" rel="noopener noreferrer"&gt;https://zenn.dev/doshirote/articles/299796eec8ccae#nestjs%E3%81%A7%E5%AE%9F%E8%A3%85&lt;/a&gt;&lt;br&gt;
&lt;a href="https://iwaking.com/blog/how-to-send-emails-using-ejs-template-engine-with-nest-js" rel="noopener noreferrer"&gt;https://iwaking.com/blog/how-to-send-emails-using-ejs-template-engine-with-nest-js&lt;/a&gt;&lt;/p&gt;
&lt;h3&gt;
  
  
  Email Templates
&lt;/h3&gt;

&lt;p&gt;&lt;a href="https://github.com/nest-modules/mailer" rel="noopener noreferrer"&gt;nest-module/mailer&lt;/a&gt; supports three libraries for templating:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://pugjs.org/api/getting-started.html" rel="noopener noreferrer"&gt;Pug&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://handlebarsjs.com/" rel="noopener noreferrer"&gt;Handlebars&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://ejs.co/" rel="noopener noreferrer"&gt;EJS&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;After considering the options (referencing articles like &lt;a href="https://gist.github.com/kazuma1989/e1a443b2ee28f012f0659594c302aa32" rel="noopener noreferrer"&gt;this one&lt;/a&gt;), we chose Handlebars. While Pug was appealing, we liked that Handlebars is readable to anyone who knows HTML, and its similarity to other template engines like Jinja makes it accessible to developers coming from other languages.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://nest-modules.github.io/mailer/docs/mailer.html#configuration" rel="noopener noreferrer"&gt;https://nest-modules.github.io/mailer/docs/mailer.html#configuration&lt;/a&gt;&lt;/p&gt;
&lt;h3&gt;
  
  
  Email Delivery Options in Google Cloud
&lt;/h3&gt;

&lt;p&gt;Google Cloud officially recommends three services for email delivery:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Mailjet: &lt;a href="https://cloud.google.com/compute/docs/tutorials/sending-mail/using-mailjet" rel="noopener noreferrer"&gt;https://cloud.google.com/compute/docs/tutorials/sending-mail/using-mailjet&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Mailgun: &lt;a href="https://cloud.google.com/compute/docs/tutorials/sending-mail/using-mailgun" rel="noopener noreferrer"&gt;https://cloud.google.com/compute/docs/tutorials/sending-mail/using-mailgun&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;SendGrid: &lt;a href="https://cloud.google.com/compute/docs/tutorials/sending-mail/using-sendgrid" rel="noopener noreferrer"&gt;https://cloud.google.com/compute/docs/tutorials/sending-mail/using-sendgrid&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Our Google Cloud stack is quite simple - we're just deploying our application to Cloud Run. We didn't want to add extra configurations or create additional resources for this feature, nor did we want to complicate our operations. After reviewing the documentation:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Mailjet: We'd need to verify how well SMTP configuration within an instance would work with Cloud Run.&lt;/li&gt;
&lt;li&gt;Mailgun: It wasn't clear how well we could replicate the Postfix configuration for using Mailgun as a mail relay in Cloud Run.&lt;/li&gt;
&lt;li&gt;SendGrid: The official documentation suggested we could get started just by installing the SendGrid library.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Given these considerations, SendGrid emerged as our top choice for email delivery.&lt;/p&gt;
&lt;h2&gt;
  
  
  Implementation Details
&lt;/h2&gt;

&lt;p&gt;For a smooth implementation, I recommend following the approach outlined in this article, which covers a typical implementation using nest-modules/mailer:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://notiz.dev/blog/send-emails-with-nestjs" rel="noopener noreferrer"&gt;https://notiz.dev/blog/send-emails-with-nestjs&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Here, I'll explain the additional configuration needed to use SendGrid with nest-module/mailer. To send emails through SendGrid, you need to modify the transport host, port, and auth information in the MailerModule's forRoot definition. This allows nest-module/mailer to use SendGrid for email delivery.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://www.twilio.com/blog/send-smtp-emails-node-js-sendgrid" rel="noopener noreferrer"&gt;https://www.twilio.com/blog/send-smtp-emails-node-js-sendgrid&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Here's an example configuration:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;Module&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@nestjs/common&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;MailerModule&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@nestjs-modules/mailer&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;

&lt;span class="c1"&gt;// This is a workaround for cases where the Handlebars adapter doesn't work properly during Jest execution&lt;/span&gt;
&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;adapter&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;
&lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;JEST_WORKER_ID&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;import&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@nestjs-modules/mailer/dist/adapters/handlebars.adapter&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nf"&gt;then&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="kr"&gt;module&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="nx"&gt;adapter&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;module&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;HandlebarsAdapter&lt;/span&gt;
    &lt;span class="p"&gt;},&lt;/span&gt;
  &lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nd"&gt;Module&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="na"&gt;imports&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
    &lt;span class="nx"&gt;MailerModule&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;forRoot&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
      &lt;span class="c1"&gt;// The transport configuration below is crucial&lt;/span&gt;
      &lt;span class="na"&gt;transport&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="na"&gt;host&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;smtp.sendgrid.net&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="na"&gt;port&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;587&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="na"&gt;auth&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
          &lt;span class="na"&gt;user&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;apikey&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
          &lt;span class="na"&gt;pass&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;SENDGRID_API_KEY&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
      &lt;span class="p"&gt;},&lt;/span&gt;
      &lt;span class="na"&gt;defaults&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="na"&gt;from&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;SENDGRID_FROM_MAIL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="p"&gt;},&lt;/span&gt;
      &lt;span class="na"&gt;template&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;adapter&lt;/span&gt;
        &lt;span class="p"&gt;?&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="na"&gt;dir&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;__dirname&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;/templates&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="nx"&gt;adapter&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="na"&gt;options&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
              &lt;span class="na"&gt;strict&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="p"&gt;},&lt;/span&gt;
          &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;}),&lt;/span&gt;
  &lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="p"&gt;})&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;With this setup, you should be ready to start sending emails using Nest.js, Google Cloud, and SendGrid!&lt;/p&gt;

&lt;p&gt;I hope this guide helps you in implementing your own email delivery system. If you have any questions or run into any issues, feel free to reach out or leave a comment below.&lt;/p&gt;

&lt;p&gt;Happy coding!&lt;/p&gt;

</description>
      <category>nestjs</category>
      <category>typescript</category>
      <category>googlecloud</category>
      <category>sendgrid</category>
    </item>
    <item>
      <title>Striking the Right Balance: Rapid Prototyping with Next.js and Vercel</title>
      <dc:creator>hayata-yamamoto</dc:creator>
      <pubDate>Mon, 07 Oct 2024 00:31:25 +0000</pubDate>
      <link>https://dev.to/hayata_yamamoto/striking-the-right-balance-rapid-prototyping-with-nextjs-and-vercel-4jih</link>
      <guid>https://dev.to/hayata_yamamoto/striking-the-right-balance-rapid-prototyping-with-nextjs-and-vercel-4jih</guid>
      <description>&lt;h2&gt;
  
  
  Background
&lt;/h2&gt;

&lt;p&gt;Before we dive in, let me set the stage with a few key points about my background and approach:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;I'm not particularly strong in frontend development (I've worked on both mobile and web, but I wouldn't call it my forte)&lt;/li&gt;
&lt;li&gt;Backend development is more my speed, but I don't see much value in building a backend at the prototyping stage (the database is crucial, not so much the backend itself)&lt;/li&gt;
&lt;li&gt;I have a decent grasp of ML and AI concepts&lt;/li&gt;
&lt;li&gt;This approach is tailored for small-scale, B2C services that aren't aiming for massive scale right off the bat&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Current Tech Stack
&lt;/h2&gt;

&lt;p&gt;Here's the tech stack I'm currently using for rapid prototyping:&lt;/p&gt;

&lt;h3&gt;
  
  
  Next.js
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Leveraging the App Router

&lt;ul&gt;
&lt;li&gt;Route Handlers for specific external API needs (e.g., Auth0 Triggers)&lt;/li&gt;
&lt;li&gt;Server Actions for most server-side processing, keeping it simple and fast&lt;/li&gt;
&lt;li&gt;Each &lt;code&gt;page.tsx&lt;/code&gt; in the App Router acts somewhat like a ViewModel in MVVM&lt;/li&gt;
&lt;li&gt;Keep &lt;code&gt;page.tsx&lt;/code&gt; as React Server Components (RSC)&lt;/li&gt;
&lt;li&gt;Mix and match Client and Server Components within as needed&lt;/li&gt;
&lt;li&gt;Use &lt;code&gt;router.push&lt;/code&gt; to force state updates across the app&lt;/li&gt;
&lt;li&gt;Utilize &lt;code&gt;useState&lt;/code&gt; for data that changes frequently within a page&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;li&gt;Balancing Server Components, Server Actions, and a touch of Client-side ISR

&lt;ul&gt;
&lt;li&gt;ISR comes in handy for updating data without full page reloads&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Pain point:&lt;/strong&gt; Juggling &lt;code&gt;'use server'&lt;/code&gt; and &lt;code&gt;'use client'&lt;/code&gt; can get confusing. It's easy to lose track of where components are being generated.&lt;/p&gt;

&lt;h3&gt;
  
  
  Vercel
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;One-stop-shop for deployments and databases&lt;/li&gt;
&lt;li&gt;Embracing the "Framework-defined" approach, letting Vercel handle as much as possible

&lt;ul&gt;
&lt;li&gt;Avoiding tools like CDK to reduce onboarding friction and maintain simplicity&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;li&gt;Using v0 for design help

&lt;ul&gt;
&lt;li&gt;Leveraging v0 for Presentational Components&lt;/li&gt;
&lt;li&gt;Integrating with shadcn UI components for a cohesive design system&lt;/li&gt;
&lt;li&gt;Tip: Let v0 handle modifications to &lt;code&gt;/components&lt;/code&gt; for consistency&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Integrations:&lt;/strong&gt;&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Auth0

&lt;ul&gt;
&lt;li&gt;Great for B2C with a generous free tier&lt;/li&gt;
&lt;li&gt;Quick to implement with built-in authentication screens&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Pain point:&lt;/strong&gt; Debugging Triggers can be a nightmare due to limited logging&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Neon (Serverless Postgres)

&lt;ul&gt;
&lt;li&gt;Chose Neon over alternatives like Supabase for better Vercel integration&lt;/li&gt;
&lt;li&gt;Seamless env variable management through Vercel CLI&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Pain point:&lt;/strong&gt; Table management through Vercel's integration page can be cumbersome&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;&lt;strong&gt;Vercel Wishlist:&lt;/strong&gt; Please make Blob Storage generally available soon!&lt;/p&gt;

&lt;h2&gt;
  
  
  Proposed Project Structure
&lt;/h2&gt;

&lt;p&gt;Based on the article &lt;a href="https://zenn.dev/akfm/books/nextjs-basic-principle/viewer/part_2_container_1st_design" rel="noopener noreferrer"&gt;Next.js の基本原則から学ぶシステム設計&lt;/a&gt;, here's a suggested project structure:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;app/
  page.tsx
  products/
    _components/     # components
      XxxXxx.ts     # Data fetching container component (server component) 
      action.ts      # Colocation for server actions
    page.tsx         # UI assembly using _components (server component)
components/          # Presentational components (client components)
  ui/                # shadcn UI components
  xxx-xxx.tsx        # v0 auto-generated components
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This structure aims to separate concerns while maintaining a clear organization that aligns with Next.js App Router conventions and the principles of rapid prototyping.&lt;/p&gt;

&lt;h2&gt;
  
  
  Closing Thoughts
&lt;/h2&gt;

&lt;p&gt;This approach allows for quick iterations without getting bogged down in excessive code or infrastructure management. By leveraging tools like Next.js, Vercel, and their integrations, we can focus on building and validating our ideas rapidly.&lt;/p&gt;

&lt;p&gt;Remember, the goal here is to strike a balance – we're not going full no-code, but we're also not building everything from scratch. This middle ground allows for flexibility, speed, and the ability to scale when needed.&lt;/p&gt;

&lt;p&gt;What are your thoughts on this approach? Have you found other tools or methods that work well for rapid prototyping in the JavaScript ecosystem?&lt;/p&gt;

</description>
      <category>nextjs</category>
      <category>vercel</category>
      <category>typescript</category>
      <category>product</category>
    </item>
    <item>
      <title>Next.js and Prisma: Efficiently Creating Seed Data for Your App</title>
      <dc:creator>hayata-yamamoto</dc:creator>
      <pubDate>Mon, 07 Oct 2024 00:13:30 +0000</pubDate>
      <link>https://dev.to/hayata_yamamoto/nextjs-and-prisma-efficiently-creating-seed-data-for-your-app-1a12</link>
      <guid>https://dev.to/hayata_yamamoto/nextjs-and-prisma-efficiently-creating-seed-data-for-your-app-1a12</guid>
      <description>&lt;p&gt;When developing applications with Next.js and Prisma, one common challenge is creating seed data for your database. This process can be particularly tricky when working with TypeScript and the latest Next.js features like the App Router. In this blog post, we'll explore an effective approach to generating seed data for your Next.js and Prisma-based projects.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Challenge
&lt;/h2&gt;

&lt;p&gt;Our scenario involves:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;A project using TypeScript, Next.js (with App Router), and Prisma&lt;/li&gt;
&lt;li&gt;PostgreSQL as the database&lt;/li&gt;
&lt;li&gt;Using &lt;code&gt;prisma migrate&lt;/code&gt; for database migrations&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The main issue arises when trying to run TypeScript files for seeding data, as the default Next.js configuration doesn't always play nicely with this process.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Solution
&lt;/h2&gt;

&lt;p&gt;After researching various approaches, we found a solution that doesn't compromise Next.js's recommended settings. The key is to create a separate TypeScript configuration file specifically for seeding data.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 1: Set Up the Environment
&lt;/h3&gt;

&lt;p&gt;First, ensure you have &lt;code&gt;ts-node&lt;/code&gt; installed:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;pnpm add &lt;span class="nt"&gt;-D&lt;/span&gt; ts-node
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Step 2: Create a Local TypeScript Configuration
&lt;/h3&gt;

&lt;p&gt;Create a &lt;code&gt;tsconfig.local.json&lt;/code&gt; file in your project root. You can start by copying your existing &lt;code&gt;tsconfig.json&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;cp &lt;/span&gt;tsconfig.json tsconfig.local.json
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then, modify &lt;code&gt;tsconfig.local.json&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"compilerOptions"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;...&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;other&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;options&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;remain&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;same&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"module"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"commonjs"&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Step 3: Update package.json
&lt;/h3&gt;

&lt;p&gt;Add a &lt;code&gt;prisma.seed&lt;/code&gt; script to your &lt;code&gt;package.json&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;...&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;other&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;configurations&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"prisma"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"seed"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"ts-node --project tsconfig.local.json prisma/seeds/main.ts"&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Step 4: Organize Your Seed Files
&lt;/h3&gt;

&lt;p&gt;Structure your seed files like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;prisma/
    migrations/
    seeds/
        0_users.ts
        1_books.ts
        main.ts
    schema.prisma
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Step 5: Write Your Seed Logic
&lt;/h3&gt;

&lt;p&gt;Here's an example of how to structure your seed files:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;0_users.ts&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="kd"&gt;type&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;PrismaClient&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;@prisma/client&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;email&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;test@example.com&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;seedUsers&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;async &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;prisma&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;PrismaClient&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;start&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;Date&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;now&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Seeding users...&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;user&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;prisma&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;upsert&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
        &lt;span class="na"&gt;where&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;email&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="na"&gt;update&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{},&lt;/span&gt;
        &lt;span class="na"&gt;create&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="nx"&gt;email&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Test User&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="p"&gt;});&lt;/span&gt;

    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;end&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;Date&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;now&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`Seeding users completed in &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;end&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="nx"&gt;start&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;ms`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;user&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;};&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="nx"&gt;seedUsers&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;main.ts&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;PrismaClient&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;@prisma/client&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;seedUsers&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;./0_users&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;seedBooks&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;./1_books&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;prisma&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;PrismaClient&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="k"&gt;async&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;main&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;start&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;Date&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Seeding database...&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;user&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nf"&gt;seedUsers&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;prisma&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;books&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nf"&gt;seedBooks&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;prisma&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;end&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;Date&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`Seeding completed: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;end&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getTime&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="nx"&gt;start&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getTime&lt;/span&gt;&lt;span class="p"&gt;()}&lt;/span&gt;&lt;span class="s2"&gt;ms`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nf"&gt;main&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
    &lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;then&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;async &lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;prisma&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;$disconnect&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="p"&gt;})&lt;/span&gt;
    &lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;catch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;async &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;e&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;error&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;e&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
        &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;prisma&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;$disconnect&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
        &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;exit&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="p"&gt;});&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Step 6: Running Seeds
&lt;/h3&gt;

&lt;p&gt;To run your seeds, you can use a task runner like Make. Here's an example Makefile entry:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight make"&gt;&lt;code&gt;&lt;span class="nl"&gt;prisma-seed-dev&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
    dotenv &lt;span class="nt"&gt;-e&lt;/span&gt; .env &lt;span class="nt"&gt;--&lt;/span&gt; npx prisma db seed
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then, you can run &lt;code&gt;make prisma-seed-dev&lt;/code&gt; to execute your seed scripts.&lt;/p&gt;

&lt;h2&gt;
  
  
  Advanced: Handling Dependencies
&lt;/h2&gt;

&lt;p&gt;For more complex seeding scenarios with dependencies between tables, you can create a simple pipeline using Promises. Here's an example of how you might structure this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;user&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nf"&gt;seedUsers&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;prisma&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;books&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nf"&gt;seedBooks&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;prisma&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nb"&gt;Promise&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;all&lt;/span&gt;&lt;span class="p"&gt;([&lt;/span&gt;
    &lt;span class="nf"&gt;seedX&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;prisma&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;books&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;].&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nf"&gt;then&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;async &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;x&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nb"&gt;Promise&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;all&lt;/span&gt;&lt;span class="p"&gt;([&lt;/span&gt;
            &lt;span class="nf"&gt;seedXX&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;prisma&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
            &lt;span class="nf"&gt;seedXXX&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;prisma&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;    
        &lt;span class="p"&gt;]);&lt;/span&gt;
    &lt;span class="p"&gt;}),&lt;/span&gt;
    &lt;span class="nf"&gt;seedY&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;prisma&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;books&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;].&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nf"&gt;then&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;async &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;y&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nb"&gt;Promise&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;all&lt;/span&gt;&lt;span class="p"&gt;([&lt;/span&gt;
            &lt;span class="nf"&gt;seedYY&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;prisma&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;y&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
            &lt;span class="nf"&gt;seedYYY&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;prisma&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;y&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
        &lt;span class="p"&gt;]);&lt;/span&gt;
    &lt;span class="p"&gt;})&lt;/span&gt;
&lt;span class="p"&gt;]);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This approach allows you to handle dependencies between your seed data efficiently.&lt;/p&gt;

&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;By using a separate TypeScript configuration for seeding and structuring your seed files carefully, you can create a robust and efficient seeding process for your Next.js and Prisma-based applications. This approach maintains compatibility with Next.js's recommended settings while giving you the flexibility to run TypeScript-based seed scripts.&lt;/p&gt;

&lt;p&gt;Remember to adjust the seeding logic based on your specific database schema and requirements. Happy coding!&lt;/p&gt;

</description>
      <category>nextjs</category>
      <category>prisma</category>
      <category>testing</category>
      <category>typescript</category>
    </item>
  </channel>
</rss>
