🗣 🤖 Talking to machines

The key in AI-assisted coding is to know how to talk to your AI assistant.

The key in AI-assisted coding is to know how to communicate with your AI assistant, which requires some basic programming knowledge.

You might dream of a scenario where you simply type, “Give me the full code for a web app to create the AI Jingle Maker,” but this isn’t feasible (yet).

Knowing where to start and how to progress is essential.

I advise you to learn the basics of Python + HTML + CSS + JS via one of the courses available for free on the open web. This will take you a few weeks . Then you’ll feel comfortable in your conversations with your AI assistant (ChatGPT, GitHub Copilot, Cody,..)

Before engaging in your first chat, you have to pick your tech stack.

I’ve chosen to develop all my projects in Flask/Python + HTML, Tailwind CSS and vanilla javascript.

Why vanilla javascript and not React? Well, because it enables me to deploy the app as a single project on Railway. I don’t need to decouple the frontend and backend code. For the type of micro SaaS I’m building, it makes things much easier (for me at least).

🤖 Here’s what ChatGPT thinks about my JS approach.

Using vanilla JavaScript for both frontend and backend development can indeed simplify the deployment process, especially for micro SaaS products that you're looking to ship quickly and efficiently. Here are a few reasons why your approach is beneficial:

Simplicity: Vanilla JavaScript doesn't require additional libraries or frameworks, making the codebase more straightforward to understand and manage. This simplicity is especially advantageous when you're working on microservices or smaller projects where the overhead of a framework like React might not be justified.

Single Project Deployment: By not needing to decouple frontend and backend, you can manage your application as a single project. This approach streamlines the deployment process on platforms like Railway, where you might prefer a simplified setup for rapid development cycles. It reduces the complexity associated with managing separate repositories or dealing with cross-origin resource sharing (CORS) issues.

Flexibility: Vanilla JavaScript gives you full control over the implementation details. You're not tied to the conventions or architectural decisions imposed by frameworks. This flexibility can be crucial when you need to make quick adjustments or when you're experimenting with new ideas.

Performance: For smaller applications, vanilla JavaScript can lead to better performance since you're not loading unnecessary code from frameworks or libraries. This lean approach can make your micro SaaS products more responsive and efficient.

Learning and Problem Solving: Working directly with vanilla JavaScript enhances your understanding of the core language and web development principles. This deep knowledge can be beneficial when troubleshooting or optimizing your application, as you're not reliant on framework-specific solutions.

Your strategy aligns well with the goals of shipping products rapidly and maintaining a manageable complexity level. It's a practical approach for developers who value speed, simplicity, and control over their development process.

👨‍💻 Let’s get our hands (not so) dirty with some coding, in 3 prompts. Ready? Let’s go!

The first prompt

I ask the AI to “give me the boilerplate of a Flask Web App rendering index.html.” (which will be pasted into main.py at the root of the project).

from flask import Flask, render_template

app = Flask(__name__)

@app.route('/')
def home():
    return render_template('index.html')

if __name__ == '__main__':
    app.run(debug=True)

Thanks to my basic Python knowledge, I know that I have to create at the root of my project a templates folder with a file called index.html

Here’s the architecture of a basic Flask web app (deployed on Railway):

The second prompt

I ask the AI to “give me the boilerplate of a HTML page nicely styled with Tailwind CSS (using the CDN), introducing the services of an AI-assisted developer creating micro SaaS applications, outlining the 5 key advantages of the method, presented as a row of cards, stacked on mobile.“

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>AI-Assisted Developer Services</title>
    <link href="https://cdn.jsdelivr.net/npm/[email protected]/dist/tailwind.min.css" rel="stylesheet">
</head>
<body class="bg-gray-100">

<div class="container mx-auto px-4 py-8">
    <h1 class="text-3xl font-bold text-center mb-8">AI-Assisted Developer Services</h1>
    
    <div class="grid md:grid-cols-2 lg:grid-cols-5 gap-4">
        <!-- Card 1 -->
        <div class="bg-white rounded-lg p-6 shadow-lg">
            <h2 class="font-bold text-xl mb-2">Speed</h2>
            <p>Quickly generate prototypes and MVPs, reducing time to market.</p>
        </div>
        
        <!-- Card 2 -->
        <div class="bg-white rounded-lg p-6 shadow-lg">
            <h2 class="font-bold text-xl mb-2">Efficiency</h2>
            <p>Automate repetitive tasks, focusing on creative and critical aspects.</p>
        </div>
        
        <!-- Card 3 -->
        <div class="bg-white rounded-lg p-6 shadow-lg">
            <h2 class="font-bold text-xl mb-2">Scalability</h2>
            <p>Easily scale solutions to meet growing customer demands.</p>
        </div>
        
        <!-- Card 4 -->
        <div class="bg-white rounded-lg p-6 shadow-lg">
            <h2 class="font-bold text-xl mb-2">Innovation</h2>
            <p>Leverage AI for innovative features and services.</p>
        </div>
        
        <!-- Card 5 -->
        <div class="bg-white rounded-lg p-6 shadow-lg">
            <h2 class="font-bold text-xl mb-2">Cost-Effectiveness</h2>
            <p>Reduce development costs through efficient resource use.</p>
        </div>
    </div>
