<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>Forem: Arsy Opraza Akma</title>
    <description>The latest articles on Forem by Arsy Opraza Akma (@arasopraza).</description>
    <link>https://forem.com/arasopraza</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F1111033%2Faef9f491-a664-4419-9ff3-ae39cb717a18.jpg</url>
      <title>Forem: Arsy Opraza Akma</title>
      <link>https://forem.com/arasopraza</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://forem.com/feed/arasopraza"/>
    <language>en</language>
    <item>
      <title>How to Use RAG with Amazon Bedrock + Nova for Building Chatbots</title>
      <dc:creator>Arsy Opraza Akma</dc:creator>
      <pubDate>Thu, 25 Sep 2025 06:43:59 +0000</pubDate>
      <link>https://forem.com/aws-builders/how-to-use-rag-with-amazon-bedrock-nova-for-building-chatbots-3ddn</link>
      <guid>https://forem.com/aws-builders/how-to-use-rag-with-amazon-bedrock-nova-for-building-chatbots-3ddn</guid>
      <description>&lt;p&gt;Recently, I have been exploring Retrieval-Augmented Generation (RAG) and building a chatbot for fun. The reason became I interested in RAG because i use AI every day, especially Generative AI, such as large language models (LLM). LLM so helpful and often provide impressive responses.&lt;/p&gt;

&lt;p&gt;However, LLM-generated response have a challenge. These response need to include with factual information. When you use an LLM to generate a response, it relies only on the data on which it was trained.&lt;/p&gt;

&lt;p&gt;For example, when you ask, "What food should I eat when I do X?", the result will likely be a impressive, grammatically correct and logical response, but because it isn't based on factual or contextual data, it maybe inaccurate.&lt;/p&gt;

&lt;p&gt;In contrast, you can use a data or knowledge with some relevant, factual context and information to generate a contextualized, relevant, and accurate response.&lt;/p&gt;

&lt;p&gt;The data or knowledge can be any document of relevant data to provide relevant information. For example, you could use data from a daily food you eat to help answer the prompt "What food should i eat when do X?" so that the response includes relevant response.&lt;/p&gt;

&lt;p&gt;To ensure that an LLM provides accurate and domain-specific responses, you can use Retrieval-Augmented Generation (RAG).&lt;/p&gt;

&lt;p&gt;RAG is a process of optimizing the output of a large language model using retrieving information technique that is relevant to the user's prompt.&lt;/p&gt;

&lt;p&gt;RAG have three steps:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Retrieve data based on the user prompt.&lt;/li&gt;
&lt;li&gt;Augment the prompt with knowledge data.&lt;/li&gt;
&lt;li&gt;Use a language model to generate a response.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;By retrieving context from specified data, you ensure that the LLM uses relevant information when responding, rather than relying solely on its training data&lt;/p&gt;

&lt;p&gt;A standard RAG app usually has two main parts:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Indexing: a process that takes data from a source, organizes it, and stores it in an index.&lt;/li&gt;
&lt;li&gt;Retrieval and generation: the RAG workflow itself, where a user’s query is received, the system looks up the most relevant information from the index, and then sends that context to the model to generate a response.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In my explorations, I will build a simple chatbot that can generate answers based on a provided document using the following tools:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Langchain&lt;/li&gt;
&lt;li&gt;Bedrock Embedding&lt;/li&gt;
&lt;li&gt;Amazon titan embedding model&lt;/li&gt;
&lt;li&gt;Amazon nova for chat model&lt;/li&gt;
&lt;li&gt;Chroma as Vector DB&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fokvyq6107xuas2p6t9gb.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fokvyq6107xuas2p6t9gb.png" alt=" " width="800" height="450"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;So, we will start by indexing. Let's go!&lt;/p&gt;

&lt;h2&gt;
  
  
  Setup
&lt;/h2&gt;

&lt;p&gt;First, we will setup tools that will we use. Install this packages:&lt;br&gt;
pip install -qU "langchain[aws]" langchain-aws langchain-chroma PyMuPDF langchain-text-splitters langchain-community langgraph&lt;/p&gt;
&lt;h2&gt;
  
  
  Indexing
&lt;/h2&gt;

