I Scored 1000/1000 on AWS Certified AI Practitioner (AIF-C01) Here’s Every Resource I Used

TL;DR I passed the AWS Certified AI Practitioner (AIF-C01) exam with a perfect score of 1000/1000 using a deliberate four-layer system: video lectures, reading materials, hands-on labs, and practice exams. Everything I used is listed below free and paid.

Why I Decided to Pursue AIF-C01

AI is no longer a specialty skill reserved for data scientists and ML engineers. In 2025 and beyond, it is becoming a baseline expectation for anyone working in cloud, DevOps, architecture, or engineering.

When AWS launched the AI Practitioner certification (AIF-C01) in October 2024, I saw it as the right opportunity to validate what I had been learning and signal to employers that I genuinely understood the AWS AI ecosystem — not just at a surface level, but deeply enough to make real architectural decisions.

Passing AIF-C01 demonstrates that you understand:

  • ✅ Generative AI — concepts, use cases, and limitations
  • ✅ Foundation Models — how they work and how to select them
  • ✅ Amazon Bedrock — the core GenAI service on AWS
  • ✅ Amazon SageMaker — for ML model training and deployment
  • ✅ Prompt Engineering — techniques for effective model interaction
  • ✅ Responsible AI — bias, fairness, explainability, governance
  • ✅ AI Security on AWS — securing AI workloads end to end

The Honest Truth About This Exam

Most people approach this exam in one of two wrong ways:

Over-preparing with the wrong materials — spending weeks on deep ML theory that simply is not tested at this level.

Under-preparing because it sounds “foundational” — treating it like a vocabulary quiz and getting blindsided by scenario-heavy questions.

Neither approach works. What works is a deliberate, four-layer study system aligned to how AWS actually writes its questions.

Here is exactly what that looks like.

My Four-Layer Study System

Layer 1 — 🎥 Video Lectures: Build Your Mental Model First

Before you touch any documentation or practice question, you need a solid mental picture of how AWS AI services connect and why they exist. These courses gave me that foundation.

🆓 FREE

Andrew Brown — freeCodeCamp (15-Hour Full Course)

This is the most comprehensive free resource available for AIF-C01. Andrew covers every exam domain in depth, and publishing it on freeCodeCamp’s YouTube channel means it is always free. I watched this first before touching anything else.

🔗 Watch on YouTube

AWS Skill Builder — Official Exam Prep Learning Plan

Built directly by AWS, this learning plan tells you exactly what AWS expects you to know. If you want to study from the source, this is it. The free tier gives you access to digital courses and exam prep content.

🔗 Access AWS Skill Builder

💰 PAID

Stéphane Maarek — Udemy (Ultimate AIF-C01 Course)

Over 2.5 million students trust Stéphane for AWS certification prep. His AIF-C01 course is hands-on, laser-focused on exam objectives, and includes a built-in practice exam. Worth every penny.

🔗 Udemy Course

Tutorials Dojo — Video Course 2026

Structured by exam domain and kept fully updated as AWS updates the exam blueprint. Excellent for visual learners who want a clean, no-filler walkthrough without the detours.

🔗 Tutorials Dojo Video Course

Layer 2 — 📖 Reading Materials: Lock In the Details

Video gets you approximately 70% of the way there. Reading is what closes the remaining gap. Edge cases, service limits, key definitions, and the subtle differences between AWS AI tools all live in written form.

💰 PAID

Tutorials Dojo — Study Guide eBook

Over 300 pages of structured notes, cheat sheets, and domain-by-domain breakdowns. This became my go-to reference during final revision. The cheat sheets alone are worth the price.

🔗 Study Guide eBook

🆓 FREE

Tutorials Dojo — AIF-C01 Exam Guide and Study Path

A free, community-trusted resource that maps every exam domain to the right study materials. This is your study roadmap. Bookmark it on day one and return to it regularly.

🔗 Tutorials Dojo Exam Guide

AWS Official Exam Guide PDF

