# Security in actions

ในบทความนี้เราจะมาดูการเขียนโค้ดด้าน **Security** ขั้นพื้นฐานกัน ว่ามีอะไรบ้างที่เราควรจะต้องรู้จัก และ จะเรียกใช้งานมันให้ถูกหลักได้ยังไงกันบ้าง ซึ่งบนความก่อนหน้า **ดช.แมวน้ำ** ได้สอนแนวคิดเรื่อง [**การเก็บรหัสผ่านที่ถูกต้อง**](https://www.saladpuk.com/basic/security101/secure-password) ในแง่ทฤษฎีไปละ รอบนี้เราจะมาดูกันว่าแล้วเราจะเขียนโค้ดออกมาจริงๆยังไงนั่นเอง

{% hint style="info" %}
**แนะนำให้อ่าน**\
บทความนี้เป็นส่วนหนึ่งของคอร์ส [👦 Security พื้นฐาน](https://saladpuk.gitbook.io/learn/basic/security101) ถ้าเพื่อนๆสนใจอยากรู้หลักในการรักษาความปลอดภัยตั้งแต่เริ่มต้นเลย ก็กดอ่านที่ตัวสีฟ้าๆได้เลยนะ
{% endhint %}

## 🤨 Security สำคัญหร๋า ?

ได้มีการทำสถิติของข้อมูลที่รั่วไหลตั้งแต่ปี 2013 ไว้แล้วพบว่า **ข้อมูลที่รั่วออกไปมีแค่ 4% เท่านั้นที่ถูกทำเรื่อง security ไว้** นั่นหมายความว่าซอฟต์แวร์โปรเจคต่างๆไม่ค่อยได้ทำเรื่อง security นั่นเอง ซึ่งทำให้ `ข้อมูลส่วนตัว` `รหัสบัตรเครดิต` `รหัสประชาชน` `เบอร์โทร` ของหลายๆคนหลุดเข้าไปในตลาดมืดแล้วนั่นเองครัช&#x20;

![มิน่าบริษัทประกันโทรมาหาผมบ่อยจุง 🤣](/files/-MbgjTqon4UaOF57Io7W)

จากข้อมูลด้านบนจริงๆก็จะเหมารวมว่าเขาไม่ได้ทำเรื่อง Security ทั้งหมดก็ไม่ได้ แต่อาจเกิดจาก **ทำไม่ถูกวิธี** ก็เป็นได้ เช่น ถ้าเราไปหาเซิร์จตาม google เราก็จะพบคำแนะนำให้เราใช้ MD5 อยู่เต็มไปหมด (MD5 ปัจจุบันเราถือว่ามันไม่ปลอดภัยแล้ว) ดังนั้นเรามาลองดูกันว่าถ้าเราจะเขียนโค้ดในด้าน Security เขาเขียนยังไงกันบ้างกัลลล์

## 😎 Random number

พื้นฐานของการทำเรื่อง Security คือการ **สร้างความลับที่มีแต่เราเท่านั้นที่รู้ขึ้นมา** ซึ่งโดยปรกติเราก็จะทำการเขียนโค้ดสุ่มเลขมั่วๆขึ้นมาซักอย่างเพื่อใช้มันเป็น [กุญแจลับ](https://www.saladpuk.com/basic/security101/https-in-a-nutshell#undefined-2) นั่นเอง

{% hint style="info" %}
**ตัวอย่างกุญแจลับ**\
เราอาจจะสุ่มเลข 0\~9 ขึ้นมา 1 ตัวเพื่อใช้เป็นกุญแจลับของเราก็ได้ แต่มันก็จะไม่ปลอดภัยเพราะมันเป็นเลขหลักเดียว ดังนั้นเราก็อาจจะสุ่มมาซัก 15 หลัก เพื่อยากต่อการคาดเดาก็ได้ เพราะโอกาสที่คนอื่นจะเดารหัสลับของเราถูกนั้นมีแค่ 1 ใน 1,000 ล้านล้าน นั่นเอง
{% endhint %}

ซึ่งแค่สุ่มเลข 15 หลักก็ไม่คณามันสมองของเหล่าโปรแกรมเมอร์หรอก เขียนโค้ดแพร๊บ แกร๊กๆๆ

```csharp
var randomNumbers = new int[15];
var random = new Random();
for (int i = 0; i < randomNumbers.Length; i++)
{
    randomNumbers[i] = random.Next(0, 10);
}
var secret = string.Join(string.Empty, randomNumbers);
Console.WriteLine(secret);
```

ยินดีด้วยคุณสอบ Security ตกเรียบร้อยแล้ว 🤣 ... ไม่ได้ล้อเล่นนะ โค้ดด้านบนไม่ได้มีอะไรผิดเบย แต่สิ่งที่ผิดคือ **การเลือกใช้ Random ผิด** เพราะการสุ่มในโลกของคอมพิวเตอร์นั้นสามารถคำนวณได้นั่นเอง ซึ่งมันหมายความว่าถ้ามีคนหลอกวิธีการคำนวณได้ การสุ่มก็จะไม่ใช่การสุ่มอีกต่อไปเพราะเขาสามารถเลือกได้ว่าอยากให้มันสุ่มออกมาเป็นเลขอะไรนั่นเอง

### 🤔 การสุ่มถูกคำนวณได้ ?

การสุ่มของคอมพิวเตอร์นั้นไม่มีอยู่จริง เพราะคอมมันคิดเองไม่ได้ มันเลยต้องไปอ่านค่าอะไรมาซักอย่าง เช่น ข้อมูลใน Memory, CPU, Network บลาๆ แล้วเอาของพวกนั้นมาประกอบกันเป็นเลขสุ่มให้เรานั่นเอง นั่นหมายความว่า ถ้าเรารู้ วิธีการสร้างเลข random เราก็สามารถกำหนดผลลัพท์ของมันได้นั่นเอง

{% hint style="info" %}
**ตัวอย่าง**\
สมมุติว่าคลาส Random มันจะไปเอาเลขจาก Memory ที่ตำแหน่ง x มาบวกกับเลขใน CPU ที่ตำแหน่ง y โดยเอาเลขหลักหน่วยมาเป็นผลลัพท์ของการสุ่มเสมอ คราวนี้เราอยากให้มันสุ่มเลขอะไร เราก็แค่ไปกำหนดค่าใน Memory, CPU ในตำแหน่งนั้นๆ เราก็จะได้ผลลัพท์ที่เรา lock ไว้แล้วนั่นเอง
{% endhint %}

ข้อเสียของการ Random ที่สามารถคำนวณได้คือ มันไม่ปลอดภัย เพราะว่าถ้าเกิดเครื่องเรามีไวรัสฝังอยู่แล้วตอนที่เราไปสร้างกุญแจลับปุ๊ป พวกไวรัสก็เพียงแค่ไปกำหนดค่าตามวิธีการคำนวณของการ random ก็เป็นอันจบเลย เพราะคนร้ายสามารถเลือกได้ว่าจะสร้างกุญแจอะไรให้เรา

### 😐 การสุ่มที่คำนวณไม่ได้ ?

เนื่องจากการสุ่มโดยทั่วไปที่เราใช้เขียนโค้ดนั้นถูกคำนวณได้ ดังนั้นก็มีคนคิดวิธีทำให้มันสุ่มในสุ่มซ้อนกันไปทำให้เกิดการคาดเดาไม่ได้ว่าจริงๆแล้วการสุ่มรอบนี้จะไปอ่านค่าอะไร ตำแหน่งไหน สูตรในรอบนี้จะใช้อะไร บลาๆ ซึ่งข้อดีคือมัน**สามารถป้องกันการถูกกำหนดผลลัพท์ได้ แต่ก็ต้องแลกมากับความช้าในการสร้าง**นั่นเอง ซึ่งการสุ่มแบบนี้ในแต่ละภาษาจะมี library เฉพาะทางของมันเอง เช่นใน .NET ก็จะเป็น [`System.Security.Cryptography`](https://docs.microsoft.com/en-us/dotnet/api/system.security.cryptography?view=net-5.0) นั่นเอง ดังนั้นการสุ่มที่ปลอดภัยในสาย .NET นั้นต้องใช้คลาส [`RNGCryptoServiceProvider`](https://docs.microsoft.com/en-us/dotnet/api/system.security.cryptography.rngcryptoserviceprovider?view=net-5.0) เข้ามาช่วย ซึ่งก็จะได้ผลลัพท์ออกมาเช่นนี้ครัช

```csharp
using var rng = new RNGCryptoServiceProvider();
var byteResult = new byte[32];
rng.GetBytes(byteResult);
var resultText = Convert.ToBase64String(byteResult);
System.Console.WriteLine($"RNG: {resultText}");
```

## 🧭 เนื้อหาทั้งหมด

เนื่องจากช่วงนี้ **ดช.แมวน้ำ** ติดภาระกิจจนเกือบไม่มีเวลานอนมาตั้งแต่ต้นปี 2021 ละ แต่ด้วยหลายๆอย่างเลยอยากแชร์ความรู้ให้เพื่อนๆ ดังนั้นกระป๋มจะขอซอยเป็นบทย่อยๆเอาละกันนะกั๊ฟ

{% hint style="info" %}
คอร์สนี้กำลังค่อยๆเขียนอยู่ ใครที่ไม่อยากพลาดอัพเดทก็เข้าไปกดติดตามที่ลิงค์นี้ [**Mr.Saladpuk**](https://www.facebook.com/mr.saladpuk) ได้เลย&#x20;
{% endhint %}

{% content-ref url="/pages/-MbmbGe1Oe63\_fLR1W6z" %}
[Hash function](/basic/security101/security-in-actions/hash-function.md)
{% endcontent-ref %}

* HMAC Functions
* Salt & Pepper
* Key Derivation
* Symmetric Encryption
* Asymmetric Encryption
* Digital Signature
* Security in Practice

{% hint style="success" %}
เกลียด ชอบ ถูกใจ อยากติดตาม อยากติชมแนะนำด่าทอ หรืออะไรก็แล้วแต่ (ห้ามมายืมเงิน) จิ้มลงมาที่เพจนี้ได้เลย [**Mr.Saladpuk**](https://www.facebook.com/mr.saladpuk) และจะเป็นประคุณอันล้นพ้นถ้ากด Like + Follow + Share ให้ด้วยขอรับ น้ำตาจิไหล 🥺
{% endhint %}

![ช่องทางสนับสนุนค่าอาหารแมวน้ำกั๊ฟ 😘](/files/-MKNmp9HEqzREDsXrZ0H)


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://www.saladpuk.com/basic/security101/security-in-actions.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