&lt;p&gt;After we setup the project, next we will indexing. Indexing data have this part:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Load: Start by loading data.&lt;/li&gt;
&lt;li&gt;Split: Break big documents into smaller pieces.&lt;/li&gt;
&lt;li&gt;Store: Save those in a storage system that supports indexing and searching. This is often done with a Vector Store combined with an embeddings model.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Write following code.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;embeddings = BedrockEmbeddings(model_id="amazon.titan-embed-text-v2:0")
vector_store = Chroma(
    collection_name=COLLECTION,
    embedding_function=embeddings,
    persist_directory=DB_DIR,
)
splitter = RecursiveCharacterTextSplitter(chunk_size=1000, chunk_overlap=100)

def index_documents():
    print("📂 Loading and indexing documents...")
    loader = PyMuPDFLoader(PDF_PATH, mode="page")
    docs = loader.load()
    chunks = splitter.split_documents(docs)

    vector_store.add_documents(chunks)
    vector_store.persist()
    print(f"✅ Indexed {len(chunks)} chunks into {DB_DIR}")
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;First, we set up embeddings using Amazon’s Titan model. Embeddings as a way to turn text into numbers so the computer can understand and compare meaning. &lt;/p&gt;

&lt;p&gt;Then, we create a vector database with Chroma that can store and search those embeddings. We also set up a text splitter so large documents can be cut into smaller, manageable chunks of around 1,000 characters each, with a bit of overlap to keep context intact.&lt;/p&gt;

&lt;p&gt;The function &lt;code&gt;index_documents()&lt;/code&gt;, creates a loader that reads a PDF file (located at PDF_PATH). The mode="page" means it treats each page of the PDF as a separate unit.&lt;/p&gt;

&lt;p&gt;Then, split the documents into smaller part (chunking) and saves those chunks into the vector database. &lt;/p&gt;

&lt;p&gt;At the end, you’ll have your document neatly indexed, so later when a user asks a question, the system can quickly find the right pieces of text to feed into AI model.&lt;/p&gt;

&lt;h2&gt;
  
  
  Retrieval and Generation
&lt;/h2&gt;

&lt;p&gt;Now, it’s time to build the core application. The goal is to make a simple app that takes a user’s question, finds the most relevant documents, sends both the question and those documents to a model, and then gives back an answer.&lt;/p&gt;

&lt;p&gt;For generation, we will use the chat model with Amazon Nova. Write following code.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;llm = init_chat_model("us.amazon.nova-lite-v1:0", model_provider="bedrock_converse")
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then, write RAG pipeline. We will write state for application. Write this code.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from langchain_core.documents import Document
from typing_extensions import List, TypedDict

class State(TypedDict):
    question: str
    context: List[Document]
    answer: str
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We will keep track of the question, the context (docs we retrieve), and the answer.&lt;/p&gt;

&lt;p&gt;Next, write this function.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;def retrieve(state: State):
    retrieved_docs = vector_store.similarity_search(state["question"], k=4)
    return {"context": retrieved_docs}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When a user asks a question, this part looks inside the vector database and pulls out the top 4 most relevant documents. Those docs will become the context for the model to use.&lt;/p&gt;

&lt;p&gt;After that, write system prompt and create generate function.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;SYSTEM_PROMPT = "Your system prompt"

def generate(state: State):
    if not state["context"]:
        return {"answer": "Sorry, i can't answers."}

    docs_content = "\n\n".join(doc.page_content for doc in state["context"])
    user_payload = f"""Context: {docs_content} Question: {state['question']} Answer:"""
    messages = [
        SystemMessage(content=SYSTEM_PROMPT),
        HumanMessage(content=user_payload)
    ]
    response = llm.invoke(messages)
    return {"answer": response.content}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Lastly, we compile our application into a single graph object. In this case, we are just connecting the retrieval and generation steps into a single sequence.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;graph_builder = StateGraph(State)
graph_builder.add_sequence([retrieve, generate])
graph_builder.add_edge(START, "retrieve")
graph = graph_builder.compile()
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is the complete code.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import argparse
import os
import textwrap
import langchain
from typing_extensions import List, TypedDict

from langchain_aws import BedrockEmbeddings
from langchain_text_splitters import RecursiveCharacterTextSplitter
from langchain_core.documents import Document
from langchain_community.document_loaders import PyMuPDFLoader
from langchain_chroma import Chroma
from langchain.chat_models import init_chat_model
from langchain.schema import SystemMessage, HumanMessage
from langgraph.graph import START, StateGraph


# ===================================================================
# Global Config
# ===================================================================
langchain.verbose = False
langchain.debug = False
langchain.llm_cache = None

DB_DIR = "./chroma_langchain_db"
COLLECTION = "example_collection"
PDF_PATH = "docs/ilovepdf_merged.pdf"

