<?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: LHJ Piper</title>
    <description>The latest articles on DEV Community by LHJ Piper (@piperliu).</description>
    <link>https://dev.to/piperliu</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%2F2888699%2Fe8454067-8067-4f24-9bf5-2117401a3dcb.jpeg</url>
      <title>DEV Community: LHJ Piper</title>
      <link>https://dev.to/piperliu</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/piperliu"/>
    <language>en</language>
    <item>
      <title>Unlocking Easy Encryption with `easy-cipher-mate`: A Developer's Dream Come True</title>
      <dc:creator>LHJ Piper</dc:creator>
      <pubDate>Sun, 02 Mar 2025 05:23:23 +0000</pubDate>
      <link>https://dev.to/piperliu/unlocking-easy-encryption-with-easy-cipher-mate-a-developers-dream-come-true-2n0d</link>
      <guid>https://dev.to/piperliu/unlocking-easy-encryption-with-easy-cipher-mate-a-developers-dream-come-true-2n0d</guid>
      <description>&lt;p&gt;In a world where data breaches make headlines daily, securing sensitive information is no longer optional—it's a necessity. Yet, for many developers, encryption feels like a daunting maze. JavaScript encryption libraries often come with steep learning curves: picking the right algorithm, managing keys securely, handling initialization vectors, and avoiding rookie mistakes that could expose your data. And what about those times when you just need a quick, reliable way to encrypt a file without writing a single line of code? The command-line tools out there are either too complex or nonexistent for simple tasks.&lt;/p&gt;

&lt;p&gt;Say goodbye to those headaches. Meet &lt;strong&gt;&lt;code&gt;easy-cipher-mate&lt;/code&gt;&lt;/strong&gt;, a game-changing library and CLI tool that brings encryption to your fingertips—whether you're coding in Node.js, working in the browser, or just need a fast terminal command. With robust algorithms like AES-GCM and ChaCha20-Poly1305, it simplifies secure text and file encryption while offering a seamless experience for both beginners and seasoned pros. Let’s dive into how this tool can transform your workflow, with real-world examples and a peek under the hood for the geeks among us.&lt;/p&gt;




&lt;h2&gt;
  
  
  What is &lt;code&gt;easy-cipher-mate&lt;/code&gt;?
&lt;/h2&gt;

&lt;p&gt;&lt;code&gt;easy-cipher-mate&lt;/code&gt; is a versatile encryption powerhouse designed to make security accessible. Here’s what it offers:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Multiple Algorithms&lt;/strong&gt;: Choose AES-GCM for trusted symmetric encryption or ChaCha20-Poly1305 for high-performance scenarios.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Text and File Encryption&lt;/strong&gt;: Secure strings in your app or entire files on disk.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;CLI Convenience&lt;/strong&gt;: Encrypt and decrypt files directly from the command line—no coding required.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Multi-Language Support&lt;/strong&gt;: Handle different text encodings for global applications.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Flexible Configuration&lt;/strong&gt;: Set up encryption via code, environment variables, or JSON files.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Whether you're safeguarding user data in a web app or locking down sensitive config files, this tool has you covered.&lt;/p&gt;




&lt;h2&gt;
  
  
  Installing &lt;code&gt;easy-cipher-mate&lt;/code&gt;
&lt;/h2&gt;

&lt;p&gt;If you’re new to this, don’t worry—installation is a breeze. Open your terminal and run:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install &lt;/span&gt;easy-cipher-mate
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Or, if you prefer Yarn:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;yarn add easy-cipher-mate
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That’s it! You’re ready to start securing your data.&lt;/p&gt;




&lt;h2&gt;
  
  
  Solving Real Problems with the CLI
&lt;/h2&gt;

&lt;p&gt;Imagine you’re a system administrator tasked with securing a &lt;code&gt;secrets.json&lt;/code&gt; file containing API keys. Writing a custom script feels like overkill, and you need it done &lt;em&gt;now&lt;/em&gt;. With &lt;code&gt;easy-cipher-mate&lt;/code&gt;’s CLI, it’s a one-liner.&lt;/p&gt;

&lt;h3&gt;
  
  
  Encrypting a File
&lt;/h3&gt;