Always read from the source. This document tells you precisely which services, concepts, and task statements are in scope. Every serious candidate should read it once at the start and once again before exam day.

🔗 AWS Official Exam Guide PDF

Jayendra Patil — AIF-C01 Learning Path

Jayendra achieved a perfect score on this exam. His notes are precise, well-organized, and cover technical nuances that most courses gloss over. This is the most underrated free resource on this list.

🔗 Jayendra Patil Learning Path

Layer 3 — 🛠️ Hands-On Labs: Experience What You Cannot Memorize

The AIF-C01 exam is packed with scenario-based questions. Reading about Amazon Bedrock or SageMaker is simply not the same as actually using them. These resources gave me real exposure without requiring a massive AWS bill.

🆓 FREE

AWS PartyRock

Build GenAI applications directly in your browser with zero infrastructure setup or cost. Ideal for understanding how Foundation Models behave, how prompting works in practice, and how to compose AI workflows.

🔗 partyrock.aws

AWS Workshops

Guided, self-paced labs covering Bedrock, SageMaker, Responsible AI, and more. These workshops are built by AWS engineers and reflect real-world architecture patterns you will encounter in exam scenarios.

🔗 workshops.aws

AWS Skill Builder — Standard (Free) Plan

The free tier of Skill Builder includes digital courses, guided lab previews, and exam prep content directly from AWS. There is genuinely no excuse to skip this one.

🔗 skillbuilder.aws

💰 PAID

Whizlabs — AIF-C01 Labs and Practice Tests

Hands-on lab environments combined with practice questions in one platform. A solid all-in-one option if you prefer to keep your study tools consolidated.

🔗 Whizlabs AIF-C01

Layer 4 — 📝 Practice Exams: Train Your Brain Under Pressure

Knowing the material and performing under exam conditions are two completely different things. Practice tests taught me time management, exposed every weak spot I had, and eliminated the surprises on exam day.

My rule: Do not sit the real exam until you are consistently scoring 85%+ across multiple practice test sets under timed conditions.

🆓 FREE

Open Exam Prep — 100+ Free AIF-C01 Questions

Over 100 free practice questions with AI-powered explanations. No account required. A fast, zero-friction way to check your readiness across all exam domains.

🔗 open-exam-prep.com/practice/aws-ai-practitioner

Community Study Notes — GitHub

Personal notes and practice questions from a candidate who passed AIF-C01. Questions are close to actual exam difficulty. An excellent free supplementary resource for the final week of prep.

🔗 github.com/vicsz/aif-c01-study-notes

💰 PAID

Jon Bonso / Tutorials Dojo — Practice Exams

The gold standard for AWS practice tests. Detailed explanations for every answer, domain-based filtering, built-in cheat sheets, and unlimited access for one year. These practice exams alone raised my readiness score by roughly 20 percentage points.

🔗 Tutorials Dojo Practice Exams

Stéphane Maarek & Abhishek Singh — Udemy Practice Exams

Human-crafted, exam blueprint-aligned questions with diagram-rich explanations. Built by instructors who collectively hold over 20 AWS certifications. Highly recommended for your final week of preparation.

🔗 Udemy Practice Exams

My Study Timeline

Here is a rough breakdown of how I structured my preparation:

Week Focus
Week 1 Andrew Brown’s full course (video) + AWS Official Exam Guide PDF
Week 2 AWS Skill Builder learning plan + Stéphane Maarek’s Udemy course
Week 3 Jayendra Patil notes + Tutorials Dojo exam guide + PartyRock hands-on
Week 4 AWS Workshops labs + Tutorials Dojo Study Guide eBook
Week 5–6 Full practice exam sets — Tutorials Dojo + Udemy (timed, reviewed every wrong answer)
Final 48hrs Light review of cheat sheets only — no new material

Key Lessons Learned

1. Scenario questions are everything.
The exam does not test definitions in isolation. It tests whether you can select the right AWS AI service or architecture pattern given a specific business scenario. Always study the why behind each service, not just the what.

