Compare commits

...

20 Commits

Author SHA1 Message Date
08431fd6c6 Adds white token for thumbnail 2026-02-16 18:04:44 -08:00
7972692eff Adds black thumbnail token 2026-02-16 18:02:28 -08:00
e1b290d6bc Adds colored greater-good tokens 2026-02-16 17:36:16 -08:00
e769bbebff Adds marker tokens 2026-02-16 17:20:17 -08:00
cebf8b08dc Some draft work on vibe-coding-errors 2025-09-25 17:35:14 -07:00
551a9d286d Moves unpublished articles into a drafts folder. 2025-09-25 17:28:35 -07:00
54419e3808 Hides unpublished articles from the RSS 2025-09-15 16:01:17 -07:00
89aec92b2e Fixes compliation error on checking-in-on-2025 2025-09-15 15:54:01 -07:00
80082864a7 Fixes site root URL 2025-09-15 15:48:50 -07:00
3a26219434 Adds stub for vibe-coding article 2025-09-15 15:47:32 -07:00
a2e315413f Drafts for values and Checking in on 2025 2025-08-09 16:23:34 -07:00
89533e006f Fix layout for multiple blog entries. Adds max width. 2025-07-31 17:05:28 -07:00
8a73044c19 Fix pub gate on Forge of God 2025-07-31 15:29:18 -07:00
75c9322fd0 Fixes error due to missing date 2025-07-31 14:59:14 -07:00
96ee56fc1f Fix foooter stats 2025-07-31 14:51:11 -07:00
ae109330d9 Adds Forge of God Review 2025-07-18 20:33:07 -07:00
e73005968d Adds domain to the path for counter requests. 2025-07-10 15:29:09 -07:00
80ea47644c Adds test counter to footer. 2025-07-10 15:03:09 -07:00
f82fe9206f [I Forgot to use AI] Revisions. Publish. 2025-06-26 15:05:35 -07:00
b93123a8c9 Minor post fixes. Makes posts publishable with a date 2025-06-26 14:57:34 -07:00
28 changed files with 393 additions and 51 deletions

View File

@@ -7,11 +7,10 @@ import react from "@astrojs/react";
// https://astro.build/config // https://astro.build/config
export default defineConfig({ export default defineConfig({
site: "https://example.com", site: "https://www.blazestar.net",
integrations: [mdx(), sitemap(), react()], integrations: [mdx(), sitemap(), react()],
vite: { vite: {
plugins: [], plugins: [],
}, },
}); });

Binary file not shown.

After

Width:  |  Height:  |  Size: 44 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 62 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 37 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 41 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 46 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 41 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 41 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 11 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 57 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 62 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 70 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 62 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 11 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 62 KiB

View File

@@ -4,6 +4,15 @@ const today = new Date();
<footer> <footer>
&copy; {today.getFullYear()} Periodic. All rights reserved. &copy; {today.getFullYear()} Periodic. All rights reserved.
<script>
window.goatcounter = {
path: (path) => `${location.host}${path}`,
};
</script>
<script
data-goatcounter="https://goatcounter.blazestar.net/count"
async
src="https://goatcounter.blazestar.net/count.js"></script>
</footer> </footer>
<style> <style>
footer { footer {

View File

@@ -10,7 +10,8 @@ const blog = defineCollection({
title: z.string(), title: z.string(),
description: z.string(), description: z.string(),
// Transform string to Date object // Transform string to Date object
pubDate: z.coerce.date(), // Presence of this value indicates that the post is published
pubDate: z.coerce.date().optional(),
updatedDate: z.coerce.date().optional(), updatedDate: z.coerce.date().optional(),
heroImage: image().optional(), heroImage: image().optional(),
}), }),

View File