embeddings = BedrockEmbeddings(model_id="amazon.titan-embed-text-v2:0")
vector_store = Chroma(
    collection_name=COLLECTION,
    embedding_function=embeddings,
    persist_directory=DB_DIR,
)

llm = init_chat_model("us.amazon.nova-lite-v1:0", model_provider="bedrock_converse")

splitter = RecursiveCharacterTextSplitter(chunk_size=1000, chunk_overlap=100)


# ===================================================================
# Indexing Function
# ===================================================================
def index_documents():
    print("📂 Loading and indexing documents...")
    loader = PyMuPDFLoader(PDF_PATH, mode="page")
    docs = loader.load()
    chunks = splitter.split_documents(docs)

    vector_store.add_documents(chunks)
    vector_store.persist()
    print(f"✅ Indexed {len(chunks)} chunks into {DB_DIR}")


# ===================================================================
# RAG Pipeline
# ===================================================================
class State(TypedDict):
    question: str
    context: List[Document]
    answer: str


def retrieve(state: State):
    retrieved_docs = vector_store.similarity_search(state["question"], k=4)
    return {"context": retrieved_docs}


SYSTEM_PROMPT = "Your system prompts".
def generate(state: State):
    if not state["context"]:
        return {"answer": "Sorry, i can't answers."}

    docs_content = "\n\n".join(doc.page_content for doc in state["context"])
    user_payload = f"""Context: {docs_content} Question: {state['question']} Answer:"""
    messages = [
        SystemMessage(content=SYSTEM_PROMPT),
        HumanMessage(content=user_payload)
    ]
    response = llm.invoke(messages)
    return {"answer": response.content}

graph_builder = StateGraph(State)
graph_builder.add_sequence([retrieve, generate])
graph_builder.add_edge(START, "retrieve")
graph = graph_builder.compile()

def query_pipeline(question: str):
    response = graph.invoke({"question": question})
    print(f"Question: {question}\nAnswer: {response['answer']}")


# ===================================================================
# CLI Entrypoint
# ===================================================================
if __name__ == "__main__":
    parser = argparse.ArgumentParser()
    parser.add_argument("--index", action="store_true", help="Index documents into vector DB")
    parser.add_argument("--query", type=str, help="Run a query against the DB")
    args = parser.parse_args()

    if args.index:
        index_documents()
    elif args.query:
        query_pipeline(args.query)
    else:
        parser.print_help()
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You can test give a prompt and ask a questions that relate with information on the documents.&lt;/p&gt;

&lt;p&gt;If you encounter error, make sure you have a access to the Amazon Bedrock and the Amazon Titan and Nova models. &lt;/p&gt;

&lt;p&gt;Thanks for reading.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Want to connect?
Arsy Opraza, Curriculum Developer at Dicoding.
https://www.linkedin.com/in/arasopraza/
https://github.com/arasopraza
https://twitter.com/arsyopraza
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



</description>
      <category>rag</category>
      <category>ai</category>
      <category>chatbot</category>
    </item>
    <item>
      <title>Beginner-Friendly: Cara Bangun Serverless Function dengan AWS Lambda</title>
      <dc:creator>Arsy Opraza Akma</dc:creator>
      <pubDate>Wed, 11 Jun 2025 17:40:45 +0000</pubDate>
      <link>https://forem.com/aws-builders/beginner-friendly-cara-bangun-serverless-function-dengan-aws-lambda-28ma</link>
      <guid>https://forem.com/aws-builders/beginner-friendly-cara-bangun-serverless-function-dengan-aws-lambda-28ma</guid>
      <description>&lt;p&gt;Dulu ketika sering datang ke event dan conference IT, banyak yang bahas mengenai AWS Lambda. Katanya sih modern app udah pake AWS Lambda.&lt;/p&gt;

&lt;p&gt;Ketika lihat demonya, wah keren juga ya, kok bisa gitu. Sayangnya, cuma sebatas itu dan ga mencari tahu lebih detail dan nyobain AWS Lambda.&lt;/p&gt;

&lt;p&gt;Nah, apa sih AWS Lambda itu. Yuk kita bahas!&lt;/p&gt;

&lt;h2&gt;
  
  
  AWS Lambda: Solusi Praktis untuk Backend Modern
&lt;/h2&gt;

&lt;p&gt;AWS Lambda adalah layanan dari AWS yang memungkinkan untuk run code tanpa manage server. Yap, sering kali orang bilangnya serverless. &lt;/p&gt;