2. Amazon Bedrock is central.
Bedrock appears throughout the exam in multiple domains. Make sure you understand model selection, knowledge bases, agents, guardrails, and how it integrates with other AWS services.

3. Responsible AI is not an afterthought.
AWS takes Responsible AI seriously in this exam. Bias, fairness, transparency, explainability, and governance are tested in dedicated questions and embedded in scenario questions too.

4. Do not skip hands-on practice.
Even one hour on PartyRock or an AWS Workshop gives you an intuitive understanding that reading cannot replicate. Scenario questions become significantly easier when you have seen the service behave in practice.

5. Practice test reviews matter more than practice test scores.
Every wrong answer is a study opportunity. Do not just note your score and move on — read every explanation, especially for questions you got right by guessing.

Quick Reference: All Resources in One Place

🆓 Free Resources

Category Resource Link
Video Andrew Brown — freeCodeCamp 15hr Link
Video AWS Skill Builder Official Plan Link
Reading Tutorials Dojo Exam Guide Link
Reading AWS Official Exam Guide PDF Link
Reading Jayendra Patil Learning Path Link
Labs AWS PartyRock Link
Labs AWS Workshops Link
Practice Open Exam Prep — 100+ Questions Link
Practice Community GitHub Notes Link

💰 Paid Resources

Category Resource Link
Video Stéphane Maarek — Udemy Link
Video Tutorials Dojo Video Course 2026 Link
Reading Tutorials Dojo Study Guide eBook Link
Labs Whizlabs AIF-C01 Link
Practice Tutorials Dojo — Jon Bonso Link
Practice Maarek & Abhishek — Udemy Link

Final Thoughts

The AWS AI Practitioner certification is not just a badge — it is a signal that you have taken the time to understand where cloud and AI intersect. That intersection is exactly where most of the interesting, high-value work is happening right now.

Layer your preparation intentionally:

  • Videos for building the big picture
  • Reading for locking in the fine print
  • Labs for developing real instincts
  • Practice tests for building confidence under pressure

That combination is what turned my preparation into a perfect 1000/1000 result — and it will work for you too.

If you are currently preparing for AIF-C01, drop a question in the comments below. I read everything and answer every serious question.

If this article helped you, please share it with your team or anyone in your network who is working toward their AWS AI certification. The more people who pass, the stronger our collective cloud community becomes.

Good luck — you have got this. ☁️

#aws #awscertification #aipractitioner #aifc01 #generativeai #amazonbedrock #machinelearning #cloudcomputing #devops #certification

Go – Struct and Interface

Hi Everyone,

Let’s try to understand, Struct and Interface in Go programming language

Struct –

struct is also called as structure, so normally we have some built in data types which are provided by the language, such as int, float64, string, bool etc

but suppose we want to create our own custom data type, how can we achieve this ? so in order to solve this problem we can use struct which helps us to create our own custom data type in which related data is grouped together, once we have this new custom data type, we can use it in our programs, like when when declaring a variable or when declaring and assigning the value

what problem structs are solving ?

If we want to represent a real-world entity in our program we don’t have any type for it, so to solve this problem, Golang provides us structs, which allow us to group related data together and create a custom type.

for example –

suppose we want to store data of 100 users, so we have a program which ask us to enter details of a user like name, email, phone and address and then storing it, and after that it will ask us whether we want add the data of another user or not, this we way we need to add the data of 100 users.

Now question is where we are storing this data ?

one approach is we create separate arrays or slices for each property and then store the data , but the problem is, the data is not grouped together as it is stored separately

But what we wanted to achieve, is to keep the related data together right, hence we use use structs which helps us to create a type of similar data

type User struct {
    name    string 
    email   string
    phone   string
    address string
}

so to solve above problem of storing data of 100 users, what we can do is since we have a new type “User”, so we can create an array or a slice of “User” type

var users [100]User

var users []User

Interview Answer –