@@ -0,0 +1,163 @@
---
title: "Checking in on 2025 - Where we are and where we are headed."
description: "At the beginning of the year I made a few predictions about where things were headed. It's been a chaotic and tumultuous seven months. It's worth reviewing my predictions to see how they have borne out, where they were accurate, where they were incorrect and what I may have missed."
---
I was lost at the start of the year. I couldn't see forward. Donald Trump had just recently won the presidency and was poised to unleash chaos on the U.S. government and global economy. It was hard to imagine what 2025 would look like. So much was uncertain (and still is). I sat down and attempted to gather some of the forces that I could see creating pressure on the systems of the world so that I could get some idea of where things were heading so that I could plan.
These aren't really predictions as much as an observation of pressures on the system. I didn't write down "the California fire-insurance market will collapse" as much as I wrote that climate change was going to create an increasing number of disasters and strain the insurance market.
So how well did I recognize these forces? All the ones I mention seem to still be significant. That's not really a surprise. Recognizing large forces is not hard and it's likely that they will continue to exist in six months.
Where I was most wrong was in what I missed. The things I didn't predict are the ones that will cause the most chaos because they are the ones I couldn't plan for. It's not the predictions that surprise us, it's the things we didn't predict.
## Predictions for 2025
### Growing wealth inequality
Wealth inequality has been growing in the US. This means that there are fewer people who are able to spend and drive the economy. This has a lot of knock-on effects where markets are splitting into low-end and high-end with little in the middle.
Examples:
- Lambos
- Free-to-play games
- <https://www.marketplace.org/2025/01/13/magnificent-seven-ai-stocks-make-up-a-huge-part-of-the-sp-500-artificial-intelligence/>
### Climate Change
The world's climate is becoming more extreme and unpredictable. The world also doesn't seem like it's towards addressing it. We are in for more extreme weather situations.
Examples:
- Pacific Palisade's fire
- <https://arstechnica.com/cars/2025/01/only-5-percent-of-us-car-buyers-want-an-ev-according-to-survey/>
- <https://arstechnica.com/science/2025/01/its-official-2024-was-the-warmest-year-on-record/>
- [How Climate Denial is Fueling a U.S. Homeowners Insurance Crisis and Risking a 2008-Style Financial Meltdown](https://www.nakedcapitalism.com/2025/02/how-climate-denial-is-fueling-a-u-s-homeowners-insurance-crisis-and-risking-a-2008-style-financial-meltdown.html)
- [Blackouts Are Becoming the Norm Can the U.S. Power Grid Be Saved](https://www.nakedcapitalism.com/2025/02/blackouts-are-becoming-the-norm-can-the-u-s-power-grid-be-saved.html)
Threats:
- Bigger natural disasters
- Strained insurance systems
### Conservative Themes Increase
- Xenophobia
- Transphobia
- Racism
- Misogyny
- Nationalism
- Religious division
Examples:
- Twitter
- Trump
- Facebook
- Far-right media
- <https://www.foxbusiness.com/media/mark-zuckerberg-praises-benefits-masculine-energy-calls-corporate-america-culturally-neutered>
### Economic uncertainty
- <https://www.marketplace.org/2025/02/18/new-car-sales-drop-in-january-as-dealer-lots-fill-up/>
- <https://www.marketplace.org/2025/02/17/homebuyer-demand-down-listings-housing-market-confidence-uncertainty-inflation-interest-rates/>
### Inequality and Extraction
#### Continued Automation, Off-shoring and AI
Jobs continue to be off-shored or replaced. Worker productivity is going up, but there are fewer jobs in the US.
Examples:
-
#### Capital's growing power over labor
The capital owners have more and more leverage over workers. This comes from many people looking for work and companies being able to get away with more and more consolidation, meaning fewer potential employers who can abuse workers more.
There are some attempts to push back in the form of union drives, but the incoming administration is hostile to worker power.
Examples:
- Gig work
- Retirement is getting harder
- Fight for higher minimum wages
Effects:
- Harder to switch jobs
- Lower benefits
- Growing assets as companies are more profitable
#### Rising cost-of-living
Costs will increase, and not come down any time soon.
The Easton Fire this year will all but ensure that housing prices will remain high due to the lower stock and large number of displaced people. Supplies and labor will be tied up for years.
Examples:
- Housing
- Eggs
- Education
#### Increasing household debt
Is there a crash that would happen? Probably not because there's low risk of contagion on wall street.
#### Deteriorating Health Insurance
Healthcare in the US is getting harder to get and more expensive. We seem to be reaching the point that it is becoming a national crisis. It seems unlikely that our government will make meaningful reforms since thee area is very profitable.
Examples:
- Price of insulin
- Increased claim denials
- Luigi Mangione
### Technology
#### Continued growth of AI
AI will continue to grow over the next year. It will be searching for use cases and will refine the ones it has already. Agentic AI will continue to improve.
I think it's unlikely there will be any major leaps forward.
<https://www.marketplace.org/2025/01/13/magnificent-seven-ai-stocks-make-up-a-huge-part-of-the-sp-500-artificial-intelligence/>
#### Cryptocurrency
This will gain strength over the next year, but remain niche. Prices will continue to rise for the major currencies, even as scams and rug-pulls continue.
## What I missed
### Economic Chaos
- Tariffs
- Export controls
- Dropping regulatory enforcement
- Mass layoffs
Counter-acting forces
- The Fed has stayed largely independent
### Crackdown on Facts and Dissenting Opinions
- CBS capitulation
- Trump's war against any who disagree
- Firing of BLS director over poor jobs numbers
- Rewriting of federal information to align with ideological goals
- Installing more partisan oversight in agencies
- Attacks on universities and funding
- De-funding of CPB
- RFK and the health services
### Decreased rule of law
- Pardons
- Dropping of cases
- Bribes
- Extortion law suits, e.g. CBS.
- Likely illegal firing of appointees

View File

@@ -0,0 +1,36 @@
---
title: "5 Types of AI Coding Tech Debt"
description: "AI coding assistants, or even vibe-coding agents, can create a lot of code very quickly and get features done fast. However, there are a few common ways in which vibe-coding projects tend to go off the rails and end up mired in tech-debt hell. The AI doesn't prevent you from accumulating tech-debt, in fact it allows you to create more of it more quickly. I go over a few common issues with AI code that causes it to lose it's luster on large or long projects."
---
1. Concepts
1. ROI
1. Refer to the Glyph's article.
1. Net-positive and net-negative programmers
1. Simplicity and Complexity
1. Transparency
1. Some of the ways AI fails
1. Testing
1. Debugging and logging
1. Libraries and common code
1. Performance
1. Abstract structure
1. Real-world/Domain modeling
1. How do we fix it?
1. Functional tests
2. Enforce good debugging practices
3. Build your own libraries
4. Build real-world performance tests
5. You gotta know how to design it
### Domain Modeling
While the AI can be very good at getting some code to run. It's like having an assistant who lives in another country that you only interact with through chat. Not even another country. It's like an assistant who was born in a fallout shelter and has only ever interacted with the world through a text terminal. Their entire life they have been sitting, hunched over a black screen with green text reading and reading to learn everything they can. But it's also pitch black down their. They've never _seen_ anything.
You have to tell them everything you want them to know about your specific case. Let's say you are modeling some sort of supply chain logistics. They've never actually worked on a supply chain. They've never seen a ship. They've never been annoyed by a late order or a project falling behind due to a shipping mishap. All they know is what they have read.
More than that, they have never read anything about your specific case. They only know what you have told them. You might think that this is at least as good as an intern, but even that intern sits in on meetings, chats with people in the halls, and observes the company functioning around them. They also have an intuitive grasp of things like space and time. They may have seen the ships sitting out in the harbor and realize just how hard those are to turn around.
The AI doesn't have any of that. It only knows what it's read. You have to tell it _everthing_ it needs to know in order to write code that corresponds to whatever problem you want to solve.
AI sucks at domain modeling because it has no understanding of the domain. All it can do is imitate models it's read about that might sound similar.

View File

@@ -0,0 +1,27 @@
---
title: "The Forge of God by Greg Bear"
description: "A short review"
pubDate: "Jul 18 2025"
---
[The Forge of God](https://en.wikipedia.org/wiki/The_Forge_of_God) by [Greg Bear](https://en.wikipedia.org/wiki/Greg_Bear) is a bit of an old book to be reviewing now. It was first published in 1987 and it's 2025 now. Did I pick it up without realizing this? Was a stricken with an acute case of nostalgia? Was I trapped in an abandoned house with nothing else to read? Dear reader, I assure you that nothing so exciting happened. I simply saw it on my shelf and decided to read it. I don't need any other reason that that.
As an aside, this is one of the values of having a shelf of books. I was at home one evening, I wanted something to read, and there it was. I didn't have to go find something to download onto my Kindle. I didn't have to even boot up my phone. I had an honest-to-god paper-bound book right there to choose from. I will always keep good books around for just such an occasion.
I probably first read the book about 20 years ago. That may or may not have been when I picked up this copy. I had a short Greg Bear kick where I read a many of his novels. It had been long enough that I had completely forgotten the plot. In fact, I picked this up thinking it was going to be a different novel (Eon) and it took me a few dozen pages to realize that I was reading something I had little to no recollection of. What's better than reading a good book? Getting to read it twice!
Many Sci-Fi novels like to take an established world or trope and tweak it just a bit. What if we had an epic battle of good and evil, but in space? You'd get Star Wars. What if you lived forever and could travel around anywhere in time and space? Doctor Who. What if we could clone animals from fossilized DNA? Jurassic Park. It's a fun little thought experiment to think how things would be if something were familiar but a bit different.
That's not what Greg Bear does at all. What I love about his novels is that they take a premise and follow it out beyond the logical conclusion. It leads you somewhere uncomfortable and alien. But that's exactly what the universe is. It's easy to imagine something familiar. It's a challenge to the writer and reader to imagine something unfamiliar.
The Forge of God addresses the usual trope of first contact with aliens. This has been rehashed so many times. I recently watched Arrival and it's a pretty predictable plot where the aliens arrive, there's a struggle to communicate, then the aliens impart a gift and leave and we are left with the impression that humanity is young but has much potential. The Forge of God asks, "what if the aliens were going to destroy the planet and there was nothing we could do about it?"
It's a frightening prospect, but it's real. Rogue asteroids, climate change, solar flares, the reality is that we have very little control over the world around us. There as many forces that are bigger and more powerful than anything that we can deal with. And that's even if we could all band together as a planet to defend ourselves, which seems unlikely given the state of world politics.
The book has an ensemble cast that has to confront their own powerlessness in the large and must embrace their power in the small. It is ultimately an uplifting tale about how humans can continue to find their own meaning, purpose and agency even in the face of so many things out of our control. And that's really an honest message.
Many stories want you to feel good in the end about how we'd all band together and win and everything will be okay. Life isn't like that. We are each one person moving through a vast, powerful, dangerous and wondrous world. There will be many things that we have to accept and it's up to us to figure out how we live, hope and dream within that framework.
That's what I see as the main theme of this book. It's one that exists in a lot of Greg Bear's work and I think it's what makes him such a compelling author.
And just as a note, the book mostly holds up after almost four decades. Sure, we have a lot more computing power now, but all the characters are still believable and relatable.

View File

@@ -1,28 +1,32 @@
--- ---
title: "I Forgot to Use AI On My Latest Project" title: "I Forgot to Use AI On My Latest Project"
description: "I forgot to use an LLM to assist on my latest coding project. I probably set the progress of humanity back many hours. But hey, I learned something along the way. What did I learn? That I'd rather not use an LLM on this project." description: "I forgot to use an LLM to assist on my latest coding project. I probably set the progress of humanity back many hours. But hey, I learned something along the way. What did I learn? That I'd rather not use an LLM on this project."
pubDate: "Jun 21 2025" pubDate: "Jun 26 2025"
--- ---
I forgot to use AI on my last project. All the tech bros are laughing at me right now. I'm sure in the time I wasted I could have launched a cloud-based passive-income app, but now I have to have fun staying poor. I'll cry myself to sleep right after I get the satisfaction of learning something new and building something with my own mind. I forgot to use AI on my last project. All the tech bros are laughing at me right now. I'm sure in the time I wasted I could have launched a cloud-based passive-income app, but now I'll just have fun staying poor. I'll cry myself to sleep right after I get the satisfaction of learning something new and building something with my own mind.
## Building something new just like everything else ## Building something new just like everything else
I finally decided that I should have a blog. Yes, here we are in 2025, approximately 20 years after the blog craze started and about 10 years after it ended. What better time to start a blog than in an era when content is more plentiful than other and simultaneously harder to find and discover? It's actually a perfect time because it's a perfect time for me. I finally decided that I should have a blog. Yes, here we are in 2025, approximately 20 years after the blog craze started and about 10 years after it ended. What better time to start a blog than in an era when content is the most plentiful and simultaneously harder to find and discover?
I've spent the last two decades mostly working in corporate tech. All my energy and productivity has been directed into those corporations. I've written so many detailed design docs, posted many impassioned Slack memos, carefully hand-crafted status reports. But guess what? No one really cared. A few years later they were lost in the depths of Google Drive or the Slack archives, waiting for some new employee to stumble upon them when desperately searching for an answer to how things got the way they were. Ultimately they weren't useful. Did they really reach anyone? I would like to think so, but they never had a life of their own. They were never durable, they never lasted. It's a perfect time because it's a perfect time for me.
I find I have a lot more creative energy that can be directed at the world now that I've left my corporate life behind. I'm going to start creating things that I think are meaningful. They will be meaningful to me and hopefully someone else can get some value from them as well. I've spent the last two decades mostly working in corporate tech. All my energy and productivity has been directed into those corporations. I've written so many detailed design docs, posted many impassioned Slack memos, carefully hand-crafted status reports.
But guess what? No one really cared. A few years later they were lost in the depths of Google Drive or the Slack archives, waiting for some new employee to stumble upon them when desperately searching for an answer to how things got the way they are. Did they really reach anyone? Did they ever really affect anyone? I would like to think so, but they never had a life of their own. They were never durable, they never lasted.
I have a lot more creative energy now that I've left my corporate life behind. It's energy I can start directing out into the world instead of inward towards an organization. I'm going to start creating things that I think are meaningful. They will be meaningful to me and hopefully someone else can get some value from them as well.
## How to build a blog in 2025 ## How to build a blog in 2025
I'm sure the correct answer for 99% of people is to throw something up on Medium or Substack, but I like to do things differently. I'm sure the best answer for 99% of people starting a blog is to throw up a Medium or Substack page. I like to do things differently.
I like to really understand and own my tools. This gives me a greater level of control, but really it just brings me joy. There's a pride that I can take in carefully crafting my solution. There's a joy to understanding all the choices that went into it. Sure, I could take a template off the shelf and slap it on an existing solution. It would probably be good enough, but I wouldn't know a single thing about how to update it. Why did they choose that font or margins? Why does it load data in this way or that? I like to really understand and own my tools. This gives me a greater level of control, but really it just brings me joy. There's a pride that I can take in carefully crafting my solution. There's a joy to understanding all the choices that went into it. Sure, I could take a template off the shelf and slap it on an existing solution. It would probably be good enough, but I wouldn't know a single thing about it. Why did they choose that font or margins? Why does it load data in this way or that? Why is it so slow?
It's been a while since I did any heavy front-end work. I've spent the last year or so doing back-end work in Rust, so I'm a little rusty on my CSS flex-box and grid syntax. It was time to get back to my roots and get online. It's been a while since I did any heavy front-end work. I've spent the last year or so doing back-end work in Rust, so I'm a little rusty on my CSS flex-box and grid syntax. It was time to get back to my roots and get online.
I've heard some good things about Astro, so I decided to give that one try. I also had to figure out if this Tailwind thing was worth it. I'll also have to write a bunch of HTML and CSS, and some TypeScript. I've heard some good things about Astro, so I decided to give that one try. I also have to figure out if this Tailwind thing is worth it. I'll also have to remember a bunch of HTML, CSS, and some TypeScript.
## Time to Learn ## Time to Learn
@@ -30,20 +34,22 @@ So now I'm ready to sit down and get this started. I _could_ set up an agentic L
Or I could just RTFM. Or I could just RTFM.
Or I could just start building things.
So that's what I did. I didn't even reach for the AI. So that's what I did. I didn't even reach for the AI.
I wanted to _understand_ what I was doing. That meant I wanted to have documentation open, I wanted to read a few examples, but most of all I wanted to play with it. I understand things best when I can manipulate them with my own two hands. (My own keyboard? Editor? You get the idea.) I wanted to _understand_ what I was doing. That meant I wanted to have documentation open, I wanted to read a few examples, but most of all I wanted to play with it. I understand things best when I can manipulate them with my own two hands. (My own keyboard? Editor? You get the idea.)
So I sit down and I try a few things. I load it up in my browser. I try a few other things. I play with it. I get something working, but maybe that's not the best way, so let's see if another way works too. I build and iterate. It's like a potter shaping clay. There's a feedback where I can shape the code and see the outcome and try something else. I even looked at some of the source code because I wanted to understand exactly what was going on under the hood. So I sit down and I try a few things. I load it up in my browser. I try a few other things. I play with it. I get something working, but maybe that's not the best. Let's see if another way works too. I build and iterate. It's like a potter shaping clay. There's a feedback where I can shape the code and see the outcome and try something else. It's putty in my hands. I even looked at some of the source code because I wanted to understand exactly what was going on under the hood.
## Play = Learning ## Play = Learning
It was great. I had a lot of fun. I could have had something published faster if I stuck to some common templates and used an AI to generate the code for me, but I wouldn't have enjoyed it. I wouldn't have learned. I had a lot of fun. I could have had something published faster if I stuck to some common templates and used an AI to generate the code for me, but I wouldn't have enjoyed it. I wouldn't have learned. I wouldn't know anything new.
Now I'm equipped so that the next one I build will be even better. When something breaks I'll know why and I'll know exactly how to fix it. I understand the code much more deeply than if something had generated it for me. I have a mental model of how all the little pieces fit together. Now I'm equipped so that the next one I build will be even better. When something breaks I'll know why and I'll know exactly how to fix it. I understand the code much more deeply than if something had generated it for me. I have a mental model of how all the little pieces fit together.
That's something the AI can't give me. LLMs are inherently conservative and reinforcing. They are built to tell you the most likely next thing given what you told them before. They are built to agree with you and continue your line of thought, not challenge it. That's something the AI can't give me. LLMs are inherently conservative and reinforcing. They are built to tell you the most likely next thing given what you told them before. They are built to agree with you and continue your line of thought, not challenge it.
The only way to really learn is to try things. It requires failing. It requires playing with it, poking it and seeing what falls over and what stays standing. You'll never build an intuition if you don't build it yourself. The only way to really learn is to try things. It requires failing. It requires playing with it, poking it and seeing which combination of blocks falls over and which stays standing. You'll never build an intuition if you don't build it yourself.
So my goal was never something an LLM could help me with, and that means I wasn't missing out on anything. My goal was never something an LLM could help me with, and that means I wasn't missing out on anything.

View File

@@ -0,0 +1,73 @@
---
title: Values
---
I am doing an experiment with trying to clearly define my values so that I can
know when I am living up to them.
The psychologist [Carl Rogers](https://en.wikipedia.org/wiki/Carl_Rogers)
described the idea of congruence/incongruence. It's roughly the difference
between your lived self and your ideal self. It's the difference between "I
am" and "I should". Incongruence, a large gap between the two, leads to a
tension between what you are doing and what you think you should be doing. I
believe that everyone will be happier and experience more of their potential if
they are living and growing in line with their ideals.
## My Values
### Equity
- Everyone should have the means to live a healthy and meaningful life.
- This applies to people now and in the future.
- Everyone should have a fair voice in decisions that affect them.
### Integrity
- Take responsibility for your own actions.
- Hold others accountable and responsible for their actions.
- Give honest feedback.
- Take the time to do good work.
- Be proud of your work.
- Be your authentic self.
### Sustainability and long-term thinking
- Think not about the short- or long-term, but about the equilibrium, the forever-term.
- Do not sacrifice the future for the present.
- Do not sacrifice the present for the future.
### Cooperation over competition
- We build better when we work together.
- We can challenge each other without having to compete.
- Resources should not be scarce.
- Share information, materials and goods.
- Hold others responsible for sharing alike.
### Self-improvement
- Be curious and motivated to learn and understand.
- Be open to feedback and learning.
- Learn new things.
- Seek to understand.
- Embrace failure as an opportunity to learn.
- Take the time to review and retrospect.
- Help others learn and grow by giving them resources, training and feedback.
### Self-reliance
- Enable everyone to work with minimal interruption by reducing the dependence on each other.
- We should work together but not be dependent on one another.
- Many strong units weakly coupled are more resilient than rigid or hierarchical structures.
- Invest in your health and stability.
## Corollaries
### Environmentalism
- We must preserve our planet so that future people will have at least the same opportunities we currently do.
### Anti-capitalism
- Modern capitalism is a system that is built on and perpetuates inequity.
- Modern capitalism creates and exploits dependency.

View File

@@ -20,7 +20,7 @@ const { title, description, pubDate, updatedDate, heroImage } = Astro.props;
<div class="prose"> <div class="prose">
<div class="title"> <div class="title">
<div class="date"> <div class="date">
<FormattedDate date={pubDate} /> { pubDate && <FormattedDate date={pubDate} /> }
{ {
updatedDate && ( updatedDate && (
<div class="last-updated-on"> <div class="last-updated-on">

View File

@@ -57,6 +57,7 @@ const { title = SITE_TITLE, description = SITE_DESCRIPTION } = Astro.props;
"footer footer"; "footer footer";
grid-template-columns: 20rem 1fr; grid-template-columns: 20rem 1fr;
margin: 2rem 1rem; margin: 2rem 1rem;
max-width: 1600px;
} }
.header { .header {
display: none; display: none;

View File

@@ -1,11 +1,16 @@
--- ---
import NotchedBox from '../../components/NotchedBox.astro'; import NotchedBox from '../../components/NotchedBox.astro';
import RootLayout from '../../layouts/RootLayout.astro'; import RootLayout from '../../layouts/RootLayout.astro';
import { getCollection } from 'astro:content'; import { getCollection, type CollectionEntry } from 'astro:content';
import FormattedDate from '../../components/FormattedDate.astro'; import FormattedDate from '../../components/FormattedDate.astro';
import { Image } from 'astro:assets'; import { Image } from 'astro:assets';
const posts = (await getCollection('blog')).sort( function publishedOnly(p: CollectionEntry<'blog'>): p is (CollectionEntry<'blog'> & { data: { pubDate: Date }}) {
return p.data.pubDate !== undefined;
}
const posts = (await getCollection('blog', publishedOnly))
.sort(
(a, b) => b.data.pubDate.valueOf() - a.data.pubDate.valueOf(), (a, b) => b.data.pubDate.valueOf() - a.data.pubDate.valueOf(),
); );
--- ---
@@ -16,6 +21,17 @@ const posts = (await getCollection('blog')).sort(
list-style: none; list-style: none;
margin: 0; margin: 0;
padding: 0; padding: 0;
display: flex;
flex-direction: column;
gap: 16px;
align-items: stretch;
li {
/* Required since flex won't render list-elements correctly. */
display: block;
}
a { a {
text-decoration: none; text-decoration: none;
@@ -32,6 +48,7 @@ const posts = (await getCollection('blog')).sort(
margin: 0; margin: 0;
} }
} }
a:hover .title { a:hover .title {
color: var(--color-accent); color: var(--color-accent);
} }
@@ -55,7 +72,8 @@ const posts = (await getCollection('blog')).sort(
{ post.data.description && { post.data.description &&
<p class="description"> <p class="description">
{post.data.description} {post.data.description}
</p>} </p>
}
</div> </div>
</NotchedBox> </NotchedBox>
</a> </a>

View File

@@ -1,16 +0,0 @@
import rss from '@astrojs/rss';
import { getCollection } from 'astro:content';
import { SITE_TITLE, SITE_DESCRIPTION } from '../consts';
export async function GET(context) {
const posts = await getCollection('blog');
return rss({
title: SITE_TITLE,
description: SITE_DESCRIPTION,
site: context.site,
items: posts.map((post) => ({
...post.data,
link: `/blog/${post.id}/`,
})),
});
}

25
src/pages/rss.xml.ts Normal file
View File

@@ -0,0 +1,25 @@
import rss from "@astrojs/rss";
import { SITE_TITLE, SITE_DESCRIPTION } from "../consts";
import { getCollection, type CollectionEntry } from "astro:content";
import type { AstroUserConfig } from "astro";
function publishedOnly(
p: CollectionEntry<"blog">,
): p is CollectionEntry<"blog"> & { data: { pubDate: Date } } {
return p.data.pubDate !== undefined;
}
export async function GET(context: AstroUserConfig) {
const posts = (await getCollection("blog", publishedOnly)).sort(
(a, b) => b.data.pubDate.valueOf() - a.data.pubDate.valueOf(),
);
return rss({
title: SITE_TITLE,
description: SITE_DESCRIPTION,
site: context.site as string,
items: posts.map((post) => ({
...post.data,
link: `/blog/${post.id}/`,
})),
});
}

View File

@@ -44,8 +44,8 @@
@font-face { @font-face {
font-family: "Fira Code"; font-family: "Fira Code";
src: src:
url("woff2/FiraCode-Light.woff2") format("woff2"), url("/fonts/FiraCode-Light.woff2") format("woff2"),
url("woff/FiraCode-Light.woff") format("woff"); url("/fonts/FiraCode-Light.woff") format("woff");
font-weight: 300; font-weight: 300;
font-style: normal; font-style: normal;
} }
@@ -53,8 +53,8 @@
@font-face { @font-face {
font-family: "Fira Code"; font-family: "Fira Code";
src: src:
url("woff2/FiraCode-Regular.woff2") format("woff2"), url("/fonts/FiraCode-Regular.woff2") format("woff2"),
url("woff/FiraCode-Regular.woff") format("woff"); url("/fonts/FiraCode-Regular.woff") format("woff");
font-weight: 400; font-weight: 400;
font-style: normal; font-style: normal;
} }
@@ -62,8 +62,8 @@
@font-face { @font-face {
font-family: "Fira Code"; font-family: "Fira Code";
src: src:
url("woff2/FiraCode-Medium.woff2") format("woff2"), url("/fonts/FiraCode-Medium.woff2") format("woff2"),
url("woff/FiraCode-Medium.woff") format("woff"); url("/fonts/FiraCode-Medium.woff") format("woff");
font-weight: 500; font-weight: 500;
font-style: normal; font-style: normal;
} }
@@ -71,8 +71,8 @@
@font-face { @font-face {
font-family: "Fira Code"; font-family: "Fira Code";
src: src:
url("woff2/FiraCode-SemiBold.woff2") format("woff2"), url("/fonts/FiraCode-SemiBold.woff2") format("woff2"),
url("woff/FiraCode-SemiBold.woff") format("woff"); url("/fonts/FiraCode-SemiBold.woff") format("woff");
font-weight: 600; font-weight: 600;
font-style: normal; font-style: normal;
} }
@@ -80,8 +80,8 @@
@font-face { @font-face {
font-family: "Fira Code"; font-family: "Fira Code";
src: src:
url("woff2/FiraCode-Bold.woff2") format("woff2"), url("/fonts/FiraCode-Bold.woff2") format("woff2"),
url("woff/FiraCode-Bold.woff") format("woff"); url("/fonts/FiraCode-Bold.woff") format("woff");
font-weight: 700; font-weight: 700;
font-style: normal; font-style: normal;
} }
@@ -89,8 +89,8 @@
@font-face { @font-face {
font-family: "Fira Code VF"; font-family: "Fira Code VF";
src: src:
url("woff2/FiraCode-VF.woff2") format("woff2-variations"), url("/fonts/FiraCode-VF.woff2") format("woff2-variations"),
url("woff/FiraCode-VF.woff") format("woff-variations"); url("/fonts/FiraCode-VF.woff") format("woff-variations");
/* font-weight requires a range: https://developer.mozilla.org/en-US/docs/Web/CSS/CSS_Fonts/Variable_Fonts_Guide#Using_a_variable_font_font-face_changes */ /* font-weight requires a range: https://developer.mozilla.org/en-US/docs/Web/CSS/CSS_Fonts/Variable_Fonts_Guide#Using_a_variable_font_font-face_changes */
font-weight: 300 700; font-weight: 300 700;
font-style: normal; font-style: normal;
@@ -151,7 +151,7 @@ p {
margin-bottom: 1em; margin-bottom: 1em;
} }
.prose p { .prose p {
margin-bottom: 2em; margin-bottom: 1em;
} }
textarea { textarea {
width: 100%; width: 100%;