&lt;p&gt;Run this command:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;easy-cipher-mate encrypt-file &lt;span class="nt"&gt;-i&lt;/span&gt; secrets.json &lt;span class="nt"&gt;-o&lt;/span&gt; secrets.json.encrypted &lt;span class="nt"&gt;-p&lt;/span&gt; &lt;span class="s2"&gt;"my-super-secret"&lt;/span&gt; &lt;span class="nt"&gt;-a&lt;/span&gt; aes-gcm
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;-i&lt;/code&gt;: Input file (&lt;code&gt;secrets.json&lt;/code&gt;).&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;-o&lt;/code&gt;: Output file (&lt;code&gt;secrets.json.encrypted&lt;/code&gt;).&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;-p&lt;/code&gt;: Your password.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;-a&lt;/code&gt;: Algorithm (defaults to &lt;code&gt;aes-gcm&lt;/code&gt;).&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Boom! Your file is encrypted with AES-GCM, safe from prying eyes.&lt;/p&gt;

&lt;h3&gt;
  
  
  Decrypting a File
&lt;/h3&gt;

&lt;p&gt;Later, when you need access:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;easy-cipher-mate decrypt-file &lt;span class="nt"&gt;-i&lt;/span&gt; secrets.json.encrypted &lt;span class="nt"&gt;-o&lt;/span&gt; secrets.json.decrypted &lt;span class="nt"&gt;-p&lt;/span&gt; &lt;span class="s2"&gt;"my-super-secret"&lt;/span&gt; &lt;span class="nt"&gt;-a&lt;/span&gt; aes-gcm
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The original file is back, decrypted and ready to use.&lt;/p&gt;

&lt;h3&gt;
  
  
  Encrypting Logs Line by Line
&lt;/h3&gt;

&lt;p&gt;Now, suppose you’re a developer managing a log file (&lt;code&gt;app.log&lt;/code&gt;) where each line is a sensitive event. Encrypting the whole file might not suit your needs—you want to secure each line individually for easier processing later. Here’s how:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;easy-cipher-mate encrypt-text-file &lt;span class="nt"&gt;-f&lt;/span&gt; app.log &lt;span class="nt"&gt;-p&lt;/span&gt; &lt;span class="s2"&gt;"logpassword123"&lt;/span&gt; &lt;span class="nt"&gt;-a&lt;/span&gt; aes-gcm &lt;span class="nt"&gt;-e&lt;/span&gt; utf-8
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;-f&lt;/code&gt;: File to encrypt.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;-e&lt;/code&gt;: Text encoding (e.g., &lt;code&gt;utf-8&lt;/code&gt; for standard text).&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Each non-empty line is encrypted independently and saved in place as base64-encoded text. To decrypt:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;easy-cipher-mate decrypt-text-file &lt;span class="nt"&gt;-f&lt;/span&gt; app.log &lt;span class="nt"&gt;-p&lt;/span&gt; &lt;span class="s2"&gt;"logpassword123"&lt;/span&gt; &lt;span class="nt"&gt;-a&lt;/span&gt; aes-gcm &lt;span class="nt"&gt;-e&lt;/span&gt; utf-8
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Your logs are back to readable text, line by line. This is perfect for automated scripts or incremental log processing.&lt;/p&gt;




&lt;h2&gt;
  
  
  Powering Your Code with the API
&lt;/h2&gt;

&lt;p&gt;For developers building applications, &lt;code&gt;easy-cipher-mate&lt;/code&gt; shines with its intuitive API. Let’s explore some practical scenarios.&lt;/p&gt;

&lt;h3&gt;
  
  
  Securing User Input
&lt;/h3&gt;