Golang provides us built-in data types such as int, float64, string, bool etc. But when we want to represent a real-world entity in our program we don’t have any type for it, so to solve this problem, Golang provides us structs, which allow us to group related data together and create a custom type.

Interface –

An interface focuses on behavior instead of the actual type.

example 1:

suppose we have –

Dog
Cat
Human

All of them are different types, but all of them can perform one common action – Speak()

Now instead of writing separate code for Dog, Cat, and Human, we can write code that works with anything that can Speak().

This idea of focusing on behavior is called an interface.


package main 

import "fmt"

type Speaker interface {
    speak()
}

type Dog struct {}

func (d Dog) speak() {
    fmt.Println("Dog")
}

type Cat struct {}

func (c Cat) speak() {
    fmt.Println("Cat")
}

type Human struct {}

func (h Human) speak() {
    fmt.Println("Human")
}

func speaking(s Speaker) {
    s.speak()
}

func main() {
    speaking(Dog{})
    speaking(Cat{})
    speaking(Human{})
}

Handling JSON Requests in Go

Previously, we learned how to return JSON responses from a Go server.

But APIs do not only send data — they also receive it.

Frontend applications, mobile apps, and clients commonly send JSON data to servers through HTTP requests.

In this tutorial, we will learn how to handle JSON requests in Go by decoding request bodies into structs using Go’s standard library.

By the end, you will understand:

  • how JSON request bodies work
  • how to decode JSON in Go
  • how POST requests work
  • how to process incoming client data

Prerequisites

To follow along, you should have:

  • Go installed
  • basic familiarity with Go syntax
  • understanding of the net/http package
  • basic understanding of JSON responses

You can confirm if Go is installed by running:

go version

Step 1 — Create the Project

Create a new folder for the project:

mkdir go-json-requests
cd go-json-requests

Now initialize a Go module:

go mod init go-json-requests

This creates a go.mod file for managing project dependencies.

Step 2 — Create the Server File

Create a file called main.go.

Your project structure should now look like this:

go-json-requests/
├─ go.mod
└─ main.go

Step 3 — Write the Server

Open main.go and add the following code:

package main

import (
    "encoding/json"
    "fmt"
    "net/http"
)

type User struct {
    Name string `json:"name"`
}

func userHandler(w http.ResponseWriter, r *http.Request) {
    var user User

    err := json.NewDecoder(r.Body).Decode(&user)
    if err != nil {
        http.Error(w, "Invalid JSON", http.StatusBadRequest)
        return
    }

    fmt.Fprintf(w, "Hello, %s!n", user.Name)
}

func main() {
    http.HandleFunc("/user", userHandler)

    fmt.Println("Server running on :8080")

    http.ListenAndServe(":8080", nil)
}

Now let’s unpack what is happening.

Understanding POST Requests

In the previous examples, we mainly worked with routes that returned data.

This time, the client sends data to the server.

This commonly happens using a POST request.

POST requests are used when:

  • submitting forms
  • sending JSON data
  • creating resources
  • uploading information to a server

Understanding the Struct

This struct defines the shape of the JSON data we expect:

type User struct {
    Name string `json:"name"`
}

If the client sends:

{
  "name": "Steve"
}

Go can decode that JSON into the struct.

The json:"name" tag tells Go which JSON field maps to the struct field.

Understanding Request Bodies

When a client sends data to a server, the data is stored inside the request body.

In Go, we access it using:

r.Body

The Body contains the incoming JSON data from the client.

Decoding JSON Requests

This line is the heart of the server:

json.NewDecoder(r.Body).Decode(&user)

Here’s what happens:

  • NewDecoder(r.Body) reads the incoming request body
  • Decode(&user) converts the JSON into the struct
  • &user passes a pointer so Go can modify the struct value

After decoding, the user variable contains the client data.

So Why Do We Use &user?

You may notice this part:

&user

The & symbol means:

“Use the memory address of this variable.”

The decoder needs direct access to the struct so it can fill in the fields with incoming JSON data.

Without the pointer, decoding would not work correctly.

Understanding Error Handling