</div>

</body>
</html>
T

By the way, this could be a standalone static page. See the result deployed on Netlify (in 2 seconds via a manual deploy).

👉 The whole purpose of using Flask is to introduce more advanced features, such as, for instance, a contact form.

The third prompt

I ask the AI to “add a contact form on the page, collecting the user’s name, email and a message (text area), with some JS validation of the email structure. If the message isn’t properly structured, you should display a warning. When the form has been submittted, you should display a confirmation. We’ll be using SweetAlert2. The JS logic will be in script.js in the static folder (give me the code to reference it the Flask way), I also need the CDN link for SweetAlert2. And I need the backend route for my main.py file (without the database logic at this stage), returning a success message to the client to display the pop up confirmation.”

Code to add to the body of index.html

<div class="container mx-auto px-4 py-8">
    <h2 class="text-2xl font-bold text-center mb-4">Contact Us</h2>
    <form id="contactForm" class="max-w-xl mx-auto">
        <input type="text" name="name" placeholder="Your Name" required class="block w-full p-2 mb-4 border rounded">
        <input type="email" name="email" placeholder="Your Email" required class="block w-full p-2 mb-4 border rounded">
        <textarea name="message" rows="4" placeholder="Your Message" required class="block w-full p-2 mb-4 border rounded"></textarea>
        <button type="submit" class="block w-full bg-blue-500 hover:bg-blue-700 text-white font-bold py-2 rounded">Send Message</button>
    </form>
</div>

<!-- SweetAlert2 CDN -->
<script src="https://cdn.jsdelivr.net/npm/sweetalert2@11"></script>
<!-- Flask way to reference static JS -->
<script src="{{ url_for('static', filename='app.js') }}"></script>

Code for script.js in the static folder at the root of the project

document.getElementById('contactForm').addEventListener('submit', function(event) {
    event.preventDefault(); // Prevent the form from submitting the traditional way
    
    const name = this.querySelector('[name="name"]').value;
    const email = this.querySelector('[name="email"]').value;
    const message = this.querySelector('[name="message"]').value;

    // Simple email structure validation
    if (!/\S+@\S+\.\S+/.test(email)) {
        Swal.fire({
            icon: 'error',
            title: 'Oops...',
            text: 'Please enter a valid email address.',
        });
        return;
    }

    // Send the form data to the server
    fetch('/submit-form', {
        method: 'POST',
        headers: {
            'Content-Type': 'application/json',
        },
        body: JSON.stringify({ name, email, message }),
    })
    .then(response => response.json())
    .then(data => {
        Swal.fire(
            'Success!',
            'Your message has been sent.',
            'success'
        );
    })
    .catch((error) => {
        console.error('Error:', error);
    });
});

Updated main.py code, incl. the form submission route

from flask import Flask, render_template, request, jsonify

app = Flask(__name__)

@app.route('/')
def home():
    return render_template('index.html')

@app.route('/submit-form', methods=['POST'])
def handle_form():
    # At this stage, you would process the form data
    data = request.json
    print(data) # For demonstration purposes
    # Logic to save data to the database would go here

    return jsonify({'message': 'Success! Your message has been sent.'})

if __name__ == '__main__':
    app.run(debug=True)

The next step would be to implement the database logic. 

It can be as simple as asking the AI to hook the route to a SQLite database to record the email submissions. You can watch this video where I dive into more details.

In the next edition of my newsletter, I’ll share a collection of prompts to fine tune your CSS.

Until then, enjoy coding with your favorite AI assistant, and remember that I'm available seven days a week for one-on-one coaching and custom AI-assisted development projects. I recently completed 90% of a client's project in just five working sessions—that's 25 hours for 9,500 lines of code. This example underscores the efficiency of this approach! Feel free to reach out at [email protected].

Stay tuned!

Frédérick, AI-assisted coder.

If you’d like to get a private introduction to the art of AI-assisted coding and more broadly a detailed overview of today’s Gen AI capabilities, I’m offering one-on-one 2-hour mentoring sessions “How To Talk To An AI Agent”.

Here’s the link for bookings.

Sessions are tailored to your specific business needs.

I can also assist you in the development of your own micro SaaS project.