&lt;p&gt;You’re building a chat app, and you need to encrypt messages before storing them. Here’s how to encrypt a user’s message:&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;AESGCMEncryption&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;AESGCMEncryptionConfigFromEnv&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;EncryptionService&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;easy-cipher-mate&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;algo&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;AESGCMEncryption&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;config&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;AESGCMEncryptionConfigFromEnv&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;chatsecret123&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;service&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;EncryptionService&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;algo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;config&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;encryptMessage&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;message&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Hey, let's meet at 5 PM!&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;encrypted&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;service&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;encryptText&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;message&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="s1"&gt;Encrypted:&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;encrypted&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="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;encrypted&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="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;To decrypt it later:&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;async&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;decryptMessage&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;encryptedData&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nb"&gt;ArrayBuffer&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;decrypted&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;service&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;decryptText&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;encryptedData&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="s1"&gt;Decrypted:&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;decrypted&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="c1"&gt;// "Hey, let's meet at 5 PM!"&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Simple, secure, and ready to integrate into your app.&lt;/p&gt;

&lt;h3&gt;
  
  
  Protecting a PDF Invoice
&lt;/h3&gt;

&lt;p&gt;Say you’re generating invoices as PDFs and need to encrypt them before emailing. Here’s the code:&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;readFileSync&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;writeFileSync&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;fs&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="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;AESGCMEncryption&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;AESGCMEncryptionConfigFromEnv&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;EncryptionService&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;easy-cipher-mate&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;algo&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;AESGCMEncryption&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;config&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;AESGCMEncryptionConfigFromEnv&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;invoicekey&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;service&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;EncryptionService&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;algo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;config&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;encryptInvoice&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;fileBuffer&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;readFileSync&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;invoice.pdf&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;arrayBuffer&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;fileBuffer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;buffer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;slice&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;fileBuffer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;byteOffset&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;fileBuffer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;byteOffset&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="nx"&gt;fileBuffer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;byteLength&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;encrypted&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;service&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;encryptFile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;arrayBuffer&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="nf"&gt;writeFileSync&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;invoice.pdf.encrypted&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;Buffer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;from&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;encrypted&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="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;To decrypt:&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;async&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;decryptInvoice&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;encryptedBuffer&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;readFileSync&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;invoice.pdf.encrypted&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;encryptedArrayBuffer&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;encryptedBuffer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;buffer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;slice&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="nx"&gt;encryptedBuffer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;byteOffset&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="nx"&gt;encryptedBuffer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;byteOffset&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="nx"&gt;encryptedBuffer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;byteLength&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;decrypted&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;service&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;decryptFile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;encryptedArrayBuffer&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="nf"&gt;writeFileSync&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;invoice.pdf.decrypted&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;Buffer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;from&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;decrypted&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;Your invoices are now secure and easy to manage.&lt;/p&gt;

&lt;h3&gt;
  
  
  Supporting Global Users
&lt;/h3&gt;

&lt;p&gt;If your app serves users worldwide, text encoding matters. Encrypting Japanese text, for example:&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;japaneseMessage&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;こんにちは、世界！&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;encrypted&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;service&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;encryptText&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;japaneseMessage&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;utf16le&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;decrypted&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;service&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;decryptText&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;encrypted&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="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;utf16le&lt;/span&gt;&lt;span class="dl"&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;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;decrypted&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="c1"&gt;// 'こんにちは、世界！'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Supported encodings include &lt;code&gt;utf-8&lt;/code&gt;, &lt;code&gt;utf16le&lt;/code&gt;, &lt;code&gt;base64&lt;/code&gt;, &lt;code&gt;hex&lt;/code&gt;, &lt;code&gt;latin1&lt;/code&gt;, and more—perfect for internationalization.&lt;/p&gt;




&lt;h2&gt;
  
  
  Configuration Made Easy
&lt;/h2&gt;