This section checks whether the JSON request is valid:

if err != nil {
    http.Error(w, "Invalid JSON", http.StatusBadRequest)
    return
}

If decoding fails:

  • the server sends an error response
  • the request stops processing

This helps prevent invalid client data from crashing the application.

Step 4 — Run the Server

Start the application:

go run main.go

You should see:

Server running on :8080

Step 5 — Test the API

This server expects a POST request containing JSON data.

We can test it using curl.

curl -X POST http://localhost:8080/user 
-H "Content-Type: application/json" 
-d '{"name":"Steve"}'

You should receive:

Hello, Steve!

What Happens When a Request Is Made?

Here’s the flow:

  1. The client sends a POST request
  2. JSON data is placed inside the request body
  3. Go reads the request body
  4. The JSON is decoded into a struct
  5. The server processes the data
  6. A response is sent back to the client

This is the foundation of many real-world APIs.

Where to Go Next

Now that we can decode JSON requests, we could extend this server by adding:

  • multiple API endpoints
  • JSON responses
  • CRUD operations — again, because every backend journey eventually leads there
  • databases
  • request validation
  • authentication

This is where backend development starts becoming much more interactive and dynamic.

Final Thoughts

We started with a simple server that only returned data.

Now our server can also receive and process JSON requests from clients.

Along the way, we learned about:

  • POST requests
  • request bodies
  • JSON decoding
  • structs
  • pointers
  • error handling

These concepts are essential when building APIs in Go.

Thanks for reading!

Happy coding!

Dijital pazar yerlerinin temsilcileri Bursa iş dünyasıyla bir araya geldi

Bursa Ticaret ve Sanayi Odası öncülüğünde düzenlenen ‘Dijital Pazaryeri B2B Networking 2026’ etkinliği, 60’tan fazla firmayı Türkiye’nin önde gelen 10 dijital pazar yeri platformuyla buluşturdu. BTSO Başkanı İbrahim Burkay, e-ticaret hacminin 2025’te 4,5 trilyon liraya ulaştığını belirterek dijital dönüşümün önemine vurgu yaptı.

How I Caught and Fixed an N+1 Query in My Django REST API

Every performant API eventually runs into the same silent killer: the N+1 query problem. It doesn’t crash your app. It doesn’t throw errors. It just quietly makes every list endpoint slower as your data grows — and it’s almost invisible until Sentry flags it in production.

Today, Sentry caught one on my /api/blog-posts/ endpoint. Here’s exactly what happened and how I fixed it in three lines of code.

What Is an N+1 Query?

An N+1 query happens when your code fetches a list of N records, then fires an additional query per record to fetch related data — totalling 1 + N database hits instead of a flat 2 or 3.

In Django, this usually happens silently because the ORM is lazy by default. Accessing a related object on a model instance that wasn’t eagerly loaded triggers a fresh SELECT on the spot. With 30 blog posts, that’s 30 silent queries you never wrote.

The Offending Code

The BlogPostViewSet looked clean on the surface:

class BlogPostViewSet(viewsets.ReadOnlyModelViewSet):
    queryset = BlogPost.objects.all()
    serializer_class = BlogPostSerializer
    lookup_field = "uid"

And the serializer:

class BlogPostSerializer(serializers.ModelSerializer):
    tags = BlogTagSerializer(many=True, read_only=True)
    series = BlogSeriesSerializer(read_only=True)
    ...

Spot the problem? BlogPost has two relations:

  • series — a ForeignKey to BlogSeries
  • tags — a ManyToManyField to BlogTag

When DRF serializes a list of 30 posts, it accesses post.series and post.tags on each one. Without eager loading, Django fires two extra queries per post — one to fetch the series, one to fetch the tags. That’s 1 + 60 queries for a 30-post list.

The featured action had the same issue:

@action(detail=False, methods=["get"])
def featured(self, request):
    queryset = BlogPost.objects.filter(date_published__isnull=False).order_by(
        "-date_published",
    )[:3]

