+```
+
+এখন, আমরা আমাদের ডিএ্যাপস-এ আমাদের Alchemy Web3 এন্ডপয়েন্ট সেট আপ করতে প্রস্তুত! চলুন আমাদের `util` ফোল্ডারের মধ্যে থাকা `interact.js` ফাইলে ফিরে যাই এবং ফাইলের শীর্ষে নিম্নলিখিত কোডটি যোগ করি:
+
+```javascript
+// interact.js
+
+require("dotenv").config()
+const alchemyKey = process.env.REACT_APP_ALCHEMY_KEY
+const { createAlchemyWeb3 } = require("@alch/alchemy-web3")
+const web3 = createAlchemyWeb3(alchemyKey)
+
+//export const helloWorldContract;
+```
+
+উপরে, আমরা প্রথমে আমাদের `.env` ফাইল থেকে Alchemy কী ইম্পোর্ট করেছি এবং তারপর আমাদের Alchemy Web3 এন্ডপয়েন্ট স্থাপন করার জন্য `createAlchemyWeb3`-এ আমাদের `alchemyKey` পাস করেছি।
+
+এই এন্ডপয়েন্ট প্রস্তুত হলে, এখন আমাদের স্মার্ট কন্ট্র্যাক্ট লোড করার সময়!
+
+#### আপনার Hello World স্মার্ট কন্ট্র্যাক্ট লোড করা হচ্ছে {#loading-your-hello-world-smart-contract}
+
+আপনার Hello World স্মার্ট কন্ট্র্যাক্ট লোড করার জন্য, আপনার এর কন্ট্র্যাক্ট ঠিকানা এবং ABI প্রয়োজন হবে, উভয়ই Etherscan-এ পাওয়া যাবে যদি আপনি [এই টিউটোরিয়ালের পর্ব ৩ সম্পূর্ণ করে থাকেন।](/developers/tutorials/hello-world-smart-contract-fullstack/#part-3-publish-your-smart-contract-to-etherscan-part-3-publish-your-smart-contract-to-etherscan)
+
+#### Etherscan থেকে আপনার কন্ট্র্যাক্ট ABI কীভাবে পাবেন {#how-to-get-your-contract-abi-from-etherscan}
+
+আপনি যদি এই টিউটোরিয়ালের পর্ব ৩ এড়িয়ে যান, আপনি ঠিকানা [0x6f3f635A9762B47954229Ea479b4541eAF402A6A](https://goerli.etherscan.io/address/0x6f3f635a9762b47954229ea479b4541eaf402a6a#code) সহ HelloWorld কন্ট্র্যাক্ট ব্যবহার করতে পারেন। এর ABI [এখানে](https://goerli.etherscan.io/address/0x6f3f635a9762b47954229ea479b4541eaf402a6a#code) পাওয়া যাবে।
+
+একটি কন্ট্র্যাক্ট ABI একটি কন্ট্র্যাক্ট কোন ফাংশনটি চালু করবে তা নির্দিষ্ট করার জন্য এবং ফাংশনটি আপনার প্রত্যাশিত ফর্ম্যাটে ডেটা ফেরত দেবে তা নিশ্চিত করার জন্য প্রয়োজনীয়। আমাদের কন্ট্র্যাক্ট ABI কপি করার পর, আসুন এটিকে আপনার `src` ডিরেক্টরিতে `contract-abi.json` নামে একটি JSON ফাইল হিসেবে সংরক্ষণ করি।
+
+আপনার contract-abi.json আপনার src ফোল্ডারে সংরক্ষণ করা উচিত।
+
+আমাদের কন্ট্র্যাক্ট ঠিকানা, ABI, এবং Alchemy Web3 এন্ডপয়েন্ট নিয়ে, আমরা আমাদের স্মার্ট কন্ট্র্যাক্টের একটি উদাহরণ লোড করতে [কন্ট্র্যাক্ট পদ্ধতি](https://docs.web3js.org/api/web3-eth-contract/class/Contract) ব্যবহার করতে পারি। `interact.js` ফাইলে আপনার কন্ট্র্যাক্ট ABI ইম্পোর্ট করুন এবং আপনার কন্ট্র্যাক্ট ঠিকানা যোগ করুন।
+
+```javascript
+// interact.js
+
+const contractABI = require("../contract-abi.json")
+const contractAddress = "0x6f3f635A9762B47954229Ea479b4541eAF402A6A"
+```
+
+আমরা এখন অবশেষে আমাদের `helloWorldContract` ভেরিয়েবলটি আনকমেন্ট করতে পারি, এবং আমাদের AlchemyWeb3 এন্ডপয়েন্ট ব্যবহার করে স্মার্ট কন্ট্র্যাক্ট লোড করতে পারি:
+
+```javascript
+// interact.js
+export const helloWorldContract = new web3.eth.Contract(
+ contractABI,
+ contractAddress
+)
+```
+
+সংক্ষেপে, আপনার `interact.js`-এর প্রথম ১২টি লাইন এখন এরকম দেখতে হবে:
+
+```javascript
+// interact.js
+
+require("dotenv").config()
+const alchemyKey = process.env.REACT_APP_ALCHEMY_KEY
+const { createAlchemyWeb3 } = require("@alch/alchemy-web3")
+const web3 = createAlchemyWeb3(alchemyKey)
+
+const contractABI = require("../contract-abi.json")
+const contractAddress = "0x6f3f635A9762B47954229Ea479b4541eAF402A6A"
+
+export const helloWorldContract = new web3.eth.Contract(
+ contractABI,
+ contractAddress
+)
+```
+
+এখন যে আমাদের কন্ট্র্যাক্ট লোড হয়েছে, আমরা আমাদের `loadCurrentMessage` ফাংশনটি বাস্তবায়ন করতে পারি!
+
+#### আপনার `interact.js` ফাইলে `loadCurrentMessage` বাস্তবায়ন করা {#implementing-loadCurrentMessage-in-your-interact-js-file}
+
+এই ফাংশনটি খুবই সহজ। আমরা আমাদের কন্ট্র্যাক্ট থেকে পড়ার জন্য একটি সহজ অ্যাসিঙ্ক web3 কল করব। আমাদের ফাংশনটি স্মার্ট কন্ট্র্যাক্টে সংরক্ষিত বার্তা ফেরত দেবে:
+
+আপনার `interact.js` ফাইলে `loadCurrentMessage` আপডেট করে নিম্নলিখিতটি করুন:
+
+```javascript
+// interact.js
+
+export const loadCurrentMessage = async () => {
+ const message = await helloWorldContract.methods.message().call()
+ return message
+}
+```
+
+যেহেতু আমরা এই স্মার্ট কন্ট্র্যাক্টটি আমাদের UI-তে প্রদর্শন করতে চাই, আসুন আমাদের `HelloWorld.js` কম্পোনেন্টে `useEffect` ফাংশনটি নিম্নলিখিতভাবে আপডেট করি:
+
+```javascript
+// HelloWorld.js
+
+//একবারই বলা হয়
+useEffect(async () => {
+ const message = await loadCurrentMessage()
+ setMessage(message)
+}, [])
+```
+
+লক্ষ্য করুন, আমরা চাই যে আমাদের `loadCurrentMessage` শুধুমাত্র কম্পোনেন্টের প্রথম রেন্ডারের সময় একবার কল করা হোক। আমরা শীঘ্রই `addSmartContractListener` বাস্তবায়ন করব যাতে স্মার্ট কন্ট্র্যাক্টে বার্তা পরিবর্তন হওয়ার পরে UI স্বয়ংক্রিয়ভাবে আপডেট হয়।
+
+আমাদের লিসেনারে ডুব দেওয়ার আগে, আসুন দেখি আমরা এখন পর্যন্ত কী করেছি! আপনার `HelloWorld.js` এবং `interact.js` ফাইলগুলি সংরক্ষণ করুন, এবং তারপরে [http://localhost:3000/](http://localhost:3000/)-এ যান
+
+আপনি লক্ষ্য করবেন যে বর্তমান বার্তায় আর "নেটওয়ার্কের সাথে কোনো সংযোগ নেই" লেখা নেই। পরিবর্তে এটি স্মার্ট কন্ট্র্যাক্টে সংরক্ষিত বার্তা প্রতিফলিত করে। দারুণ!
+
+#### আপনার UI এখন স্মার্ট কন্ট্র্যাক্টে সংরক্ষিত বার্তা প্রতিফলিত করবে {#your-UI-should-now-reflect-the-message-stored-in-the-smart-contract}
+
+এখন সেই লিসেনারের কথা বলি...
+
+#### `addSmartContractListener` বাস্তবায়ন করুন {#implement-addsmartcontractlistener}
+
+আপনি যদি এই টিউটোরিয়াল সিরিজের [পর্ব ১-এ](https://docs.alchemy.com/alchemy/tutorials/hello-world-smart-contract#step-10-write-our-contract) লেখা `HelloWorld.sol` ফাইলটি মনে করেন, আপনি মনে করতে পারবেন যে `UpdatedMessages` নামে একটি স্মার্ট কন্ট্র্যাক্ট ইভেন্ট আছে যা আমাদের স্মার্ট কন্ট্র্যাক্টের `update` ফাংশন চালু করার পরে নির্গত হয় (লাইন ৯ এবং ২৭ দেখুন):
+
+```javascript
+// HelloWorld.sol
+
+// সিমেন্টিক ভার্সনিং ব্যবহার করে সলিডিটির সংস্করণ নির্দিষ্ট করে।
+// আরও জানুন: https://solidity.readthedocs.io/en/v0.5.10/layout-of-source-files.html#pragma
+pragma solidity ^0.7.3;
+
+// `HelloWorld` নামের একটি কন্ট্র্যাক্ট সংজ্ঞায়িত করে।
+// একটি কন্ট্র্যাক্ট হল ফাংশন এবং ডেটার একটি সংগ্রহ (তার স্টেট)। একবার স্থাপন করা হলে, একটি কন্ট্র্যাক্ট ইথেরিয়াম ব্লকচেইনে একটি নির্দিষ্ট ঠিকানায় থাকে। আরও জানুন: https://solidity.readthedocs.io/en/v0.5.10/structure-of-a-contract.html
+contract HelloWorld {
+
+ //আপডেট ফাংশন কল করা হলে নির্গত হয়
+ //স্মার্ট কন্ট্র্যাক্ট ইভেন্টগুলি হল আপনার কন্ট্র্যাক্টের জন্য আপনার অ্যাপ ফ্রন্ট-এন্ডে ব্লকচেইনে কিছু ঘটেছে তা জানানোর একটি উপায়, যা নির্দিষ্ট ইভেন্টের জন্য 'শুনতে' পারে এবং সেগুলি ঘটলে ব্যবস্থা নিতে পারে।
+ event UpdatedMessages(string oldStr, string newStr);
+
+ // `string` টাইপের একটি স্টেট ভেরিয়েবল `message` ঘোষণা করে।
+ // স্টেট ভেরিয়েবলগুলি হল এমন ভেরিয়েবল যার মানগুলি স্থায়ীভাবে কন্ট্র্যাক্ট স্টোরেজে সংরক্ষণ করা হয়। `public` কীওয়ার্ডটি কন্ট্র্যাক্টের বাইরে থেকে ভেরিয়েবলগুলিকে অ্যাক্সেসযোগ্য করে তোলে এবং একটি ফাংশন তৈরি করে যা অন্য কন্ট্র্যাক্ট বা ক্লায়েন্টরা মান অ্যাক্সেস করার জন্য কল করতে পারে।
+ string public message;
+
+ // অনেক ক্লাস-ভিত্তিক অবজেক্ট-ওরিয়েন্টেড ভাষার মতো, একটি কনস্ট্রাক্টর হল একটি বিশেষ ফাংশন যা শুধুমাত্র কন্ট্র্যাক্ট তৈরির সময় কার্যকর করা হয়।
+ // কনস্ট্রাক্টরগুলি কন্ট্র্যাক্টের ডেটা ইনিশিয়ালাইজ করতে ব্যবহৃত হয়। আরও জানুন:https://solidity.readthedocs.io/en/v0.5.10/contracts.html#constructors
+ constructor(string memory initMessage) {
+
+ // একটি স্ট্রিং আর্গুমেন্ট `initMessage` গ্রহণ করে এবং কন্ট্র্যাক্টের `message` স্টোরেজ ভেরিয়েবলে মান সেট করে)।
+ message = initMessage;
+ }
+
+ // একটি পাবলিক ফাংশন যা একটি স্ট্রিং আর্গুমেন্ট গ্রহণ করে এবং `message` স্টোরেজ ভেরিয়েবল আপডেট করে।
+ function update(string memory newMessage) public {
+ string memory oldMsg = message;
+ message = newMessage;
+ emit UpdatedMessages(oldMsg, newMessage);
+ }
+}
+```
+
+স্মার্ট কন্ট্র্যাক্ট ইভেন্টগুলি আপনার কন্ট্র্যাক্টের জন্য ব্লকচেইনে কিছু ঘটেছে (অর্থাৎ, একটি _ইভেন্ট_ হয়েছে) তা আপনার ফ্রন্ট-এন্ড অ্যাপ্লিকেশনে জানানোর একটি উপায়, যা নির্দিষ্ট ইভেন্টগুলির জন্য 'শুনতে' পারে এবং সেগুলি ঘটলে ব্যবস্থা নিতে পারে।
+
+`addSmartContractListener` ফাংশনটি বিশেষভাবে আমাদের Hello World স্মার্ট কন্ট্র্যাক্টের `UpdatedMessages` ইভেন্টের জন্য শুনবে এবং নতুন বার্তা প্রদর্শন করার জন্য আমাদের UI আপডেট করবে।
+
+`addSmartContractListener`-কে নিম্নলিখিতভাবে পরিবর্তন করুন:
+
+```javascript
+// HelloWorld.js
+
+function addSmartContractListener() {
+ helloWorldContract.events.UpdatedMessages({}, (error, data) => {
+ if (error) {
+ setStatus("😥 " + error.message)
+ } else {
+ setMessage(data.returnValues[1])
+ setNewMessage("")
+ setStatus("🎉 আপনার বার্তা আপডেট করা হয়েছে!")
+ }
+ })
+}
+```
+
+আসুন দেখা যাক লিসেনার যখন একটি ইভেন্ট সনাক্ত করে তখন কী হয়:
+
+- যদি ইভেন্ট নির্গত হওয়ার সময় একটি ত্রুটি ঘটে, তবে এটি আমাদের `status` স্টেট ভেরিয়েবলের মাধ্যমে UI-তে প্রতিফলিত হবে।
+- অন্যথায়, আমরা ফেরত দেওয়া `data` অবজেক্ট ব্যবহার করব। `data.returnValues` একটি শূন্য-সূচীকৃত অ্যারে যেখানে প্রথম উপাদানটি আগের বার্তা এবং দ্বিতীয় উপাদানটি আপডেট করা বার্তা সংরক্ষণ করে। সব মিলিয়ে, একটি সফল ইভেন্টে আমরা আমাদের `message` স্ট্রিংটিকে আপডেট করা বার্তায় সেট করব, `newMessage` স্ট্রিংটি পরিষ্কার করব এবং আমাদের `status` স্টেট ভেরিয়েবলটি আপডেট করব যাতে প্রতিফলিত হয় যে আমাদের স্মার্ট কন্ট্র্যাক্টে একটি নতুন বার্তা প্রকাশিত হয়েছে।
+
+অবশেষে, আসুন আমাদের লিসেনারকে আমাদের `useEffect` ফাংশনে কল করি যাতে এটি `HelloWorld.js` কম্পোনেন্টের প্রথম রেন্ডারে শুরু হয়। সব মিলিয়ে, আপনার `useEffect` ফাংশনটি এইরকম দেখতে হবে:
+
+```javascript
+// HelloWorld.js
+
+useEffect(async () => {
+ const message = await loadCurrentMessage()
+ setMessage(message)
+ addSmartContractListener()
+}, [])
+```
+
+এখন যেহেতু আমরা আমাদের স্মার্ট কন্ট্র্যাক্ট থেকে পড়তে সক্ষম, এটিতে কীভাবে লিখতেও হয় তা বের করা দুর্দান্ত হবে! তবে, আমাদের ডিএ্যাপস-এ লিখতে হলে, আমাদের প্রথমে একটি ইথেরিয়াম ওয়ালেট এর সাথে সংযুক্ত থাকতে হবে।
+
+সুতরাং, এরপর আমরা আমাদের ইথেরিয়াম ওয়ালেট (MetaMask) সেট আপ করব এবং তারপরে এটি আমাদের ডিএ্যাপস-এর সাথে সংযোগ করব!
+
+### ধাপ ৪: আপনার ইথেরিয়াম ওয়ালেট সেট আপ করুন {#step-4-set-up-your-ethereum-wallet}
+
+ইথেরিয়াম চেইনে কিছু লিখতে, ব্যবহারকারীদের তাদের ভার্চুয়াল ওয়ালেটের ব্যক্তিগত কী ব্যবহার করে লেনদেন স্বাক্ষর করতে হবে। এই টিউটোরিয়ালের জন্য, আমরা [MetaMask](https://metamask.io/) ব্যবহার করব, যা ব্রাউজারে একটি ভার্চুয়াল ওয়ালেট এবং আপনার ইথেরিয়াম অ্যাকাউন্টের ঠিকানা পরিচালনা করতে ব্যবহৃত হয়, কারণ এটি শেষ-ব্যবহারকারীর জন্য এই লেনদেন স্বাক্ষর করা খুব সহজ করে তোলে।
+
+আপনি যদি Ethereum-এ লেনদেন কিভাবে কাজ করে সে সম্পর্কে আরও বুঝতে চান, তাহলে ইথেরিয়াম ফাইন্ডেশনের [এই পৃষ্ঠাটি](/developers/docs/transactions/) দেখুন।
+
+#### MetaMask ডাউনলোড করুন {#download-metamask}
+
+আপনি [এখানে](https://metamask.io/download) বিনামূল্যে একটি MetaMask অ্যাকাউন্ট ডাউনলোড এবং তৈরি করতে পারেন। যখন আপনি একটি অ্যাকাউন্ট তৈরি করছেন, বা যদি আপনার আগে থেকেই একটি অ্যাকাউন্ট থাকে, তবে উপরের ডানদিকে থাকা "Goerli Test Network"-এ স্যুইচ করতে ভুলবেন না (যাতে আমরা আসল টাকা নিয়ে কাজ না করি)।
+
+#### একটি ফসেট থেকে ইথার যোগ করুন {#add-ether-from-a-faucet}
+
+ইথেরিয়াম ব্লকচেইনে একটি লেনদেন স্বাক্ষর করার জন্য, আমাদের কিছু নকল Eth লাগবে। Eth পেতে আপনি [FaucETH](https://fauceth.komputing.org)-এ যেতে পারেন এবং আপনার Goerli অ্যাকাউন্টের ঠিকানা লিখতে পারেন, "ফান্ড অনুরোধ করুন"-এ ক্লিক করুন, তারপরে ড্রপডাউনে "Ethereum Testnet Goerli" নির্বাচন করুন এবং অবশেষে আবার "ফান্ড অনুরোধ করুন" বোতামটি ক্লিক করুন। এর কিছুক্ষণ পরেই আপনার MetaMask অ্যাকাউন্টে Eth দেখতে পাবেন!
+
+#### আপনার ব্যালেন্স পরীক্ষা করুন {#check-your-balance}
+
+আমাদের ব্যালেন্স সেখানে আছে কিনা তা দুবার চেক করতে, চলুন [Alchemy’s composer tool](https://composer.alchemyapi.io/?composer_state=%7B%22network%22%3A0%2C%22methodName%22%3A%22eth_getBalance%22%2C%22paramValues%22%3A%5B%22%22%2C%22latest%22%5D%7D) ব্যবহার করে একটি [eth_getBalance](https://docs.alchemyapi.io/alchemy/documentation/alchemy-api-reference/json-rpc#eth_getbalance) রিকোয়েস্ট করি। এটি আমাদের ওয়ালেটে থাকা Eth-এর পরিমাণ ফেরত দেবে। আপনার MetaMask অ্যাকাউন্ট অ্যাড্রেস ইনপুট করার পরে এবং “অনুরোধ পাঠান”-এ ক্লিক করার পরে, আপনার এইরকম একটি প্রতিক্রিয়া দেখা উচিত:
+
+```text
+{"jsonrpc": "2.0", "id": 0, "result": "0xde0b6b3a7640000"}
+```
+
+**দ্রষ্টব্য:** এই ফলাফলটি wei-তে, eth-এ নয়। Wei ইথারের ক্ষুদ্রতম একক হিসাবে ব্যবহৃত হয়। wei থেকে eth-এ রূপান্তর হলো: 1 eth = 10¹⁸ wei। সুতরাং যদি আমরা 0xde0b6b3a7640000 কে দশমিকে রূপান্তর করি, আমরা 1\*10¹⁸ পাই যা 1 eth-এর সমান।
+
+যাক বাবা! আমাদের নকল টাকা সব আছে! 🤑
+
+### ধাপ ৫: MetaMask-কে আপনার UI-এর সাথে সংযোগ করুন {#step-5-connect-metamask-to-your-UI}
+
+এখন যেহেতু আমাদের MetaMask ওয়ালেট সেট আপ করা হয়েছে, চলুন আমাদের dApp-কে এর সাথে সংযুক্ত করি!
+
+#### `connectWallet` ফাংশন {#the-connectWallet-function}
+
+আমাদের `interact.js` ফাইলে, আসুন `connectWallet` ফাংশনটি বাস্তবায়ন করি, যা আমরা তারপরে আমাদের `HelloWorld.js` কম্পোনেন্টে কল করতে পারি।
+
+আসুন `connectWallet`-কে নিম্নলিখিতভাবে পরিবর্তন করি:
+
+```javascript
+// interact.js
+
+export const connectWallet = async () => {
+ if (window.ethereum) {
+ try {
+ const addressArray = await window.ethereum.request({
+ method: "eth_requestAccounts",
+ })
+ const obj = {
+ status: "👆🏽 উপরের টেক্সট-ফিল্ডে একটি বার্তা লিখুন।",
+ address: addressArray[0],
+ }
+ return obj
+ } catch (err) {
+ return {
+ address: "",
+ status: "😥 " + err.message,
+ }
+ }
+ } else {
+ return {
+ address: "",
+ status: (
+
+
+ {" "}
+ 🦊
+ আপনাকে অবশ্যই আপনার ব্রাউজারে MetaMask ইনস্টল করতে হবে, যা একটি ভার্চুয়াল ইথেরিয়াম ওয়ালেট।
+
+
+
+ ),
+ }
+ }
+}
+```
+
+তাহলে এই বিশাল কোড ব্লকটি ঠিক কী করে?
+
+ওয়েল, প্রথমে, এটি পরীক্ষা করে যে আপনার ব্রাউজারে `window.ethereum` সক্ষম আছে কিনা।
+
+`window.ethereum` হল একটি গ্লোবাল API যা MetaMask এবং অন্যান্য ওয়ালেট প্রদানকারীরা ইনজেক্ট করে, যা ওয়েবসাইটগুলিকে ব্যবহারকারীদের ইথেরিয়াম অ্যাকাউন্টগুলির জন্য অনুরোধ করার অনুমতি দেয়। অনুমোদিত হলে, এটি ব্যবহারকারী যে ব্লকচেইনগুলির সাথে সংযুক্ত রয়েছে সেখান থেকে ডেটা পড়তে পারে এবং ব্যবহারকারীকে বার্তা এবং লেনদেন স্বাক্ষর করার পরামর্শ দিতে পারে। আরও তথ্যের জন্য [MetaMask ডক্স](https://docs.metamask.io/guide/ethereum-provider.html#table-of-contents) দেখুন!
+
+যদি `window.ethereum` উপস্থিত _না থাকে_, তার মানে MetaMask ইনস্টল করা নেই। এর ফলে একটি JSON অবজেক্ট রিটার্ন করা হয়, যেখানে রিটার্ন করা `address` একটি খালি স্ট্রিং এবং `status` JSX অবজেক্টটি ব্যবহারকারীকে MetaMask ইনস্টল করার বার্তা দেয়।
+
+এখন যদি `window.ethereum` উপস্থিত _থাকে_, তখনই বিষয়গুলো আকর্ষণীয় হয়ে ওঠে।
+
+একটি try/catch লুপ ব্যবহার করে, আমরা [`window.ethereum.request({ method: \"eth_requestAccounts\" });`](https://docs.metamask.io/guide/rpc-api.html#eth-requestaccounts) কল করে MetaMask-এর সাথে সংযোগ করার চেষ্টা করব। এই ফাংশনটি কল করলে ব্রাউজারে MetaMask খুলবে, যেখানে ব্যবহারকারীকে তাদের ওয়ালেট আপনার dApp-এর সাথে সংযোগ করার জন্য অনুরোধ করা হবে।
+
+- ব্যবহারকারী যদি সংযোগ করতে চান, তবে `method: "eth_requestAccounts"` একটি অ্যারে প্রদান করবে যাতে ব্যবহারকারীর সমস্ত অ্যাকাউন্ট ঠিকানা থাকবে যা ডিএ্যাপস-এর সাথে সংযুক্ত হয়েছে। সবমিলিয়ে, আমাদের `connectWallet` ফাংশনটি একটি JSON অবজেক্ট রিটার্ন করবে যা এই অ্যারের _প্রথম_ `address` (লাইন ৯ দেখুন) এবং একটি `status` বার্তা ধারণ করবে যা ব্যবহারকারীকে স্মার্ট কন্ট্র্যাক্টে একটি বার্তা লিখতে অনুরোধ করে।
+- যদি ব্যবহারকারী সংযোগ প্রত্যাখ্যান করে, তাহলে JSON অবজেক্টটি রিটার্ন করা `address`-এর জন্য একটি খালি স্ট্রিং এবং একটি `status` বার্তা ধারণ করবে যা ব্যবহারকারীর সংযোগ প্রত্যাখ্যান করার বিষয়টি প্রতিফলিত করে।
+
+এখন যেহেতু আমরা এই `connectWallet` ফাংশনটি লিখেছি, পরবর্তী ধাপ হল এটিকে আমাদের `HelloWorld.js` কম্পোনেন্টে কল করা।
+
+#### `connectWallet` ফাংশনটি আপনার `HelloWorld.js` UI কম্পোনেন্টে যোগ করুন {#add-the-connectWallet-function-to-your-HelloWorld-js-ui-component}
+
+`HelloWorld.js`-এর `connectWalletPressed` ফাংশনে নেভিগেট করুন এবং এটিকে নিম্নলিখিতভাবে আপডেট করুন:
+
+```javascript
+// HelloWorld.js
+
+const connectWalletPressed = async () => {
+ const walletResponse = await connectWallet()
+ setStatus(walletResponse.status)
+ setWallet(walletResponse.address)
+}
+```
+
+লক্ষ্য করুন কীভাবে আমাদের বেশিরভাগ কার্যকারিতা `interact.js` ফাইল থেকে আমাদের `HelloWorld.js` কম্পোনেন্ট থেকে বিমূর্ত করা হয়েছে? এটি যাতে আমরা M-V-C প্যারাডাইম মেনে চলি!
+
+`connectWalletPressed`-এ, আমরা কেবল আমাদের ইম্পোর্ট করা `connectWallet` ফাংশনে একটি await কল করি, এবং এর প্রতিক্রিয়ার সাহায্যে, আমরা তাদের স্টেট হুকগুলির মাধ্যমে আমাদের `status` এবং `walletAddress` ভেরিয়েবলগুলি আপডেট করি।
+
+এখন, আসুন উভয় ফাইল (`HelloWorld.js` এবং `interact.js`) সংরক্ষণ করি এবং আমাদের UI পরীক্ষা করি।
+
+আপনার ব্রাউজারে [http://localhost:3000/](http://localhost:3000/) পৃষ্ঠাটি খুলুন এবং পৃষ্ঠার উপরের ডানদিকে "ওয়ালেট সংযোগ করুন" বোতামটি টিপুন।
+
+আপনার যদি MetaMask ইনস্টল করা থাকে, তাহলে আপনাকে আপনার ওয়ালেটটি আপনার dApp-এর সাথে সংযোগ করার জন্য অনুরোধ করা হবে। সংযোগ করার জন্য আমন্ত্রণ গ্রহণ করুন।
+
+আপনি দেখতে পাবেন যে ওয়ালেট বোতামটি এখন প্রতিফলিত করছে যে আপনার ঠিকানা সংযুক্ত! ইয়াসসসস 🔥
+
+এরপর, পৃষ্ঠাটি রিফ্রেশ করার চেষ্টা করুন... এটা অদ্ভুত। আমাদের ওয়ালেট বোতামটি আমাদের MetaMask সংযোগ করার জন্য অনুরোধ করছে, যদিও এটি ইতিমধ্যে সংযুক্ত রয়েছে...
+
+তবে, ভয় পাবেন না! আমরা সহজেই এটি সমাধান করতে পারি (বুঝতে পারছেন?) `getCurrentWalletConnected` বাস্তবায়ন করে, যা পরীক্ষা করবে যে কোনও ঠিকানা ইতিমধ্যে আমাদের ডিএ্যাপস-এর সাথে সংযুক্ত আছে কিনা এবং সেই অনুযায়ী আমাদের UI আপডেট করবে!
+
+#### `getCurrentWalletConnected` ফাংশন {#the-getcurrentwalletconnected-function}
+
+`interact.js` ফাইলে আপনার `getCurrentWalletConnected` ফাংশনটি নিম্নলিখিতভাবে আপডেট করুন:
+
+```javascript
+// interact.js
+
+export const getCurrentWalletConnected = async () => {
+ if (window.ethereum) {
+ try {
+ const addressArray = await window.ethereum.request({
+ method: "eth_accounts",
+ })
+ if (addressArray.length > 0) {
+ return {
+ address: addressArray[0],
+ status: "👆🏽 উপরের টেক্সট-ফিল্ডে একটি বার্তা লিখুন।",
+ }
+ } else {
+ return {
+ address: "",
+ status: "🦊 উপরের ডানদিকের বোতাম ব্যবহার করে MetaMask-এর সাথে সংযোগ করুন।",
+ }
+ }
+ } catch (err) {
+ return {
+ address: "",
+ status: "😥 " + err.message,
+ }
+ }
+ } else {
+ return {
+ address: "",
+ status: (
+
+
+ {" "}
+ 🦊
+ আপনাকে অবশ্যই আপনার ব্রাউজারে MetaMask ইনস্টল করতে হবে, যা একটি ভার্চুয়াল ইথেরিয়াম ওয়ালেট।
+
+
+
+ ),
+ }
+ }
+}
+```
+
+এই কোডটি _খুবই_ অনুরূপ `connectWallet` ফাংশনটির মতো যা আমরা আগের ধাপে লিখেছি।
+
+প্রধান পার্থক্য হল `eth_requestAccounts` মেথড কল করার পরিবর্তে, যা ব্যবহারকারীর ওয়ালেট সংযোগ করার জন্য MetaMask খোলে, এখানে আমরা `eth_accounts` মেথড কল করি, যা সহজভাবে আমাদের dApp-এর সাথে বর্তমানে সংযুক্ত MetaMask অ্যাড্রেসগুলো ধারণকারী একটি অ্যারে রিটার্ন করে।
+
+এই ফাংশনটি কার্যকর দেখতে, আসুন এটিকে আমাদের `HelloWorld.js` কম্পোনেন্টের `useEffect` ফাংশনে কল করি:
+
+```javascript
+// HelloWorld.js
+
+useEffect(async () => {
+ const message = await loadCurrentMessage()
+ setMessage(message)
+ addSmartContractListener()
+
+ const { address, status } = await getCurrentWalletConnected()
+ setWallet(address)
+ setStatus(status)
+}, [])
+```
+
+লক্ষ্য করুন, আমরা `getCurrentWalletConnected`-এ আমাদের কলের প্রতিক্রিয়া ব্যবহার করে আমাদের `walletAddress` এবং `status` স্টেট ভেরিয়েবলগুলিকে আপডেট করি।
+
+এখন যে আপনি এই কোডটি যোগ করেছেন, আসুন আমাদের ব্রাউজার উইন্ডোটি রিফ্রেশ করার চেষ্টা করি।
+
+দারুণ! বোতামটি বলা উচিত যে আপনি সংযুক্ত, এবং আপনার সংযুক্ত ওয়ালেটের অ্যাড্রেসের একটি প্রিভিউ দেখানো উচিত - এমনকি আপনি রিফ্রেশ করার পরেও!
+
+#### `addWalletListener` বাস্তবায়ন করুন {#implement-addwalletlistener}
+
+আমাদের dApp ওয়ালেট সেটআপের চূড়ান্ত ধাপ হল ওয়ালেট লিসেনার ইমপ্লিমেন্ট করা যাতে আমাদের UI আপডেট হয় যখন আমাদের ওয়ালেটের স্টেট পরিবর্তন হয়, যেমন যখন ব্যবহারকারী সংযোগ বিচ্ছিন্ন করে বা অ্যাকাউন্ট পরিবর্তন করে।
+
+আপনার `HelloWorld.js` ফাইলে, আপনার `addWalletListener` ফাংশনটি নিম্নলিখিতভাবে পরিবর্তন করুন:
+
+```javascript
+// HelloWorld.js
+
+function addWalletListener() {
+ if (window.ethereum) {
+ window.ethereum.on("accountsChanged", (accounts) => {
+ if (accounts.length > 0) {
+ setWallet(accounts[0])
+ setStatus("👆🏽 উপরের টেক্সট-ফিল্ডে একটি বার্তা লিখুন।")
+ } else {
+ setWallet("")
+ setStatus("🦊 উপরের ডানদিকের বোতাম ব্যবহার করে MetaMask-এর সাথে সংযোগ করুন।")
+ }
+ })
+ } else {
+ setStatus(
+
+ {" "}
+ 🦊
+ আপনাকে অবশ্যই আপনার ব্রাউজারে MetaMask ইনস্টল করতে হবে, যা একটি ভার্চুয়াল ইথেরিয়াম ওয়ালেট।
+
+
+ )
+ }
+}
+```
+
+আমি বাজি ধরতে পারি যে এই মুহূর্তে এখানে কী ঘটছে তা বোঝার জন্য আপনার আর আমাদের সাহায্যের প্রয়োজন নেই, তবে সম্পূর্ণতার জন্য, আসুন দ্রুত এটি ভেঙে দেখা যাক:
+
+- প্রথমে, আমাদের ফাংশন পরীক্ষা করে যে `window.ethereum` সক্রিয় আছে কিনা (অর্থাৎ MetaMask ইনস্টল করা আছে)।
+ - যদি না থাকে, আমরা কেবল আমাদের `status` স্টেট ভেরিয়েবলটিকে একটি JSX স্ট্রিং-এ সেট করি যা ব্যবহারকারীকে MetaMask ইনস্টল করার জন্য অনুরোধ করে।
+ - যদি এটি সক্রিয় থাকে, আমরা লাইন ৩-এ `window.ethereum.on(\"accountsChanged\")` লিসেনার সেট আপ করি যা MetaMask ওয়ালেটের স্টেট পরিবর্তন শোনে, যার মধ্যে রয়েছে যখন ব্যবহারকারী dApp-এ একটি অতিরিক্ত অ্যাকাউন্ট সংযোগ করে, অ্যাকাউন্ট পরিবর্তন করে বা একটি অ্যাকাউন্ট সংযোগ বিচ্ছিন্ন করে। যদি অন্তত একটি অ্যাকাউন্ট সংযুক্ত থাকে, তাহলে `walletAddress` স্টেট ভেরিয়েবলটি লিসেনারের দ্বারা রিটার্ন করা `accounts` অ্যারের প্রথম অ্যাকাউন্ট হিসেবে আপডেট হয়। অন্যথায়, `walletAddress` একটি খালি স্ট্রিং হিসাবে সেট করা হয়।
+
+সবশেষে, আমাদের এটিকে আমাদের `useEffect` ফাংশনে কল করতে হবে:
+
+```javascript
+// HelloWorld.js
+
+useEffect(async () => {
+ const message = await loadCurrentMessage()
+ setMessage(message)
+ addSmartContractListener()
+
+ const { address, status } = await getCurrentWalletConnected()
+ setWallet(address)
+ setStatus(status)
+
+ addWalletListener()
+}, [])
+```
+
+এবং এটাই সব! আমরা সফলভাবে আমাদের সমস্ত ওয়ালেট কার্যকারিতা প্রোগ্রামিং সম্পন্ন করেছি! এখন আমাদের শেষ কাজ: আমাদের স্মার্ট কন্ট্র্যাক্টে সংরক্ষিত বার্তা আপডেট করা!
+
+### ধাপ ৬: `updateMessage` ফাংশনটি বাস্তবায়ন করুন {#step-6-implement-the-updateMessage-function}
+
+ঠিক আছে বন্ধুরা, আমরা শেষ পর্যায়ে পৌঁছেছি! আপনার `interact.js` ফাইলের `updateMessage`-এ, আমরা নিম্নলিখিতগুলি করতে যাচ্ছি:
+
+1. নিশ্চিত করুন যে আমরা আমাদের স্মার্ট কন্টাক্টে যে বার্তাটি প্রকাশ করতে চাই তা বৈধ
+2. MetaMask ব্যবহার করে আমাদের লেনদেন স্বাক্ষর করুন
+3. আমাদের `HelloWorld.js` ফ্রন্টএন্ড কম্পোনেন্ট থেকে এই ফাংশনটি কল করুন
+
+এতে খুব বেশি সময় লাগবে না; চলুন এই ডিএ্যাপসটি শেষ করি!
+
+#### ইনপুট ত্রুটি হ্যান্ডলিং {#input-error-handling}
+
+স্বাভাবিকভাবেই, ফাংশনের শুরুতে কিছু ধরণের ইনপুট ত্রুটি হ্যান্ডলিং থাকা যুক্তিযুক্ত।
+
+আমরা চাইব যে যদি কোনো MetaMask এক্সটেনশন ইনস্টল করা না থাকে, কোনো ওয়ালেট সংযুক্ত না থাকে (অর্থাৎ, পাস করা `address` একটি খালি স্ট্রিং হয়), বা `message` একটি খালি স্ট্রিং হয়, তাহলে আমাদের ফাংশনটি তাড়াতাড়ি ফিরে আসবে। `updateMessage`-এ নিম্নলিখিত ত্রুটি হ্যান্ডলিং যোগ করুন:
+
+```javascript
+// interact.js
+
+export const updateMessage = async (address, message) => {
+ if (!window.ethereum || address === null) {
+ return {
+ status:
+ "💡 ব্লকচেইনে বার্তা আপডেট করতে আপনার MetaMask ওয়ালেট সংযোগ করুন।",
+ }
+ }
+
+ if (message.trim() === "") {
+ return {
+ status: "❌ আপনার বার্তা একটি খালি স্ট্রিং হতে পারে না।",
+ }
+ }
+}
+```
+
+এখন যে এটিতে সঠিক ইনপুট ত্রুটি হ্যান্ডলিং রয়েছে, এখন MetaMask এর মাধ্যমে লেনদেন স্বাক্ষর করার সময়!
+
+#### আমাদের লেনদেন স্বাক্ষর করা {#signing-our-transaction}
+
+আপনি যদি ঐতিহ্যবাহী ওয়েব3 ইথেরিয়াম লেনদেনের সাথে ইতিমধ্যে স্বাচ্ছন্দ্য বোধ করেন, তবে আমরা পরবর্তীতে যে কোডটি লিখব তা খুব পরিচিত হবে। আপনার ইনপুট ত্রুটি হ্যান্ডলিং কোডের নীচে, `updateMessage`-এ নিম্নলিখিতগুলি যোগ করুন:
+
+```javascript
+// interact.js
+
+//লেনদেন প্যারামিটার সেট আপ করুন
+const transactionParameters = {
+ to: contractAddress, // কন্ট্র্যাক্ট প্রকাশনার সময় ছাড়া প্রয়োজনীয়।
+ from: address, // ব্যবহারকারীর সক্রিয় ঠিকানার সাথে মিলতে হবে।
+ data: helloWorldContract.methods.update(message).encodeABI(),
+}
+
+//লেনদেন স্বাক্ষর করুন
+try {
+ const txHash = await window.ethereum.request({
+ method: "eth_sendTransaction",
+ params: [transactionParameters],
+ })
+ return {
+ status: (
+
+ ✅{" "}
+
+ Etherscan-এ আপনার লেনদেনের স্থিতি দেখুন!
+
+
+ ℹ️ নেটওয়ার্ক দ্বারা লেনদেন যাচাই হয়ে গেলে, বার্তাটি
+ স্বয়ংক্রিয়ভাবে আপডেট হয়ে যাবে।
+
+ ),
+ }
+} catch (error) {
+ return {
+ status: "😥 " + error.message,
+ }
+}
+```
+
+আসুন দেখা যাক কী ঘটছে। প্রথমে, আমরা আমাদের লেনদেনের প্যারামিটার সেট আপ করি, যেখানে:
+
+- `to` প্রাপকের ঠিকানা (আমাদের স্মার্ট কন্ট্র্যাক্ট) নির্দিষ্ট করে
+- `from` লেনদেনের স্বাক্ষরকারীকে নির্দিষ্ট করে, যা আমাদের ফাংশনে পাস করা `address` ভেরিয়েবল
+- `data` আমাদের Hello World স্মার্ট কন্ট্র্যাক্টের `update` পদ্ধতিতে কল ধারণ করে, যা ইনপুট হিসাবে আমাদের `message` স্ট্রিং ভেরিয়েবল গ্রহণ করে
+
+তারপর, আমরা একটি অ্যাওয়েট কল করি, `window.ethereum.request`, যেখানে আমরা MetaMask-কে লেনদেন স্বাক্ষর করতে বলি। লক্ষ্য করুন, ১১ এবং ১২ লাইনে, আমরা আমাদের eth পদ্ধতি, `eth_sendTransaction` নির্দিষ্ট করছি এবং আমাদের `transactionParameters` পাস করছি।
+
+এই সময়ে, MetaMask ব্রাউজারে খুলবে, এবং ব্যবহারকারীকে ট্রানজ্যাকশন সাইন বা প্রত্যাখ্যান করতে অনুরোধ করবে।
+
+- যদি লেনদেন সফল হয়, ফাংশনটি একটি JSON অবজেক্ট প্রদান করবে যেখানে `status` JSX স্ট্রিং ব্যবহারকারীকে তাদের লেনদেন সম্পর্কে আরও তথ্যের জন্য Etherscan দেখতে অনুরোধ করে।
+- যদি লেনদেন ব্যর্থ হয়, ফাংশনটি একটি JSON অবজেক্ট প্রদান করবে যেখানে `status` স্ট্রিং ত্রুটির বার্তা রিলে করে।
+
+সব মিলিয়ে, আমাদের `updateMessage` ফাংশনটি এইরকম দেখতে হবে:
+
+```javascript
+// interact.js
+
+export const updateMessage = async (address, message) => {
+ //ইনপুট ত্রুটি হ্যান্ডলিং
+ if (!window.ethereum || address === null) {
+ return {
+ status:
+ "💡 ব্লকচেইনে বার্তা আপডেট করতে আপনার MetaMask ওয়ালেট সংযোগ করুন।",
+ }
+ }
+
+ if (message.trim() === "") {
+ return {
+ status: "❌ আপনার বার্তা একটি খালি স্ট্রিং হতে পারে না।",
+ }
+ }
+
+ //লেনদেন প্যারামিটার সেট আপ করুন
+ const transactionParameters = {
+ to: contractAddress, // কন্ট্র্যাক্ট প্রকাশনার সময় ছাড়া প্রয়োজনীয়।
+ from: address, // ব্যবহারকারীর সক্রিয় ঠিকানার সাথে মিলতে হবে।
+ data: helloWorldContract.methods.update(message).encodeABI(),
+ }
+
+ //লেনদেন স্বাক্ষর করুন
+ try {
+ const txHash = await window.ethereum.request({
+ method: "eth_sendTransaction",
+ params: [transactionParameters],
+ })
+ return {
+ status: (
+
+ ✅{" "}
+
+ Etherscan-এ আপনার লেনদেনের স্থিতি দেখুন!
+
+
+ ℹ️ নেটওয়ার্ক দ্বারা লেনদেন যাচাই হয়ে গেলে, বার্তাটি
+ স্বয়ংক্রিয়ভাবে আপডেট হয়ে যাবে।
+
+ ),
+ }
+ } catch (error) {
+ return {
+ status: "😥 " + error.message,
+ }
+ }
+}
+```
+
+সবশেষে, আমাদের `updateMessage` ফাংশনটিকে আমাদের `HelloWorld.js` কম্পোনেন্টের সাথে সংযোগ করতে হবে।
+
+#### `updateMessage`-কে `HelloWorld.js` ফ্রন্টএন্ডের সাথে সংযোগ করুন {#connect-updatemessage-to-the-helloworld-js-frontend}
+
+আমাদের `onUpdatePressed` ফাংশনটি ইম্পোর্ট করা `updateMessage` ফাংশনে একটি অ্যাওয়েট কল করবে এবং `status` স্টেট ভেরিয়েবলটি পরিবর্তন করবে যাতে আমাদের লেনদেন সফল হয়েছে নাকি ব্যর্থ হয়েছে তা প্রতিফলিত হয়:
+
+```javascript
+// HelloWorld.js
+
+const onUpdatePressed = async () => {
+ const { status } = await updateMessage(walletAddress, newMessage)
+ setStatus(status)
+}
+```
+
+এটি খুবই পরিচ্ছন্ন এবং সহজ। আর জানেন কী... আপনার ডিএ্যাপস সম্পূর্ণ!!!
+
+এগিয়ে যান এবং **আপডেট** বোতামটি পরীক্ষা করুন!
+
+### আপনার নিজের কাস্টম ডিএ্যাপস তৈরি করুন {#make-your-own-custom-dapp}
+
+ওয়াও, আপনি টিউটোরিয়ালের শেষ পর্যন্ত পৌঁছেছেন! সংক্ষেপে, আপনি শিখেছেন কীভাবে:
+
+- আপনার ডিএ্যাপস প্রজেক্টের সাথে একটি MetaMask ওয়ালেট সংযোগ করা
+- [Alchemy Web3](https://docs.alchemy.com/alchemy/documentation/alchemy-web3) API ব্যবহার করে আপনার স্মার্ট কন্ট্র্যাক্ট থেকে ডেটা পড়া
+- MetaMask ব্যবহার করে ইথেরিয়াম লেনদেন স্বাক্ষর করা
+
+এখন আপনি এই টিউটোরিয়ালের দক্ষতা প্রয়োগ করে আপনার নিজের কাস্টম ডিএ্যাপস প্রজেক্ট তৈরি করার জন্য সম্পূর্ণরূপে সজ্জিত! বরাবরের মতো, আপনার যদি কোনো প্রশ্ন থাকে, তাহলে [Alchemy Discord](https://discord.gg/gWuC7zB)-এ আমাদের কাছে সাহায্যের জন্য পৌঁছাতে দ্বিধা করবেন না। 🧙♂️
+
+এই টিউটোরিয়ালটি সম্পূর্ণ করার পর, টুইটারে [@alchemyplatform](https://twitter.com/AlchemyPlatform)-এ আমাদের ট্যাগ করে আপনার অভিজ্ঞতা কেমন ছিল বা আপনার কোনো মতামত থাকলে আমাদের জানান!
diff --git a/public/content/translations/bn/developers/tutorials/hello-world-smart-contract/index.md b/public/content/translations/bn/developers/tutorials/hello-world-smart-contract/index.md
new file mode 100644
index 00000000000..bf5ea083d3a
--- /dev/null
+++ b/public/content/translations/bn/developers/tutorials/hello-world-smart-contract/index.md
@@ -0,0 +1,366 @@
+---
+title: "শিক্ষানবিশদের জন্য হ্যালো ওয়ার্ল্ড স্মার্ট কন্ট্র্যাক্ট"
+description: "Ethereum-এ একটি সহজ স্মার্ট কন্ট্র্যাক্ট লেখা এবং স্থাপন করার উপর একটি পরিচিতি টিউটোরিয়াল।"
+author: "elanh"
+tags:
+ [
+ "সলিডিটি",
+ "hardhat",
+ "alchemy",
+ "স্মার্ট কন্ট্র্যাক্ট",
+ "ডেপ্লয়িং"
+ ]
+skill: beginner
+lang: bn
+published: 2021-03-31
+---
+
+আপনি যদি ব্লকচেইন ডেভেলপমেন্টে নতুন হন এবং কোথা থেকে শুরু করবেন তা না জানেন, অথবা আপনি যদি শুধুমাত্র স্মার্ট কন্ট্র্যাক্টগুলি কীভাবে স্থাপন এবং তার সাথে ইন্টারঅ্যাক্ট করতে হয় তা বুঝতে চান, তাহলে এই নির্দেশিকাটি আপনার জন্য। আমরা একটি ভার্চুয়াল ওয়ালেট [MetaMask](https://metamask.io/), [Solidity](https://docs.soliditylang.org/en/v0.8.0/), [Hardhat](https://hardhat.org/), এবং [Alchemy](https://www.alchemy.com/eth) ব্যবহার করে Sepolia টেস্ট নেটওয়ার্কে একটি সহজ স্মার্ট কন্ট্র্যাক্ট তৈরি এবং স্থাপন করার মাধ্যমে দেখাব (যদি আপনি এখনও এর কোনটির অর্থ না বোঝেন তবে চিন্তা করবেন না, আমরা এটি ব্যাখ্যা করব)।
+
+এই টিউটোরিয়ালের [পার্ট 2](https://docs.alchemy.com/docs/interacting-with-a-smart-contract)-তে আমরা দেখব কিভাবে আমাদের স্মার্ট কন্ট্র্যাক্টটি এখানে স্থাপন করার পরে তার সাথে ইন্টারঅ্যাক্ট করা যায়, এবং [পার্ট 3](https://www.alchemy.com/docs/submitting-your-smart-contract-to-etherscan)-তে আমরা দেখব কিভাবে এটি Etherscan-এ প্রকাশ করা যায়।
+
+যেকোনো সময়ে আপনার কোনো প্রশ্ন থাকলে [Alchemy Discord](https://discord.gg/gWuC7zB)-এ যোগাযোগ করতে পারেন!
+
+## ধাপ 1: Ethereum নেটওয়ার্কের সাথে সংযোগ করুন {#step-1}
+
+Ethereum চেইনে রিকুয়েস্ট করার অনেক উপায় আছে। সহজ করার জন্য, আমরা Alchemy-তে একটি বিনামূল্যের অ্যাকাউন্ট ব্যবহার করব, এটি একটি ব্লকচেইন ডেভেলপার প্ল্যাটফর্ম এবং API যা আমাদের নিজস্ব নোড চালানোর প্রয়োজন ছাড়াই Ethereum চেইনের সাথে যোগাযোগ করতে দেয়। প্ল্যাটফর্মটিতে পর্যবেক্ষণ এবং বিশ্লেষণের জন্য ডেভেলপার টুলসও রয়েছে যা আমরা এই টিউটোরিয়ালে আমাদের স্মার্ট কন্ট্র্যাক্ট স্থাপনার আড়ালে কী ঘটছে তা বোঝার জন্য ব্যবহার করব। আপনার যদি আগে থেকেই একটি Alchemy অ্যাকাউন্ট না থাকে, [আপনি এখানে বিনামূল্যে সাইন আপ করতে পারেন](https://dashboard.alchemy.com/signup)।
+
+## ধাপ 2: আপনার অ্যাপ (এবং API কী) তৈরি করুন {#step-2}
+
+একবার আপনি একটি Alchemy অ্যাকাউন্ট তৈরি করে ফেললে, আপনি একটি অ্যাপ তৈরি করে একটি API কী জেনারেট করতে পারেন। এটি আমাদের Sepolia টেস্ট নেটওয়ার্কে অনুরোধ করার অনুমতি দেবে। আপনি যদি টেস্টনেটের সাথে পরিচিত না হন, তাহলে [এই পেজটি](/developers/docs/networks/) দেখুন।
+
+1. ন্যাভ বারে "Select an app" নির্বাচন করে এবং "Create new app" ক্লিক করে আপনার Alchemy ড্যাশবোর্ডের "Create new app" পেজে যান
+
+
+
+2. আপনার অ্যাপের নাম দিন “Hello World”, একটি সংক্ষিপ্ত বিবরণ দিন, এবং একটি ব্যবহারের ক্ষেত্র বেছে নিন, যেমন, "Infra & Tooling."। এরপরে, "Ethereum" অনুসন্ধান করুন এবং নেটওয়ার্কটি নির্বাচন করুন।
+
+
+
+3. এগিয়ে যেতে "Next" এ ক্লিক করুন, তারপর "Create app" এ এবং এটিই! আপনার অ্যাপটি একটি API কী কপির জন্য উপলব্ধ সহ ন্যাভ বার ড্রপডাউন মেনুতে উপস্থিত হওয়া উচিত।
+
+## ধাপ 3: একটি Ethereum অ্যাকাউন্ট (অ্যাড্রেস) তৈরি করুন {#step-3}
+
+লেনদেন পাঠানো এবং গ্রহণ করার জন্য আমাদের একটি Ethereum অ্যাকাউন্ট প্রয়োজন। এই টিউটোরিয়ালের জন্য, আমরা MetaMask ব্যবহার করব, যা ব্রাউজারের একটি ভার্চুয়াল ওয়ালেট এবং আপনার Ethereum অ্যাকাউন্ট অ্যাড্রেস পরিচালনা করতে ব্যবহৃত হয়। [লেনদেন](/developers/docs/transactions/) সম্পর্কে আরও।
+
+আপনি [এখানে](https://metamask.io/download) বিনামূল্যে MetaMask ডাউনলোড করতে এবং একটি Ethereum অ্যাকাউন্ট তৈরি করতে পারেন। আপনি যখন একটি অ্যাকাউন্ট তৈরি করছেন, অথবা যদি আপনার আগে থেকেই একটি অ্যাকাউন্ট থাকে, তাহলে নেটওয়ার্ক ড্রপডাউন মেনু ব্যবহার করে "Sepolia" টেস্ট নেটওয়ার্কে স্যুইচ করতে ভুলবেন না (যাতে আমরা আসল টাকা নিয়ে কাজ না করি)।
+
+আপনি যদি Sepolia তালিকাভুক্ত না দেখেন, তাহলে মেনুতে যান, তারপর Advanced-এ যান এবং "Show test networks" চালু করতে নিচে স্ক্রোল করুন। নেটওয়ার্ক নির্বাচন মেনুতে, টেস্টনেটগুলির একটি তালিকা খুঁজে পেতে "Custom" ট্যাবটি বেছে নিন এবং "Sepolia" নির্বাচন করুন।
+
+
+
+## ধাপ 4: একটি ফসেট থেকে ইথার যোগ করুন {#step-4}
+
+টেস্ট নেটওয়ার্কে আমাদের স্মার্ট কন্ট্র্যাক্ট স্থাপন করার জন্য, আমাদের কিছু নকল Eth লাগবে। Sepolia ETH পেতে আপনি বিভিন্ন ফসেটের একটি তালিকা দেখতে [Sepolia নেটওয়ার্কের বিবরণ](/developers/docs/networks/#sepolia)-এ যেতে পারেন। যদি একটি কাজ না করে, তবে অন্যটি চেষ্টা করুন কারণ সেগুলি মাঝে মাঝে খালি হয়ে যেতে পারে। নেটওয়ার্ক ট্রাফিকের কারণে আপনার নকল ETH পেতে কিছু সময় লাগতে পারে। কিছুক্ষণ পরেই আপনার Metamask অ্যাকাউন্টে ETH দেখতে পাবেন!
+
+## ধাপ 5: আপনার ব্যালেন্স পরীক্ষা করুন {#step-5}
+
+আমাদের ব্যালেন্স আছে কিনা তা দুবার পরীক্ষা করার জন্য, আসুন [Alchemy’s composer tool](https://sandbox.alchemy.com/?network=ETH_SEPOLIA&method=eth_getBalance&body.id=1&body.jsonrpc=2.0&body.method=eth_getBalance&body.params%5B0%5D=&body.params%5B1%5D=latest) ব্যবহার করে একটি [eth_getBalance](/developers/docs/apis/json-rpc/#eth_getbalance) অনুরোধ করি। এটি আমাদের ওয়ালেটে থাকা ETH-এর পরিমাণ ফেরত দেবে। আপনার MetaMask অ্যাকাউন্ট অ্যাড্রেস ইনপুট করার পরে এবং “অনুরোধ পাঠান”-এ ক্লিক করার পরে, আপনার এইরকম একটি প্রতিক্রিয়া দেখা উচিত:
+
+```json
+{ "jsonrpc": "2.0", "id": 0, "result": "0x2B5E3AF16B1880000" }
+```
+
+> **দ্রষ্টব্য:** এই ফলাফলটি ETH-এ নয়, wei-তে। Wei ইথারের ক্ষুদ্রতম একক হিসাবে ব্যবহৃত হয়। wei থেকে ETH-তে রূপান্তর হল: 1 eth = 1018 wei। সুতরাং যদি আমরা 0x2B5E3AF16B1880000 কে দশমিকে রূপান্তর করি তাহলে আমরা 5\*10¹⁸ পাই যা 5 ETH এর সমান।
+>
+> যাক বাবা! আমাদের নকল টাকা সব আছে ।
+
+## ধাপ 6: আমাদের প্রজেক্ট শুরু করুন {#step-6}
+
+প্রথমে, আমাদের প্রজেক্টের জন্য একটি ফোল্ডার তৈরি করতে হবে। আপনার কমান্ড লাইনে যান এবং টাইপ করুন:
+
+```
+mkdir hello-world
+cd hello-world
+```
+
+এখন যেহেতু আমরা আমাদের প্রজেক্ট ফোল্ডারের ভিতরে আছি, আমরা প্রজেক্টটি শুরু করতে `npm init` ব্যবহার করব। আপনার যদি আগে থেকেই npm ইনস্টল করা না থাকে, তাহলে [এই নির্দেশাবলী](https://docs.alchemyapi.io/alchemy/guides/alchemy-for-macs#1-install-nodejs-and-npm) অনুসরণ করুন (আমাদের Node.js-ও লাগবে তাই সেটিও ডাউনলোড করুন!)।
+
+```
+npm init
+```
+
+ইনস্টলেশন প্রশ্নগুলির উত্তর আপনি কীভাবে দেন তা সত্যিই গুরুত্বপূর্ণ নয়, রেফারেন্সের জন্য আমরা কীভাবে এটি করেছি তা এখানে রয়েছে:
+
+```
+প্যাকেজের নাম: (hello-world)
+ভার্সন: (1.0.0)
+বিবরণ: হ্যালো ওয়ার্ল্ড স্মার্ট কন্ট্র্যাক্ট
+এন্ট্রি পয়েন্ট: (index.js)
+টেস্ট কমান্ড:
+গিট রিপোজিটরি:
+কীওয়ার্ড:
+লেখক:
+লাইসেন্স: (ISC)
+/Users/.../.../.../hello-world/package.json এ লিখতে চলেছি:
+
+{
+ "name": "hello-world",
+ "version": "1.0.0",
+ "description": "হ্যালো ওয়ার্ল্ড স্মার্ট কন্ট্র্যাক্ট",
+ "main": "index.js",
+ "scripts": {
+ "test": "echo \"Error: no test specified\" && exit 1"
+ },
+ "author": "",
+ "license": "ISC"
+}
+```
+
+package.json অনুমোদন করুন এবং আমরা এগিয়ে যাওয়ার জন্য প্রস্তুত!
+
+## ধাপ 7: [Hardhat](https://hardhat.org/getting-started/#overview) ডাউনলোড করুন {#step-7}
+
+Hardhat হল আপনার Ethereum সফ্টওয়্যার কম্পাইল, স্থাপন, পরীক্ষা এবং ডিবাগ করার জন্য একটি ডেভেলপমেন্ট পরিবেশ। এটি ডেভেলপারদের লাইভ চেইনে স্থাপন করার আগে স্থানীয়ভাবে স্মার্ট কন্ট্র্যাক্ট এবং ডিএ্যাপস তৈরি করতে সাহায্য করে।
+
+আমাদের `hello-world` প্রজেক্টের ভিতরে চালান:
+
+```
+npm install --save-dev hardhat
+```
+
+[ইনস্টলেশন নির্দেশাবলী](https://hardhat.org/getting-started/#overview) সম্পর্কে আরও বিস্তারিত জানতে এই পৃষ্ঠাটি দেখুন।
+
+## ধাপ 8: Hardhat প্রজেক্ট তৈরি করুন {#step-8}
+
+আমাদের প্রজেক্ট ফোল্ডারের ভিতরে চালান:
+
+```
+npx hardhat
+```
+
+তারপরে আপনার একটি স্বাগত বার্তা এবং আপনি কী করতে চান তা নির্বাচন করার একটি বিকল্প দেখতে পাওয়া উচিত। “একটি খালি hardhat.config.js তৈরি করুন” নির্বাচন করুন:
+
+```
+888 888 888 888 888
+888 888 888 888 888
+888 888 888 888 888
+8888888888 8888b. 888d888 .d88888 88888b. 8888b. 888888
+888 888 "88b 888P" d88" 888 888 "88b "88b 888
+888 888 .d888888 888 888 888 888 888 .d888888 888
+888 888 888 888 888 Y88b 888 888 888 888 888 Y88b.
+888 888 "Y888888 888 "Y88888 888 888 "Y888888 "Y888
+
+👷 Hardhat v2.0.11-এ আপনাকে স্বাগতম 👷?
+
+আপনি কি করতে চান? …
+একটি নমুনা প্রজেক্ট তৈরি করুন
+❯ একটি খালি hardhat.config.js তৈরি করুন
+প্রস্থান করুন
+```
+
+এটি আমাদের জন্য একটি `hardhat.config.js` ফাইল তৈরি করবে যেখানে আমরা আমাদের প্রজেক্টের জন্য সমস্ত সেট আপ নির্দিষ্ট করব (ধাপ 13-এ)।
+
+## ধাপ 9: প্রজেক্ট ফোল্ডার যোগ করুন {#step-9}
+
+আমাদের প্রজেক্টকে সংগঠিত রাখতে আমরা দুটি নতুন ফোল্ডার তৈরি করব। আপনার কমান্ড লাইনে আপনার প্রজেক্টের রুট ডিরেক্টরিতে নেভিগেট করুন এবং টাইপ করুন:
+
+```
+mkdir contracts
+mkdir scripts
+```
+
+- `contracts/` হল যেখানে আমরা আমাদের হ্যালো ওয়ার্ল্ড স্মার্ট কন্ট্র্যাক্ট কোড ফাইল রাখব
+- `scripts/` হল যেখানে আমরা আমাদের কন্ট্র্যাক্ট স্থাপন এবং ইন্টারঅ্যাক্ট করার জন্য স্ক্রিপ্ট রাখব
+
+## ধাপ 10: আমাদের কন্ট্র্যাক্ট লিখুন {#step-10}
+
+আপনি হয়তো নিজেকে জিজ্ঞাসা করছেন, আমরা কখন কোড লিখতে যাচ্ছি?? আচ্ছা, আমরা এখানে, ধাপ 10-এ।
+
+আপনার প্রিয় এডিটরে হ্যালো-ওয়ার্ল্ড প্রজেক্টটি খুলুন (আমরা [VSCode](https://code.visualstudio.com/) পছন্দ করি)। স্মার্ট কন্ট্র্যাক্টগুলি সলিডিটি নামক একটি ভাষায় লেখা হয় যা আমরা আমাদের HelloWorld.sol স্মার্ট কন্ট্র্যাক্ট লিখতে ব্যবহার করব।
+
+1. "contracts" ফোল্ডারে যান এবং HelloWorld.sol নামে একটি নতুন ফাইল তৈরি করুন
+2. নিচে Ethereum ফাউন্ডেশন থেকে একটি নমুনা Hello World স্মার্ট কন্ট্র্যাক্ট দেওয়া হলো যা আমরা এই টিউটোরিয়ালের জন্য ব্যবহার করব। নিচের বিষয়বস্তুগুলি আপনার HelloWorld.sol ফাইলে কপি এবং পেস্ট করুন, এবং এই কন্ট্র্যাক্টটি কী করে তা বোঝার জন্য মন্তব্যগুলি পড়তে ভুলবেন না:
+
+```solidity
+// সলিডিটির ভার্সন নির্দিষ্ট করে, সেমান্টিক ভার্সনিং ব্যবহার করে।
+// আরও জানুন: https://solidity.readthedocs.io/en/v0.5.10/layout-of-source-files.html#pragma
+pragma solidity ^0.7.0;
+
+// `HelloWorld` নামে একটি কন্ট্র্যাক্ট সংজ্ঞায়িত করে।
+// একটি কন্ট্র্যাক্ট হল ফাংশন এবং ডেটার (তার স্টেট) একটি সংগ্রহ। একবার স্থাপন করা হলে, একটি কন্ট্র্যাক্ট Ethereum ব্লকচেইনের একটি নির্দিষ্ট অ্যাড্রেসে থাকে। আরও জানুন: https://solidity.readthedocs.io/en/v0.5.10/structure-of-a-contract.html
+contract HelloWorld {
+
+ // `string` টাইপের একটি স্টেট ভেরিয়েবল `message` ঘোষণা করে।
+ // স্টেট ভেরিয়েবল হল এমন ভেরিয়েবল যার মানগুলি স্থায়ীভাবে কন্ট্র্যাক্ট স্টোরেজে সংরক্ষিত থাকে। `public` কীওয়ার্ডটি ভেরিয়েবলগুলিকে কন্ট্র্যাক্টের বাইরে থেকে অ্যাক্সেসযোগ্য করে তোলে এবং একটি ফাংশন তৈরি করে যা অন্য কন্ট্র্যাক্ট বা ক্লায়েন্টরা মান অ্যাক্সেস করার জন্য কল করতে পারে।
+ string public message;
+
+ // অনেক ক্লাস-ভিত্তিক অবজেক্ট-ওরিয়েন্টেড ভাষার মতো, একটি কনস্ট্রাক্টর হল একটি বিশেষ ফাংশন যা শুধুমাত্র কন্ট্র্যাক্ট তৈরির সময় কার্যকর করা হয়।
+ // কনস্ট্রাক্টরগুলি কন্ট্র্যাক্টের ডেটা শুরু করতে ব্যবহৃত হয়। আরও জানুন:https://solidity.readthedocs.io/en/v0.5.10/contracts.html#constructors
+ constructor(string memory initMessage) {
+
+ // একটি স্ট্রিং আর্গুমেন্ট `initMessage` গ্রহণ করে এবং মানটি কন্ট্র্যাক্টের `message` স্টোরেজ ভেরিয়েবলে সেট করে)।
+ message = initMessage;
+ }
+
+ // একটি পাবলিক ফাংশন যা একটি স্ট্রিং আর্গুমেন্ট গ্রহণ করে এবং `message` স্টোরেজ ভেরিয়েবল আপডেট করে।
+ function update(string memory newMessage) public {
+ message = newMessage;
+ }
+}
+```
+
+এটি একটি অত্যন্ত সহজ স্মার্ট কন্ট্র্যাক্ট যা তৈরির সময় একটি বার্তা সংরক্ষণ করে এবং `update` ফাংশন কল করে আপডেট করা যায়।
+
+## ধাপ 11: আপনার প্রজেক্টে MetaMask এবং Alchemy সংযোগ করুন {#step-11}
+
+আমরা একটি MetaMask ওয়ালেট, Alchemy অ্যাকাউন্ট তৈরি করেছি এবং আমাদের স্মার্ট কন্ট্র্যাক্ট লিখেছি, এখন এই তিনটি সংযোগ করার সময়।
+
+আপনার ভার্চুয়াল ওয়ালেট থেকে পাঠানো প্রতিটি লেনদেনের জন্য আপনার অনন্য ব্যক্তিগত কী ব্যবহার করে একটি স্বাক্ষরের প্রয়োজন। আমাদের প্রোগ্রামকে এই অনুমতি দেওয়ার জন্য, আমরা আমাদের ব্যক্তিগত কী (এবং Alchemy API কী) একটি এনভায়রনমেন্ট ফাইলে নিরাপদে সংরক্ষণ করতে পারি।
+
+> লেনদেন পাঠানো সম্পর্কে আরও জানতে, ওয়েব3 ব্যবহার করে লেনদেন পাঠানোর উপর [এই টিউটোরিয়ালটি](/developers/tutorials/sending-transactions-using-web3-and-alchemy/) দেখুন।
+
+প্রথমে, আপনার প্রজেক্ট ডিরেক্টরিতে ডটএনভ প্যাকেজটি ইনস্টল করুন:
+
+```
+npm install dotenv --save
+```
+
+তারপর, আমাদের প্রজেক্টের রুট ডিরেক্টরিতে একটি `.env` ফাইল তৈরি করুন, এবং এতে আপনার MetaMask ব্যক্তিগত কী এবং HTTP Alchemy API URL যোগ করুন।
+
+- আপনার প্রাইভেট কী এক্সপোর্ট করতে [এই নির্দেশাবলী](https://support.metamask.io/configure/accounts/how-to-export-an-accounts-private-key/) অনুসরণ করুন
+- HTTP Alchemy API URL পেতে নিচে দেখুন
+
+
+
+Alchemy API URL কপি করুন
+
+আপনার `.env` ফাইলটি এইরকম দেখতে হবে:
+
+```
+API_URL = "https://eth-sepolia.g.alchemy.com/v2/আপনার-এপিআই-কি"
+PRIVATE_KEY = "আপনার-মেটামাস্ক-প্রাইভেট-কি"
+```
+
+এগুলিকে আমাদের কোডের সাথে সংযোগ করতে, আমরা ধাপ 13-এ আমাদের `hardhat.config.js` ফাইলে এই ভেরিয়েবলগুলিকে রেফারেন্স করব।
+
+
+
+
+.env কমিট করবেন না! অনুগ্রহ করে নিশ্চিত করুন যে আপনার .env ফাইলটি কারো সাথে শেয়ার বা প্রকাশ করবেন না, কারণ এটি করার মাধ্যমে আপনি আপনার গোপনীয়তাগুলির সাথে আপস করছেন। আপনি যদি সংস্করণ নিয়ন্ত্রণ ব্যবহার করেন, তাহলে আপনার .env একটি gitignore ফাইলে যোগ করুন।
+
+
+
+
+## ধাপ 12: Ethers.js ইনস্টল করুন {#step-12-install-ethersjs}
+
+Ethers.js একটি লাইব্রেরি যা [স্ট্যান্ডার্ড JSON-RPC পদ্ধতিগুলিকে](/developers/docs/apis/json-rpc/) আরও ব্যবহারকারী-বান্ধব পদ্ধতির সাথে র্যাপ করে Ethereum-এর সাথে ইন্টারঅ্যাক্ট করা এবং অনুরোধ করা সহজ করে তোলে।
+
+Hardhat অতিরিক্ত টুলিং এবং বর্ধিত কার্যকারিতার জন্য [প্লাগইন](https://hardhat.org/plugins/) একীভূত করা খুব সহজ করে তোলে। আমরা কন্ট্র্যাক্ট স্থাপনার জন্য [Ethers প্লাগইন](https://hardhat.org/docs/plugins/official-plugins#hardhat-ethers) এর সুবিধা নেব ([Ethers.js](https://github.com/ethers-io/ethers.js/)-এর কিছু খুব পরিষ্কার কন্ট্র্যাক্ট স্থাপন পদ্ধতি রয়েছে)।
+
+আপনার প্রজেক্ট ডিরেক্টরিতে টাইপ করুন:
+
+```
+npm install --save-dev @nomiclabs/hardhat-ethers "ethers@^5.0.0"
+```
+
+আমরা পরবর্তী ধাপে আমাদের `hardhat.config.js`-এ ethers এর প্রয়োজনীয়তাও যোগ করব।
+
+## ধাপ 13: hardhat.config.js আপডেট করুন {#step-13-update-hardhatconfigjs}
+
+আমরা এখন পর্যন্ত বেশ কিছু নির্ভরতা এবং প্লাগইন যোগ করেছি, এখন আমাদের `hardhat.config.js` আপডেট করতে হবে যাতে আমাদের প্রজেক্ট তাদের সকলের সম্পর্কে জানতে পারে।
+
+আপনার `hardhat.config.js` আপডেট করে এইরকম করুন:
+
+```
+require('dotenv').config();
+
+require("@nomiclabs/hardhat-ethers");
+const { API_URL, PRIVATE_KEY } = process.env;
+
+/**
+* @type import('hardhat/config').HardhatUserConfig
+*/
+module.exports = {
+ solidity: "0.7.3",
+ defaultNetwork: "sepolia",
+ networks: {
+ hardhat: {},
+ sepolia: {
+ url: API_URL,
+ accounts: [`0x${PRIVATE_KEY}`]
+ }
+ },
+}
+```
+
+## ধাপ 14: আমাদের কন্ট্র্যাক্ট কম্পাইল করুন {#step-14-compile-our-contracts}
+
+সবকিছু ঠিকঠাক কাজ করছে কিনা তা নিশ্চিত করতে, আসুন আমাদের কন্ট্র্যাক্ট কম্পাইল করি। `compile` টাস্কটি অন্তর্নির্মিত হার্ডহ্যাট টাস্কগুলির মধ্যে একটি।
+
+কমান্ড লাইন থেকে রান করুন:
+
+```
+npx hardhat compile
+```
+
+আপনি `SPDX license identifier not provided in source file` সম্পর্কে একটি সতর্কবার্তা পেতে পারেন, কিন্তু সে সম্পর্কে চিন্তা করার দরকার নেই — আশা করি বাকি সব ঠিক আছে! যদি না হয়, আপনি সবসময় [Alchemy ডিসকর্ড](https://discord.gg/u72VCg3)-এ বার্তা দিতে পারেন।
+
+## ধাপ 15: আমাদের ডিপ্লয় স্ক্রিপ্ট লিখুন {#step-15-write-our-deploy-scripts}
+
+এখন যেহেতু আমাদের কন্ট্র্যাক্ট লেখা হয়ে গেছে এবং আমাদের কনফিগারেশন ফাইল প্রস্তুত, এখন আমাদের কন্ট্র্যাক্ট ডেপ্লয় স্ক্রিপ্ট লেখার সময়।
+
+`scripts/` ফোল্ডারে যান এবং `deploy.js` নামে একটি নতুন ফাইল তৈরি করুন, এতে নিম্নলিখিত বিষয়বস্তু যোগ করুন:
+
+```
+async function main() {
+ const HelloWorld = await ethers.getContractFactory("HelloWorld");
+
+ // ডিপ্লয়মেন্ট শুরু করুন, একটি প্রতিশ্রুতি প্রদান করে যা একটি কন্ট্র্যাক্ট অবজেক্টে সমাধান করে
+ const hello_world = await HelloWorld.deploy("Hello World!");
+ console.log("কন্ট্র্যাক্টটি এই ঠিকানায় স্থাপন করা হয়েছে:", hello_world.address);}
+
+main()
+ .then(() => process.exit(0))
+ .catch(error => {
+ console.error(error);
+ process.exit(1);
+ });
+```
+
+Hardhat তাদের [কন্ট্র্যাক্টস টিউটোরিয়াল](https://hardhat.org/tutorial/testing-contracts.html#writing-tests)-এ এই কোডের প্রতিটি লাইন কী করে তা চমৎকারভাবে ব্যাখ্যা করেছে, আমরা এখানে তাদের ব্যাখ্যাগুলি গ্রহণ করেছি।
+
+```
+const HelloWorld = await ethers.getContractFactory("HelloWorld");
+```
+
+ethers.js-এ একটি `ContractFactory` হল একটি অ্যাবস্ট্রাকশন যা নতুন স্মার্ট কন্ট্র্যাক্ট স্থাপন করতে ব্যবহৃত হয়, তাই এখানে `HelloWorld` হল আমাদের হ্যালো ওয়ার্ল্ড কন্ট্র্যাক্টের ইনস্ট্যান্সের জন্য একটি ফ্যাক্টরি। `hardhat-ethers` প্লাগইন ব্যবহার করার সময় `ContractFactory` এবং `Contract` ইনস্ট্যান্সগুলি ডিফল্টরূপে প্রথম সাইনারের সাথে সংযুক্ত থাকে।
+
+```
+const hello_world = await HelloWorld.deploy();
+```
+
+একটি `ContractFactory`-এ `deploy()` কল করা ডিপ্লয়মেন্ট শুরু করবে, এবং একটি `Promise` প্রদান করবে যা একটি `Contract`-এ সমাধান করে। এটি সেই অবজেক্ট যার আমাদের প্রতিটি স্মার্ট কন্ট্র্যাক্ট ফাংশনের জন্য একটি পদ্ধতি রয়েছে।
+
+## ধাপ 16: আমাদের কন্ট্র্যাক্ট স্থাপন করুন {#step-16-deploy-our-contract}
+
+আমরা অবশেষে আমাদের স্মার্ট কন্ট্র্যাক্ট স্থাপন করার জন্য প্রস্তুত! কমান্ড লাইনে যান এবং চালান:
+
+```
+npx hardhat run scripts/deploy.js --network sepolia
+```
+
+তারপরে আপনার এইরকম কিছু দেখা উচিত:
+
+```
+কন্ট্র্যাক্টটি এই ঠিকানায় স্থাপন করা হয়েছে: 0x6cd7d44516a20882cEa2DE9f205bF401c0d23570
+```
+
+যদি আমরা [Sepolia etherscan](https://sepolia.etherscan.io/) এ যাই এবং আমাদের কন্ট্র্যাক্টের ঠিকানা অনুসন্ধান করি তবে আমরা দেখতে পাব যে এটি সফলভাবে স্থাপন করা হয়েছে। লেনদেনটি এইরকম কিছু দেখাবে:
+
+
+
+`From` ঠিকানাটি আপনার MetaMask অ্যাকাউন্টের ঠিকানার সাথে মিলবে এবং To ঠিকানায় “Contract Creation” লেখা থাকবে কিন্তু যদি আমরা লেনদেনে ক্লিক করি তবে আমরা `To` ক্ষেত্রে আমাদের কন্ট্র্যাক্টের ঠিকানা দেখতে পাব:
+
+
+
+অভিনন্দন! আপনি এইমাত্র Ethereum চেইনে একটি স্মার্ট কন্ট্র্যাক্ট স্থাপন করেছেন 🎉
+
+নেপথ্যে কী ঘটছে তা বোঝার জন্য, আসুন আমাদের [Alchemy ড্যাশবোর্ড](https://dashboard.alchemyapi.io/explorer)-এর এক্সপ্লোরার ট্যাবে নেভিগেট করি। আপনার যদি একাধিক Alchemy অ্যাপ থাকে তবে অ্যাপ দ্বারা ফিল্টার করতে এবং “Hello World” নির্বাচন করতে ভুলবেন না।
+
+
+এখানে আপনি কয়েকটি JSON-RPC কল দেখতে পাবেন যা Hardhat/Ethers আমাদের জন্য হুডের নিচে তৈরি করেছে যখন আমরা `.deploy()` ফাংশনটি কল করেছি। এখানে দুটি গুরুত্বপূর্ণ বিষয় হল [`eth_sendRawTransaction`](https://www.alchemy.com/docs/node/abstract/abstract-api-endpoints/eth-send-raw-transaction), যা আমাদের কন্ট্র্যাক্টকে Sepolia চেইনে লেখার অনুরোধ, এবং [`eth_getTransactionByHash`](https://www.alchemy.com/docs/node/abstract/abstract-api-endpoints/eth-get-transaction-by-hash) যা হ্যাস দেওয়া হলে আমাদের লেনদেন সম্পর্কে তথ্য পড়ার অনুরোধ (লেনদেনের সময় একটি সাধারণ প্যাটার্ন)। লেনদেন পাঠানো সম্পর্কে আরও জানতে, [Web3 ব্যবহার করে লেনদেন পাঠানো](/developers/tutorials/sending-transactions-using-web3-and-alchemy/) এই টিউটোরিয়ালটি দেখুন।
+
+এই টিউটোরিয়ালের পার্ট 1 এর জন্য এটুকুই, পার্ট 2-এ আমরা আমাদের প্রাথমিক বার্তা আপডেট করে আমাদের [স্মার্ট কন্ট্র্যাক্টের সাথে ইন্টারঅ্যাক্ট করব](https://www.alchemy.com/docs/interacting-with-a-smart-contract), এবং পার্ট 3-এ আমরা [আমাদের স্মার্ট কন্ট্র্যাক্ট Etherscan-এ প্রকাশ করব](https://www.alchemy.com/docs/submitting-your-smart-contract-to-etherscan) যাতে সবাই জানতে পারে কিভাবে এর সাথে ইন্টারঅ্যাক্ট করতে হয়।
+
+**Alchemy সম্পর্কে আরও জানতে চান? আমাদের [ওয়েবসাইট](https://www.alchemy.com/eth) দেখুন। কখনো কোনো আপডেট মিস করতে চান না? [এখানে](https://www.alchemy.com/newsletter) আমাদের নিউজলেটারে সাবস্ক্রাইব করুন! আমাদের [Discord](https://discord.gg/u72VCg3)-এও যোগ দিতে ভুলবেন না।**.
diff --git a/public/content/translations/bn/developers/tutorials/how-to-implement-an-erc721-market/index.md b/public/content/translations/bn/developers/tutorials/how-to-implement-an-erc721-market/index.md
new file mode 100644
index 00000000000..4afbaf5d6b6
--- /dev/null
+++ b/public/content/translations/bn/developers/tutorials/how-to-implement-an-erc721-market/index.md
@@ -0,0 +1,145 @@
+---
+title: "কিভাবে একটি ERC-721 বাজার প্রয়োগ করবেন"
+description: "কিভাবে একটি বিকেন্দ্রীভূত ক্লাসিফায়েড বোর্ডে টোকেনাইজড আইটেম বিক্রির জন্য রাখবেন"
+author: "Alberto Cuesta Cañada"
+tags: [ "স্মার্ট কন্ট্র্যাক্ট", "erc-721", "সলিডিটি", "টোকেন" ]
+skill: intermediate
+lang: bn
+published: 2020-03-19
+source: Hackernoon
+sourceUrl: https://hackernoon.com/how-to-implement-an-erc721-market-1e1a32j9
+---
+
+এই আর্টিকেলে, আমি আপনাকে দেখাতে যাচ্ছি কিভাবে Ethereum ব্লকচেইনের জন্য Craigslist কোড করতে হয়।
+
+Gumtree, Ebay এবং Craigslist-এর আগে, ক্লাসিফায়েড বোর্ডগুলি বেশিরভাগই কর্ক বা কাগজ দিয়ে তৈরি ছিল। স্কুলের করিডোরে, সংবাদপত্রে, রাস্তার আলোতে, দোকানের সামনে ক্লাসিফায়েড বোর্ড ছিল।
+
+ইন্টারনেটের সাথে সাথে এই সবকিছু বদলে গেছে। একটি নির্দিষ্ট ক্লাসিফায়েড বোর্ড দেখতে পারা মানুষের সংখ্যা বহুগুণে বেড়ে গেছে। এর সাথে, তারা যে বাজারগুলির প্রতিনিধিত্ব করে তা অনেক বেশি দক্ষ হয়ে ওঠে এবং বিশ্বব্যাপী আকারে স্কেল করা হয়েছিল। Ebay একটি বিশাল ব্যবসা যার উৎপত্তি এই শারীরিক ক্লাসিফায়েড বোর্ডগুলি থেকে হয়েছে।
+
+ব্লকচেইনের সাথে এই বাজারগুলি আরও একবার পরিবর্তনের জন্য প্রস্তুত, আমি আপনাকে দেখাই কিভাবে।
+
+## নগদীকরণ {#monetization}
+
+একটি পাবলিক ব্লকচেইন ক্লাসিফায়েড বোর্ডের ব্যবসায়িক মডেল Ebay এবং কোম্পানির থেকে ভিন্ন হতে হবে।
+
+প্রথমত, এখানে [বিকেন্দ্রীকরণের দৃষ্টিকোণ](/developers/docs/web2-vs-web3/) রয়েছে। বিদ্যমান প্ল্যাটফর্মগুলিকে তাদের নিজস্ব সার্ভার বজায় রাখতে হবে। একটি বিকেন্দ্রীভূত প্ল্যাটফর্ম তার ব্যবহারকারীদের দ্বারা রক্ষণাবেক্ষণ করা হয়, তাই প্ল্যাটফর্মের মালিকের জন্য মূল প্ল্যাটফর্মটি চালানোর খরচ শূন্যে নেমে আসে।
+
+তারপর রয়েছে ফ্রন্ট এন্ড, ওয়েবসাইট বা ইন্টারফেস যা প্ল্যাটফর্মে অ্যাক্সেস দেয়। এখানে অনেক বিকল্প আছে। প্ল্যাটফর্মের মালিকরা অ্যাক্সেস সীমাবদ্ধ করতে পারে এবং প্রত্যেককে তাদের ইন্টারফেস ব্যবহার করতে বাধ্য করতে পারে, একটি ফি চার্জ করে। প্ল্যাটফর্মের মালিকরা অ্যাক্সেস খোলার সিদ্ধান্তও নিতে পারে (জনগণের হাতে ক্ষমতা!) এবং যে কাউকে প্ল্যাটফর্মে ইন্টারফেস তৈরি করতে দিন। অথবা মালিকরা সেই চরম পর্যায়গুলোর মাঝখানে যেকোনো পদ্ধতির সিদ্ধান্ত নিতে পারেন।
+
+_আমার চেয়ে বেশি দূরদৃষ্টিসম্পন্ন ব্যবসায়িক নেতারা জানবেন কিভাবে এটিকে নগদীকরণ করা যায়। আমি শুধু দেখছি যে এটি স্থিতাবস্থা থেকে আলাদা এবং সম্ভবত লাভজনক।_
+
+উপরন্তু, এখানে অটোমেশন এবং পেমেন্টের দৃষ্টিকোণ রয়েছে। কিছু জিনিস খুব [কার্যকরভাবে টোকেনাইজড](https://hackernoon.com/tokenization-of-digital-assets-g0ffk3v8s?ref=hackernoon.com) করা যেতে পারে এবং একটি ক্লাসিফায়েড বোর্ডে ট্রেড করা যেতে পারে। টোকেনাইজড অ্যাসেটগুলি একটি ব্লকচেইনে সহজেই স্থানান্তর করা যায়। অত্যন্ত জটিল পেমেন্ট পদ্ধতি একটি ব্লকচেইনে সহজেই প্রয়োগ করা যেতে পারে।
+
+আমি এখানে শুধু একটি ব্যবসায়িক সুযোগের গন্ধ পাচ্ছি। কোনো চলমান খরচ ছাড়াই একটি ক্লাসিফায়েড বোর্ড সহজেই প্রয়োগ করা যেতে পারে, প্রতিটি লেনদেনে অন্তর্ভুক্ত জটিল পেমেন্ট পাথ সহ। আমি নিশ্চিত যে কেউ এটি কিসের জন্য ব্যবহার করতে হবে সে সম্পর্কে একটি ধারণা নিয়ে আসবে।
+
+আমি শুধু এটি তৈরি করে খুশি। চলুন কোডটি একবার দেখে নেওয়া যাক।
+
+## বাস্তবায়ন {#implementation}
+
+কিছু সময় আগে আমরা ব্যবসায়িক ক্ষেত্রের উদাহরণ বাস্তবায়ন এবং অন্যান্য ভাল জিনিস সহ একটি [ওপেন সোর্স রিপোজিটরি](https://github.com/HQ20/contracts?ref=hackernoon.com) শুরু করেছি, অনুগ্রহ করে একবার দেখুন।
+
+এই [Ethereum ক্লাসিফায়েড বোর্ড](https://github.com/HQ20/contracts/tree/master/contracts/classifieds?ref=hackernoon.com) এর কোডটি সেখানে আছে, দয়া করে এটি ব্যবহার করুন এবং যথেচ্ছভাবে ব্যবহার করুন। শুধু সচেতন থাকুন যে কোডটি অডিট করা হয়নি এবং এতে টাকা লাগানোর আগে আপনাকে নিজের যথাযথ সতর্কতা অবলম্বন করতে হবে।
+
+বোর্ডের মূল বিষয়গুলি জটিল নয়। বোর্ডের সমস্ত বিজ্ঞাপনগুলি কয়েকটি ফিল্ড সহ একটি স্ট্রাকট হবে:
+
+```solidity
+struct Trade {
+ address poster;
+ uint256 item;
+ uint256 price;
+ bytes32 status; // খোলা, কার্যকর, বাতিল
+}
+```
+
+সুতরাং বিজ্ঞাপন পোস্ট করার জন্য কেউ একজন আছেন। বিক্রির জন্য একটি আইটেম। আইটেমটির জন্য একটি মূল্য। ট্রেডের স্ট্যাটাস যা খোলা, কার্যকর বা বাতিল হতে পারে।
+
+এই সমস্ত ট্রেড একটি ম্যাপিংয়ে রাখা হবে। কারণ Solidity-তে সবকিছুই একটি ম্যাপিং বলে মনে হয়। এছাড়াও কারণ এটি সুবিধাজনক।
+
+```solidity
+mapping(uint256 => Trade) public trades;
+```
+
+একটি ম্যাপিং ব্যবহার করার অর্থ হল, এটি পোস্ট করার আগে আমাদের প্রতিটি বিজ্ঞাপনের জন্য একটি আইডি তৈরি করতে হবে এবং এটিতে কাজ করার আগে আমাদের একটি বিজ্ঞাপনের আইডি জানতে হবে। স্মার্ট কন্ট্র্যাক্ট বা ফ্রন্ট-এন্ডে এর সাথে মোকাবিলা করার একাধিক উপায় রয়েছে। আপনার যদি কিছু দিকনির্দেশনার প্রয়োজন হয় তবে জিজ্ঞাসা করুন।
+
+এরপরে প্রশ্ন আসে যে আমরা যে আইটেমগুলি নিয়ে কাজ করি সেগুলি কী, এবং লেনদেনের জন্য অর্থ প্রদানের জন্য ব্যবহৃত এই মুদ্রাটি কী।
+
+আইটেমগুলির জন্য, আমরা কেবল জিজ্ঞাসা করতে যাচ্ছি যে তারা [ERC-721](https://github.com/OpenZeppelin/openzeppelin-contracts/blob/master/contracts/token/ERC721/IERC721.sol?ref=hackernoon.com) ইন্টারফেসটি প্রয়োগ করে, যা প্রকৃতপক্ষে ব্লকচেইনে বাস্তব বিশ্বের আইটেমগুলিকে উপস্থাপন করার একটি উপায়, যদিও এটি [ডিজিটাল অ্যাসেটগুলির সাথে সবচেয়ে ভাল কাজ করে](https://hackernoon.com/tokenization-of-digital-assets-g0ffk3v8s?ref=hackernoon.com)। আমরা কনস্ট্রাক্টরে আমাদের নিজস্ব ERC721 কন্ট্র্যাক্ট নির্দিষ্ট করতে যাচ্ছি, যার অর্থ আমাদের ক্লাসিফায়েড বোর্ডের যেকোনো অ্যাসেটকে আগে থেকে টোকেনাইজড করতে হবে।
+
+পেমেন্টের জন্য, আমরা একই ধরনের কিছু করতে যাচ্ছি। বেশিরভাগ ব্লকচেইন প্রকল্প তাদের নিজস্ব [ERC-20](https://github.com/OpenZeppelin/openzeppelin-contracts/blob/master/contracts/token/ERC20/ERC20.sol?ref=hackernoon.com) ক্রিপটোকারেন্সি সংজ্ঞায়িত করে। অন্য কেউ কেউ DAI-এর মতো একটি মূলধারার মুদ্রা ব্যবহার করতে পছন্দ করেন। এই ক্লাসিফায়েড বোর্ডে, আপনার মুদ্রা কী হবে তা নির্মাণের সময় আপনাকে সিদ্ধান্ত নিতে হবে। সহজ।
+
+```solidity
+constructor (
+ address _currencyTokenAddress, address _itemTokenAddress
+) public {
+ currencyToken = IERC20(_currencyTokenAddress);
+ itemToken = IERC721(_itemTokenAddress);
+ tradeCounter = 0;
+}
+```
+
+আমরা প্রায় সেখানে পৌঁছে গেছি। আমরা বিজ্ঞাপন, ট্রেডের জন্য আইটেম এবং পেমেন্টের জন্য একটি মুদ্রা পেয়েছি। একটি বিজ্ঞাপন তৈরি করার অর্থ হল একটি আইটেম এসক্রোতে রাখা, এটি দেখানোর জন্য যে এটি আপনার কাছে আছে এবং আপনি এটি দুবার পোস্ট করেননি, সম্ভবত একটি ভিন্ন বোর্ডে।
+
+নীচের কোডটি ঠিক তাই করে। আইটেমটি এসক্রোতে রাখে, বিজ্ঞাপন তৈরি করে, কিছু হাউসকিপিং করে।
+
+```solidity
+function openTrade(uint256 _item, uint256 _price)
+ public
+{
+ itemToken.transferFrom(msg.sender, address(this), _item);
+ trades[tradeCounter] = Trade({
+ poster: msg.sender,
+ item: _item,
+ price: _price,
+ status: "Open"
+ });
+ tradeCounter += 1;
+ emit TradeStatusChange(tradeCounter - 1, "Open");
+}
+```
+
+ট্রেডটি গ্রহণ করার অর্থ হল একটি বিজ্ঞাপন (ট্রেড) বেছে নেওয়া, মূল্য পরিশোধ করা, আইটেমটি গ্রহণ করা। নীচের কোডটি একটি ট্রেড পুনরুদ্ধার করে। এটি উপলব্ধ কিনা তা পরীক্ষা করে। আইটেমটির জন্য অর্থ প্রদান করে। আইটেমটি পুনরুদ্ধার করে। বিজ্ঞাপন আপডেট করে।
+
+```solidity
+function executeTrade(uint256 _trade)
+ public
+{
+ Trade memory trade = trades[_trade];
+ require(trade.status == "Open", "ট্রেডটি খোলা নেই।");
+ currencyToken.transferFrom(msg.sender, trade.poster, trade.price);
+ itemToken.transferFrom(address(this), msg.sender, trade.item);
+ trades[_trade].status = "Executed";
+ emit TradeStatusChange(_trade, "Executed");
+}
+```
+
+অবশেষে, আমাদের কাছে বিক্রেতাদের জন্য একটি বিকল্প রয়েছে ক্রেতা গ্রহণ করার আগে একটি ট্রেড থেকে সরে আসার। কিছু মডেলে, বিজ্ঞাপনগুলি মেয়াদ শেষ হওয়ার আগে কিছু সময়ের জন্য লাইভ থাকে। আপনার বাজারের ডিজাইনের উপর নির্ভর করে এটি আপনার পছন্দ।
+
+কোডটি একটি ট্রেড কার্যকর করার জন্য ব্যবহৃত কোডের সাথে খুব সাদৃশ্যপূর্ণ, শুধুমাত্র এখানে কোনো মুদ্রা হাতবদল হয় না এবং আইটেমটি বিজ্ঞাপন পোস্টারের কাছে ফিরে যায়।
+
+```solidity
+function cancelTrade(uint256 _trade)
+ public
+{
+ Trade memory trade = trades[_trade];
+ require(
+ msg.sender == trade.poster,
+ "ট্রেড শুধুমাত্র পোস্টার দ্বারা বাতিল করা যেতে পারে।"
+ );
+ require(trade.status == "Open", "ট্রেডটি খোলা নেই।");
+ itemToken.transferFrom(address(this), trade.poster, trade.item);
+ trades[_trade].status = "Cancelled";
+ emit TradeStatusChange(_trade, "Cancelled");
+}
+```
+
+এই পর্যন্তই। আপনি বাস্তবায়নের শেষ পর্যন্ত পৌঁছেছেন। কোডে প্রকাশ করা হলে কিছু ব্যবসায়িক ধারণা কতটা সংক্ষিপ্ত হয় তা বেশ আশ্চর্যজনক, এবং এটি সেইসব ক্ষেত্রের মধ্যে একটি। সম্পূর্ণ কন্ট্র্যাক্টটি [আমাদের রেপোতে](https://github.com/HQ20/contracts/blob/master/contracts/classifieds/Classifieds.sol) দেখুন।
+
+## উপসংহার {#conclusion}
+
+ক্লাসিফায়েড বোর্ডগুলি একটি সাধারণ বাজার কনফিগারেশন যা ইন্টারনেটের সাথে ব্যাপকভাবে প্রসারিত হয়েছে, এবং কিছু একচেটিয়া বিজয়ীর সাথে এটি একটি অত্যন্ত জনপ্রিয় ব্যবসায়িক মডেল হয়ে উঠেছে।
+
+ক্লাসিফায়েড বোর্ডগুলি ব্লকচেইন পরিবেশে নকল করার জন্য একটি সহজ টুল, যার কিছু নির্দিষ্ট বৈশিষ্ট্য রয়েছে যা বিদ্যমান জায়ান্টদের জন্য একটি চ্যালেঞ্জ তৈরি করা সম্ভব করবে।
+
+এই আর্টিকেলে, আমি একটি ক্লাসিফায়েড বোর্ড ব্যবসার ব্যবসায়িক বাস্তবতা এবং প্রযুক্তিগত বাস্তবায়নের মধ্যে একটি সেতুবন্ধন করার চেষ্টা করেছি। আপনার যদি সঠিক দক্ষতা থাকে তবে এই জ্ঞান আপনাকে বাস্তবায়নের জন্য একটি দৃষ্টিভঙ্গি এবং একটি রোডম্যাপ তৈরি করতে সাহায্য করবে।
+
+বরাবরের মতো, আপনি যদি মজাদার কিছু তৈরি করতে চান এবং কিছু পরামর্শ চান, তাহলে অনুগ্রহ করে [আমার সাথে যোগাযোগ করুন](https://albertocuesta.es/)! আমি সাহায্য করতে সবসময় খুশি।
diff --git a/public/content/translations/bn/developers/tutorials/how-to-mint-an-nft/index.md b/public/content/translations/bn/developers/tutorials/how-to-mint-an-nft/index.md
new file mode 100644
index 00000000000..ddf3326fa85
--- /dev/null
+++ b/public/content/translations/bn/developers/tutorials/how-to-mint-an-nft/index.md
@@ -0,0 +1,335 @@
+---
+title: "কীভাবে একটি NFT মিন্ট করবেন (NFT টিউটোরিয়াল সিরিজের পার্ট 2/3)"
+description: "এই টিউটোরিয়ালে আমাদের স্মার্ট কন্ট্র্যাক্ট এবং Web3 ব্যবহার করে Ethereum ব্লকচেইনে কীভাবে একটি NFT মিন্ট করতে হয় তা বর্ণনা করা হয়েছে।"
+author: "Sumi Mudgil"
+tags:
+ [
+ "ERC-721",
+ "alchemy",
+ "সলিডিটি",
+ "স্মার্ট কন্ট্র্যাক্ট"
+ ]
+skill: beginner
+lang: bn
+published: 2021-04-22
+---
+
+[Beeple](https://www.nytimes.com/2021/03/11/arts/design/nft-auction-christies-beeple.html): $69 মিলিয়ন
+[3LAU](https://www.forbes.com/sites/abrambrown/2021/03/03/3lau-nft-nonfungible-tokens-justin-blau/?sh=5f72ef64643b): $11 মিলিয়ন
+[Grimes](https://www.theguardian.com/music/2021/mar/02/grimes-sells-digital-art-collection-non-fungible-tokens): $6 মিলিয়ন
+
+তারা সবাই Alchemy-এর শক্তিশালী API ব্যবহার করে তাদের NFT মিন্ট করেছে। এই টিউটোরিয়ালে, আমরা আপনাকে \<10 মিনিটের মধ্যে একই কাজটি কীভাবে করতে হয় তা শেখাব।
+
+“একটি NFT মিন্ট করা” হল ব্লকচেইনে আপনার ERC-721 টোকেনের একটি অনন্য ইনস্ট্যান্স প্রকাশ করার কাজ। [এই NFT টিউটোরিয়াল সিরিজের পার্ট 1](/developers/tutorials/how-to-write-and-deploy-an-nft/) থেকে আমাদের স্মার্ট কন্ট্র্যাক্ট ব্যবহার করে, আসুন আমাদের Web3 দক্ষতা দিয়ে একটি NFT মিন্ট করি। এই টিউটোরিয়াল শেষে, আপনি আপনার মন (এবং ওয়ালেট) যতগুলো চায় ততগুলো NFT মিন্ট করতে পারবেন!
+
+চলুন শুরু করা যাক!
+
+## ধাপ 1: Web3 ইনস্টল করুন {#install-web3}
+
+আপনি যদি আপনার NFT স্মার্ট কন্ট্র্যাক্ট তৈরির প্রথম টিউটোরিয়ালটি অনুসরণ করে থাকেন, তাহলে আপনার ইতিমধ্যেই Ethers.js ব্যবহারের অভিজ্ঞতা আছে। Web3 হল Ethers-এর মতোই, কারণ এটি একটি লাইব্রেরি যা Ethereum ব্লকচেইনে রিকোয়েস্ট তৈরি করা সহজ করতে ব্যবহৃত হয়। এই টিউটোরিয়ালে আমরা [Alchemy Web3](https://docs.alchemyapi.io/alchemy/documentation/alchemy-web3) ব্যবহার করব, যা একটি উন্নত Web3 লাইব্রেরি যা অটোম্যাটিক পুনরায় চেষ্টা এবং শক্তিশালী WebSocket সাপোর্ট প্রদান করে।
+
+আপনার প্রজেক্টের হোম ডিরেক্টরিতে রান করুন:
+
+```
+npm install @alch/alchemy-web3
+```
+
+## ধাপ 2: একটি `mint-nft.js` ফাইল তৈরি করুন {#create-mintnftjs}
+
+আপনার স্ক্রিপ্ট ডিরেক্টরির ভিতরে, একটি `mint-nft.js` ফাইল তৈরি করুন এবং কোডের নিম্নলিখিত লাইনগুলি যোগ করুন:
+
+```js
+require("dotenv").config()
+const API_URL = process.env.API_URL
+const { createAlchemyWeb3 } = require("@alch/alchemy-web3")
+const web3 = createAlchemyWeb3(API_URL)
+```
+
+## ধাপ 3: আপনার কন্ট্র্যাক্টের ABI নিন {#contract-abi}
+
+আমাদের কন্ট্র্যাক্টের ABI (অ্যাপ্লিকেশন বাইনারি ইন্টারফেস) হল আমাদের স্মার্ট কন্ট্র্যাক্টের সাথে ইন্টারঅ্যাক্ট করার ইন্টারফেস। আপনি [এখানে](https://docs.alchemyapi.io/alchemy/guides/eth_getlogs#what-are-ab-is) কন্ট্র্যাক্ট ABI সম্পর্কে আরও জানতে পারেন। Hardhat স্বয়ংক্রিয়ভাবে আমাদের জন্য একটি ABI তৈরি করে এবং `MyNFT.json` ফাইলে সেভ করে। এটি ব্যবহার করার জন্য আমাদের `mint-nft.js` ফাইলে নিম্নলিখিত কোডের লাইনগুলি যোগ করে বিষয়বস্তু পার্স করতে হবে:
+
+```js
+const contract = require("../artifacts/contracts/MyNFT.sol/MyNFT.json")
+```
+
+আপনি যদি ABI দেখতে চান তবে আপনি এটি আপনার কনসোলে প্রিন্ট করতে পারেন:
+
+```js
+console.log(JSON.stringify(contract.abi))
+```
+
+`mint-nft.js` রান করতে এবং আপনার ABI কনসোলে প্রিন্ট করা দেখতে, আপনার টার্মিনালে নেভিগেট করুন এবং রান করুন:
+
+```js
+node scripts/mint-nft.js
+```
+
+## ধাপ 4: IPFS ব্যবহার করে আপনার NFT-এর জন্য মেটাডেটা কনফিগার করুন {#config-meta}
+
+আপনার যদি পার্ট 1-এ আমাদের টিউটোরিয়াল থেকে মনে থাকে, আমাদের `mintNFT` স্মার্ট কন্ট্র্যাক্ট ফাংশন একটি tokenURI প্যারামিটার নেয় যা NFT-এর মেটাডেটা বর্ণনাকারী একটি JSON ডকুমেন্টে রিসলভ হওয়া উচিত — যা সত্যিই NFT-কে জীবন্ত করে তোলে, এটিকে কনফিগারযোগ্য বৈশিষ্ট্য, যেমন নাম, বর্ণনা, ছবি এবং অন্যান্য অ্যাট্রিবিউট পেতে দেয়।
+
+> _ইন্টারপ্ল্যানেটারি ফাইল সিস্টেম (IPFS) হল একটি ডিস্ট্রিবিউটেড ফাইল সিস্টেমে ডেটা সংরক্ষণ এবং শেয়ার করার জন্য একটি ডিসেন্ট্রালাইজড প্রোটোকল এবং পিয়ার-টু-পিয়ার নেটওয়ার্ক।_
+
+আমরা Pinata ব্যবহার করব, একটি সুবিধাজনক IPFS API এবং টুলকিট, আমাদের NFT অ্যাসেট এবং মেটাডেটা সংরক্ষণ করার জন্য যাতে আমাদের NFT সত্যিই ডিসেন্ট্রালাইজড হয়। আপনার যদি Pinata অ্যাকাউন্ট না থাকে, তাহলে [এখানে](https://app.pinata.cloud) একটি বিনামূল্যের অ্যাকাউন্টের জন্য সাইন আপ করুন এবং আপনার ইমেল যাচাই করার পদক্ষেপগুলি সম্পূর্ণ করুন।
+
+আপনি একটি অ্যাকাউন্ট তৈরি করার পরে:
+
+- “Files” পেজে নেভিগেট করুন এবং পেজের উপরের বাম দিকে নীল "Upload" বোতামে ক্লিক করুন।
+
+- Pinata-তে একটি ছবি আপলোড করুন — এটি আপনার NFT-এর জন্য ছবির অ্যাসেট হবে। আপনার ইচ্ছামত অ্যাসেটের নাম দিন
+
+- আপলোড করার পরে, আপনি "Files" পেজের টেবিলে ফাইলের তথ্য দেখতে পাবেন। আপনি একটি CID কলামও দেখতে পাবেন। আপনি এটির পাশের কপি বোতামে ক্লিক করে CID কপি করতে পারেন। আপনি আপনার আপলোড দেখতে পারেন এখানে: `https://gateway.pinata.cloud/ipfs/`। উদাহরণস্বরূপ, আমরা IPFS-এ যে ছবিটি ব্যবহার করেছি তা [এখানে](https://gateway.pinata.cloud/ipfs/QmZdd5KYdCFApWn7eTZJ1qgJu18urJrP9Yh1TZcZrZxxB5) পেতে পারেন।
+
+যারা দেখে শিখতে বেশি পছন্দ করে, তাদের জন্য উপরের পদক্ষেপগুলি এখানে সংক্ষিপ্ত করা হয়েছে:
+
+
+
+এখন, আমরা Pinata-তে আরও একটি ডকুমেন্ট আপলোড করতে চাই। কিন্তু তা করার আগে, আমাদের এটি তৈরি করতে হবে!
+
+আপনার রুট ডিরেক্টরিতে, `nft-metadata.json` নামে একটি নতুন ফাইল তৈরি করুন এবং নিম্নলিখিত json কোড যোগ করুন:
+
+```json
+{
+ "attributes": [
+ {
+ "trait_type": "Breed",
+ "value": "Maltipoo"
+ },
+ {
+ "trait_type": "Eye color",
+ "value": "Mocha"
+ }
+ ],
+ "description": "বিশ্বের সবচেয়ে আদুরে এবং সংবেদনশীল কুকুরছানা।",
+ "image": "ipfs://QmWmvTJmJU3pozR9ZHFmQC2DNDwi2XJtf3QGyYiiagFSWb",
+ "name": "Ramses"
+}
+```
+
+json-এর ডেটা পরিবর্তন করতে দ্বিধা করবেন না। আপনি অ্যাট্রিবিউট বিভাগ থেকে সরাতে বা যোগ করতে পারেন। সবচেয়ে গুরুত্বপূর্ণ, নিশ্চিত করুন যে ইমেজ ফিল্ডটি আপনার IPFS ছবির লোকেশনে পয়েন্ট করে — অন্যথায়, আপনার NFT-তে একটি (খুব সুন্দর!) কুকুরের ছবি থাকবে।
+
+JSON ফাইলটি এডিট করা হয়ে গেলে, এটি সেভ করুন এবং ছবিটি আপলোড করার জন্য আমরা যে পদক্ষেপগুলি অনুসরণ করেছিলাম সেগুলি অনুসরণ করে Pinata-তে আপলোড করুন।
+
+
+
+## ধাপ 5: আপনার কন্ট্র্যাক্টের একটি ইনস্ট্যান্স তৈরি করুন {#instance-contract}
+
+এখন, আমাদের কন্ট্র্যাক্টের সাথে ইন্টারঅ্যাক্ট করার জন্য, আমাদের কোডে এটির একটি ইনস্ট্যান্স তৈরি করতে হবে। এটি করার জন্য আমাদের কন্ট্র্যাক্ট অ্যাড্রেসের প্রয়োজন হবে যা আমরা ডিপ্লয়মেন্ট থেকে অথবা [Blockscout](https://eth-sepolia.blockscout.com/) থেকে কন্ট্র্যাক্ট ডিপ্লয় করতে ব্যবহৃত অ্যাড্রেসটি খুঁজে পেতে পারি।
+
+
+
+উপরের উদাহরণে, আমাদের কন্ট্র্যাক্ট অ্যাড্রেস হল 0x5a738a5c5fe46a1fd5ee7dd7e38f722e2aef7778।
+
+এরপরে আমরা ABI এবং অ্যাড্রেস ব্যবহার করে আমাদের কন্ট্র্যাক্ট তৈরি করতে Web3 [কন্ট্র্যাক্ট মেথড](https://docs.web3js.org/api/web3-eth-contract/class/Contract) ব্যবহার করব। আপনার `mint-nft.js` ফাইলে, নিম্নলিখিতগুলি যোগ করুন:
+
+```js
+const contractAddress = "0x5a738a5c5fe46a1fd5ee7dd7e38f722e2aef7778"
+
+const nftContract = new web3.eth.Contract(contract.abi, contractAddress)
+```
+
+## ধাপ 6: `.env` ফাইলটি আপডেট করুন {#update-env}
+
+এখন, Ethereum চেইনে ট্রানজ্যাকশন তৈরি এবং পাঠানোর জন্য, আমরা অ্যাকাউন্ট নন্স (নিচে ব্যাখ্যা করা হবে) পেতে আপনার পাবলিক Ethereum অ্যাকাউন্ট অ্যাড্রেস ব্যবহার করব।
+
+আপনার পাবলিক কী আপনার `.env` ফাইলে যোগ করুন — আপনি যদি টিউটোরিয়ালের পার্ট 1 সম্পন্ন করে থাকেন, তাহলে আমাদের `.env` ফাইলটি এখন এইরকম দেখতে হবে:
+
+```js
+API_URL = "https://eth-sepolia.g.alchemy.com/v2/আপনার-এপিআই-কী"
+PRIVATE_KEY = "আপনার-প্রাইভেট-অ্যাকাউন্ট-অ্যাড্রেস"
+PUBLIC_KEY = "আপনার-পাবলিক-অ্যাকাউন্ট-অ্যাড্রেস"
+```
+
+## ধাপ 7: আপনার ট্রানজ্যাকশন তৈরি করুন {#create-txn}
+
+প্রথমে, আসুন `mintNFT(tokenData)` নামে একটি ফাংশন সংজ্ঞায়িত করি এবং নিম্নলিখিতগুলি করে আমাদের ট্রানজ্যাকশন তৈরি করি:
+
+1. `.env` ফাইল থেকে আপনার _PRIVATE_KEY_ এবং _PUBLIC_KEY_ নিন।
+
+2. এরপরে, আমাদের অ্যাকাউন্ট নন্স বের করতে হবে। নন্স স্পেসিফিকেশনটি আপনার অ্যাড্রেস থেকে পাঠানো ট্রানজ্যাকশনের সংখ্যা ট্র্যাক করতে ব্যবহৃত হয় — যা আমাদের নিরাপত্তার উদ্দেশ্যে এবং [রিপ্লে অ্যাটাক](https://docs.alchemyapi.io/resources/blockchain-glossary#account-nonce) প্রতিরোধ করার জন্য প্রয়োজন। আপনার অ্যাড্রেস থেকে পাঠানো ট্রানজ্যাকশনের সংখ্যা পেতে, আমরা [getTransactionCount](https://docs.alchemyapi.io/documentation/alchemy-api-reference/json-rpc#eth_gettransactioncount) ব্যবহার করি।
+
+3. অবশেষে আমরা নিম্নলিখিত তথ্য দিয়ে আমাদের ট্রানজ্যাকশন সেট আপ করব:
+
+- `'from': PUBLIC_KEY` — আমাদের ট্রানজ্যাকশনের উৎস হল আমাদের পাবলিক অ্যাড্রেস
+
+- `'to': contractAddress` — যে কন্ট্র্যাক্টের সাথে আমরা ইন্টারঅ্যাক্ট করতে এবং ট্রানজ্যাকশন পাঠাতে চাই
+
+- `'nonce': nonce` — আমাদের অ্যাড্রেস থেকে পাঠানো ট্রানজ্যাকশনের সংখ্যা সহ অ্যাকাউন্ট নন্স
+
+- `'gas': estimatedGas` — ট্রানজ্যাকশনটি সম্পূর্ণ করার জন্য প্রয়োজনীয় আনুমানিক গ্যাস
+
+- `'data': nftContract.methods.mintNFT(PUBLIC_KEY, md).encodeABI()` — এই ট্রানজ্যাকশনে আমরা যে গণনাটি করতে চাই — যা এই ক্ষেত্রে একটি NFT মিন্ট করা
+
+আপনার `mint-nft.js` ফাইলটি এখন এইরকম দেখতে হবে:
+
+```js
+ require('dotenv').config();
+ const API_URL = process.env.API_URL;
+ const PUBLIC_KEY = process.env.PUBLIC_KEY;
+ const PRIVATE_KEY = process.env.PRIVATE_KEY;
+
+ const { createAlchemyWeb3 } = require("@alch/alchemy-web3");
+ const web3 = createAlchemyWeb3(API_URL);
+
+ const contract = require("../artifacts/contracts/MyNFT.sol/MyNFT.json");
+ const contractAddress = "0x5a738a5c5fe46a1fd5ee7dd7e38f722e2aef7778";
+ const nftContract = new web3.eth.Contract(contract.abi, contractAddress);
+
+ async function mintNFT(tokenURI) {
+ const nonce = await web3.eth.getTransactionCount(PUBLIC_KEY, 'latest'); //সর্বশেষ নন্স পান
+
+ //ট্রানজ্যাকশন
+ const tx = {
+ 'from': PUBLIC_KEY,
+ 'to': contractAddress,
+ 'nonce': nonce,
+ 'gas': 500000,
+ 'data': nftContract.methods.mintNFT(PUBLIC_KEY, tokenURI).encodeABI()
+ };
+ }
+```
+
+## ধাপ 8: ট্রানজ্যাকশন সাইন করুন {#sign-txn}
+
+এখন যেহেতু আমরা আমাদের ট্রানজ্যাকশন তৈরি করেছি, আমাদের এটি পাঠানোর জন্য সাইন করতে হবে। এখানে আমরা আমাদের প্রাইভেট কী ব্যবহার করব।
+
+`web3.eth.sendSignedTransaction` আমাদের ট্রানজ্যাকশন হ্যাস দেবে, যা আমরা আমাদের ট্রানজ্যাকশনটি মাইনিং হয়েছে এবং নেটওয়ার্ক দ্বারা ড্রপ করা হয়নি তা নিশ্চিত করতে ব্যবহার করতে পারি। আপনি লক্ষ্য করবেন ট্রানজ্যাকশন সাইনিং বিভাগে, আমরা কিছু এরর চেকিং যোগ করেছি যাতে আমরা জানতে পারি আমাদের ট্রানজ্যাকশনটি সফলভাবে হয়েছে কিনা।
+
+```js
+require("dotenv").config()
+const API_URL = process.env.API_URL
+const PUBLIC_KEY = process.env.PUBLIC_KEY
+const PRIVATE_KEY = process.env.PRIVATE_KEY
+
+const { createAlchemyWeb3 } = require("@alch/alchemy-web3")
+const web3 = createAlchemyWeb3(API_URL)
+
+const contract = require("../artifacts/contracts/MyNFT.sol/MyNFT.json")
+const contractAddress = "0x5a738a5c5fe46a1fd5ee7dd7e38f722e2aef7778"
+const nftContract = new web3.eth.Contract(contract.abi, contractAddress)
+
+async function mintNFT(tokenURI) {
+ const nonce = await web3.eth.getTransactionCount(PUBLIC_KEY, "latest") //সর্বশেষ নন্স পান
+
+ //ট্রানজ্যাকশন
+ const tx = {
+ from: PUBLIC_KEY,
+ to: contractAddress,
+ nonce: nonce,
+ gas: 500000,
+ data: nftContract.methods.mintNFT(PUBLIC_KEY, tokenURI).encodeABI(),
+ }
+
+ const signPromise = web3.eth.accounts.signTransaction(tx, PRIVATE_KEY)
+ signPromise
+ .then((signedTx) => {
+ web3.eth.sendSignedTransaction(
+ signedTx.rawTransaction,
+ function (err, hash) {
+ if (!err) {
+ console.log(
+ "আপনার ট্রানজ্যাকশনের হ্যাস হল: ",
+ hash,
+ "\nআপনার ট্রানজ্যাকশনের স্ট্যাটাস দেখতে Alchemy-র মেমপুল দেখুন!"
+ )
+ } else {
+ console.log(
+ "আপনার ট্রানজ্যাকশন জমা দেওয়ার সময় কিছু ভুল হয়েছে:",
+ err
+ )
+ }
+ }
+ )
+ })
+ .catch((err) => {
+ console.log(" Promise ব্যর্থ হয়েছে:", err)
+ })
+}
+```
+
+## ধাপ 9: `mintNFT` কল করুন এবং node `mint-nft.js` রান করুন {#call-mintnft-fn}
+
+Pinata-তে আপলোড করা `metadata.json`-এর কথা মনে আছে? Pinata থেকে এর হ্যাসকোড নিন এবং `mintNFT` ফাংশনে নিম্নলিখিতটি প্যারামিটার হিসাবে পাস করুন `https://gateway.pinata.cloud/ipfs/`
+
+হ্যাসকোড কীভাবে পাবেন তা এখানে দেওয়া হল:
+
+_Pinata-তে আপনার এনএফটি মেটাডেটা হ্যাসকোড কীভাবে পাবেন_
+
+> আলাদা উইন্ডোতে `https://gateway.pinata.cloud/ipfs/` লোড করে ডাবল-চেক করুন যে আপনার কপি করা হ্যাসকোডটি আপনার **metadata.json**-এর সাথে লিঙ্ক করে। পেজটি নিচের স্ক্রিনশটের মতো দেখতে হবে:
+
+_আপনার পেজে json মেটাডেটা প্রদর্শন করা উচিত_
+
+সব মিলিয়ে, আপনার কোডটি এইরকম দেখতে হবে:
+
+```js
+require("dotenv").config()
+const API_URL = process.env.API_URL
+const PUBLIC_KEY = process.env.PUBLIC_KEY
+const PRIVATE_KEY = process.env.PRIVATE_KEY
+
+const { createAlchemyWeb3 } = require("@alch/alchemy-web3")
+const web3 = createAlchemyWeb3(API_URL)
+
+const contract = require("../artifacts/contracts/MyNFT.sol/MyNFT.json")
+const contractAddress = "0x5a738a5c5fe46a1fd5ee7dd7e38f722e2aef7778"
+const nftContract = new web3.eth.Contract(contract.abi, contractAddress)
+
+async function mintNFT(tokenURI) {
+ const nonce = await web3.eth.getTransactionCount(PUBLIC_KEY, "latest") //সর্বশেষ নন্স পান
+
+ //ট্রানজ্যাকশন
+ const tx = {
+ from: PUBLIC_KEY,
+ to: contractAddress,
+ nonce: nonce,
+ gas: 500000,
+ data: nftContract.methods.mintNFT(PUBLIC_KEY, tokenURI).encodeABI(),
+ }
+
+ const signPromise = web3.eth.accounts.signTransaction(tx, PRIVATE_KEY)
+ signPromise
+ .then((signedTx) => {
+ web3.eth.sendSignedTransaction(
+ signedTx.rawTransaction,
+ function (err, hash) {
+ if (!err) {
+ console.log(
+ "আপনার ট্রানজ্যাকশনের হ্যাস হল: ",
+ hash,
+ "\nআপনার ট্রানজ্যাকশনের স্ট্যাটাস দেখতে Alchemy-র মেমপুল দেখুন!"
+ )
+ } else {
+ console.log(
+ "আপনার ট্রানজ্যাকশন জমা দেওয়ার সময় কিছু ভুল হয়েছে:",
+ err
+ )
+ }
+ }
+ )
+ })
+ .catch((err) => {
+ console.log("Promise ব্যর্থ হয়েছে:", err)
+ })
+}
+
+mintNFT("ipfs://QmYueiuRNmL4MiA2GwtVMm6ZagknXnSpQnB3z2gWbz36hP")
+```
+
+এখন, আপনার NFT ডিপ্লয় করতে `node scripts/mint-nft.js` রান করুন। কয়েক সেকেন্ড পরে, আপনার টার্মিনালে এইরকম একটি প্রতিক্রিয়া দেখতে পাওয়া উচিত:
+
+ ```
+ আপনার ট্রানজ্যাকশনের হ্যাস হল: 0x301791fdf492001fcd9d5e5b12f3aa1bbbea9a88ed24993a8ab2cdae2d06e1e8
+
+ আপনার ট্রানজ্যাকশনের স্থিতি দেখতে Alchemy-র মেমপুল দেখুন!
+ ```
+
+এরপরে, আপনার ট্রানজ্যাকশনের স্থিতি দেখতে (এটি পেন্ডিং, মাইনিং করা বা নেটওয়ার্ক দ্বারা ড্রপ করা হয়েছে কিনা) আপনার [Alchemy mempool](https://dashboard.alchemyapi.io/mempool) ভিজিট করুন। যদি আপনার ট্রানজ্যাকশনটি ড্রপ হয়ে যায়, তবে [Blockscout](https://eth-sepolia.blockscout.com/) চেক করা এবং আপনার ট্রানজ্যাকশন হ্যাস অনুসন্ধান করাও সহায়ক।
+
+_Etherscan-এ আপনার NFT ট্রানজ্যাকশন হ্যাস দেখুন_
+
+এবং এটাই সব! আপনি এখন Ethereum ব্লকচেইনে একটি NFT ডিপ্লয় এবং মিন্ট করেছেন
+
+`mint-nft.js` ব্যবহার করে আপনি আপনার মন (এবং ওয়ালেট) যতগুলো চায় ততগুলো NFT মিন্ট করতে পারবেন! শুধু NFT-এর মেটাডেটা বর্ণনাকারী একটি নতুন tokenURI পাস করতে ভুলবেন না (অন্যথায়, আপনি কেবল বিভিন্ন ID সহ একগুচ্ছ অভিন্ন NFT তৈরি করবেন)।
+
+সম্ভবত, আপনি আপনার ওয়ালেটে আপনার NFT দেখাতে সক্ষম হতে চাইবেন — তাই [পার্ট 3: আপনার ওয়ালেটে আপনার NFT কীভাবে দেখবেন](/developers/tutorials/how-to-view-nft-in-metamask/) দেখতে ভুলবেন না!
diff --git a/public/content/translations/bn/developers/tutorials/how-to-mock-solidity-contracts-for-testing/index.md b/public/content/translations/bn/developers/tutorials/how-to-mock-solidity-contracts-for-testing/index.md
new file mode 100644
index 00000000000..dd7053184b0
--- /dev/null
+++ b/public/content/translations/bn/developers/tutorials/how-to-mock-solidity-contracts-for-testing/index.md
@@ -0,0 +1,102 @@
+---
+title: "পরীক্ষার জন্য সলিডিটি স্মার্ট কন্ট্র্যাক্টগুলিকে কীভাবে মক করা যায়"
+description: "পরীক্ষার সময় আপনার কন্ট্র্যাক্টগুলো নিয়ে কেন মজা করা উচিত"
+author: Markus Waas
+lang: bn
+tags: [ "সলিডিটি", "স্মার্ট কন্ট্র্যাক্ট", "পরীক্ষা", "মকিং" ]
+skill: intermediate
+published: 2020-05-02
+source: soliditydeveloper.com
+sourceUrl: https://soliditydeveloper.com/mocking-contracts
+---
+
+[মক অবজেক্ট](https://wikipedia.org/wiki/Mock_object) অবজেক্ট-ওরিয়েন্টেড প্রোগ্রামিং-এর একটি সাধারণ ডিজাইন প্যাটার্ন। পুরাতন ফরাসি শব্দ 'mocquer' থেকে এসেছে যার অর্থ 'মজা করা', এটি 'বাস্তব কিছু অনুকরণ করা'-তে বিকশিত হয়েছে যা আমরা আসলে প্রোগ্রামিংয়ে করে থাকি। অনুগ্রহ করে শুধুমাত্র আপনার স্মার্ট কন্ট্র্যাক্টগুলো নিয়ে মজা করুন যদি আপনি চান, কিন্তু যখনই পারেন সেগুলোকে মক করুন। এটি আপনার জীবনকে সহজ করে তোলে।
+
+## মকস দিয়ে কন্ট্র্যাক্টের ইউনিট-টেস্টিং {#unit-testing-contracts-with-mocks}
+
+একটি কন্ট্র্যাক্ট মক করার অর্থ হল সেই কন্ট্র্যাক্টের একটি দ্বিতীয় সংস্করণ তৈরি করা যা মূলটির মতোই আচরণ করে, কিন্তু এমনভাবে যা ডেভেলপার দ্বারা সহজেই নিয়ন্ত্রণ করা যায়। আপনি প্রায়শই জটিল কন্ট্র্যাক্টের সম্মুখীন হন যেখানে আপনি কেবল [কন্ট্র্যাক্টের ছোট অংশ ইউনিট-টেস্ট](/developers/docs/smart-contracts/testing/) করতে চান। সমস্যা হল, যদি এই ছোট অংশটি পরীক্ষা করার জন্য একটি খুব নির্দিষ্ট কন্ট্র্যাক্ট স্টেটের প্রয়োজন হয় যেখানে পৌঁছানো কঠিন?
+
+আপনি প্রতিবার জটিল টেস্ট সেটআপ লজিক লিখতে পারেন যা কন্ট্র্যাক্টটিকে প্রয়োজনীয় স্টেটে নিয়ে আসে অথবা আপনি একটি মক লিখুন। ইনহেরিটেন্সের মাধ্যমে একটি কন্ট্র্যাক্ট মক করা সহজ। কেবলমাত্র একটি দ্বিতীয় মক কন্ট্র্যাক্ট তৈরি করুন যা মূলটি থেকে ইনহেরিট করে। এখন আপনি আপনার মকের ফাংশনগুলি ওভাররাইড করতে পারেন। আসুন একটি উদাহরণ দিয়ে এটি দেখি।
+
+## উদাহরণ: প্রাইভেট ERC20 {#example-private-erc20}
+
+আমরা একটি উদাহরণ ERC-20 কন্ট্র্যাক্ট ব্যবহার করি যার একটি প্রাথমিক প্রাইভেট সময় রয়েছে। মালিক ব্যক্তিগত ব্যবহারকারীদের পরিচালনা করতে পারেন এবং শুধুমাত্র তাদেরকেই শুরুতে টোকেন গ্রহণ করার অনুমতি দেওয়া হবে। একটি নির্দিষ্ট সময় অতিবাহিত হয়ে গেলে, প্রত্যেককে টোকেন ব্যবহার করার অনুমতি দেওয়া হবে। আপনি যদি কৌতূহলী হন, আমরা নতুন OpenZeppelin contracts v3 থেকে [`_beforeTokenTransfer`](https://docs.openzeppelin.com/contracts/5.x/extending-contracts#using-hooks) হুক ব্যবহার করছি।
+
+```solidity
+pragma solidity ^0.6.0;
+
+import "@openzeppelin/contracts/token/ERC20/ERC20.sol";
+import "@openzeppelin/contracts/access/Ownable.sol";
+
+contract PrivateERC20 is ERC20, Ownable {
+ mapping (address => bool) public isPrivateUser;
+ uint256 private publicAfterTime;
+
+ constructor(uint256 privateERC20timeInSec) ERC20("PrivateERC20", "PRIV") public {
+ publicAfterTime = now + privateERC20timeInSec;
+ }
+
+ function addUser(address user) external onlyOwner {
+ isPrivateUser[user] = true;
+ }
+
+ function isPublic() public view returns (bool) {
+ return now >= publicAfterTime;
+ }
+
+ function _beforeTokenTransfer(address from, address to, uint256 amount) internal virtual override {
+ super._beforeTokenTransfer(from, to, amount);
+
+ require(_validRecipient(to), "PrivateERC20: অবৈধ প্রাপক");
+ }
+
+ function _validRecipient(address to) private view returns (bool) {
+ if (isPublic()) {
+ return true;
+ }
+
+ return isPrivateUser[to];
+ }
+}
+```
+
+এবং এখন আসুন এটি মক করি।
+
+```solidity
+pragma solidity ^0.6.0;
+import "../PrivateERC20.sol";
+
+contract PrivateERC20Mock is PrivateERC20 {
+ bool isPublicConfig;
+
+ constructor() public PrivateERC20(0) {}
+
+ function setIsPublic(bool isPublic) external {
+ isPublicConfig = isPublic;
+ }
+
+ function isPublic() public view returns (bool) {
+ return isPublicConfig;
+ }
+}
+```
+
+আপনি নিম্নলিখিত ত্রুটি বার্তাগুলির মধ্যে একটি পাবেন:
+
+- `PrivateERC20Mock.sol: TypeError: Overriding function is missing "override" specifier.`
+- `PrivateERC20.sol: TypeError: Trying to override non-virtual function. Did you forget to add "virtual"?.`
+
+যেহেতু আমরা নতুন 0.6 সলিডিটি সংস্করণ ব্যবহার করছি, তাই যে ফাংশনগুলি ওভাররাইড করা যেতে পারে তার জন্য আমাদের `virtual` কীওয়ার্ড এবং ওভাররাইডিং ফাংশনের জন্য override যোগ করতে হবে। সুতরাং আসুন আমরা উভয় `isPublic` ফাংশনে সেগুলি যোগ করি।
+
+এখন আপনার ইউনিট টেস্টে, আপনি পরিবর্তে `PrivateERC20Mock` ব্যবহার করতে পারেন। আপনি যখন প্রাইভেট ব্যবহারের সময় আচরণ পরীক্ষা করতে চান, তখন `setIsPublic(false)` ব্যবহার করুন এবং একইভাবে পাবলিক ব্যবহারের সময় পরীক্ষা করার জন্য `setIsPublic(true)` ব্যবহার করুন। অবশ্যই আমাদের উদাহরণে, আমরা সময় অনুযায়ী পরিবর্তন করার জন্য [টাইম হেল্পার](https://docs.openzeppelin.com/test-helpers/0.5/api#increase) ব্যবহার করতে পারতাম। কিন্তু মকিং-এর ধারণা এখন স্পষ্ট হওয়া উচিত এবং আপনি এমন পরিস্থিতি কল্পনা করতে পারেন যেখানে সময় এগিয়ে দেওয়াটা এত সহজ নয়।
+
+## অনেক কন্ট্র্যাক্ট মক করা {#mocking-many-contracts}
+
+প্রতিটি মকের জন্য যদি আপনাকে আরেকটি কন্ট্র্যাক্ট তৈরি করতে হয় তবে এটি অগোছালো হয়ে যেতে পারে। যদি এটি আপনাকে বিরক্ত করে, আপনি [MockContract](https://github.com/gnosis/mock-contract) লাইব্রেরিটি দেখতে পারেন। এটি আপনাকে তৎক্ষণাৎ কন্ট্র্যাক্টগুলির আচরণ ওভাররাইড এবং পরিবর্তন করতে দেয়। তবে, এটি কেবল অন্য একটি কন্ট্র্যাক্টে কল মক করার জন্য কাজ করে, তাই এটি আমাদের উদাহরণের জন্য কাজ করবে না।
+
+## মকিং আরও শক্তিশালী হতে পারে {#mocking-can-be-even-more-powerful}
+
+মকিংয়ের ক্ষমতা এখানেই শেষ নয়।
+
+- ফাংশন যোগ করা: কেবল একটি নির্দিষ্ট ফাংশন ওভাররাইড করাই কার্যকর নয়, অতিরিক্ত ফাংশন যোগ করাও কার্যকর। টোকেনের জন্য একটি ভাল উদাহরণ হল একটি অতিরিক্ত `mint` ফাংশন থাকা যা যেকোনো ব্যবহারকারীকে বিনামূল্যে নতুন টোকেন পেতে দেয়।
+- টেস্টনেটে ব্যবহার: যখন আপনি আপনার ডিএ্যাপ-এর সাথে টেস্টনেটে আপনার কন্ট্র্যাক্টগুলি স্থাপন এবং পরীক্ষা করেন, তখন একটি মকড সংস্করণ ব্যবহার করার কথা বিবেচনা করুন। ফাংশন ওভাররাইড করা এড়িয়ে চলুন যদি না আপনার সত্যিই প্রয়োজন হয়। আপনি সর্বোপরি আসল লজিক পরীক্ষা করতে চান। কিন্তু উদাহরণস্বরূপ একটি রিসেট ফাংশন যোগ করা কার্যকর হতে পারে যা কেবল কন্ট্র্যাক্টের স্টেটকে শুরুতে রিসেট করে, কোনো নতুন স্থাপনার প্রয়োজন নেই। স্পষ্টতই আপনি এটি একটি মেইননেট কন্ট্র্যাক্টে রাখতে চাইবেন না।
diff --git a/public/content/translations/bn/developers/tutorials/how-to-use-echidna-to-test-smart-contracts/index.md b/public/content/translations/bn/developers/tutorials/how-to-use-echidna-to-test-smart-contracts/index.md
new file mode 100644
index 00000000000..911b0c274aa
--- /dev/null
+++ b/public/content/translations/bn/developers/tutorials/how-to-use-echidna-to-test-smart-contracts/index.md
@@ -0,0 +1,708 @@
+---
+title: "স্মার্ট কন্ট্র্যাক্ট পরীক্ষা করার জন্য Echidna কীভাবে ব্যবহার করবেন"
+description: "স্বয়ংক্রিয়ভাবে স্মার্ট কন্ট্র্যাক্ট পরীক্ষা করার জন্য Echidna কীভাবে ব্যবহার করবেন"
+author: "Trailofbits"
+lang: bn
+tags:
+ [
+ "সলিডিটি",
+ "স্মার্ট কন্ট্র্যাক্ট",
+ "নিরাপত্তা",
+ "পরীক্ষা",
+ "ফাজিং"
+ ]
+skill: advanced
+published: 2020-04-10
+source: Building secure contracts
+sourceUrl: https://github.com/crytic/building-secure-contracts/tree/master/program-analysis/echidna
+---
+
+## ইনস্টলেশন {#installation}
+
+ডকারের মাধ্যমে অথবা প্রি-কম্পাইলড বাইনারি ব্যবহার করে Echidna ইনস্টল করা যেতে পারে।
+
+### ডকারের মাধ্যমে Echidna {#echidna-through-docker}
+
+```bash
+docker pull trailofbits/eth-security-toolbox
+docker run -it -v "$PWD":/home/training trailofbits/eth-security-toolbox
+```
+
+_শেষ কমান্ডটি একটি docker-এ eth-security-toolbox চালায় যেটির আপনার বর্তমান ডিরেক্টরিতে অ্যাক্সেস আছে। আপনি আপনার হোস্ট থেকে ফাইলগুলো পরিবর্তন করতে পারেন, এবং docker থেকে ফাইলগুলোতে টুলস চালাতে পারেন_
+
+ডকারের ভিতরে, চালান:
+
+```bash
+solc-select 0.5.11
+cd /home/training
+```
+
+### বাইনারি {#binary}
+
+[https://github.com/crytic/echidna/releases/tag/v1.4.0.0](https://github.com/crytic/echidna/releases/tag/v1.4.0.0)
+
+## প্রপার্টি-ভিত্তিক ফাজিং এর ভূমিকা {#introduction-to-property-based-fuzzing}
+
+Echidna হলো একটি প্রপার্টি-ভিত্তিক ফাজার, যা আমরা আমাদের আগের ব্লগপোস্টগুলোতে বর্ণনা করেছি ([1](https://blog.trailofbits.com/2018/03/09/echidna-a-smart-fuzzer-for-ethereum/), [2](https://blog.trailofbits.com/2018/05/03/state-machine-testing-with-echidna/), [3](https://blog.trailofbits.com/2020/03/30/an-echidna-for-all-seasons/)).
+
+### ফাজিং {#fuzzing}
+
+[ফাজিং](https://wikipedia.org/wiki/Fuzzing) নিরাপত্তা কমিউনিটিতে একটি সুপরিচিত কৌশল। এটিতে প্রোগ্রামের মধ্যে বাগ খুঁজে বের করার জন্য কম-বেশি র্যান্ডম ইনপুট তৈরি করা হয়। প্রচলিত সফটওয়্যারের জন্য ফাজার (যেমন [AFL](http://lcamtuf.coredump.cx/afl/) বা [LibFuzzer](https://llvm.org/docs/LibFuzzer.html)) বাগ খুঁজে বের করার জন্য দক্ষ টুলস হিসেবে পরিচিত।
+
+শুধুমাত্র র্যান্ডম ইনপুট তৈরি করার বাইরেও, ভালো ইনপুট তৈরি করার জন্য অনেক কৌশল এবং স্ট্র্যাটেজি রয়েছে, যার মধ্যে রয়েছে:
+
+- প্রতিটি এক্সিকিউশন থেকে ফিডব্যাক পাওয়া এবং তা ব্যবহার করে জেনারেশনকে গাইড করা। উদাহরণস্বরূপ, যদি একটি নতুন জেনারেটেড ইনপুট একটি নতুন পথ আবিষ্কার করে, তবে তার কাছাকাছি নতুন ইনপুট জেনারেট করা অর্থপূর্ণ হতে পারে।
+- একটি কাঠামোগত সীমাবদ্ধতাকে সম্মান করে ইনপুট তৈরি করা। উদাহরণস্বরূপ, যদি আপনার ইনপুটে একটি চেক্সামসহ একটি হেডার থাকে, তাহলে ফাজারকে চেক্সাম ভ্যালিডেট করে এমন ইনপুট তৈরি করতে দেওয়াটা যুক্তিযুক্ত হবে।
+- নতুন ইনপুট তৈরি করার জন্য পরিচিত ইনপুট ব্যবহার করা: যদি আপনার কাছে বৈধ ইনপুটের একটি বড় ডেটাসেটের অ্যাক্সেস থাকে, তাহলে আপনার ফাজার স্ক্র্যাচ থেকে জেনারেশন শুরু করার পরিবর্তে সেগুলো থেকে নতুন ইনপুট তৈরি করতে পারে। এগুলোকে সাধারণত _সিড_ বলা হয়।
+
+### প্রপার্টি-ভিত্তিক ফাজিং {#property-based-fuzzing}
+
+Echidna একটি নির্দিষ্ট ফাজার পরিবারের অন্তর্গত: এটি প্রপার্টি-ভিত্তিক ফাজিং যা [QuickCheck](https://wikipedia.org/wiki/QuickCheck) দ্বারা ব্যাপকভাবে অনুপ্রাণিত। ক্লাসিক ফাজারের বিপরীতে, যা ক্র্যাশ খুঁজে বের করার চেষ্টা করে, Echidna ব্যবহারকারী-সংজ্ঞায়িত ইনভেরিয়েন্টগুলো ভাঙার চেষ্টা করবে।
+
+স্মার্ট কন্ট্র্যাক্টে, ইনভেরিয়েন্টগুলো হলো সলিডিটি ফাংশন, যা কন্ট্র্যাক্ট পৌঁছাতে পারে এমন যেকোনো ভুল বা অবৈধ স্টেটকে উপস্থাপন করতে পারে, যার মধ্যে রয়েছে:
+
+- ভুল অ্যাক্সেস কন্ট্রোল: আক্রমণকারী কন্ট্র্যাক্টের মালিক হয়ে গিয়েছে।
+- ভুল স্টেট মেশিন: কন্ট্র্যাক্ট পজ করা অবস্থায় টোকেনগুলো ট্রান্সফার করা যেতে পারে।
+- ভুল অ্যারিথমেটিক: ব্যবহারকারী তার ব্যালেন্স আন্ডারফ্লো করতে পারে এবং সীমাহীন ফ্রি টোকেন পেতে পারে।
+
+### Echidna দিয়ে একটি প্রপার্টি পরীক্ষা করা {#testing-a-property-with-echidna}
+
+আমরা দেখব কীভাবে Echidna দিয়ে একটি স্মার্ট কন্ট্র্যাক্ট পরীক্ষা করা যায়। টার্গেট হলো নিম্নলিখিত স্মার্ট কন্ট্র্যাক্ট [`token.sol`](https://github.com/crytic/building-secure-contracts/blob/master/program-analysis/echidna/example/token.sol):
+
+```solidity
+contract Token{
+ mapping(address => uint) public balances;
+ function airdrop() public{
+ balances[msg.sender] = 1000;
+ }
+ function consume() public{
+ require(balances[msg.sender]>0);
+ balances[msg.sender] -= 1;
+ }
+ function backdoor() public{
+ balances[msg.sender] += 1;
+ }
+}
+```
+
+আমরা এই অনুমানটি করব যে এই টোকেনের নিম্নলিখিত বৈশিষ্ট্যগুলো অবশ্যই থাকতে হবে:
+
+- যেকোনো ব্যক্তির কাছে সর্বোচ্চ 1000টি টোকেন থাকতে পারে
+- টোকেনটি ট্রান্সফার করা যাবে না (এটি কোনো ERC20 টোকেন নয়)
+
+### একটি প্রপার্টি লিখুন {#write-a-property}
+
+Echidna প্রপার্টিগুলো হলো সলিডিটি ফাংশন। একটি প্রপার্টিতে অবশ্যই থাকতে হবে:
+
+- কোনো আর্গুমেন্ট থাকবে না
+- সফল হলে `true` রিটার্ন করবে
+- এর নাম `echidna` দিয়ে শুরু হতে হবে
+
+Echidna করবে:
+
+- প্রপার্টি পরীক্ষা করার জন্য স্বয়ংক্রিয়ভাবে আর্বিট্রারি ট্রানজ্যাকশন জেনারেট করবে।
+- কোনো প্রপার্টি `false` রিটার্ন করলে বা কোনো এরর থ্রো করলে সেই ট্রানজ্যাকশনগুলো রিপোর্ট করবে।
+- একটি প্রপার্টি কল করার সময় সাইড-ইফেক্ট বাতিল করবে (অর্থাৎ, যদি প্রপার্টি কোনো স্টেট ভ্যারিয়েবল পরিবর্তন করে, পরীক্ষার পরে তা বাতিল করা হয়)
+
+নিম্নলিখিত প্রপার্টিটি পরীক্ষা করে যে কলারের কাছে 1000টির বেশি টোকেন নেই:
+
+```solidity
+function echidna_balance_under_1000() public view returns(bool){
+ return balances[msg.sender] <= 1000;
+}
+```
+
+আপনার কন্ট্র্যাক্টকে আপনার প্রপার্টি থেকে আলাদা করতে ইনহেরিটেন্স ব্যবহার করুন:
+
+```solidity
+contract TestToken is Token{
+ function echidna_balance_under_1000() public view returns(bool){
+ return balances[msg.sender] <= 1000;
+ }
+ }
+```
+
+[`token.sol`](https://github.com/crytic/building-secure-contracts/blob/master/program-analysis/echidna/example/token.sol) প্রপার্টিটি প্রয়োগ করে এবং টোকেন থেকে ইনহেরিট করে।
+
+### একটি কন্ট্র্যাক্ট শুরু করুন {#initiate-a-contract}
+
+Echidna-এর জন্য আর্গুমেন্ট ছাড়া একটি [কন্সট্রাক্টর](/developers/docs/smart-contracts/anatomy/#constructor-functions) প্রয়োজন। যদি আপনার কন্ট্র্যাক্টের জন্য একটি নির্দিষ্ট ইনিশিয়ালাইজেশন প্রয়োজন হয়, তবে আপনাকে তা কন্সট্রাক্টরের মধ্যে করতে হবে।
+
+Echidna-তে কিছু নির্দিষ্ট অ্যাড্রেস রয়েছে:
+
+- `0x00a329c0648769A73afAc7F9381E08FB43dBEA72` যা কন্সট্রাক্টরকে কল করে।
+- `0x10000`, `0x20000`, এবং `0x00a329C0648769a73afAC7F9381e08fb43DBEA70` যা র্যান্ডমভাবে অন্য ফাংশনগুলোকে কল করে।
+
+আমাদের বর্তমান উদাহরণে কোনো বিশেষ ইনিশিয়ালাইজেশনের প্রয়োজন নেই, ফলস্বরূপ আমাদের কন্সট্রাক্টরটি খালি।
+
+### Echidna চালান {#run-echidna}
+
+Echidna চালু করা হয় এভাবে:
+
+```bash
+echidna-test contract.sol
+```
+
+যদি contract.sol-এ একাধিক কন্ট্র্যাক্ট থাকে, আপনি টার্গেট নির্দিষ্ট করতে পারেন:
+
+```bash
+echidna-test contract.sol --contract MyContract
+```
+
+### সারসংক্ষেপ: একটি প্রপার্টি পরীক্ষা করা {#summary-testing-a-property}
+
+নিম্নলিখিতটি আমাদের উদাহরণের উপর echidna চালানোর সারসংক্ষেপ:
+
+```solidity
+contract TestToken is Token{
+ constructor() public {}
+ function echidna_balance_under_1000() public view returns(bool){
+ return balances[msg.sender] <= 1000;
+ }
+ }
+```
+
+```bash
+echidna-test testtoken.sol --contract TestToken
+...
+
+echidna_balance_under_1000: failed!💥
+ Call sequence, shrinking (1205/5000):
+ airdrop()
+ backdoor()
+
+...
+```
+
+Echidna খুঁজে পেয়েছে যে `backdoor` কল করা হলে প্রপার্টিটি লঙ্ঘিত হয়।
+
+## ফাজিং ক্যাম্পেইনের সময় কল করার জন্য ফাংশন ফিল্টার করা {#filtering-functions-to-call-during-a-fuzzing-campaign}
+
+আমরা দেখব ফাজ করা হবে এমন ফাংশনগুলো কীভাবে ফিল্টার করতে হয়।
+টার্গেট হলো নিম্নলিখিত স্মার্ট কন্ট্র্যাক্ট:
+
+```solidity
+contract C {
+ bool state1 = false;
+ bool state2 = false;
+ bool state3 = false;
+ bool state4 = false;
+
+ function f(uint x) public {
+ require(x == 12);
+ state1 = true;
+ }
+
+ function g(uint x) public {
+ require(state1);
+ require(x == 8);
+ state2 = true;
+ }
+
+ function h(uint x) public {
+ require(state2);
+ require(x == 42);
+ state3 = true;
+ }
+
+ function i() public {
+ require(state3);
+ state4 = true;
+ }
+
+ function reset1() public {
+ state1 = false;
+ state2 = false;
+ state3 = false;
+ return;
+ }
+
+ function reset2() public {
+ state1 = false;
+ state2 = false;
+ state3 = false;
+ return;
+ }
+
+ function echidna_state4() public returns (bool) {
+ return (!state4);
+ }
+}
+```
+
+এই ছোট উদাহরণটি Echidna-কে একটি স্টেট ভ্যারিয়েবল পরিবর্তন করার জন্য একটি নির্দিষ্ট ট্রানজ্যাকশন সিকোয়েন্স খুঁজে বের করতে বাধ্য করে।
+এটি একটি ফাজারের জন্য কঠিন (এর জন্য [Manticore](https://github.com/trailofbits/manticore)-এর মতো একটি সিম্বলিক এক্সিকিউশন টুল ব্যবহার করার পরামর্শ দেওয়া হয়)।
+এটি যাচাই করার জন্য আমরা Echidna চালাতে পারি:
+
+```bash
+echidna-test multi.sol
+...
+echidna_state4: passed! 🎉
+Seed: -3684648582249875403
+```
+
+### ফাংশন ফিল্টার করা {#filtering-functions}
+
+এই কন্ট্র্যাক্টটি পরীক্ষা করার জন্য সঠিক সিকোয়েন্স খুঁজে পেতে Echidna-এর সমস্যা হচ্ছে কারণ দুটি রিসেট ফাংশন (`reset1` এবং `reset2`) সমস্ত স্টেট ভ্যারিয়েবলকে `false`-এ সেট করে দেবে।
+তবে, আমরা রিসেট ফাংশনকে ব্ল্যাকলিস্ট করতে বা শুধুমাত্র `f`, `g`,
+`h` এবং `i` ফাংশনগুলোকে হোয়াইটলিস্ট করতে একটি বিশেষ Echidna ফিচার ব্যবহার করতে পারি।
+
+ফাংশন ব্ল্যাকলিস্ট করতে, আমরা এই কনফিগারেশন ফাইলটি ব্যবহার করতে পারি:
+
+```yaml
+filterBlacklist: true
+filterFunctions: ["reset1", "reset2"]
+```
+
+ফাংশন ফিল্টার করার আরেকটি উপায় হলো হোয়াইটলিস্টেড ফাংশনগুলোকে তালিকাভুক্ত করা। এটি করার জন্য, আমরা এই কনফিগারেশন ফাইলটি ব্যবহার করতে পারি:
+
+```yaml
+filterBlacklist: false
+filterFunctions: ["f", "g", "h", "i"]
+```
+
+- `filterBlacklist` ডিফল্টভাবে `true` থাকে।
+- ফিল্টারিং শুধুমাত্র নামের উপর ভিত্তি করে করা হবে (প্যারামিটার ছাড়া)। আপনার যদি `f()` এবং `f(uint256)` থাকে, তাহলে `"f"` ফিল্টারটি উভয় ফাংশনের সাথেই মিলবে।
+
+### Echidna চালান {#run-echidna-1}
+
+`blacklist.yaml` কনফিগারেশন ফাইল দিয়ে Echidna চালাতে:
+
+```bash
+echidna-test multi.sol --config blacklist.yaml
+...
+echidna_state4: failed!💥
+ Call sequence:
+ f(12)
+ g(8)
+ h(42)
+ i()
+```
+
+Echidna প্রায় সঙ্গে সঙ্গেই প্রপার্টিটি ভুল প্রমাণ করার জন্য ট্রানজ্যাকশনের সিকোয়েন্স খুঁজে বের করবে।
+
+### সারসংক্ষেপ: ফাংশন ফিল্টার করা {#summary-filtering-functions}
+
+Echidna একটি ফাজিং ক্যাম্পেইনের সময় কল করার জন্য ফাংশনগুলোকে ব্ল্যাকলিস্ট বা হোয়াইটলিস্ট করতে পারে, এটি ব্যবহার করে:
+
+```yaml
+filterBlacklist: true
+filterFunctions: ["f1", "f2", "f3"]
+```
+
+```bash
+echidna-test contract.sol --config config.yaml
+...
+```
+
+`filterBlacklist` বুলিয়ানের মানের উপর ভিত্তি করে Echidna `f1`, `f2` এবং `f3` কে ব্ল্যাকলিস্ট করে বা শুধুমাত্র এগুলোকে কল করে একটি ফাজিং ক্যাম্পেইন শুরু করে।
+
+## Echidna দিয়ে Solidity-এর অ্যাসার্ট কীভাবে পরীক্ষা করবেন {#how-to-test-soliditys-assert-with-echidna}
+
+এই সংক্ষিপ্ত টিউটোরিয়ালে, আমরা দেখাব কীভাবে কন্ট্র্যাক্টে অ্যাসারশন চেকিং পরীক্ষা করতে Echidna ব্যবহার করা যায়। ধরা যাক আমাদের কাছে এইরকম একটি কন্ট্র্যাক্ট আছে:
+
+```solidity
+contract Incrementor {
+ uint private counter = 2**200;
+
+ function inc(uint val) public returns (uint){
+ uint tmp = counter;
+ counter += val;
+ // tmp <= counter
+ return (counter - tmp);
+ }
+}
+```
+
+### একটি অ্যাসারশন লিখুন {#write-an-assertion}
+
+আমরা নিশ্চিত করতে চাই যে `tmp` এর পার্থক্য রিটার্ন করার পরে `counter`-এর চেয়ে কম বা সমান। আমরা একটি
+Echidna প্রপার্টি লিখতে পারতাম, কিন্তু আমাদের `tmp` মানটি কোথাও সংরক্ষণ করতে হবে। পরিবর্তে, আমরা এইরকম একটি অ্যাসারশন ব্যবহার করতে পারি:
+
+```solidity
+contract Incrementor {
+ uint private counter = 2**200;
+
+ function inc(uint val) public returns (uint){
+ uint tmp = counter;
+ counter += val;
+ assert (tmp <= counter);
+ return (counter - tmp);
+ }
+}
+```
+
+### Echidna চালান {#run-echidna-2}
+
+অ্যাসারশন ফেইলিওর টেস্টিং সক্ষম করতে, একটি [Echidna কনফিগারেশন ফাইল](https://github.com/crytic/echidna/wiki/Config) `config.yaml` তৈরি করুন:
+
+```yaml
+checkAsserts: true
+```
+
+যখন আমরা Echidna-তে এই কন্ট্র্যাক্টটি চালাই, আমরা প্রত্যাশিত ফলাফল পাই:
+
+```bash
+echidna-test assert.sol --config config.yaml
+Analyzing contract: assert.sol:Incrementor
+assertion in inc: failed!💥
+ Call sequence, shrinking (2596/5000):
+ inc(21711016731996786641919559689128982722488122124807605757398297001483711807488)
+ inc(7237005577332262213973186563042994240829374041602535252466099000494570602496)
+ inc(86844066927987146567678238756515930889952488499230423029593188005934847229952)
+
+Seed: 1806480648350826486
+```
+
+আপনি দেখতে পাচ্ছেন, Echidna `inc` ফাংশনে কিছু অ্যাসারশন ফেইলিওর রিপোর্ট করছে। প্রতিটি ফাংশনে একাধিক অ্যাসারশন যোগ করা সম্ভব, কিন্তু Echidna বলতে পারে না কোন অ্যাসারশনটি ব্যর্থ হয়েছে।
+
+### কখন এবং কীভাবে অ্যাসারশন ব্যবহার করবেন {#when-and-how-use-assertions}
+
+অ্যাসারশনগুলো সুস্পষ্ট প্রপার্টির বিকল্প হিসেবে ব্যবহার করা যেতে পারে, বিশেষ করে যদি পরীক্ষা করার শর্তগুলো কোনো `f` অপারেশনের সঠিক ব্যবহারের সাথে সরাসরি সম্পর্কিত হয়। কিছু কোডের পরে অ্যাসারশন যোগ করলে তা নিশ্চিত করবে যে এটি এক্সিকিউট হওয়ার ঠিক পরেই চেকটি ঘটবে:
+
+```solidity
+function f(..) public {
+ // কিছু জটিল কোড
+ ...
+ assert (condition);
+ ...
+}
+
+```
+
+বিপরীতে, একটি সুস্পষ্ট echidna প্রপার্টি ব্যবহার করলে র্যান্ডমভাবে ট্রানজ্যাকশন এক্সিকিউট হবে এবং এটি ঠিক কখন পরীক্ষা করা হবে তা নিশ্চিত করার কোনো সহজ উপায় নেই। এই ওয়ার্কঅ্যারাউন্ডটি করা এখনও সম্ভব:
+
+```solidity
+function echidna_assert_after_f() public returns (bool) {
+ f(..);
+ return(condition);
+}
+```
+
+তবে, কিছু সমস্যা আছে:
+
+- যদি `f`-কে `internal` বা `external` হিসেবে ডিক্লেয়ার করা হয় তবে এটি ব্যর্থ হয়।
+- `f`-কে কল করার জন্য কোন আর্গুমেন্ট ব্যবহার করা উচিত তা স্পষ্ট নয়।
+- যদি `f` রিভার্ট করে, প্রপার্টিটি ব্যর্থ হবে।
+
+সাধারণভাবে, আমরা অ্যাসারশন কীভাবে ব্যবহার করতে হয় সে সম্পর্কে [জন রেগেরের সুপারিশ](https://blog.regehr.org/archives/1091) অনুসরণ করার পরামর্শ দিই:
+
+- অ্যাসারশন চেকিংয়ের সময় কোনো সাইড এফেক্ট জোর করে প্রয়োগ করবেন না। উদাহরণস্বরূপ: `assert(ChangeStateAndReturn() == 1)`
+- স্পষ্ট স্টেটমেন্ট অ্যাসার্ট করবেন না। উদাহরণস্বরূপ, `assert(var >= 0)` যেখানে `var`-কে `uint` হিসেবে ডিক্লেয়ার করা হয়েছে।
+
+অবশেষে, অনুগ্রহ করে `assert`-এর পরিবর্তে `require` **ব্যবহার করবেন না**, কারণ Echidna এটি সনাক্ত করতে পারবে না (কিন্তু কন্ট্র্যাক্টটি যাইহোক রিভার্ট করবে)।
+
+### সারসংক্ষেপ: অ্যাসারশন চেকিং {#summary-assertion-checking}
+
+নিম্নলিখিতটি আমাদের উদাহরণের উপর echidna চালানোর সারসংক্ষেপ:
+
+```solidity
+contract Incrementor {
+ uint private counter = 2**200;
+
+ function inc(uint val) public returns (uint){
+ uint tmp = counter;
+ counter += val;
+ assert (tmp <= counter);
+ return (counter - tmp);
+ }
+}
+```
+
+```bash
+echidna-test assert.sol --config config.yaml
+Analyzing contract: assert.sol:Incrementor
+assertion in inc: failed!💥
+ Call sequence, shrinking (2596/5000):
+ inc(21711016731996786641919559689128982722488122124807605757398297001483711807488)
+ inc(7237005577332262213973186563042994240829374041602535252466099000494570602496)
+ inc(86844066927987146567678238756515930889952488499230423029593188005934847229952)
+
+Seed: 1806480648350826486
+```
+
+Echidna খুঁজে পেয়েছে যে `inc`-এর মধ্যে অ্যাসারশনটি ব্যর্থ হতে পারে যদি এই ফাংশনটিকে বড় আর্গুমেন্ট সহ একাধিকবার কল করা হয়।
+
+## একটি Echidna কর্পাস সংগ্রহ এবং পরিবর্তন করা {#collecting-and-modifying-an-echidna-corpus}
+
+আমরা দেখব Echidna-এর সাথে একটি ট্রানজ্যাকশন কর্পাস কীভাবে সংগ্রহ এবং ব্যবহার করতে হয়। টার্গেট হলো নিম্নলিখিত স্মার্ট কন্ট্র্যাক্ট [`magic.sol`](https://github.com/crytic/building-secure-contracts/blob/master/program-analysis/echidna/example/magic.sol):
+
+```solidity
+contract C {
+ bool value_found = false;
+ function magic(uint magic_1, uint magic_2, uint magic_3, uint magic_4) public {
+ require(magic_1 == 42);
+ require(magic_2 == 129);
+ require(magic_3 == magic_4+333);
+ value_found = true;
+ return;
+ }
+
+ function echidna_magic_values() public returns (bool) {
+ return !value_found;
+ }
+
+}
+```
+
+এই ছোট উদাহরণটি Echidna-কে একটি স্টেট ভ্যারিয়েবল পরিবর্তন করার জন্য নির্দিষ্ট মান খুঁজে বের করতে বাধ্য করে। এটি একটি ফাজারের জন্য কঠিন
+(এর জন্য [Manticore](https://github.com/trailofbits/manticore)-এর মতো একটি সিম্বলিক এক্সিকিউশন টুল ব্যবহার করার পরামর্শ দেওয়া হয়)।
+এটি যাচাই করার জন্য আমরা Echidna চালাতে পারি:
+
+```bash
+echidna-test magic.sol
+...
+
+echidna_magic_values: passed! 🎉
+
+Seed: 2221503356319272685
+```
+
+তবে, আমরা এই ফাজিং ক্যাম্পেইন চালানোর সময় কর্পাস সংগ্রহ করতে Echidna ব্যবহার করতে পারি।
+
+### একটি কর্পাস সংগ্রহ করা {#collecting-a-corpus}
+
+কর্পাস সংগ্রহ সক্ষম করতে, একটি কর্পাস ডিরেক্টরি তৈরি করুন:
+
+```bash
+mkdir corpus-magic
+```
+
+এবং একটি [Echidna কনফিগারেশন ফাইল](https://github.com/crytic/echidna/wiki/Config) `config.yaml`:
+
+```yaml
+coverage: true
+corpusDir: "corpus-magic"
+```
+
+এখন আমরা আমাদের টুলটি চালাতে পারি এবং সংগৃহীত কর্পাস পরীক্ষা করতে পারি:
+
+```bash
+echidna-test magic.sol --config config.yaml
+```
+
+Echidna এখনও সঠিক ম্যাজিক ভ্যালু খুঁজে পাচ্ছে না, তবে আমরা এর সংগৃহীত কর্পাসটি দেখতে পারি।
+উদাহরণস্বরূপ, এই ফাইলগুলোর মধ্যে একটি ছিল:
+
+```json
+[
+ {
+ "_gas'": "0xffffffff",
+ "_delay": ["0x13647", "0xccf6"],
+ "_src": "00a329c0648769a73afac7f9381e08fb43dbea70",
+ "_dst": "00a329c0648769a73afac7f9381e08fb43dbea72",
+ "_value": "0x0",
+ "_call": {
+ "tag": "SolCall",
+ "contents": [
+ "magic",
+ [
+ {
+ "contents": [
+ 256,
+ "93723985220345906694500679277863898678726808528711107336895287282192244575836"
+ ],
+ "tag": "AbiUInt"
+ },
+ {
+ "contents": [256, "334"],
+ "tag": "AbiUInt"
+ },
+ {
+ "contents": [
+ 256,
+ "68093943901352437066264791224433559271778087297543421781073458233697135179558"
+ ],
+ "tag": "AbiUInt"
+ },
+ {
+ "tag": "AbiUInt",
+ "contents": [256, "332"]
+ }
+ ]
+ ]
+ },
+ "_gasprice'": "0xa904461f1"
+ }
+]
+```
+
+স্পষ্টতই, এই ইনপুটটি আমাদের প্রপার্টিতে ফেইলিওর ট্রিগার করবে না। তবে, পরবর্তী ধাপে, আমরা দেখব এর জন্য কীভাবে এটি পরিবর্তন করতে হয়।
+
+### একটি কর্পাস সিডিং করা {#seeding-a-corpus}
+
+`magic` ফাংশনটির সাথে মোকাবিলা করার জন্য Echidna-এর কিছু সাহায্য প্রয়োজন। আমরা এর জন্য উপযুক্ত
+প্যারামিটার ব্যবহার করার জন্য ইনপুটটি কপি এবং মডিফাই করতে যাচ্ছি:
+
+```bash
+cp corpus/2712688662897926208.txt corpus/new.txt
+```
+
+আমরা `magic(42,129,333,0)` কল করার জন্য `new.txt` মডিফাই করব। এখন, আমরা Echidna পুনরায় চালাতে পারি:
+
+```bash
+echidna-test magic.sol --config config.yaml
+...
+echidna_magic_values: failed!💥
+ Call sequence:
+ magic(42,129,333,0)
+
+
+Unique instructions: 142
+Unique codehashes: 1
+Seed: -7293830866560616537
+
+```
+
+এবার, এটি খুঁজে পেয়েছে যে প্রপার্টিটি সঙ্গে সঙ্গে লঙ্ঘিত হয়েছে।
+
+## উচ্চ গ্যাস খরচের ট্রানজ্যাকশন খোঁজা {#finding-transactions-with-high-gas-consumption}
+
+আমরা দেখব Echidna দিয়ে কীভাবে উচ্চ গ্যাস খরচের ট্রানজ্যাকশন খুঁজে বের করা যায়। টার্গেট হলো নিম্নলিখিত স্মার্ট কন্ট্র্যাক্ট:
+
+```solidity
+contract C {
+ uint state;
+
+ function expensive(uint8 times) internal {
+ for(uint8 i=0; i < times; i++)
+ state = state + i;
+ }
+
+ function f(uint x, uint y, uint8 times) public {
+ if (x == 42 && y == 123)
+ expensive(times);
+ else
+ state = 0;
+ }
+
+ function echidna_test() public returns (bool) {
+ return true;
+ }
+
+}
+```
+
+এখানে `expensive`-এর একটি বড় গ্যাস খরচ থাকতে পারে।
+
+বর্তমানে, Echidna-এর পরীক্ষা করার জন্য সবসময় একটি প্রপার্টি প্রয়োজন: এখানে `echidna_test` সবসময় `true` রিটার্ন করে।
+এটি যাচাই করার জন্য আমরা Echidna চালাতে পারি:
+
+```
+echidna-test gas.sol
+...
+echidna_test: passed! 🎉
+
+Seed: 2320549945714142710
+```
+
+### গ্যাস খরচ পরিমাপ করা {#measuring-gas-consumption}
+
+Echidna-এর সাথে গ্যাস খরচ সক্ষম করতে, একটি কনফিগারেশন ফাইল `config.yaml` তৈরি করুন:
+
+```yaml
+estimateGas: true
+```
+
+এই উদাহরণে, ফলাফলগুলো সহজে বোঝার জন্য আমরা ট্রানজ্যাকশন সিকোয়েন্সের আকারও কমিয়ে দেব:
+
+```yaml
+seqLen: 2
+estimateGas: true
+```
+
+### Echidna চালান {#run-echidna-3}
+
+কনফিগারেশন ফাইল তৈরি হয়ে গেলে, আমরা এইভাবে Echidna চালাতে পারি:
+
+```bash
+echidna-test gas.sol --config config.yaml
+...
+echidna_test: passed! 🎉
+
+f used a maximum of 1333608 gas
+ Call sequence:
+ f(42,123,249) Gas price: 0x10d5733f0a Time delay: 0x495e5 Block delay: 0x88b2
+
+Unique instructions: 157
+Unique codehashes: 1
+Seed: -325611019680165325
+
+```
+
+- [HEVM](https://github.com/dapphub/dapptools/tree/master/src/hevm#hevm-) দ্বারা প্রদত্ত একটি অনুমান হলো দেখানো গ্যাস।
+
+### গ্যাস-কমানো কলগুলো ফিল্টার করা {#filtering-out-gas-reducing-calls}
+
+উপরে **ফাজিং ক্যাম্পেইনের সময় কল করার জন্য ফাংশন ফিল্টার করা** বিষয়ক টিউটোরিয়ালটি দেখায় কীভাবে আপনার টেস্টিং থেকে কিছু ফাংশন সরানো যায়।
+একটি সঠিক গ্যাস অনুমান পাওয়ার জন্য এটি অত্যন্ত গুরুত্বপূর্ণ হতে পারে।
+নিম্নলিখিত উদাহরণটি বিবেচনা করুন:
+
+```solidity
+contract C {
+ address [] addrs;
+ function push(address a) public {
+ addrs.push(a);
+ }
+ function pop() public {
+ addrs.pop();
+ }
+ function clear() public{
+ addrs.length = 0;
+ }
+ function check() public{
+ for(uint256 i = 0; i < addrs.length; i++)
+ for(uint256 j = i+1; j < addrs.length; j++)
+ if (addrs[i] == addrs[j])
+ addrs[j] = address(0x0);
+ }
+ function echidna_test() public returns (bool) {
+ return true;
+ }
+}
+```
+
+যদি Echidna সমস্ত ফাংশন কল করতে পারে, তবে এটি সহজে উচ্চ গ্যাস খরচের ট্রানজ্যাকশন খুঁজে পাবে না:
+
+```
+echidna-test pushpop.sol --config config.yaml
+...
+pop used a maximum of 10746 gas
+...
+check used a maximum of 23730 gas
+...
+clear used a maximum of 35916 gas
+...
+push used a maximum of 40839 gas
+```
+
+এর কারণ হলো খরচ `addrs`-এর আকারের উপর নির্ভর করে এবং র্যান্ডম কলগুলো অ্যারেটিকে প্রায় খালি রেখে দেয়।
+তবে, `pop` এবং `clear`-কে ব্ল্যাকলিস্ট করা আমাদের অনেক ভালো ফলাফল দেয়:
+
+```yaml
+filterBlacklist: true
+filterFunctions: ["pop", "clear"]
+```
+
+```
+echidna-test pushpop.sol --config config.yaml
+...
+push used a maximum of 40839 gas
+...
+check used a maximum of 1484472 gas
+```
+
+### সারসংক্ষেপ: উচ্চ গ্যাস খরচের ট্রানজ্যাকশন খোঁজা {#summary-finding-transactions-with-high-gas-consumption}
+
+`estimateGas` কনফিগারেশন অপশন ব্যবহার করে Echidna উচ্চ গ্যাস খরচের ট্রানজ্যাকশন খুঁজে বের করতে পারে:
+
+```yaml
+estimateGas: true
+```
+
+```bash
+echidna-test contract.sol --config config.yaml
+...
+```
+
+ফাজিং ক্যাম্পেইন শেষ হয়ে গেলে Echidna প্রতিটি ফাংশনের জন্য সর্বোচ্চ গ্যাস খরচের একটি সিকোয়েন্স রিপোর্ট করবে।
diff --git a/public/content/translations/bn/developers/tutorials/how-to-use-manticore-to-find-smart-contract-bugs/index.md b/public/content/translations/bn/developers/tutorials/how-to-use-manticore-to-find-smart-contract-bugs/index.md
new file mode 100644
index 00000000000..8c506dc8609
--- /dev/null
+++ b/public/content/translations/bn/developers/tutorials/how-to-use-manticore-to-find-smart-contract-bugs/index.md
@@ -0,0 +1,526 @@
+---
+title: "স্মার্ট কন্ট্র্যাক্টে বাগ খুঁজে বের করতে Manticore কিভাবে ব্যবহার করবেন"
+description: "স্মার্ট কন্ট্র্যাক্টে স্বয়ংক্রিয়ভাবে বাগ খুঁজে বের করতে Manticore কিভাবে ব্যবহার করবেন"
+author: Trailofbits
+lang: bn
+tags:
+ [
+ "সলিডিটি",
+ "স্মার্ট কন্ট্র্যাক্ট",
+ "নিরাপত্তা",
+ "পরীক্ষা",
+ "প্রথাগত যাচাইকরণ"
+ ]
+skill: advanced
+published: 2020-01-13
+source: Building secure contracts
+sourceUrl: https://github.com/crytic/building-secure-contracts/tree/master/program-analysis/manticore
+---
+
+এই টিউটোরিয়ালের লক্ষ্য হল কিভাবে Manticore ব্যবহার করে স্মার্ট কন্ট্র্যাক্টে স্বয়ংক্রিয়ভাবে বাগ খুঁজে বের করা যায় তা দেখানো।
+
+## ইনস্টলেশন {#installation}
+
+Manticore-এর জন্য >= python 3.6 প্রয়োজন। এটি pip-এর মাধ্যমে বা docker ব্যবহার করে ইনস্টল করা যেতে পারে।
+
+### docker-এর মাধ্যমে Manticore {#manticore-through-docker}
+
+```bash
+docker pull trailofbits/eth-security-toolbox
+docker run -it -v "$PWD":/home/training trailofbits/eth-security-toolbox
+```
+
+_শেষ কমান্ডটি একটি docker-এ eth-security-toolbox চালায় যেটির আপনার বর্তমান ডিরেক্টরিতে অ্যাক্সেস আছে। আপনি আপনার হোস্ট থেকে ফাইলগুলো পরিবর্তন করতে পারেন, এবং docker থেকে ফাইলগুলোতে টুলস চালাতে পারেন_
+
+docker-এর ভিতরে, চালান:
+
+```bash
+solc-select 0.5.11
+cd /home/trufflecon/
+```
+
+### pip-এর মাধ্যমে Manticore {#manticore-through-pip}
+
+```bash
+pip3 install --user manticore
+```
+
+solc 0.5.11 সুপারিশ করা হয়।
+
+### একটি স্ক্রিপ্ট চালানো {#running-a-script}
+
+python 3 দিয়ে একটি python স্ক্রিপ্ট চালাতে:
+
+```bash
+python3 script.py
+```
+
+## ডাইনামিক সিম্বলিক এক্সিকিউশন-এর ভূমিকা {#introduction-to-dynamic-symbolic-execution}
+
+### সংক্ষেপে ডাইনামিক সিম্বলিক এক্সিকিউশন {#dynamic-symbolic-execution-in-a-nutshell}
+
+ডাইনামিক সিম্বলিক এক্সিকিউশন (DSE) হল একটি প্রোগ্রাম অ্যানালিসিস কৌশল যা উচ্চ মাত্রার সিমেন্টিক সচেতনতার সাথে একটি স্টেট স্পেস এক্সপ্লোর করে। এই কৌশলটি "প্রোগ্রাম পাথ" আবিষ্কারের উপর ভিত্তি করে তৈরি, যা `path predicates` নামক গাণিতিক সূত্র হিসাবে উপস্থাপিত হয়। ধারণাগতভাবে, এই কৌশলটি দুটি ধাপে পাথ প্রেডিকেটগুলির উপর কাজ করে:
+
+1. এগুলি প্রোগ্রামের ইনপুটের উপর সীমাবদ্ধতা ব্যবহার করে তৈরি করা হয়।
+2. এগুলি এমন প্রোগ্রাম ইনপুট তৈরি করতে ব্যবহৃত হয় যা সংশ্লিষ্ট পাথগুলিকে এক্সিকিউট করাবে।
+
+এই পদ্ধতিটি কোনো ফলস পজিটিভ তৈরি করে না, এই অর্থে যে সমস্ত চিহ্নিত প্রোগ্রাম স্টেট কংক্রিট এক্সিকিউশনের সময় ট্রিগার করা যেতে পারে। উদাহরণস্বরূপ, যদি অ্যানালিসিস একটি ইন্টিজার ওভারফ্লো খুঁজে পায়, তবে এটি পুনরুৎপাদনযোগ্য হওয়ার নিশ্চয়তা দেওয়া হয়।
+
+### পাথ প্রেডিকেটের উদাহরণ {#path-predicate-example}
+
+DSE কীভাবে কাজ করে তার একটি ধারণা পেতে, নিম্নলিখিত উদাহরণটি বিবেচনা করুন:
+
+```solidity
+function f(uint a){
+
+ if (a == 65) {
+ // একটি বাগ উপস্থিত
+ }
+
+}
+```
+
+যেহেতু `f()`-এ দুটি পাথ রয়েছে, একটি DSE দুটি ভিন্ন পাথ প্রেডিকেট তৈরি করবে:
+
+- পাথ 1: `a == 65`
+- পাথ 2: `Not (a == 65)`
+
+প্রতিটি পাথ প্রেডিকেট একটি গাণিতিক সূত্র যা একটি তথাকথিত [SMT solver](https://wikipedia.org/wiki/Satisfiability_modulo_theories)-কে দেওয়া যেতে পারে, যা সমীকরণটি সমাধান করার চেষ্টা করবে। `পাথ 1`-এর জন্য, সলভার বলবে যে `a = 65` দিয়ে পাথটি এক্সপ্লোর করা যাবে। `পাথ 2`-এর জন্য, সলভার `a`-কে 65 ছাড়া অন্য যেকোনো মান দিতে পারে, উদাহরণস্বরূপ `a = 0`।
+
+### প্রপার্টি যাচাই করা {#verifying-properties}
+
+Manticore প্রতিটি পাথের সমস্ত এক্সিকিউশনের উপর সম্পূর্ণ নিয়ন্ত্রণ দেয়। ফলস্বরূপ, এটি আপনাকে প্রায় যেকোনো কিছুতে যথেচ্ছ সীমাবদ্ধতা যোগ করতে দেয়। এই নিয়ন্ত্রণটি কন্ট্র্যাক্টে প্রপার্টি তৈরি করার অনুমতি দেয়।
+
+নিম্নলিখিত উদাহরণটি বিবেচনা করুন:
+
+```solidity
+function unsafe_add(uint a, uint b) returns(uint c){
+ c = a + b; // কোনো ওভারফ্লো সুরক্ষা নেই
+ return c;
+}
+```
+
+এখানে ফাংশনটিতে এক্সপ্লোর করার জন্য কেবল একটি পাথ রয়েছে:
+
+- পাথ 1: `c = a + b`
+
+Manticore ব্যবহার করে, আপনি ওভারফ্লো পরীক্ষা করতে পারেন এবং পাথ প্রেডিকেটে সীমাবদ্ধতা যোগ করতে পারেন:
+
+- `c = a + b AND (c < a OR c < b)`
+
+যদি `a` এবং `b`-এর এমন একটি মূল্যায়ন খুঁজে পাওয়া সম্ভব হয় যার জন্য উপরের পাথ প্রেডিকেটটি সম্ভব, এর মানে হল আপনি একটি ওভারফ্লো খুঁজে পেয়েছেন। উদাহরণস্বরূপ সলভার `a = 10 , b = MAXUINT256` ইনপুটটি তৈরি করতে পারে।
+
+আপনি যদি একটি ফিক্সড সংস্করণ বিবেচনা করেন:
+
+```solidity
+function safe_add(uint a, uint b) returns(uint c){
+ c = a + b;
+ require(c>=a);
+ require(c>=b);
+ return c;
+}
+```
+
+ওভারফ্লো পরীক্ষাসহ সংশ্লিষ্ট সূত্রটি হবে:
+
+- `c = a + b AND (c >= a) AND (c=>b) AND (c < a OR c < b)`
+
+এই সূত্রটি সমাধান করা যায় না; অন্য কথায় এটি একটি **প্রমাণ** যে `safe_add`-এ `c` সর্বদা বৃদ্ধি পাবে।
+
+সুতরাং DSE একটি শক্তিশালী টুল, যা আপনার কোডে যথেচ্ছ সীমাবদ্ধতা যাচাই করতে পারে।
+
+## Manticore-এর অধীনে চালানো {#running-under-manticore}
+
+আমরা দেখব কিভাবে Manticore API দিয়ে একটি স্মার্ট কন্ট্র্যাক্ট এক্সপ্লোর করতে হয়। লক্ষ্য হল নিম্নলিখিত স্মার্ট কন্ট্র্যাক্ট [`example.sol`](https://github.com/crytic/building-secure-contracts/blob/master/program-analysis/manticore/examples/example.sol):
+
+```solidity
+pragma solidity >=0.4.24 <0.6.0;
+
+contract Simple {
+ function f(uint a) payable public{
+ if (a == 65) {
+ revert();
+ }
+ }
+}
+```
+
+### একটি স্বতন্ত্র এক্সপ্লোরেশন চালান {#run-a-standalone-exploration}
+
+আপনি নিম্নলিখিত কমান্ড দ্বারা সরাসরি স্মার্ট কন্ট্র্যাক্টে Manticore চালাতে পারেন (`প্রজেক্ট` একটি সলিডিটি ফাইল, বা একটি প্রজেক্ট ডিরেক্টরি হতে পারে):
+
+```bash
+$ manticore project
+```
+
+আপনি এইরকম টেস্টকেসগুলির আউটপুট পাবেন (ক্রম পরিবর্তন হতে পারে):
+
+```
+...
+... m.c.manticore:INFO: Generated testcase No. 0 - STOP
+... m.c.manticore:INFO: Generated testcase No. 1 - REVERT
+... m.c.manticore:INFO: Generated testcase No. 2 - RETURN
+... m.c.manticore:INFO: Generated testcase No. 3 - REVERT
+... m.c.manticore:INFO: Generated testcase No. 4 - STOP
+... m.c.manticore:INFO: Generated testcase No. 5 - REVERT
+... m.c.manticore:INFO: Generated testcase No. 6 - REVERT
+... m.c.manticore:INFO: Results in /home/ethsec/workshops/Automated Smart Contracts Audit - TruffleCon 2018/manticore/examples/mcore_t6vi6ij3
+...
+```
+
+অতিরিক্ত তথ্য ছাড়া, Manticore নতুন সিম্বলিক
+লেনদেনের মাধ্যমে কন্ট্র্যাক্টটি অন্বেষণ করবে যতক্ষণ না এটি কন্ট্র্যাক্টে নতুন পথ অন্বেষণ করা বন্ধ করে। Manticore একটি ব্যর্থ লেনদেনের পরে নতুন লেনদেন চালায় না (যেমন: একটি রিভার্টের পরে)।
+
+Manticore একটি `mcore_*` ডিরেক্টরিতে তথ্য আউটপুট করবে। অন্যান্য জিনিসের মধ্যে, আপনি এই ডিরেক্টরিতে পাবেন:
+
+- `global.summary`: কভারেজ এবং কম্পাইলার সতর্কতা
+- `test_XXXXX.summary`: কভারেজ, শেষ নির্দেশনা, প্রতি টেস্ট কেস অনুযায়ী অ্যাকাউন্ট ব্যালেন্স
+- `test_XXXXX.tx`: প্রতি টেস্ট কেস অনুযায়ী লেনদেনের বিস্তারিত তালিকা
+
+এখানে Manticore ৭টি টেস্ট কেস খুঁজে পেয়েছে, যা নিম্নরূপ (ফাইলের নামের ক্রম পরিবর্তন হতে পারে):
+
+| | লেনদেন 0 | লেনদেন 1 | লেনদেন 2 | ফলাফল |
+| :-------------------------------------------------------: | :---------------: | :------------------------: | -------------------------- | :----: |
+| **test_00000000.tx** | কন্ট্র্যাক্ট তৈরি | f(!=65) | f(!=65) | STOP |
+| **test_00000001.tx** | কন্ট্র্যাক্ট তৈরি | ফলব্যাক ফাংশন | | REVERT |
+| **test_00000002.tx** | কন্ট্র্যাক্ট তৈরি | | | RETURN |
+| **test_00000003.tx** | কন্ট্র্যাক্ট তৈরি | f(65) | | REVERT |
+| **test_00000004.tx** | কন্ট্র্যাক্ট তৈরি | f(!=65) | | STOP |
+| **test_00000005.tx** | কন্ট্র্যাক্ট তৈরি | f(!=65) | f(65) | REVERT |
+| **test_00000006.tx** | কন্ট্র্যাক্ট তৈরি | f(!=65) | ফলব্যাক ফাংশন | REVERT |
+
+_এক্সপ্লোরেশন সারাংশ f(!=65) বোঝায় যে f-কে 65 থেকে ভিন্ন যেকোনো মান দিয়ে কল করা হয়েছে।_
+
+আপনি যেমন লক্ষ্য করতে পারেন, Manticore প্রতিটি সফল বা রিভার্ট হওয়া লেনদেনের জন্য একটি অনন্য টেস্ট কেস তৈরি করে।
+
+আপনি যদি দ্রুত কোড এক্সপ্লোরেশন চান তবে `--quick-mode` ফ্ল্যাগটি ব্যবহার করুন (এটি বাগ ডিটেক্টর, গ্যাস গণনা ইত্যাদি নিষ্ক্রিয় করে)
+
+### API-এর মাধ্যমে একটি স্মার্ট কন্ট্র্যাক্ট ম্যানিপুলেট করা {#manipulate-a-smart-contract-through-the-api}
+
+এই বিভাগে Manticore Python API-এর মাধ্যমে কীভাবে একটি স্মার্ট কন্ট্র্যাক্ট ম্যানিপুলেট করতে হয় তা বিস্তারিতভাবে বর্ণনা করা হয়েছে। আপনি `*.py` এক্সটেনশন সহ নতুন ফাইল তৈরি করতে পারেন এবং এই ফাইলে API কমান্ডগুলি (যার মূল বিষয়গুলি নীচে বর্ণনা করা হবে) যোগ করে প্রয়োজনীয় কোড লিখতে পারেন এবং তারপরে `$ python3 *.py` কমান্ড দিয়ে এটি চালাতে পারেন। এছাড়াও আপনি নীচের কমান্ডগুলি সরাসরি পাইথন কনসোলে এক্সিকিউট করতে পারেন, কনসোলটি চালানোর জন্য `$ python3` কমান্ডটি ব্যবহার করুন।
+
+### অ্যাকাউন্ট তৈরি করা {#creating-accounts}
+
+আপনার প্রথম যা করা উচিত তা হল নিম্নলিখিত কমান্ডগুলি দিয়ে একটি নতুন ব্লকচেইন শুরু করা:
+
+```python
+from manticore.ethereum import ManticoreEVM
+
+m = ManticoreEVM()
+```
+
+একটি নন-কন্ট্র্যাক্ট অ্যাকাউন্ট [m.create_account](https://manticore.readthedocs.io/en/latest/evm.html?highlight=create_account#manticore.ethereum.ManticoreEVM.create_account) ব্যবহার করে তৈরি করা হয়:
+
+```python
+user_account = m.create_account(balance=1000)
+```
+
+একটি সলিডিটি কন্ট্র্যাক্ট [m.solidity_create_contract](https://manticore.readthedocs.io/en/latest/evm.html?highlight=solidity_create#manticore.ethereum.ManticoreEVM.create_contract) ব্যবহার করে ডিপ্লয় করা যেতে পারে:
+
+```solidity
+source_code = '''
+pragma solidity >=0.4.24 <0.6.0;
+contract Simple {
+ function f(uint a) payable public{
+ if (a == 65) {
+ revert();
+ }
+ }
+}
+'''
+# কন্ট্র্যাক্টটি শুরু করুন
+contract_account = m.solidity_create_contract(source_code, owner=user_account)
+```
+
+#### সারসংক্ষেপ {#summary}
+
+- আপনি [m.create_account](https://manticore.readthedocs.io/en/latest/evm.html?highlight=create_account#manticore.ethereum.ManticoreEVM.create_account) এবং [m.solidity_create_contract](https://manticore.readthedocs.io/en/latest/evm.html?highlight=solidity_create#manticore.ethereum.ManticoreEVM.create_contract) দিয়ে ব্যবহারকারী এবং কন্ট্র্যাক্ট অ্যাকাউন্ট তৈরি করতে পারেন।
+
+### লেনদেন এক্সিকিউট করা {#executing-transactions}
+
+Manticore দুই ধরনের লেনদেন সমর্থন করে:
+
+- র' লেনদেন: সমস্ত ফাংশন এক্সপ্লোর করা হয়
+- নামযুক্ত লেনদেন: শুধুমাত্র একটি ফাংশন এক্সপ্লোর করা হয়
+
+#### র' লেনদেন {#raw-transaction}
+
+একটি র' লেনদেন [m.transaction](https://manticore.readthedocs.io/en/latest/evm.html?highlight=transaction#manticore.ethereum.ManticoreEVM.transaction) ব্যবহার করে এক্সিকিউট করা হয়:
+
+```python
+m.transaction(caller=user_account,
+ address=contract_account,
+ data=data,
+ value=value)
+```
+
+লেনদেনের কলার, ঠিকানা, ডেটা, বা মান কংক্রিট বা সিম্বলিক উভয়ই হতে পারে:
+
+- [m.make_symbolic_value](https://manticore.readthedocs.io/en/latest/evm.html?highlight=make_symbolic_value#manticore.ethereum.ManticoreEVM.make_symbolic_value) একটি সিম্বলিক মান তৈরি করে।
+- [m.make_symbolic_buffer(size)](https://manticore.readthedocs.io/en/latest/evm.html?highlight=make_symbolic_buffer#manticore.ethereum.ManticoreEVM.make_symbolic_buffer) একটি সিম্বলিক বাইট অ্যারে তৈরি করে।
+
+উদাহরণস্বরূপ:
+
+```python
+symbolic_value = m.make_symbolic_value()
+symbolic_data = m.make_symbolic_buffer(320)
+m.transaction(caller=user_account,
+ address=contract_address,
+ data=symbolic_data,
+ value=symbolic_value)
+```
+
+যদি ডেটা সিম্বলিক হয়, Manticore লেনদেন এক্সিকিউশনের সময় কন্ট্র্যাক্টের সমস্ত ফাংশন এক্সপ্লোর করবে। ফাংশন সিলেকশন কীভাবে কাজ করে তা বোঝার জন্য [Hands on the Ethernaut CTF](https://blog.trailofbits.com/2017/11/06/hands-on-the-ethernaut-ctf/) নিবন্ধে ফলব্যাক ফাংশনের ব্যাখ্যা দেখা সহায়ক হবে।
+
+#### নামযুক্ত লেনদেন {#named-transaction}
+
+ফাংশনগুলি তাদের নামের মাধ্যমে এক্সিকিউট করা যেতে পারে।
+`f(uint var)`-কে একটি সিম্বলিক মান দিয়ে, user_account থেকে, এবং 0 ইথার সহ এক্সিকিউট করতে, ব্যবহার করুন:
+
+```python
+symbolic_var = m.make_symbolic_value()
+contract_account.f(symbolic_var, caller=user_account, value=0)
+```
+
+যদি লেনদেনের `value` নির্দিষ্ট করা না থাকে, তবে এটি ডিফল্টরূপে 0 হয়।
+
+#### সারাংশ {#summary-1}
+
+- একটি লেনদেনের আর্গুমেন্ট কংক্রিট বা সিম্বলিক হতে পারে
+- একটি র' লেনদেন সমস্ত ফাংশন এক্সপ্লোর করবে
+- ফাংশনকে তাদের নাম দিয়ে কল করা যেতে পারে
+
+### ওয়ার্কস্পেস {#workspace}
+
+`m.workspace` হল জেনারেট করা সমস্ত ফাইলের জন্য আউটপুট ডিরেক্টরি হিসাবে ব্যবহৃত ডিরেক্টরি:
+
+```python
+print("Results are in {}".format(m.workspace))
+```
+
+### এক্সপ্লোরেশন বন্ধ করুন {#terminate-the-exploration}
+
+এক্সপ্লোরেশন থামাতে [m.finalize()](https://manticore.readthedocs.io/en/latest/evm.html?highlight=finalize#manticore.ethereum.ManticoreEVM.finalize) ব্যবহার করুন। এই পদ্ধতিটি কল করার পরে আর কোনো লেনদেন পাঠানো উচিত নয় এবং Manticore প্রতিটি এক্সপ্লোর করা পাথের জন্য টেস্ট কেস তৈরি করে।
+
+### সারাংশ: Manticore-এর অধীনে চালানো {#summary-running-under-manticore}
+
+পূর্ববর্তী সমস্ত ধাপ একসাথে রাখলে, আমরা পাই:
+
+```python
+from manticore.ethereum import ManticoreEVM
+
+m = ManticoreEVM()
+
+with open('example.sol') as f:
+ source_code = f.read()
+
+user_account = m.create_account(balance=1000)
+contract_account = m.solidity_create_contract(source_code, owner=user_account)
+
+symbolic_var = m.make_symbolic_value()
+contract_account.f(symbolic_var)
+
+print("Results are in {}".format(m.workspace))
+m.finalize() # এক্সপ্লোরেশন বন্ধ করুন
+```
+
+উপরের সমস্ত কোড আপনি [`example_run.py`](https://github.com/crytic/building-secure-contracts/blob/master/program-analysis/manticore/examples/example_run.py) এর মধ্যে খুঁজে পেতে পারেন
+
+## থ্রোয়িং পাথ পাওয়া {#getting-throwing-paths}
+
+আমরা এখন `f()`-এ একটি এক্সেপশন উত্থাপনকারী পাথগুলির জন্য নির্দিষ্ট ইনপুট তৈরি করব। লক্ষ্য এখনও নিম্নলিখিত স্মার্ট কন্ট্র্যাক্ট [`example.sol`](https://github.com/crytic/building-secure-contracts/blob/master/program-analysis/manticore/examples/example.sol):
+
+```solidity
+pragma solidity >=0.4.24 <0.6.0;
+contract Simple {
+ function f(uint a) payable public{
+ if (a == 65) {
+ revert();
+ }
+ }
+}
+```
+
+### স্টেটের তথ্য ব্যবহার করা {#using-state-information}
+
+প্রতিটি এক্সিকিউট করা পাথের নিজস্ব ব্লকচেইনের স্টেট রয়েছে। একটি স্টেট হয় রেডি থাকে অথবা কিল হয়ে যায়, যার অর্থ এটি একটি THROW বা REVERT নির্দেশনায় পৌঁছেছে:
+
+- [m.ready_states](https://manticore.readthedocs.io/en/latest/states.html#accessing): রেডি থাকা স্টেটগুলির তালিকা (তারা একটি REVERT/INVALID এক্সিকিউট করেনি)
+- [m.killed_states](https://manticore.readthedocs.io/en/latest/states.html#accessings): কিল হয়ে যাওয়া স্টেটগুলির তালিকা
+- [m.all_states](https://manticore.readthedocs.io/en/latest/states.html#accessings): সমস্ত স্টেট
+
+```python
+for state in m.all_states:
+ # স্টেট নিয়ে কিছু করুন
+```
+
+আপনি স্টেটের তথ্য অ্যাক্সেস করতে পারেন। উদাহরণস্বরূপ:
+
+- `state.platform.get_balance(account.address)`: অ্যাকাউন্টের ব্যালেন্স
+- `state.platform.transactions`: লেনদেনের তালিকা
+- `state.platform.transactions[-1].return_data`: শেষ লেনদেন দ্বারা ফেরত দেওয়া ডেটা
+
+শেষ লেনদেন দ্বারা ফেরত দেওয়া ডেটা একটি অ্যারে, যা ABI.deserialize দিয়ে একটি মানে রূপান্তরিত করা যেতে পারে, উদাহরণস্বরূপ:
+
+```python
+data = state.platform.transactions[0].return_data
+data = ABI.deserialize("uint", data)
+```
+
+### কীভাবে টেস্টকেস জেনারেট করবেন {#how-to-generate-testcase}
+
+টেস্টকেস জেনারেট করতে [m.generate_testcase(state, name)](https://manticore.readthedocs.io/en/latest/evm.html?highlight=generate_testcase#manticore.ethereum.ManticoreEVM.generate_testcase) ব্যবহার করুন:
+
+```python
+m.generate_testcase(state, 'BugFound')
+```
+
+### সারাংশ {#summary-2}
+
+- আপনি m.all_states দিয়ে স্টেটের উপর ইটারেট করতে পারেন
+- `state.platform.get_balance(account.address)` অ্যাকাউন্টের ব্যালেন্স ফেরত দেয়
+- `state.platform.transactions` লেনদেনের তালিকা ফেরত দেয়
+- `transaction.return_data` হল ফেরত দেওয়া ডেটা
+- `m.generate_testcase(state, name)` স্টেটের জন্য ইনপুট জেনারেট করে
+
+### সারাংশ: থ্রোয়িং পাথ পাওয়া {#summary-getting-throwing-path}
+
+```python
+from manticore.ethereum import ManticoreEVM
+
+m = ManticoreEVM()
+
+with open('example.sol') as f:
+ source_code = f.read()
+
+user_account = m.create_account(balance=1000)
+contract_account = m.solidity_create_contract(source_code, owner=user_account)
+
+symbolic_var = m.make_symbolic_value()
+contract_account.f(symbolic_var)
+
+## একটি এক্সিকিউশন REVERT বা INVALID দিয়ে শেষ হয় কিনা তা পরীক্ষা করুন
+
+for state in m.terminated_states:
+ last_tx = state.platform.transactions[-1]
+ if last_tx.result in ['REVERT', 'INVALID']:
+ print('Throw found {}'.format(m.workspace))
+ m.generate_testcase(state, 'ThrowFound')
+```
+
+উপরের সমস্ত কোড আপনি [`example_run.py`](https://github.com/crytic/building-secure-contracts/blob/master/program-analysis/manticore/examples/example_run.py) এর মধ্যে খুঁজে পেতে পারেন
+
+_দ্রষ্টব্য আমরা একটি অনেক সহজ স্ক্রিপ্ট তৈরি করতে পারতাম, কারণ terminated_state দ্বারা ফেরত দেওয়া সমস্ত স্টেটের ফলাফলে REVERT বা INVALID থাকে: এই উদাহরণটি শুধুমাত্র API কীভাবে ম্যানিপুলেট করতে হয় তা প্রদর্শনের জন্য ছিল।_
+
+## সীমাবদ্ধতা যোগ করা {#adding-constraints}
+
+আমরা দেখব কীভাবে এক্সপ্লোরেশনকে সীমাবদ্ধ করা যায়। আমরা এই ধারণাটি ধরে নেব যে `f()`-এর
+ডকুমেন্টেশন অনুযায়ী ফাংশনটি কখনও `a == 65` দিয়ে কল করা হয় না, তাই `a == 65` সহ যেকোনো বাগ একটি আসল বাগ নয়। লক্ষ্য এখনও নিম্নলিখিত স্মার্ট কন্ট্র্যাক্ট [`example.sol`](https://github.com/crytic/building-secure-contracts/blob/master/program-analysis/manticore/examples/example.sol):
+
+```solidity
+pragma solidity >=0.4.24 <0.6.0;
+contract Simple {
+ function f(uint a) payable public{
+ if (a == 65) {
+ revert();
+ }
+ }
+}
+```
+
+### অপারেটর {#operators}
+
+[অপারেটর](https://github.com/trailofbits/manticore/blob/master/manticore/core/smtlib/operators.py) মডিউলটি সীমাবদ্ধতার ম্যানিপুলেশনকে সহজ করে, অন্যান্য জিনিসের মধ্যে এটি প্রদান করে:
+
+- Operators.AND,
+- Operators.OR,
+- Operators.UGT (আনসাইন্ড গ্রেটার দ্যান),
+- Operators.UGE (আনসাইন্ড গ্রেটার দ্যান অর ইকুয়াল টু),
+- Operators.ULT (আনসাইন্ড লোয়ার দ্যান),
+- Operators.ULE (আনসাইন্ড লোয়ার দ্যান অর ইকুয়াল টু)।
+
+মডিউলটি ইম্পোর্ট করতে নিম্নলিখিতটি ব্যবহার করুন:
+
+```python
+from manticore.core.smtlib import Operators
+```
+
+`Operators.CONCAT` একটি অ্যারের সাথে একটি মান কনক্যাটেনেট করতে ব্যবহৃত হয়। উদাহরণস্বরূপ, একটি লেনদেনের return_data-কে অন্য একটি মানের সাথে পরীক্ষা করার জন্য একটি মানে পরিবর্তন করতে হবে:
+
+```python
+last_return = Operators.CONCAT(256, *last_return)
+```
+
+### সীমাবদ্ধতা {#state-constraint}
+
+আপনি বিশ্বব্যাপী বা একটি নির্দিষ্ট স্টেটের জন্য সীমাবদ্ধতা ব্যবহার করতে পারেন।
+
+#### গ্লোবাল সীমাবদ্ধতা {#state-constraint}
+
+একটি গ্লোবাল সীমাবদ্ধতা যোগ করতে `m.constrain(constraint)` ব্যবহার করুন।
+উদাহরণস্বরূপ, আপনি একটি সিম্বলিক ঠিকানা থেকে একটি কন্ট্র্যাক্ট কল করতে পারেন, এবং এই ঠিকানাটিকে নির্দিষ্ট মানে সীমাবদ্ধ করতে পারেন:
+
+```python
+symbolic_address = m.make_symbolic_value()
+m.constraint(Operators.OR(symbolic == 0x41, symbolic_address == 0x42))
+m.transaction(caller=user_account,
+ address=contract_account,
+ data=m.make_symbolic_buffer(320),
+ value=0)
+```
+
+#### স্টেট সীমাবদ্ধতা {#state-constraint}
+
+একটি নির্দিষ্ট স্টেটে সীমাবদ্ধতা যোগ করতে [state.constrain(constraint)](https://manticore.readthedocs.io/en/latest/states.html?highlight=StateBase#manticore.core.state.StateBase.constrain) ব্যবহার করুন।
+এটি এক্সপ্লোরেশনের পরে স্টেটের উপর কিছু প্রপার্টি পরীক্ষা করার জন্য স্টেটকে সীমাবদ্ধ করতে ব্যবহার করা যেতে পারে।
+
+### সীমাবদ্ধতা পরীক্ষা করা {#checking-constraint}
+
+একটি সীমাবদ্ধতা এখনও সম্ভব কিনা তা জানতে `solver.check(state.constraints)` ব্যবহার করুন।
+উদাহরণস্বরূপ, নিম্নলিখিতটি symbolic_value-কে 65 থেকে ভিন্ন হতে সীমাবদ্ধ করবে এবং স্টেটটি এখনও সম্ভব কিনা তা পরীক্ষা করবে:
+
+```python
+state.constrain(symbolic_var != 65)
+if solver.check(state.constraints):
+ # স্টেটটি সম্ভব
+```
+
+### সারাংশ: সীমাবদ্ধতা যোগ করা {#summary-adding-constraints}
+
+পূর্ববর্তী কোডে সীমাবদ্ধতা যোগ করে, আমরা পাই:
+
+```python
+from manticore.ethereum import ManticoreEVM
+from manticore.core.smtlib.solver import Z3Solver
+
+solver = Z3Solver.instance()
+
+m = ManticoreEVM()
+
+with open("example.sol") as f:
+ source_code = f.read()
+
+user_account = m.create_account(balance=1000)
+contract_account = m.solidity_create_contract(source_code, owner=user_account)
+
+symbolic_var = m.make_symbolic_value()
+contract_account.f(symbolic_var)
+
+no_bug_found = True
+
+## একটি এক্সিকিউশন REVERT বা INVALID দিয়ে শেষ হয় কিনা তা পরীক্ষা করুন
+
+for state in m.terminated_states:
+ last_tx = state.platform.transactions[-1]
+ if last_tx.result in ['REVERT', 'INVALID']:
+ # আমরা সেই পাথ বিবেচনা করি না যেখানে a == 65
+ condition = symbolic_var != 65
+ if m.generate_testcase(state, name="BugFound", only_if=condition):
+ print(f'বাগ পাওয়া গেছে, ফলাফলগুলো {m.workspace}-এ আছে')
+ no_bug_found = False
+
+if no_bug_found:
+ print(f'কোনো বাগ পাওয়া যায়নি')
+```
+
+উপরের সমস্ত কোড আপনি [`example_run.py`](https://github.com/crytic/building-secure-contracts/blob/master/program-analysis/manticore/examples/example_run.py) এর মধ্যে খুঁজে পেতে পারেন
diff --git a/public/content/translations/bn/developers/tutorials/how-to-use-slither-to-find-smart-contract-bugs/index.md b/public/content/translations/bn/developers/tutorials/how-to-use-slither-to-find-smart-contract-bugs/index.md
new file mode 100644
index 00000000000..b65980a88d9
--- /dev/null
+++ b/public/content/translations/bn/developers/tutorials/how-to-use-slither-to-find-smart-contract-bugs/index.md
@@ -0,0 +1,239 @@
+---
+title: "স্মার্ট কন্ট্র্যাক্ট বাগ খুঁজে বের করতে কীভাবে স্লিদার ব্যবহার করবেন"
+description: "স্মার্ট কন্ট্র্যাক্টে স্বয়ংক্রিয়ভাবে বাগ খুঁজে পেতে কীভাবে স্লিদার ব্যবহার করবেন"
+author: Trailofbits
+lang: bn
+tags:
+ [
+ "সলিডিটি",
+ "স্মার্ট কন্ট্র্যাক্ট",
+ "নিরাপত্তা",
+ "পরীক্ষা"
+ ]
+skill: advanced
+published: 2020-06-09
+source: Building secure contracts
+sourceUrl: https://github.com/crytic/building-secure-contracts/tree/master/program-analysis/slither
+---
+
+## কীভাবে স্লিদার ব্যবহার করবেন {#how-to-use-slither}
+
+এই টিউটোরিয়ালের উদ্দেশ্য হলো স্মার্ট কন্ট্র্যাক্টে স্বয়ংক্রিয়ভাবে বাগ খুঁজে বের করতে কীভাবে স্লিদার ব্যবহার করা যায় তা দেখানো।
+
+- [ইনস্টলেশন](#installation)
+- [কমান্ড লাইন ব্যবহার](#command-line)
+- [স্ট্যাটিক অ্যানালাইসিসের ভূমিকা](#static-analysis): স্ট্যাটিক অ্যানালাইসিসের সংক্ষিপ্ত ভূমিকা
+- [API](#api-basics): পাইথন API-এর বর্ণনা
+
+## ইনস্টলেশন {#installation}
+
+স্লিদারের জন্য পাইথন >= 3.6 প্রয়োজন। এটি pip-এর মাধ্যমে বা docker ব্যবহার করে ইনস্টল করা যেতে পারে।
+
+pip-এর মাধ্যমে স্লিদার:
+
+```bash
+pip3 install --user slither-analyzer
+```
+
+ডকারের মাধ্যমে স্লিদার:
+
+```bash
+docker pull trailofbits/eth-security-toolbox
+docker run -it -v "$PWD":/home/trufflecon trailofbits/eth-security-toolbox
+```
+
+_শেষ কমান্ডটি একটি docker-এ eth-security-toolbox চালায় যেটির আপনার বর্তমান ডিরেক্টরিতে অ্যাক্সেস আছে। আপনি আপনার হোস্ট থেকে ফাইলগুলো পরিবর্তন করতে পারেন, এবং docker থেকে ফাইলগুলোতে টুলস চালাতে পারেন_
+
+docker-এর ভিতরে, চালান:
+
+```bash
+solc-select 0.5.11
+cd /home/trufflecon/
+```
+
+### একটি স্ক্রিপ্ট চালানো {#running-a-script}
+
+python 3 দিয়ে একটি python স্ক্রিপ্ট চালাতে:
+
+```bash
+python3 script.py
+```
+
+### কমান্ড লাইন {#command-line}
+
+**কমান্ড লাইন বনাম ব্যবহারকারী-সংজ্ঞায়িত স্ক্রিপ্ট।** স্লিদার পূর্ব-নির্ধারিত ডিটেক্টরের একটি সেট নিয়ে আসে যা অনেক সাধারণ বাগ খুঁজে পায়। কমান্ড লাইন থেকে স্লিদার কল করলে সমস্ত ডিটেক্টর চলবে, স্ট্যাটিক অ্যানালাইসিস সম্পর্কে বিস্তারিত জ্ঞানের প্রয়োজন নেই:
+
+```bash
+slither project_paths
+```
+
+ডিটেক্টর ছাড়াও, স্লিদারের [প্রিন্টার](https://github.com/crytic/slither#printers) এবং [টুলস](https://github.com/crytic/slither#tools)-এর মাধ্যমে কোড পর্যালোচনার ক্ষমতা রয়েছে।
+
+প্রাইভেট ডিটেক্টর এবং GitHub ইন্টিগ্রেশনে অ্যাক্সেস পেতে [crytic.io](https://github.com/crytic) ব্যবহার করুন।
+
+## স্ট্যাটিক বিশ্লেষণ {#static-analysis}
+
+স্লিদার স্ট্যাটিক অ্যানালাইসিস ফ্রেমওয়ার্কের ক্ষমতা এবং ডিজাইন ব্লগ পোস্টে ([1](https://blog.trailofbits.com/2018/10/19/slither-a-solidity-static-analysis-framework/), [2](https://blog.trailofbits.com/2019/05/27/slither-the-leading-static-analyzer-for-smart-contracts/)) এবং একটি [একাডেমিক পেপারে](https://github.com/trailofbits/publications/blob/master/papers/wetseb19.pdf) বর্ণনা করা হয়েছে।
+
+স্ট্যাটিক অ্যানালাইসিস বিভিন্ন ধরনের হয়ে থাকে। আপনি সম্ভবত বুঝতে পারছেন যে [clang](https://clang-analyzer.llvm.org/) এবং [gcc](https://lwn.net/Articles/806099/)-এর মতো কম্পাইলারগুলি এই গবেষণা কৌশলগুলির উপর নির্ভর করে, কিন্তু এটি ([Infer](https://fbinfer.com/), [CodeClimate](https://codeclimate.com/), [FindBugs](http://findbugs.sourceforge.net/) এবং ফর্মাল পদ্ধতির উপর ভিত্তি করে [Frama-C](https://frama-c.com/) এবং [Polyspace](https://www.mathworks.com/products/polyspace.html) -এর মতো টুলসগুলিকেও ভিত্তি করে।
+
+আমরা এখানে স্ট্যাটিক অ্যানালাইসিস কৌশল এবং গবেষকদের পুঙ্খানুপুঙ্খভাবে পর্যালোচনা করব না। পরিবর্তে, আমরা স্লিদার কীভাবে কাজ করে তা বোঝার জন্য যা প্রয়োজন তার উপর ফোকাস করব যাতে আপনি বাগ খুঁজে পেতে এবং কোড বুঝতে এটি আরও কার্যকরভাবে ব্যবহার করতে পারেন।
+
+- [কোড রিপ্রেজেন্টেশন](#code-representation)
+- [কোড অ্যানালাইসিস](#analysis)
+- [ইন্টারমিডিয়েট রিপ্রেজেন্টেশন](#intermediate-representation)
+
+### কোড রিপ্রেজেন্টেশন {#code-representation}
+
+ডাইনামিক অ্যানালাইসিসের বিপরীতে, যা একটি একক এক্সিকিউশন পথ সম্পর্কে যুক্তি দেয়, স্ট্যাটিক অ্যানালাইসিস একবারে সমস্ত পথ সম্পর্কে যুক্তি দেয়। এটি করার জন্য, এটি একটি ভিন্ন কোড রিপ্রেজেন্টেশনের উপর নির্ভর করে। দুটি সবচেয়ে সাধারণ হলো অ্যাবস্ট্র্যাক্ট সিনট্যাক্স ট্রি (AST) এবং কন্ট্রোল ফ্লো গ্রাফ (CFG)।
+
+### অ্যাবস্ট্র্যাক্ট সিনট্যাক্স ট্রি (AST) {#abstract-syntax-trees-ast}
+
+কম্পাইলার যখনই কোড পার্স করে তখনই AST ব্যবহার করা হয়। এটি সম্ভবত সবচেয়ে মৌলিক কাঠামো যার উপর স্ট্যাটিক অ্যানালাইসিস করা যেতে পারে।
+
+সংক্ষেপে, একটি AST হলো একটি স্ট্রাকচার্ড ট্রি যেখানে, সাধারণত, প্রতিটি লিফ একটি ভেরিয়েবল বা একটি কনস্ট্যান্ট ধারণ করে এবং ইন্টারনাল নোডগুলি হলো অপারেন্ড বা কন্ট্রোল ফ্লো অপারেশন। নিম্নলিখিত কোডটি বিবেচনা করুন:
+
+```solidity
+function safeAdd(uint a, uint b) pure internal returns(uint){
+ if(a + b <= a){
+ revert();
+ }
+ return a + b;
+}
+```
+
+সংশ্লিষ্ট AST দেখানো হলো:
+
+
+
+স্লিদার solc দ্বারা এক্সপোর্ট করা AST ব্যবহার করে।
+
+তৈরি করা সহজ হলেও, AST একটি নেস্টেড কাঠামো। কখনও কখনও, এটি বিশ্লেষণ করার জন্য সবচেয়ে সহজবোধ্য নয়। উদাহরণস্বরূপ, `a + b <= a` এক্সপ্রেশন দ্বারা ব্যবহৃত অপারেশনগুলি সনাক্ত করতে, আপনাকে প্রথমে `<=` এবং তারপর `+` বিশ্লেষণ করতে হবে। একটি সাধারণ পদ্ধতি হলো তথাকথিত ভিজিটর প্যাটার্ন ব্যবহার করা, যা রিকার্সিভলি ট্রি-এর মাধ্যমে নেভিগেট করে। স্লিদার-এ [`ExpressionVisitor`](https://github.com/crytic/slither/blob/master/slither/visitors/expression/expression.py) -তে একটি জেনেরিক ভিজিটর রয়েছে।
+
+নিম্নলিখিত কোডটি এক্সপ্রেশনে একটি অ্যাডিশন আছে কিনা তা সনাক্ত করতে `ExpressionVisitor` ব্যবহার করে:
+
+```python
+from slither.visitors.expression.expression import ExpressionVisitor
+from slither.core.expressions.binary_operation import BinaryOperationType
+
+class HasAddition(ExpressionVisitor):
+
+ def result(self):
+ return self._result
+
+ def _post_binary_operation(self, expression):
+ if expression.type == BinaryOperationType.ADDITION:
+ self._result = True
+
+visitor = HasAddition(expression) # expression হলো সেই এক্সপ্রেশন যা পরীক্ষা করা হবে
+print(f'এক্সপ্রেশন {expression}-এ একটি অ্যাডিশন আছে: {visitor.result()}')
+```
+
+### কন্ট্রোল ফ্লো গ্রাফ (CFG) {#control-flow-graph-cfg}
+
+দ্বিতীয় সবচেয়ে সাধারণ কোড রিপ্রেজেন্টেশন হলো কন্ট্রোল ফ্লো গ্রাফ (CFG)। এর নাম অনুসারে, এটি একটি গ্রাফ-ভিত্তিক রিপ্রেজেন্টেশন যা সমস্ত এক্সিকিউশন পথ প্রকাশ করে। প্রতিটি নোডে এক বা একাধিক ইন্সট্রাকশন থাকে। গ্রাফের এজগুলি কন্ট্রোল ফ্লো অপারেশন (if/then/else, loop, ইত্যাদি) উপস্থাপন করে। আমাদের আগের উদাহরণের CFG হলো:
+
+
+
+CFG হলো সেই রিপ্রেজেন্টেশন যার উপর ভিত্তি করে বেশিরভাগ অ্যানালাইসিস তৈরি করা হয়।
+
+আরও অনেক কোড রিপ্রেজেন্টেশন বিদ্যমান। আপনি যে অ্যানালাইসিস করতে চান সেই অনুযায়ী প্রতিটি রিপ্রেজেন্টেশনের সুবিধা এবং অসুবিধা রয়েছে।
+
+### অ্যানালাইসিস {#analysis}
+
+স্লিদার দিয়ে আপনি যে সবচেয়ে সহজ ধরনের অ্যানালাইসিস করতে পারেন তা হলো সিনট্যাকটিক অ্যানালাইসিস।
+
+### সিনট্যাক্স অ্যানালাইসিস {#syntax-analysis}
+
+স্লিদার কোডের বিভিন্ন উপাদান এবং তাদের রিপ্রেজেন্টেশনের মাধ্যমে নেভিগেট করে প্যাটার্ন ম্যাচিং-এর মতো একটি পদ্ধতি ব্যবহার করে অসামঞ্জস্যতা এবং ত্রুটি খুঁজে বের করতে পারে।
+
+উদাহরণস্বরূপ, নিম্নলিখিত ডিটেক্টরগুলি সিনট্যাক্স-সম্পর্কিত সমস্যাগুলি খুঁজে বের করে:
+
+- [স্টেট ভেরিয়েবল শ্যাডোইং](https://github.com/crytic/slither/wiki/Detector-Documentation#state-variable-shadowing): সমস্ত স্টেট ভেরিয়েবলের উপর ইটারেট করে এবং ইনহেরিট করা কন্ট্র্যাক্টের কোনো ভেরিয়েবলকে শ্যাডো করছে কিনা তা পরীক্ষা করে ([state.py#L51-L62](https://github.com/crytic/slither/blob/0441338e055ab7151b30ca69258561a5a793f8ba/slither/detectors/shadowing/state.py#L51-L62))
+
+- [ভুল ERC20 ইন্টারফেস](https://github.com/crytic/slither/wiki/Detector-Documentation#incorrect-erc20-interface): ভুল ERC20 ফাংশন সিগনেচার খুঁজে বের করে ([incorrect_erc20_interface.py#L34-L55](https://github.com/crytic/slither/blob/0441338e055ab7151b30ca69258561a5a793f8ba/slither/detectors/erc/incorrect_erc20_interface.py#L34-L55))
+
+### সেমান্টিক অ্যানালাইসিস {#semantic-analysis}
+
+সিনট্যাক্স অ্যানালাইসিসের বিপরীতে, একটি সেমান্টিক অ্যানালাইসিস আরও গভীরে গিয়ে কোডের “অর্থ” বিশ্লেষণ করে। এই পরিবারে কিছু বিস্তৃত ধরনের অ্যানালাইসিস অন্তর্ভুক্ত রয়েছে। এগুলো আরও শক্তিশালী এবং দরকারী ফলাফলের দিকে নিয়ে যায়, কিন্তু এগুলো লেখা আরও জটিল।
+
+সবচেয়ে উন্নত দুর্বলতা সনাক্তকরণের জন্য সেমান্টিক অ্যানালাইসিস ব্যবহার করা হয়।
+
+#### ডেটা ডিপেন্ডেন্সি অ্যানালাইসিস {#fixed-point-computation}
+
+একটি ভেরিয়েবল `variable_a`-কে `variable_b`-এর উপর ডেটা-ডিপেন্ডেন্ট বলা হয় যদি এমন একটি পথ থাকে যার জন্য `variable_a`-এর মান `variable_b` দ্বারা প্রভাবিত হয়।
+
+নিম্নলিখিত কোডে, `variable_a` `variable_b`-এর উপর নির্ভরশীল:
+
+```solidity
+// ...
+variable_a = variable_b + 1;
+```
+
+স্লিদার-এর বিল্ট-ইন [ডেটা ডিপেন্ডেন্সি](https://github.com/crytic/slither/wiki/data-dependency) ক্ষমতা রয়েছে, এর ইন্টারমিডিয়েট রিপ্রেজেন্টেশনের জন্য ধন্যবাদ (যা পরবর্তী বিভাগে আলোচনা করা হয়েছে)।
+
+ডেটা ডিপেন্ডেন্সি ব্যবহারের একটি উদাহরণ [বিপজ্জনক স্ট্রিক্ট ইকুয়ালিটি ডিটেক্টর](https://github.com/crytic/slither/wiki/Detector-Documentation#dangerous-strict-equalities)-এ পাওয়া যাবে। এখানে স্লিদার একটি বিপজ্জনক মানের সাথে স্ট্রিক্ট ইকুয়ালিটি তুলনা খুঁজবে ([incorrect_strict_equality.py#L86-L87](https://github.com/crytic/slither/blob/6d86220a53603476f9567c3358524ea4db07fb25/slither/detectors/statements/incorrect_strict_equality.py#L86-L87)), এবং ব্যবহারকারীকে জানাবে যে `==`-এর পরিবর্তে `>=` বা `<=` ব্যবহার করা উচিত, যাতে একজন আক্রমণকারী কন্ট্র্যাক্টকে ফাঁদে ফেলতে না পারে। অন্যান্য বিষয়গুলির মধ্যে, ডিটেক্টর `balanceOf(address)`-এ একটি কলের রিটার্ন মানকে বিপজ্জনক হিসাবে বিবেচনা করবে ([incorrect_strict_equality.py#L63-L64](https://github.com/crytic/slither/blob/6d86220a53603476f9567c3358524ea4db07fb25/slither/detectors/statements/incorrect_strict_equality.py#L63-L64)), এবং এর ব্যবহার ট্র্যাক করতে ডেটা ডিপেন্ডেন্সি ইঞ্জিন ব্যবহার করবে।
+
+#### ফিক্সড-পয়েন্ট কম্পিউটেশন {#fixed-point-computation}
+
+যদি আপনার অ্যানালাইসিস CFG-এর মাধ্যমে নেভিগেট করে এবং এজগুলি অনুসরণ করে, তাহলে আপনি সম্ভবত ইতিমধ্যে ভিজিট করা নোডগুলি দেখতে পাবেন। উদাহরণস্বরূপ, যদি একটি লুপ নীচে দেখানো হিসাবে উপস্থাপন করা হয়:
+
+```solidity
+for(uint i; i < range; ++){
+ variable_a += 1
+}
+```
+
+আপনার অ্যানালাইসিসকে জানতে হবে কখন থামতে হবে। এখানে দুটি প্রধান কৌশল রয়েছে: (1) প্রতিটি নোডে একটি সসীম সংখ্যক বার ইটারেট করা, (2) একটি তথাকথিত _ফিক্সপয়েন্ট_ গণনা করা। একটি ফিক্সপয়েন্ট মূলত বোঝায় যে এই নোডটি বিশ্লেষণ করা কোনো অর্থপূর্ণ তথ্য প্রদান করে না।
+
+ফিক্সপয়েন্ট ব্যবহারের একটি উদাহরণ রিএন্ট্রেন্সি ডিটেক্টরে পাওয়া যায়: স্লিদার নোডগুলি এক্সপ্লোর করে, এবং এক্সটার্নাল কল, সংগ্রহস্থলে লেখা এবং পড়া খুঁজে বের করে। একবার এটি একটি ফিক্সপয়েন্টে পৌঁছালে ([reentrancy.py#L125-L131](https://github.com/crytic/slither/blob/master/slither/detectors/reentrancy/reentrancy.py#L125-L131)), এটি এক্সপ্লোরেশন বন্ধ করে দেয়, এবং বিভিন্ন রিএন্ট্রেন্সি প্যাটার্নের মাধ্যমে ([reentrancy_benign.py](https://github.com/crytic/slither/blob/b275bcc824b1b932310cf03b6bfb1a1fef0ebae1/slither/detectors/reentrancy/reentrancy_benign.py), [reentrancy_read_before_write.py](https://github.com/crytic/slither/blob/b275bcc824b1b932310cf03b6bfb1a1fef0ebae1/slither/detectors/reentrancy/reentrancy_read_before_write.py), [reentrancy_eth.py](https://github.com/crytic/slither/blob/b275bcc824b1b932310cf03b6bfb1a1fef0ebae1/slither/detectors/reentrancy/reentrancy_eth.py)) একটি রিএন্ট্রেন্সি আছে কিনা তা দেখতে ফলাফল বিশ্লেষণ করে।
+
+কার্যকর ফিক্সড পয়েন্ট কম্পিউটেশন ব্যবহার করে অ্যানালাইসিস লেখার জন্য অ্যানালাইসিসটি কীভাবে তার তথ্য প্রচার করে সে সম্পর্কে একটি ভাল বোঝার প্রয়োজন।
+
+### ইন্টারমিডিয়েট রিপ্রেজেন্টেশন {#intermediate-representation}
+
+একটি ইন্টারমিডিয়েট রিপ্রেজেন্টেশন (IR) হলো এমন একটি ভাষা যা মূল ভাষার চেয়ে স্ট্যাটিক অ্যানালাইসিসের জন্য বেশি উপযোগী। স্লিদার Solidity-কে তার নিজস্ব IR: [SlithIR](https://github.com/crytic/slither/wiki/SlithIR)-এ অনুবাদ করে।
+
+আপনি যদি শুধুমাত্র বেসিক চেক লিখতে চান তবে SlithIR বোঝা প্রয়োজন নয়। তবে, আপনি যদি উন্নত সেমান্টিক অ্যানালাইসিস লেখার পরিকল্পনা করেন তবে এটি কাজে আসবে। [SlithIR](https://github.com/crytic/slither/wiki/Printer-documentation#slithir) এবং [SSA](https://github.com/crytic/slither/wiki/Printer-documentation#slithir-ssa) প্রিন্টারগুলি আপনাকে কোডটি কীভাবে অনুবাদ করা হয় তা বুঝতে সাহায্য করবে।
+
+## API বেসিকস {#api-basics}
+
+স্লিদারের একটি API আছে যা আপনাকে কন্ট্র্যাক্ট এবং তার ফাংশনগুলির মৌলিক বৈশিষ্ট্যগুলি এক্সপ্লোর করতে দেয়।
+
+একটি কোডবেস লোড করতে:
+
+```python
+from slither import Slither
+slither = Slither('/path/to/project')
+
+```
+
+### কন্ট্র্যাক্ট এবং ফাংশন এক্সপ্লোর করা {#exploring-contracts-and-functions}
+
+একটি `Slither` অবজেক্টের আছে:
+
+- `contracts (list(Contract)`: কন্ট্র্যাক্টের তালিকা
+- `contracts_derived (list(Contract)`: এমন কন্ট্র্যাক্টের তালিকা যা অন্য কোনো কন্ট্র্যাক্ট দ্বারা ইনহেরিট করা হয়নি (কন্ট্র্যাক্টের উপসেট)
+- `get_contract_from_name (str)`: তার নাম থেকে একটি কন্ট্র্যাক্ট রিটার্ন করুন
+
+একটি `Contract` অবজেক্টের আছে:
+
+- `name (str)`: কন্ট্র্যাক্টের নাম
+- `functions (list(Function))`: ফাংশনের তালিকা
+- `modifiers (list(Modifier))`: মডিফায়ারের তালিকা
+- `all_functions_called (list(Function/Modifier))`: কন্ট্র্যাক্ট দ্বারা পৌঁছানো যায় এমন সমস্ত ইন্টারনাল ফাংশনের তালিকা
+- `inheritance (list(Contract))`: ইনহেরিটেড কন্ট্র্যাক্টের তালিকা
+- `get_function_from_signature (str)`: তার সিগনেচার থেকে একটি ফাংশন রিটার্ন করুন
+- `get_modifier_from_signature (str)`: তার সিগনেচার থেকে একটি মডিফায়ার রিটার্ন করুন
+- `get_state_variable_from_name (str)`: তার নাম থেকে একটি StateVariable রিটার্ন করুন
+
+একটি `Function` বা একটি `Modifier` অবজেক্টের আছে:
+
+- `name (str)`: ফাংশনের নাম
+- `contract (contract)`: যে কন্ট্র্যাক্টে ফাংশনটি ডিক্লেয়ার করা হয়েছে
+- `nodes (list(Node))`: ফাংশন/মডিফায়ারের CFG গঠনকারী নোডগুলির তালিকা
+- `entry_point (Node)`: CFG-এর এন্ট্রি পয়েন্ট
+- `variables_read (list(Variable))`: পড়া ভেরিয়েবলের তালিকা
+- `variables_written (list(Variable))`: লেখা ভেরিয়েবলের তালিকা
+- `state_variables_read (list(StateVariable))`: পড়া স্টেট ভেরিয়েবলের তালিকা (variables`read-এর উপসেট)
+- `state_variables_written (list(StateVariable))`: লেখা স্টেট ভেরিয়েবলের তালিকা (variables`written-এর উপসেট)