&lt;p&gt;&lt;code&gt;easy-cipher-mate&lt;/code&gt; offers flexible configuration options:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Environment Variables&lt;/strong&gt;:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;  &lt;span class="nb"&gt;export &lt;/span&gt;&lt;span class="nv"&gt;ECM_AESGCM_PASSWORD&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s2"&gt;"mysecret"&lt;/span&gt;
  &lt;span class="nb"&gt;export &lt;/span&gt;&lt;span class="nv"&gt;ECM_AESGCM_SALT&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="si"&gt;$(&lt;/span&gt;&lt;span class="nb"&gt;echo&lt;/span&gt; &lt;span class="nt"&gt;-n&lt;/span&gt; &lt;span class="s2"&gt;"salt123"&lt;/span&gt; | &lt;span class="nb"&gt;base64&lt;/span&gt;&lt;span class="si"&gt;)&lt;/span&gt;
  &lt;span class="nb"&gt;export &lt;/span&gt;&lt;span class="nv"&gt;ECM_AESGCM_IV&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="si"&gt;$(&lt;/span&gt;&lt;span class="nb"&gt;echo&lt;/span&gt; &lt;span class="nt"&gt;-n&lt;/span&gt; &lt;span class="s2"&gt;"iv456"&lt;/span&gt; | &lt;span class="nb"&gt;base64&lt;/span&gt;&lt;span class="si"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then in code:&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;config&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;AESGCMEncryptionConfigFromEnv&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;JSON Config&lt;/strong&gt;:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&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;"password"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"mysecret"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"salt"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"c2FsdDEyMw=="&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;base&lt;/span&gt;&lt;span class="mi"&gt;64&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"salt123"&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"iv"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"aXY0NTY="&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;base&lt;/span&gt;&lt;span class="mi"&gt;64&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"iv456"&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"textEncoding"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"utf-8"&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;p&gt;Load it with:&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;config&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;AESGCMEncryptionConfigFromJSONFile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;config.json&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Choose what fits your workflow—coding, scripting, or both.&lt;/p&gt;




&lt;h2&gt;
  
  
  For the Geeks: A Peek Under the Hood
&lt;/h2&gt;

&lt;p&gt;Curious about how it works? Let’s look at the key derivation in &lt;code&gt;AESGCMEncryption.ts&lt;/code&gt;. The library uses PBKDF2 to turn your password into a secure key:&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;async&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;deriveKey&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;password&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="nx"&gt;salt&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nb"&gt;Uint8Array&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt; &lt;span class="nb"&gt;Promise&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;CryptoKey&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;encoder&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;TextEncoder&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;keyMaterial&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;crypto&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;subtle&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;importKey&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;raw&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="nx"&gt;encoder&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;encode&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;password&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
    &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;PBKDF2&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;deriveKey&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="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;crypto&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;subtle&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;deriveKey&lt;/span&gt;&lt;span class="p"&gt;(&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;PBKDF2&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="nx"&gt;salt&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;iterations&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;100000&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;hash&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;SHA-256&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;
    &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="nx"&gt;keyMaterial&lt;/span&gt;&lt;span class="p"&gt;,&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;AES-GCM&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;length&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;256&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;encrypt&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;decrypt&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;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This process iterates 100,000 times with SHA-256 hashing, making brute-force attacks impractical. The Web Crypto API then handles the actual encryption, ensuring top-tier security standards. For files, the same key encrypts the entire buffer, while the CLI’s line-by-line mode applies this per line, encoding results in base64 for text compatibility.&lt;/p&gt;




&lt;h2&gt;
  
  
  Why You’ll Love &lt;code&gt;easy-cipher-mate&lt;/code&gt;
&lt;/h2&gt;

&lt;p&gt;From its dead-simple CLI to its developer-friendly API, &lt;code&gt;easy-cipher-mate&lt;/code&gt; takes the pain out of encryption. It’s fast, secure, and flexible enough for any use case—whether you’re a novice securing your first file or a pro building a global app. Install it today with &lt;code&gt;npm install easy-cipher-mate&lt;/code&gt;, and see how easy encryption can be.&lt;/p&gt;

&lt;p&gt;Ready to lock down your data? Give &lt;code&gt;easy-cipher-mate&lt;/code&gt; a spin and share your experience!&lt;/p&gt;

</description>
    </item>
    <item>
      <title>Don’t Let AI Programming Ruin Your Career—Treat Them as Your Interns, Not Employees or Teachers!</title>
      <dc:creator>LHJ Piper</dc:creator>
      <pubDate>Thu, 20 Feb 2025 16:30:55 +0000</pubDate>
      <link>https://dev.to/piperliu/dont-let-ai-programming-ruin-your-career-treat-them-as-your-interns-not-employees-or-teachers-16bo</link>
      <guid>https://dev.to/piperliu/dont-let-ai-programming-ruin-your-career-treat-them-as-your-interns-not-employees-or-teachers-16bo</guid>
      <description>&lt;p&gt;&lt;em&gt;Disclaimer: This article contains no AI-generated content; it is entirely handwritten. The first draft of this article was generated in Chinese and translated into English by Grok-3.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Yesterday, I came across some expressions of concern, such as “&lt;a href="https://mp.weixin.qq.com/s/5JvSmHIf23xhwn6wnmiE9g" rel="noopener noreferrer"&gt;AI is Cultivating a Generation of ‘Illiterate Programmers’ Who Can’t Code&lt;/a&gt;.” I also recall earlier claims that “AI will ruin junior programmers.” Whether you agree or disagree, you must admit there’s some truth to these views—they’re not entirely baseless.&lt;/p&gt;

&lt;p&gt;Here are the main points of these concerns:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;AI-assisted programming causes problem-solving skills to deteriorate, as people have fewer chances to think independently.&lt;/li&gt;
&lt;li&gt;There’s a “withdrawal” effect from AI programming, leaving people feeling dumber or slower without it.&lt;/li&gt;
&lt;li&gt;“We haven’t become ‘10x programmers’ thanks to AI; we’ve just become 10 times more dependent on it.”&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Speaking for myself, I feel rather fortunate. Before large language models became widespread—or even existed—I had already patiently built a relatively solid foundation in computer science. I diligently completed assignments, projects, and exams from classic courses like Zhejiang University’s data structures and MIT’s operating systems. By the end of 2022, when I needed to write my graduation thesis, the initial version of GPT-3.5/ChatGPT emerged—just in time.&lt;/p&gt;

&lt;p&gt;If I had started my studies a few years later, I’d surely question the value of learning foundational knowledge. Even if I recognized its importance and began studying, I might not be willing to learn as thoroughly as I did in the “pre-AI era.” I might toss classic papers to AI and ask it to summarize the key points for me. If I didn’t understand something, I’d ask AI rather than digging into the paper myself. For course assignments, AI would auto-complete them for me, and since humans are naturally lazy, I’d struggle to resist: “Oh, it filled in a bunch for me—well, that’s the gist of it, I get it, as long as it runs and finishes the assignment!” Worse still, since solutions to course assignments have long been part of AI’s training data, the auto-completed work would likely be flawless—robbing me of the chance to sharpen my debugging skills with tools like GDB during my student years. When such a student later tackles real-world problems where AI’s solutions aren’t perfect, they’ll face challenges far tougher than those met by engineers from the “pre-AI era.”&lt;/p&gt;

&lt;p&gt;Yet, unlike all professions in history that have faced “elimination threats,” software engineers—or programmers—are the most inclined to “actively embrace new things.” It’s a job requirement, after all.&lt;/p&gt;

&lt;p&gt;So, how do we safely “embrace” this double-edged sword, this “demon”?&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Treat AI programming assistants as your interns, not as employees, colleagues, or teachers!&lt;/strong&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  1) Your subordinates or colleagues are accountable for their code, but your interns are not.
&lt;/h3&gt;