A fresh BlogPost.objects call with no eager loading.

The Fix

Django gives me two tools for this:

  • select_related() — for ForeignKey and OneToOne relations. Issues a SQL JOIN and fetches everything in a single query.
  • prefetch_related() — for ManyToMany and reverse FK relations. Issues a second query and caches the results in Python.

The fix:

class BlogPostViewSet(viewsets.ReadOnlyModelViewSet):
    queryset = BlogPost.objects.select_related("series").prefetch_related("tags")
    serializer_class = BlogPostSerializer
    lookup_field = "uid"

    @action(detail=False, methods=["get"])
    def featured(self, request):
        queryset = (
            BlogPost.objects.select_related("series")
            .prefetch_related("tags")
            .filter(date_published__isnull=False)
            .order_by("-date_published")[:3]
        )
        serializer = self.get_serializer(queryset, many=True)
        return Response(serializer.data)

With 30 posts, the list endpoint now costs 3 queries regardless of dataset size:

  1. SELECT * FROM core_blogpost ...
  2. SELECT * FROM core_blogseries WHERE id IN (...)
  3. SELECT * FROM core_blogtag INNER JOIN core_blogpost_tags WHERE blogpost_id IN (...)

The Bonus Fix

While auditing the blog endpoint, I spotted the same pattern in TestimonialViewSet. Its serializer accesses project.title and project.slug, but the queryset had no select_related:

# Before
queryset = Testimonial.objects.all()

# After
queryset = Testimonial.objects.select_related("project")

One extra line, one less N+1.

How to Spot This in Your Own Code

The pattern is always the same — look for any ViewSet or view where:

  1. The queryset has no select_related or prefetch_related
  2. The serializer accesses a related field (source="relation.field", nested serializers, SerializerMethodField that touches obj.relation)

Tools that help catch this before Sentry does:

  • django-debug-toolbar — shows query counts per request in the browser
  • nplusone — raises exceptions in tests when N+1 queries are detected
  • Sentry Performance — catches it in production with query traces

The best time to catch an N+1 is during code review. Any time you write a nested serializer, ask: does the queryset for this view eagerly load this relation?

Takeaway

The Django ORM’s lazy evaluation is a feature, not a bug — but it requires discipline at the queryset layer. A clean-looking viewset with objects.all() is often hiding a query storm one serializer away.

The rule of thumb: every relation accessed in a serializer needs a corresponding select_related or prefetch_related on the queryset. Make it a checklist item on every PR that touches a ViewSet.

How to Start Coding as a Student: A Complete Beginner’s Guide 🚀

Hey everyone! 👋

If you are a student and thinking about stepping into the world of coding, you are in the exact right place. At first, coding can look intimidating with all those complex lines of text, but here is the truth: coding is like a superpower that anyone can learn—no matter your age or background!
In this article, I’m sharing a simple, no-nonsense roadmap to help any student kickstart their programming journey without getting overwhelmed.

🗺️ The Simple Roadmap
Step 1: Build Logic (Scratch): If you are an absolute beginner, start with Scratch (scratch.mit.edu). It uses drag-and-drop blocks to teach you how coding logic works through simple games.

Step 2: Build Websites (HTML & CSS): Want to make websites? Learn HTML (to add text and images) and CSS (to make it look colorful and beautiful).

Step 3: Try Python: If you want to build apps or explore AI, start with Python. It is the easiest language because it reads just like English.

🛠️ Best Free Resources
You don’t need to spend any money! Use these free platforms:

freeCodeCamp.org (Great for interactive coding)

W3Schools (Perfect for quick HTML/CSS notes)

YouTube (Search for “Free HTML/CSS beginner tutorials”)

💡 3 Golden Rules

Don’t Memorize: Coding is about logic, not learning lines by heart. Google is your best friend!

Expect Mistakes: Your code will break, and that is completely normal. Fixing bugs is how we learn.

Be Consistent: Coding for 30 minutes every day is much better than coding for 5 hours once a week.