&lt;p&gt;Lambda dapat running code pada infrastruktur komputasi dengan ketersediaan tinggi dan mengelola semua sumber daya komputasi, termasuk pemeliharaan server dan sistem operasi, penyediaan kapasitas, penskalaan otomatis, dan pencatatan.&lt;/p&gt;

&lt;p&gt;Code tersebut diatur ke dalam sebuah Lambda functions. AWS Lambda hanya ngerunning function jika diperlukan saja. Untuk detail pricing-nya, dapat dilihat di bawah ini.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fxc8ywo5h175hcd7flrdu.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fxc8ywo5h175hcd7flrdu.png" alt="AWS Lambda Pricing" width="800" height="450"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Detailnya, dapat dibaca di halaman Lambda Pricing.&lt;/p&gt;

&lt;h2&gt;
  
  
  Kapan saatnya menggunakan Lambda?
&lt;/h2&gt;

&lt;p&gt;Gunakan Lambda ketika menangani kasus berikut.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Stream processing: AWS Lambda dapat digunakan untuk real-time streaming data bersamaan dengan Amazon Kinesis. Data yang distream terdiri dari activity tracking, log filtering, dan transaction order processing.&lt;/li&gt;
&lt;li&gt;File processing: Gunakan Amazon Simple Storage Service (Amazon S3) untuk  trigger Lambda untuk data processing secara real time setelah upload data ke Amazon S3.&lt;/li&gt;
&lt;li&gt;Web applications: Lambda dapat digabungkan dengan services AWS lainnya untuk membangun web app yang powerful. Developer bisa menggunakan infrastructure as code (IaC) seperti AWS CloudFormation, AWS Cloud Development Kit (AWS CDK), AWS Serverless Application Model, dan AWS Step Functions.&lt;/li&gt;
&lt;li&gt;Mobile backends: Lambda dan Amazon API Gateway dapat digunakan untuk autentikasi dan proses API Request. Gunakan juga AWS Amplify untuk terintegrasi dengan iOS, Android, Web, dan React Native.&lt;/li&gt;
&lt;li&gt;IoT backends: Bangun serverless backends menggunakan  Lambda untuk menangani web, mobile, IoT, dan third-party API.&lt;/li&gt;
&lt;li&gt;Database Operations dan Integration: Gunakan  Lambda untuk proses interaksi dengan database seperti Amazon RDS.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Oke, itu kasus yang pas untuk menggunakan Lambda. Lalu, apa saja fitur yang ada di Lambda?&lt;/p&gt;

&lt;h2&gt;
  
  
  Fitur utama Lambda
&lt;/h2&gt;

&lt;p&gt;Berikut adalah beberapa fitur utama dari Lambda.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Environment variables: Dapat menggunakan environment variables tanpa mengubah code.&lt;/li&gt;
&lt;li&gt;Versions: Versioning dapat digunakan untuk mengelola versi deployments dariLambda functions.&lt;/li&gt;
&lt;li&gt;VPC networks: Lambda menjadi lebih aman dengan adanya VPC networks.&lt;/li&gt;
&lt;li&gt;File system: Function dapat dikonfigurasi untuk mount sebuah Amazon Elastic File System (Amazon EFS) file system ke direktori lokal.&lt;/li&gt;
&lt;li&gt;Function URLs: URL function merupakan dedicated HTTP(S) endpoint untuk Lambda function. &lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Itu beberapa fitur utama dari Lambda. Nah, biar lebih seru, setelah mengenal teori dasar dari Lambda. Kini, saatnya untuk nyobain langsung.&lt;/p&gt;

