Your project is finished, documented, defended and published: Project presentation closed off the last pending task. This lesson teaches no new syntax and adds nothing to the project; it is here for what comes next, which is a legitimate and fairly anxious question when a course ends: so what now? We are going to answer it in four movements. First, an honest stocktake of what you can do today and could not do nine modules ago. Second, the map of what exists out there that this course did not cover, so that you know what is there and what it is for. Third, the career paths that open up from where you are, with realistic expectations. And fourth, a concrete three-month plan, because the difference between the person still programming a year from now and the one who gave up is not talent: it is having the next thing to do.
Contents
- The road travelled
- EasyTask, from v0.1 to v1.0
- What this course did not cover
- Choosing a path
- How to keep learning
- Professional habits worth consolidating
- Working with AI assistants
- Common mistakes made by beginners
- A plan for the next three months
- Common mistakes and tips
- Exercises
- Conclusion
- The road travelled
You started without knowing what a variable was. This is the inventory, module by module, of what you can do now; read it slowly, because the normal feeling at the end of a course is that you know nothing, and that is not what the table says:
| Module | What you can do now |
|---|---|
| 1. Introduction | Explain what programming is and why Python; set up an environment with venv and VS Code; turn a problem into an algorithm with pseudocode, flowcharts and a desk check |
| 2. Basic concepts | Handle variables and types, operators and expressions; read and write data with input and f-strings; convert types and validate input with the presence, type, domain and coherence framework |
| 3. Control structures | Decide with conditionals, repeat with loops, cut out with break and continue, use match/case and build an application loop with its menu |
| 4. Functions | Define functions with parameters and return values, reason about scope with LEGB, decompose a program top-down with main(), separate input/output from logic and use functions as values |
| 5. Data structures | Choose sensibly between list, string, dictionary, set and tuple; nest them; and persist data in text, CSV and JSON |
| 6. Algorithms | Search linearly and with binary search, sort with sorted and key, write recursive functions with memoisation and reason about cost with big-O, measuring before optimising |
| 7. Objects | Design classes with __init__, methods, __str__, @property and @dataclass; compose collections of objects; use basic inheritance; and organise code into modules and packages |
| 8. Good practices | Document with docstrings, annotations and a README; debug with try/except, logging and a debugger; version with Git; write tests with pytest; and refactor with PEP 8, black and ruff |
| 9. Final project | Define a project's scope, design it, plan it, implement it in increments, test it, present it and publish it |
That last row is the one that carries the most weight. Plenty of people know Python syntax; considerably fewer have taken a project of their own from an idea to a published v1.0. The first is learned in a few weeks; the second is what it takes to work.
- EasyTask, from v0.1 to v1.0
If you need tangible proof of the road travelled, there it is in EasyTask. It started out as three print calls and a list, and ended up as an installable package with tests. Its story is the story of the course:
| Version | What it was | Module |
|---|---|---|
| v0.1 | A handful of print calls with the tasks typed in by hand |
2 |
| v0.2 | A menu in a while True with options that actually did something |
3 |
| v0.3 | Separate functions, main() and the logic set apart from the screen |
4 |
| v0.4 | A list of dictionaries and saving to JSON: the tasks survived closing | 5 |
| v0.5 | Searching, filters and sorting by priority and date, with its cost measured | 6 |
| v0.6 | Task and RecurringTask classes, an Agenda class, a package with modules |
7 |
| v0.21 → v1.0 | Docstrings, types, README, CHANGELOG, try/except, logging, Git, eight green tests, black and ruff |
8 |
The distance shows best by comparing the same idea written at the beginning and at the end. This is how the tasks were listed in v0.1:
tasks = ["Sole Bakery logo", "Book fair poster", "Vidal account website"]
print("Pending tasks:")
print("1. " + tasks[0])
print("2. " + tasks[1])
print("3. " + tasks[2])And this is how in v1.0:
def list_tasks(agenda: Agenda, assignee: str | None = None) -> None:
"""Shows the pending tasks, optionally for a single assignee."""
pending = agenda.filter_by(completed=False, assignee=assignee)
if not pending:
print("There are no pending tasks.")
return
for task in agenda.sorted_tasks(pending, key="priority"):
print(task)Nine modules sit between those two snippets: functions with parameters and default values, type annotations, a docstring, a class encapsulating the collection, filtering and sorting by criterion, the empty-list case anticipated and __str__ doing the formatting. But the important difference is not the syntax, it is that the second one works with three tasks and with three hundred, and that it can be tested, changed and extended without rewriting it.
Marta, Luis and Nuria started with a notebook where they wrote down who was doing what for Solé Bakery and ended up with a tool that shares out the studio's work, flags what is urgent and loses nothing. That leap — from a real problem told in one sentence to a program that solves it — is exactly the one you have just made with your own project, this time without anybody telling you what to write at each step.
- What this course did not cover
A fundamentals course covers the foundations, and the foundations are not the building. This is what is out there, what each thing is for and when it makes sense to get into it:
| Topic | What it is for | When you will need it |
|---|---|---|
| Advanced OOP | Multiple inheritance, abstract classes, magic methods, design patterns: modelling complex domains without repeating code | When your project goes beyond three or four classes and you notice duplication between them |
| Databases and SQL | Storing, querying and relating large volumes of data with integrity and without loading everything into memory | As soon as a project passes a few thousand records or needs complex queries; it is the first thing I would recommend |
| Web programming | HTTP, REST APIs, JSON over the network, frameworks like Flask or Django: getting people to use your program from a browser | When you want your project to leave your computer |
| Graphical interfaces | Tkinter, PyQt or a web interface: windows, buttons and forms instead of a text menu | When the end user is not somebody comfortable with a terminal |
| Concurrency and asynchrony | Threads, processes and async/await: doing several things at once without the program blocking |
When you spend a lot of time waiting on the network or the disk, or process large volumes |
| Advanced data structures | Stacks, queues, trees and graphs: solving problems where a list or a dictionary is not enough (routes, hierarchies, undo) | When the problem has the shape of a network or a hierarchy; it also comes up in technical interviews |
| Regular expressions | Searching for and extracting text patterns in one line: validating formats, parsing logs, cleaning data | As soon as you work with free text; it is one of the best returns per hour invested |
So that the recommendation about databases does not stay abstract, look at the same query — "August food expenses over 50 euros" — with what you know today and with SQL:
# With what you know today: load everything into memory and filter
result = [t for t in ledger
if t.category == "food"
and t.date.isoformat().startswith("2026-08")
and t.amount < -50]-- With SQL: the database filters without loading anything into your program
SELECT * FROM transactions
WHERE category = 'food' AND date LIKE '2026-08%' AND amount < -50;With 200 transactions the first version is perfect and simpler. With 200,000, the first loads the whole file into memory and walks every element, while the second uses indexes and returns the result without your program ever seeing the rest. That is the exact moment to learn SQL: when the problem shows up, not before.
Two pieces of advice about this table. First: do not turn it into a to-do list. Trying to learn all seven topics in a row is the fastest way to learn none of them. Second: learn each one when a project of yours needs it. When your expense program gets slow with 20,000 transactions, SQL will stop being a school subject and become the solution to your problem, and then you learn in a weekend what otherwise takes a month.
- Choosing a path
With what you know today you can already start any of these paths. None is better; they depend on the kind of problem you feel like solving. They all share the same trunk — the one you have just climbed — and separate afterwards:
flowchart TD
B["Fundamentals<br/>this course"] --> W["Web development"]
B --> D["Data and analysis"]
B --> A["Automation<br/>and scripting"]
B --> M["Mobile development"]
B --> S["Systems and DevOps"]
W --> WB["Back-end<br/>SQL, HTTP, Flask"]
W --> WF["Front-end<br/>HTML, CSS, JavaScript"]
D --> DD["SQL, pandas,<br/>statistics"]
A --> AA["Regex, APIs,<br/>scheduled jobs"]
M --> MM["Kotlin or Swift"]
S --> SS["Linux, Docker,<br/>CI/CD, cloud"]
The expectations in the last column are honest, not motivational:
| Path | What you do | What you learn next | How it connects to the course | Realistic expectation |
|---|---|---|---|---|
| Web development (back-end) | Servers answering requests, APIs, business logic, databases | SQL, HTTP, Flask or Django, authentication, deployment | Your logic and storage layers are exactly what sits behind an API; only the interface changes | 6-12 months of steady work to reach first-job level |
| Web development (front-end) | What the user sees in the browser: interface, interaction, accessibility | HTML, CSS, JavaScript, then React or similar | You change language, but variables, functions, conditionals and structures transfer wholesale | Similar; you have to learn another base language |
| Data and analysis | Cleaning, analysing and visualising data; reports and models | SQL, pandas, NumPy, statistics, matplotlib, then machine learning | Your dictionaries, your CSV and your JSON are the step before pandas | 6-12 months; the statistics weigh as much as the code |
| Automation and scripting | Programs that do repetitive tasks: files, reports, integrations | Regular expressions, APIs, os and pathlib, scheduled jobs |
It is the closest thing to what you already know how to do; you could start tomorrow | Weeks to be useful in your own job |
| Mobile development | Applications for Android or iOS | Kotlin or Swift, an app's life cycle, app stores | The fundamentals transfer; the environment and the language are new | 9-18 months; it is the biggest jump from here |
| Systems and DevOps | Making software deploy, run and stay monitored reliably | Linux, networking, Docker, CI/CD, cloud, infrastructure as code | Git, the command line and scripting are the daily basis of the trade | 12+ months; people usually come in from systems or from development |
And a note no course catalogue will give you: automation is the path with the best ratio of effort to immediate usefulness. If you work in something that is not programming, a script that saves you two hours a week of repetitive work gives you results in the first month, gives you something real to show and keeps you programming. Long roads are much easier to walk when there are rewards along the way.
- How to keep learning
The rule that sums up everything else: you learn by building. Reading about programming and programming resemble each other about as much as reading about swimming and swimming. A course, a book or a video is for finding out that something exists and how it is used; the knowledge sticks when you apply it to a problem that did not come with a solution.
Next projects, in increasing difficulty. Pick the next step, not the whole building:
| Level | Project | What new thing it forces you to learn |
|---|---|---|
| 1 | Your final project, version 1.1: the Shoulds that were left out | Nothing new; consolidation and work on code of your own already written |
| 2 | A script that automates something real from your day to day | pathlib, regular expressions, command-line arguments |
| 3 | The same project, with the data in SQLite instead of JSON | Basic SQL, queries, data integrity |
| 4 | A program that consumes a public API (weather, transport, books) | HTTP, requests, third-party JSON, handling network errors |
| 5 | A small web application with Flask on top of your project | Routes, templates, forms, deployment |
Programming challenges. Platforms like Exercism, Codewars or Advent of Code give you closed problems with a verifiable solution. They are an excellent gym for algorithms and data structures, and a poor substitute for projects: they train you to solve twenty-line problems, not to build systems. Half an hour two or three times a week is fine; living there is not.
Reading other people's code. It is the most underrated skill and the one you will practise most in a real job, where 80 % of the time is spent reading code you did not write. Start with small projects, following this route and these questions:
| Order | What you look at | Question you ask yourself |
|---|---|---|
| 1 | README | Do I understand what it does and for whom in one minute? |
| 2 | File structure | Do I recognise the layers: model, logic, storage, interface? |
| 3 | The entry point | Where does execution start and what does it call first? |
| 4 | Any module | How do they name functions? How long is each one? |
| 5 | The tests | What do they consider important to test? |
| 6 | The commit history | How do they write the messages? Big or small commits? |
Half an hour following that route over two or three projects gives you more structural judgement than several tutorials, because you see real decisions taken by people with more experience.
Contributing to open source projects. It sounds unreachable and it is not. The real way in is not fixing a complex bug, but this sequence:
- Use a small open source tool that you already find useful.
- Find something that does not work, or that the documentation does not explain well.
- Search its repository for issues labelled
good first issue, which exist precisely for newcomers. - Read its contribution guide (
CONTRIBUTING.md) and respect its style, even if it is not yours. - Propose a small, well-explained change, and accept the review you are given.
The first accepted contribution teaches you more about teamwork — reviews, project style, technical discussion — than any course.
Studying the official documentation. It is a skill you train, not a punishment. Python's documentation has three parts worth telling apart: the Tutorial (for learning something new), the Library Reference (for looking up exactly what a function does) and the HOWTOs (excellent topic guides, like the one on regular expressions or the one on logging). Get into the habit of searching there first and in forums afterwards; forums give you a recipe, the documentation gives you the model.
- Professional habits worth consolidating
You have already practised these five habits during the course. What decides your progress is not learning them again, it is not abandoning them when nobody is asking you to keep them:
- Version everything from minute one.
git initis the first command of any project, even if it is a thirty-line script and even if you are not going to share it. The cost is zero and it saves you thefinal_version_2_goodfolder. - Test what matters. You do not need to cover everything: test the calculations, the domain rules and the persistence. That is what lets you change code without fear, and without that confidence projects seize up.
- Write for whoever comes next, which is almost always you three months from now. Clear names, short functions, a README explaining the why. Code is written once and read many times.
- Measure before optimising. Intuition about performance is wrong almost every time. Measure, find the real slow point and optimise only that (06-04). The rest of the time, prioritise clarity.
- Finish what you start. It is the hardest habit and the one that will set you apart the most. A finished project, however modest, teaches and demonstrates; ten half-built ones do neither.
- Working with AI assistants
AI assistants are part of the job and there is no sense pretending otherwise. The useful question is not whether to use them, but how to use them so that they add without stopping you learning. The difference lies in whether the assistant does the work for you or with you:
| Use that adds | Use that stops you learning |
|---|---|
"Explain what this TypeError means and why it happens" |
"Fix this error for me" without reading the explanation |
| "Review this function and tell me what code smells you see" | "Write the function for me" |
| "What alternatives are there to this structure and what does each imply?" | "Which is best?" and accepting it without judgement |
| "Give me three exercises on dictionaries and mark them" | Asking for the solution before trying |
| "Explain this snippet of somebody else's code line by line" | Pasting generated code you do not understand |
The difference shows in how you phrase the request. Compare:
Bad: "Write me a function that calculates the total by category."
Good: "This is my total_by_category function (pasting it). It returns the totals
correctly but the order is not what I expect. What might be going on and why?"The second question starts from your code, describes the observed behaviour and asks for an explanation, not a replacement. It is the difference between walking away with a function and walking away understanding why sorted sorts by the second element of the tuple.
Three practical rules that work well:
- Try the problem for twenty minutes before asking. The learning happens during the attempt, not in the answer. Asking after trying is research; asking before is dependency.
- Never paste code you could not rewrite. Not out of purity, but for practical consequences: when it fails in production, or when you are asked about it in an interview, you will have to understand it anyway.
- Always verify. Assistants get things wrong with apparent confidence: they invent functions that do not exist, use obsolete APIs and make subtle logic errors. Your automated tests and the official documentation are the filter.
The skill that really matters — and that assistants do not replace — is knowing what to build, how to structure it and how to check that it works. That is precisely what you have been practising in this module.
- Common mistakes made by beginners
Four patterns that derail a lot of people in the year following a first course, with their concrete antidote:
| Mistake | How it shows up | Antidote |
|---|---|---|
| Hopping from technology to technology | You start Django, two weeks later React because "it is more in demand", then Rust | Pick one and give it six months. Depth transfers between technologies; nibbling does not |
| Tutorial hell | You chain courses and videos with a sense of learning, but you cannot start anything on your own from a blank page | For every hour of tutorial, one hour building something the tutorial did not explain |
| Comparing yourself with veterans | You see code from somebody with fifteen years in the trade and conclude that this is not for you | Compare yourself with your self of three months ago. And remember that that code started out bad too |
| Not finishing anything | Five projects at 60 %, none published | Cut the scope until it fits (MoSCoW from 09-01) and finish one, however small |
A fifth, less discussed and very common: studying without applying anything for months while waiting to be "ready" to do something real. There is no such moment. You are ready as soon as you start; the rest is learned along the way, exactly as you have just done with your project.
- A plan for the next three months
A concrete plan is worth more than any list of resources. This one assumes between five and eight hours a week, which is what you can sustain alongside other things. Adapt it, but keep the structure: there is always a project under way, and the studying serves the project.
flowchart LR
S1["Weeks 1-2<br/>v1.1 of your project"] --> S2["Weeks 3-4<br/>Automation script"]
S2 --> S3["Weeks 5-8<br/>SQL and SQLite"]
S3 --> S4["Weeks 9-10<br/>Consume an API"]
S4 --> S5["Weeks 11-12<br/>Second project published"]
| Weeks | Goal | What you do | Verifiable result |
|---|---|---|---|
| 1-2 | Consolidate | Your project v1.1: the improvement plan from 09-04 and one or two Shoulds | A published v1.1 tag |
| 3-4 | Automate something real | A script that saves you a repetitive task of your own | A script you genuinely use every week |
| 5-8 | Serious persistence | Learn basic SQL and migrate your project from JSON to SQLite | The project works the same, but with a database |
| 9-10 | Reach out to the world | Consume a public API in a small project | A program that fetches data from the internet and processes it |
| 11-12 | Choose a path | A serious tutorial on the path from section 4 you have chosen, and something of your own on top | A second published project with its README |
Four rules to keep the plan alive:
- Fixed slots in the calendar. "When I can" means never. Two evenings and a stretch at the weekend work better than five hours in a row on a Sunday.
- Short, frequent sessions beat spaced-out marathons: that is how memory works, and marathons leave the code half done.
- End every session with something committed and a note on where you were (09-03). Picking things back up is what eats the most time.
- Review the plan every month. If something does not fit your real life, change it; an abandoned plan teaches nothing.
Common Mistakes and Tips
- Confusing "finishing a course" with "having finished". This course is the foundations. Programming is learned over years and always under construction; that is not bad news, it is the interesting part of the trade.
- Choosing a path by what is fashionable. Fashions change every two years and your own interest does not. Choose by the kind of problem you feel like solving: if it does not interest you, you will not survive the curve.
- Waiting to be "ready". Nobody ever feels ready. Impostor syndrome keeps veterans company too; you live with it, you do not cure it by studying more.
- Learning theory without a project. A topic studied without applying it is forgotten in weeks. Every new thing has to go into something you are building.
- Measuring progress in hours of video. Progress is measured in problems solved and projects published, not in tutorials consumed.
- Tip: keep a learning log. A file where you note down, every week, what you did and what you found hard. In six months it will be the proof of your progress on the day it feels like you are not progressing.
- Tip: find people. A community, a local group, somebody to talk about what you are doing with. Programming alone for a long time becomes an uphill slog, and most of what you learn after a course is learned by talking to others.
- Tip: come back to this material when you need it. Nobody remembers the syntax of
sortedwithkeyor the order ofopen's arguments. Looking it up is not a failure: it is the normal work.
Exercises
The last three exercises of the course are not about code: they are about direction. Do them in writing, in a file you can reread a few months from now.
Exercise 1: An honest stocktake
Go through the table in section 1 and score your real command of each module from 1 to 3 (1: I recognise it but would not apply it on my own; 2: I apply it with a reference to hand; 3: I apply it fluently). For each module scoring a 1, write one concrete task that would take it up to a 2, in less than two hours of work. Add a list of the five things you can do today and could not do nine modules ago, with the example from the project that proves it.
Exercise 2: Choosing a path and the next project
Using the table in section 4, choose a path and write half a page justifying why: what kind of problems it solves, why they interest you, what time expectation you accept and what three concrete things you would have to learn first. Then define your next project with the definition document from 09-01 — problem, MoSCoW and five requirements — choosing whichever level from section 5 is yours.
Exercise 3: Your three-month plan
Adapt the table in section 9 to your real availability: write down the weekly hours you genuinely have (not the ones you would like), the concrete slots in the calendar and the verifiable result of each two-week block. Add a "monthly review" row and note the exact date of the first one. Keep it somewhere you will see it.
Solutions
Solution 1. There is no single solution, but there is a way of checking you have done it well: the five things in the second list must be pointable at in your project, with a file and a line. For example, "I know how to separate the logic from the interface" → ledger.py contains no print at all; "I know how to write tests" → tests/test_model.py with nine cases; "I know how to use version control" → git log with twenty commits and a tag. If any claim has no evidence, it is one you are still learning, and that is useful information too. Rubric: does each point have evidence? Do the tasks for the modules scoring a 1 fit into two hours and are they concrete ("write three parametrised tests", not "revise testing")?
Solution 2. A well-made justification talks about problems, not technologies: "I want the tools I use every day to stop wasting my time, so I am starting with automation, and from there probably the back-end" is a solid answer; "I choose data because it pays well" will not sustain the following six months. Rubric: does your justification mention the kind of problem and not just the name of the path? Do you accept the time expectation from the table? Is your next project one step up, not a leap? Does it have its Won't box written?
Solution 3. The plan in section 9 is the template. The two usual failings: planning with your ideal hours instead of your real ones — a fifteen-hour-a-week plan that is really five gets abandoned in week three — and not setting a verifiable result, which makes it impossible to know whether you are on track. Rubric: are the weekly hours realistic and placed in concrete calendar slots? Does each block end in something verifiable (a tag, a script in use, a published repository)? Is there always a project under way, with the studying at its service? Does the first review have a date?
Conclusion
Nine modules ago, the first lesson explained what programming was and the first exercise consisted of writing a print. Today you know how to turn a problem into an algorithm, handle types and validate input, decide and repeat with control structures, break a program down into functions, choose the right data structure and store it on disk, search, sort and reason about the cost of what you write, design classes and organise a package, and work the way work is really done: documenting, debugging, versioning, testing and refactoring. And above all that, you know how to take a project of your own from an idea to a published version, which is the skill nobody can teach you in a lesson because it is only acquired by doing it all the way through once. You have now done it.
What lies ahead is a map, not a homework list: databases, the web, graphical interfaces, concurrency, advanced structures, regular expressions and advanced OOP, each in its own time and always when a project of yours needs it. The paths — web, data, automation, mobile, systems — are chosen by the kind of problem you feel like solving, not by the fashion of the year, and they all start from where you are now. You move forward by building: the next step, always just one, with challenges and reading other people's code as the gym and the official documentation as the source. It is sustained with habits — version everything, test what matters, write for whoever comes next, measure before optimising and finish what you start — and it is protected from the four classic derailments: hopping from technology to technology, tutorial hell, comparing yourself with veterans and not finishing anything. AI assistants make good company if you use them to understand, review and explore alternatives, and bad company if you delegate to them the work that is your learning. And so that none of this stays as an intention, there is the three-month plan with fixed slots, short sessions and a verifiable result every fortnight.
At Alba Studio, Marta is still coordinating Luis and Nuria, Solé Bakery still asks for last-minute changes and the book fair comes round every year. EasyTask went from three print calls to a package with green tests because somebody decided, one day, to solve a small, specific problem and then did not abandon it. Your project now has the same story and it is entirely yours: the idea, the design, every decision and every bug you fixed at eleven at night. That — choosing a problem, understanding it, building the solution and finishing it — is programming, and you have now done it once. Everything that comes from here on is the same operation with more tools. Thank you for making it this far, and may the next project be better than this one.
Fundamentals of Programming
Module 1: Introduction to Programming
- What is programming?
- History of programming
- Programming languages
- Development environments
- From problem to algorithm
Module 2: Core Concepts
- Variables and data types
- Operators and expressions
- Input and output
- Type conversion and data validation
Module 3: Control Structures
Module 4: Functions and Procedures
- Defining and using functions
- Parameters and return values
- Variable scope
- Breaking a program down into functions
- Functions as values: lambda and higher order
Module 5: Data Structures
- Lists and arrays
- Strings
- Dictionaries and sets
- Tuples and nested structures
- Saving data to files: text, CSV and JSON
Module 6: Basic Algorithms
Module 7: Objects and Code Organisation
- From data to objects: classes and instances
- Attributes, methods and the constructor
- Collections of objects
- Modules, packages and imports
Module 8: Good Practices and Tools
- Documentation and comments
- Debugging and error handling
- Version control
- Automated testing
- Style, readability and refactoring