&lt;p&gt;If code you wrote with AI has bugs, would you sue the AI company? Of course not—they’ve already disclaimed liability. Even if it’s code written by AI or commits suggested by AI, the responsibility ultimately falls on you.&lt;/p&gt;

&lt;p&gt;What’s that? Your company has integrated AI into CI/CD, like using AI to procedurally write unit tests? No problem—if the AI’s code fails, whoever deployed the AI is accountable.&lt;/p&gt;

&lt;p&gt;In short, responsibility must land on a human. If you fully entrust your work to an AI tool, you can’t say when issues arise, “This was written by so-and-so; go find them!”&lt;/p&gt;

&lt;p&gt;For critical logic written by AI, you must review it yourself, just as you’d carefully check an intern’s code before it goes into production.&lt;/p&gt;

&lt;p&gt;Moreover, you should be extra cautious about letting AI access highly sensitive information. It’s like not allowing a summer intern to touch your company’s most competitive core technology. Imagine this: the internship ends, the intern leaves, and with the confidential knowledge gained from you, they land a full-time job at your competitor. Would you make interns sign non-compete agreements? Hardly practical.&lt;/p&gt;

&lt;p&gt;AI programming assistants carry a similar risk, though it’s unlikely AI companies care about our mundane business code. Still, for programmers, safeguarding core data, keys, and code is worth considering. My initial suggestions are:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Store passwords, tokens, and other sensitive info in profile files like &lt;code&gt;~/.bashrc&lt;/code&gt;, reading them as environment variables at runtime.&lt;/li&gt;
&lt;li&gt;Or ensure your project’s config files are ignored by AI tools.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  2) Assign your intern one task at a time—don’t rush.
&lt;/h3&gt;