&lt;h2&gt;
  
  
  Hands-on Serverless dengan Lambda
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;Buka halaman Lambda.
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fa5yhibcmqhqjyub3y3lo.png" alt="Dashboard Lambda" width="800" height="421"&gt;
&lt;/li&gt;
&lt;li&gt;Pilih &lt;em&gt;&lt;strong&gt;Create Functions&lt;/strong&gt;&lt;/em&gt;.&lt;/li&gt;
&lt;li&gt;Kemudian, pilih &lt;strong&gt;&lt;em&gt;Author from scratch&lt;/em&gt;&lt;/strong&gt;
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fhlwomddvzuvatjywluzj.png" alt="Halaman Create Function" width="800" height="421"&gt;
&lt;/li&gt;
&lt;li&gt;Pada bagian &lt;em&gt;basic information&lt;/em&gt;, berikan nilai untuk &lt;em&gt;function name&lt;/em&gt;. Misalnya, myFunctionDemo.&lt;/li&gt;
&lt;li&gt;Untuk &lt;em&gt;&lt;strong&gt;Runtime&lt;/strong&gt;&lt;/em&gt;, dapat memilih beberapa bahasa pemrograman tetapi saat ini cukup pilih Node.js 22.&lt;/li&gt;
&lt;li&gt;Selanjutnya, untuk &lt;em&gt;architecture&lt;/em&gt; pilih x86_64.
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fkzr15fjfoqv4rj4khicx.png" alt="Tampilan basic information" width="800" height="250"&gt;
&lt;/li&gt;
&lt;li&gt;Konfigurasi lainnya biarkan saja bernilai default. Klik &lt;em&gt;&lt;strong&gt;Create function&lt;/strong&gt;&lt;/em&gt;.&lt;/li&gt;
&lt;li&gt;Lambda akan membuat sebuah code. Untuk mengubah code tersebut dapat dilakukan dengan cara _ console's built-in code editor_.
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fh7dytyysywrb22ryjpir.png" alt="Console built-in code editor" width="800" height="416"&gt;
&lt;/li&gt;
&lt;li&gt;Misalnya, pengen ngubah teks "Hello from Lambda!" menjadi "Hello from Demo Lambda!". Langsung saja buka berkas index.mjs dan ubah kode yang ada pada bagian kanan.
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F1103tfs6afk2dpaft6eq.png" alt="Halaman code editor" width="800" height="416"&gt;
&lt;/li&gt;
&lt;li&gt;Setelah itu, pada bagian DEPLOY, pilih Deploy.
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fzw5jfhu45enkndkqbr58.png" alt="Tampilan DEPLOY" width="303" height="138"&gt;
&lt;/li&gt;
&lt;li&gt;Untuk menguji memanggil Lambda functions dapat dilakukan melalui console code editor. Buatlah sebuah test event dengan cara di bagian TEST EVENTS, pilih &lt;em&gt;&lt;strong&gt;Create test event&lt;/strong&gt;&lt;/em&gt;.
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fbygqucu0gyfxvaxg5e6p.png" alt="TEST EVENT" width="302" height="64"&gt;
&lt;/li&gt;
&lt;li&gt;Masukin nama "testEvent" dan di Event JSON section, tambahkan sebuah JSON sederhana.
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;{
  "name": "Ini test lambda"
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;Klik &lt;em&gt;save&lt;/em&gt;.
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F6lt7odazcen6eokckpui.png" alt="Tampilan create test event" width="634" height="582"&gt;
&lt;/li&gt;
&lt;li&gt;Kemudian, masih di bagian TEST EVENTS, klik icon run.
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fysyqgo2t9lfkkzwboyz5.png" alt="Test events run" width="454" height="144"&gt;
&lt;/li&gt;
&lt;li&gt;Jika tidak ada error, akan berhasil dengan message yang muncul pada bagian OUTPUT di code editor.
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3ynjqscc3dlbgpouxwv2.png" alt="Tab OUTPUT" width="800" height="416"&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Oke, mudah, kan?&lt;/p&gt;

&lt;p&gt;Nah, setelah deploy Lambda function, kita bisa memanggilnya dengan beberapa cara seperti:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The Lambda console&lt;/li&gt;
&lt;li&gt;The AWS SDK&lt;/li&gt;
&lt;li&gt;The Invoke API&lt;/li&gt;
&lt;li&gt;The AWS Command Line Interface (AWS CLI)&lt;/li&gt;
&lt;li&gt;A function URL HTTP(S) endpoint&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Kita akan coba salah satu cara yaitu function URL. Simak caranya!&lt;/p&gt;

&lt;h2&gt;
  
  
  Invoke Lambda Function via URL HTTP(S)
&lt;/h2&gt;

&lt;p&gt;Untuk membuat function URL dapat dilakukan dengan 4 langkah.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Buka &lt;em&gt;tab Configuration&lt;/em&gt; dan pilih Function URL.
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F9qo06yjqcfqberuf6wja.png" alt="Tab configuration" width="800" height="416"&gt;
&lt;/li&gt;
&lt;li&gt;Kemudian, klik &lt;em&gt;&lt;strong&gt;Create function URL&lt;/strong&gt;&lt;/em&gt;.&lt;/li&gt;
&lt;li&gt;Untuk Auth type, silakan pilih &lt;em&gt;NONE&lt;/em&gt;.&lt;/li&gt;
&lt;li&gt;Terakhir, klik &lt;em&gt;&lt;strong&gt;Save&lt;/strong&gt;&lt;/em&gt;.
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Flafgh2zfabiyd1nofymu.png" alt="Halaman create function URL" width="800" height="416"&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Endpoint untuk function URL akan tampak di bagian Function URL.&lt;br&gt;
&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fyqcdb4cae1lub64wj77r.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fyqcdb4cae1lub64wj77r.png" alt="Endpoint function URL" width="800" height="416"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;h2&gt;
  
  
  Menguji Function URL.
&lt;/h2&gt;

&lt;p&gt;Untuk mengujinya, akses endpoint tersebut di browser/Postman/cURL.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Flpmbwv40qowqh5nn0d4k.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Flpmbwv40qowqh5nn0d4k.png" alt="Tampilan cURL" width="800" height="33"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Yey, Berhasil!&lt;/p&gt;
&lt;h2&gt;
  
  
  Melihat function's invocation records di CloudWatch Logs
&lt;/h2&gt;

&lt;p&gt;Ketika memanggil function di luar dari Lambda console, kita harus menggunakan CloudWatch Logs untuk melihat hasil eksekusi function-nya.&lt;/p&gt;

&lt;p&gt;Caranya akses laman &lt;a href="https://console.aws.amazon.com/cloudwatch/home#logs:" rel="noopener noreferrer"&gt;https://console.aws.amazon.com/cloudwatch/home#logs:&lt;/a&gt; secara otomatis akan terdapat log group yang dihasilkan oleh Lambda. &lt;/p&gt;

&lt;p&gt;Klik nama log group-nya.&lt;br&gt;
&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fy7v0wofaad4mvdbqeakh.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fy7v0wofaad4mvdbqeakh.png" alt="CloudWatchs log group" width="800" height="416"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Pilih &lt;em&gt;&lt;strong&gt;log stream&lt;/strong&gt;&lt;/em&gt; dari salah satu function invocations dan akan tampak seperti berikut.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;2025-06-11T17:06:24.229Z
INIT_START Runtime Version: nodejs:22.v43 Runtime Version ARN: arn:aws:lambda:ap-southeast-2::runtime:fd2e05b324f99edd3c6e17800b2535deb79bcce74b7506d595a94870b3d9bd2e
2025-06-11T17:06:24.377Z
START RequestId: 00529f70-dd62-414b-9aa4-483fc6a67b2a Version: $LATEST
2025-06-11T17:06:24.398Z
END RequestId: 00529f70-dd62-414b-9aa4-483fc6a67b2a
2025-06-11T17:06:24.398Z
REPORT RequestId: 00529f70-dd62-414b-9aa4-483fc6a67b2a Duration: 20.25 ms Billed Duration: 21 ms Memory Size: 128 MB Max Memory Used: 72 MB Init Duration: 144.59 ms
2025-06-11T17:06:24.895Z
START RequestId: 5d824554-3eb4-4f83-9826-36605c566659 Version: $LATEST
2025-06-11T17:06:24.916Z
END RequestId: 5d824554-3eb4-4f83-9826-36605c566659
2025-06-11T17:06:24.917Z
REPORT RequestId: 5d824554-3eb4-4f83-9826-36605c566659 Duration: 20.46 ms Billed Duration: 21 ms Memory Size: 128 MB Max Memory Used: 73 MB
2025-06-11T17:07:37.237Z
START RequestId: 3c86fb4b-a7a5-4fe8-b959-f1b2d91e24ff Version: $LATEST
2025-06-11T17:07:37.256Z
END RequestId: 3c86fb4b-a7a5-4fe8-b959-f1b2d91e24ff
2025-06-11T17:07:37.256Z
REPORT RequestId: 3c86fb4b-a7a5-4fe8-b959-f1b2d91e24ff Duration: 2.17 ms Billed Duration: 3 ms Memory Size: 128 MB Max Memory Used: 73 MB
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Gampang, kan?&lt;/p&gt;

&lt;p&gt;Di blog ini, kita udah melewati proses mulai dari bikin Lambda function, testing via test event, sampe expose via Function URL dan ngetes pake cURL.&lt;/p&gt;

&lt;p&gt;Next step? Integrasi ke use case real. Bisa buat webhook, backend microservice, sampai automation kecil-kecilan.&lt;/p&gt;

</description>
      <category>serverless</category>
      <category>webdev</category>
      <category>programming</category>
      <category>cloud</category>
    </item>
  </channel>
</rss>