&lt;p&gt;Think back to your first meeting with an intern—a fresh-faced newbie on their first internship. How did you introduce the upcoming work?&lt;/p&gt;

&lt;p&gt;Was it like this?&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Hello, student. Now, assume you’re a senior Go language engineer who’ll provide me with secure, elegant Go backend system solutions.&lt;/li&gt;
&lt;li&gt;I need a backend system for an image hosting service, supporting image uploads, downloads, list queries, and more.&lt;/li&gt;
&lt;li&gt;Pay special attention to the image storage solution and caching scheme for preview images, as project cost is a key factor.&lt;/li&gt;
&lt;li&gt;Choose the most ecosystem-friendly Go language service framework to ensure smooth future development and maintenance.&lt;/li&gt;
&lt;li&gt;The project must be highly scalable, with corresponding hot-update solutions.&lt;/li&gt;
&lt;li&gt;Produce excellent API documentation to ease frontend integration.&lt;/li&gt;
&lt;li&gt;Don’t skip linting, static checks, or unit tests.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;If you said that to an intern, you’d witness the epitome of bewilderment. Obviously, you wouldn’t do that.&lt;/p&gt;

&lt;p&gt;You shouldn’t do it with AI either. In other words, being too greedy often leads to subpar results and wasted time. We should treat each interaction with AI like a meeting with an intern.&lt;/p&gt;

&lt;p&gt;For example:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;First meeting (asking DeepSeek-R1 or another reasoning model): I want to design a high-performance image hosting backend system. I’m skilled in Go—are there any recommended existing solutions? If not, how should we design it? How do we plan the project?

&lt;ul&gt;
&lt;li&gt;This first meeting is like letting the intern plan their summer project, then refining and finalizing it.&lt;/li&gt;
&lt;li&gt;At the end of the chat, you can ask AI to output a summary of the design plan, structure diagram, tech stack, etc., much like having the intern summarize the project for you. Then, use that summary to kick off the next meeting or AI chat.&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;li&gt;Second meeting (using the prior “meeting summary” as a pre-prompt for the AI programming tool): Based on the current project design, let’s start building the minimal viable functionality. Let’s first design the first service in the dependency injection!

&lt;ul&gt;
&lt;li&gt;In this second meeting, letting AI generate specific code is akin to having the intern write code.&lt;/li&gt;
&lt;li&gt;If something’s off, fix it yourself to prevent cascading errors.&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;li&gt;Subsequent meetings would focus on daily progress.&lt;/li&gt;

&lt;/ul&gt;

&lt;p&gt;Here’s a tip:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Models like GPT-O1 or DeepSeek-R1 excel at reasoning but are slower (since they reason before outputting) and costlier, so use them for project design.&lt;/li&gt;
&lt;li&gt;For daily code generation, opt for inference models like DeepSeek-V3 or Claude-Sonnet-3.5—they’re faster and cheaper. If your project context is clear and well-structured, the code quality is often solid. Especially if you’ve already implemented one unit test, AI will follow it to nail the rest perfectly. But if you ask AI to write unit tests from scratch, it might not fully match your expectations.&lt;/li&gt;
&lt;/ol&gt;

&lt;h3&gt;
  
  
  3) You can’t leave an intern’s project completely untouched.
&lt;/h3&gt;

&lt;p&gt;This comes from personal experience. I have a mild compulsion to write some code daily. But over the past six months, that habit morphed into “having AI generate some code daily.” Surprisingly, my productivity slowed down.&lt;/p&gt;

&lt;p&gt;During the New Year holiday, I wanted to build a simple SPA (Single Page Application) with basic Vue3 logic. Over five days, I made zero progress. Unable to focus on code during the holiday, I opted to rely entirely on AI assistance.&lt;/p&gt;

&lt;p&gt;Eventually, I was stunned to see AI spinning in circles on my project. I’d defined a basic &lt;code&gt;FileUploader.vue&lt;/code&gt; component (somewhat complex), and in &lt;code&gt;XXXView.vue&lt;/code&gt;, my AI couldn’t decide whether to use it or write new file upload logic, spawning a host of new issues.&lt;/p&gt;

&lt;p&gt;As the holiday neared its end, I finally sat down and looked closely. The logic was so simple! I wrote it myself in no time.&lt;/p&gt;

&lt;p&gt;You might say I misused the AI tool or that it’s better with React than Vue. But you can’t guarantee this black box won’t stall on slightly novel problems.&lt;/p&gt;

&lt;p&gt;Especially when your code hits production issues, you can’t expect an intern to rush from school to fix it, just as you can’t expect AI to deliver spot-on answers in a pinch.&lt;/p&gt;

&lt;p&gt;For AI-written projects, it’s best to understand how they’re implemented. That way, when you need to tweak them, you can dive in quickly.&lt;/p&gt;

&lt;h3&gt;
  
  
  4) You can’t use an intern as your search engine.
&lt;/h3&gt;

&lt;p&gt;Copying every bug to AI right away is absurd, laughable, and sad. Even if AI advances for another decade, this habit will remain absurd, laughable, and sad—unless you’ve got a cutting-edge brain-computer interface feeding AI all your perceptions and context.&lt;/p&gt;

&lt;p&gt;Handing error messages to AI is fine, of course. But it shouldn’t be an instinct. Otherwise, why employ you as an engineer? For problems you can roughly pinpoint with your brain, a quick search engine query beats asking AI in speed and fit.&lt;/p&gt;

&lt;p&gt;The same applies to basic info lookups. Programmers these days seem too lazy to read documentation.&lt;/p&gt;

&lt;p&gt;Imagine you’re using the &lt;code&gt;aws s3 sync&lt;/code&gt; command and want to know what &lt;code&gt;--exact-timestamps&lt;/code&gt; does. Would you call an intern over and ask, “What’s this parameter do, and give me a few specific examples?”&lt;/p&gt;

&lt;p&gt;Two minutes later, the intern returns with a markdown report cobbled together from sketchy blogs. You read it, half-grasping it, unsure if it’s accurate.&lt;/p&gt;

&lt;p&gt;Why not just search &lt;code&gt;doc: aws s3 sync --exact-timestamps&lt;/code&gt; on a search engine? In five seconds, you’d have the most official, reliable, and clear documentation in front of you. It’s all text—why settle for someone else’s regurgitated version?&lt;/p&gt;

&lt;h3&gt;
  
  
  5) An intern can be an expert in certain areas, and that’s not shameful.
&lt;/h3&gt;

&lt;p&gt;Suppose your boss wants to launch a CUDA-related business line and names you the technical lead. You could recruit interns who’ve worked with CUDA in school and listen to their ideas during project design.&lt;/p&gt;

&lt;p&gt;Likewise, when we hit new problems and lack direction, we can “consult” AI. Just as we might consult interns—expertise varies, and that’s normal.&lt;/p&gt;

&lt;p&gt;But with interns, you wouldn’t carelessly toss out shallow questions. Even for something simple, you’d ask rigorously: “Given the current situation, what’s the better technical route? Please outline it based on ecosystem, development difficulty, maintenance difficulty, performance, cost, etc.” You should engage AI the same way to maximize the value of the information you get.&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;Conclusion&lt;/strong&gt;: Those who know me might recall that a year ago, I’d always put “AI” in quotes. I don’t believe today’s probabilistic models have true “intelligence.” I still feel that way. But I also believe we should move with the times rather than cling to formalities. Though I personally dislike AI tools, I’d wager that, outside of professional researchers, I’m among the most active, proactive, and extensive users of new AI tools. Let’s learn critically together, keep improving, and strive for excellence.&lt;/p&gt;

</description>
      <category>code</category>
      <category>ai</category>
      <category>programming</category>
      <category>career</category>
    </item>
  </channel>
</rss>
