Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .github/workflows/vale-docs-linter.yml
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,11 @@ jobs:
# github-pr-check, github-pr-review, github-check
reporter: github-pr-check
fail_on_error: false
# Pinned so a new Vale release can't change what the check does
# without a PR. 3.24.0 is what "latest" resolved to on 22 Oct 2026.
version: 3.24.0
# .vale.ini lists no packages, so there is nothing to download.
sync: false
env:
# Required, set by GitHub actions automatically:
# https://docs.github.com/en/actions/security-guides/automatic-token-authentication#about-the-github_token-secret
Expand Down
84 changes: 21 additions & 63 deletions .vale.ini
Original file line number Diff line number Diff line change
Expand Up @@ -6,80 +6,38 @@ MinAlertLevel = suggestion

SkippedScopes = script

# Pinned by release URL rather than tracking latest, so a new upstream version
# cannot start enforcing rules nobody has reviewed. `vale sync` fetches these,
# and the action runs it. `Packages` takes URLs but not name@version.
Packages = https://github.com/vale-cli/Google/releases/download/v0.6.3/Google.zip, https://github.com/vale-cli/proselint/releases/download/v0.3.4/proselint.zip, https://github.com/vale-cli/write-good/releases/download/v0.4.1/write-good.zip
# Only Fly's own style and Vale's built-in rules. The Google, proselint and
# write-good packages are gone: nearly all of their rules were already off,
# and the rest flagged things nobody acted on. With no packages there is
# nothing for `vale sync` to fetch, so the workflow skips it.
#
# What runs: Fly.WordList, the house vocabulary, and Vale.Repetition, which
# catches doubled words.

[*.{md,mdx,markerb}]
BasedOnStyles = Fly, Google, proselint, Vale, write-good
BasedOnStyles = Fly, Vale

# Fly rules that we can turn back on when other things get cleaned up
Fly.Exclamation = NO
Fly.Headings = NO
Fly.Latin = NO
Fly.Machine = NO # we can do an initial search and replace and then this rule will be less noisy and more useful
Fly.Machine = NO
Fly.OxfordComma = NO
Fly.SentenceLength = NO # turn on later; then reduce further?
Fly.Spelling = NO # off until the vocabulary covers MDX pages: 369 unflagged-before terms, mostly product and tool names
Fly.SentenceLength = NO
Fly.Spelling = NO # off for good: covering MDX pages meant vetting 369 terms, then maintaining the list
Fly.Us = NO

# other style stuff turned off temporarily
Google.Contractions = NO
Google.DateFormat = NO
Google.EmDash = NO
Google.EnDash = NO
Google.FirstPerson = NO
Google.HeadingPunctuation = NO
Google.LyHyphens = NO
Google.OptionalPlurals = NO
Google.Ordinal = NO
Google.Periods = NO
Google.Ranges = NO
Google.Slang = NO
Google.Spelling = NO
Vale.Avoid = NO # its one reject-list entry, healthcheck, is already in Fly.WordList
Vale.Repetition = warning # error by default, which shows a doubled word as a red annotation
Vale.Spelling = NO # Fly.Spelling would replace it, and that's off
Vale.Terms = NO # enforces vocab-term casing even inside code, and prints raw regex vocab entries as suggested fixes

proselint.But = NO
proselint.Cliches = NO
proselint.Typography = NO
proselint.Very = NO
# Generated in other repos, so a suggestion here can't be acted on in this
# one: flyctl/cmd comes from superfly/flyctl, models.mdx from the Machines spec.
[flyctl/cmd/*.mdx]
BasedOnStyles =

write-good.Passive = NO
write-good.So = NO
write-good.ThereIs = NO
write-good.TooWordy = NO


# Google style guide stuff that we're turning off or replacing permanently
Google.Acronyms = NO # we don't have a rule for acronyms yet and this is noisy
Google.AMPM = NO # don't need
Google.Colons = NO # don't need
Google.Ellipses = NO # don't need
Google.Exclamation = NO # replaced by Fly.Exclamation
Google.Gender = NO # we don't refer to gender in docs
Google.GenderBias = NO # we don't refer to gender in docs
Google.Headings = NO # replaced by Fly.Headings
Google.Latin = NO # replaced by Fly.Latin
Google.OxfordComma = NO # replaced by Fly.OxfordComma
Google.Parens = NO # triggered by links so not useful right now
Google.Passive = NO # duplicate of write-good.Passive
Google.Quotes = NO # too many false positives
Google.Semicolons = NO # don't need this
Google.Spacing = NO # extra spaces aren't rendered anyway
Google.Units = NO # we don't care about unit spacing right now
Google.We = NO # we are OK with "we" sometimes
Google.Will = NO # TBD whether to use this or not
Google.WordList = NO # replaced by Fly.WordList

# Write good styles turned off permanently
write-good.Cliches = NO # duplicate of proselint.Cliches
write-good.E-Prime = NO # too bossy and weird
write-good.Weasel = NO # too arbitrary

# Vale.Avoid = NO
Vale.Repetition = NO # replaced by good-write.Illusions which has an adjustable error level
Vale.Spelling = NO # replaced by Fly.Spelling
Vale.Terms = NO # noisy false positives: enforces vocab-term casing even inside code, and prints raw regex vocab entries as suggested fixes
[api/machines/models.mdx]
BasedOnStyles =

[formats]
markerb = md # maps our markerb file extension to md for linting
Expand Down
2 changes: 1 addition & 1 deletion blueprints/shared-nothing.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -279,7 +279,7 @@
so your users see something while they are waiting.
</Info>

If you go to https://smooth.fly.dev/ the server nearest to you will need to spin up the index application. And if, from there, you click on demo, a second application will be started. While you might get lucky and somebody else (or a bot) may have already started these for you, the normal case is that you will have to wait.

Check warning on line 282 in blueprints/shared-nothing.mdx

View workflow job for this annotation

GitHub Actions / Vale linter

[vale] reported by reviewdog 🐶 Consider using 'click' or 'click in' instead of 'click on'. Raw Output: {"message":"Consider using 'click' or 'click in' instead of 'click on'.","location":{"path":"blueprints/shared-nothing.mdx","range":{"start":{"line":282,"column":132},"end":{"line":282,"column":140}}},"severity":"INFO","code":{"value":"Fly.WordList"}}

Since all the services that are needed to support this application are on one machine, `fly deploy` can't simply start a new machine, wait for it to start, direct traffic to it, and only then start dismantling the previous machine. Instead, each machine needs to be taken offline, have the rootfs replaced with a new image, and all of its services restarted. Once that is complete, migrations need to be run on that machine; and in my case I may have several SQLite databases that need to be upgraded. I also have each machine that comes up rsync with the primary region. And finally, I generate an operational NGINX configuration and run [nginx reload](https://docs.nginx.com/nginx/admin-guide/basic-functionality/runtime-control/).

Expand All @@ -299,7 +299,7 @@
command.
</Info>

Now lets look at what happens when I create a new event, in a new region. I (a human) get an email, I bring up my admin UI (on an instance of the index app I mentioned above). I fill out a form for the new event. I go to a separate page and add a new region. I then go to a third form where I can review and apply the changes. This involves regenerating my map, and I need to update the NGINX configuration in every existing region. There are shortcuts I can utilize which will update files on each machine and reload the NGINX configuration, but I went that way I would need to ensure that the end result exactly matches the reproducible result that a subsequent `fly deploy` would produce. I don't need that headache, so I'm actually using `fly deploy` which can add tens of seconds to the actual deploy time.

Check warning on line 302 in blueprints/shared-nothing.mdx

View workflow job for this annotation

GitHub Actions / Vale linter

[vale] reported by reviewdog 🐶 Consider using 'use' instead of 'utilize'. Raw Output: {"message":"Consider using 'use' instead of 'utilize'.","location":{"path":"blueprints/shared-nothing.mdx","range":{"start":{"line":302,"column":466},"end":{"line":302,"column":473}}},"severity":"INFO","code":{"value":"Fly.WordList"}}

I started out running the various commands manually, but that grew old fast. So eventually
I invested in creating an admin UI.
Expand Down Expand Up @@ -347,7 +347,7 @@
Next up volumes. I have 9 machines with 3GB disks, and 2 machines that only need 1G each.
29GB at \$0.15 per month is \$4.35.

I have a dedicated IPv4 address in order to use ssh. This adds \$2.00 per month.
I have a dedicated IPv4 address to use ssh. This adds \$2.00 per month.

Outbound transfer is well under the free allowance, but for completeness I'm seeing about 16GB in North America and Europe,
which at \$0.02 per GB amounts to \$0.32. And about 0.1GB in Asia Pacific, which at \$0.04 per GB adds less than a cent,
Expand Down Expand Up @@ -437,5 +437,5 @@
## Related reading

- [Getting Started with N‑Tier Architecture](/blueprints/n-tier-architecture) A contrasting architecture pattern where state is shared across the data tier — useful for understanding when shared‑nothing *isn’t* the best fit.
- [Session Affinity (a.k.a. Sticky Sessions)](/blueprints/sticky-sessions) Focused on routing and state‑isolation patterns that often come up when you adopt a shared‑nothing approach and need to keep state local to a machine.

Check warning on line 440 in blueprints/shared-nothing.mdx

View workflow job for this annotation

GitHub Actions / Vale linter

[vale] reported by reviewdog 🐶 Consider using 'or' or 'also known as' instead of 'a.k.a'. Raw Output: {"message":"Consider using 'or' or 'also known as' instead of 'a.k.a'.","location":{"path":"blueprints/shared-nothing.mdx","range":{"start":{"line":440,"column":22},"end":{"line":440,"column":27}}},"severity":"INFO","code":{"value":"Fly.WordList"}}
- [Networking](/networking) The comprehensive networking overview (private networks, Anycast, WireGuard tunnels, routing) — helpful when building globally distributed isolated nodes in a shared‐nothing architecture.
2 changes: 1 addition & 1 deletion blueprints/staging-prod-isolation.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ All Fly.io accounts start with a "personal" organization. You can create as many

Before you create a new organization, here's what you need to know:

- You can consolidate billing for multiple organizations under a a single parent organization, or you can create regular organizations with separate payment methods and billing. Learn more about [unified billing](/about/billing#unified-billing).
- You can consolidate billing for multiple organizations under a single parent organization, or you can create regular organizations with separate payment methods and billing. Learn more about [unified billing](/about/billing#unified-billing).
- You invite or remove members in each organization separately.
- An organization can have multiple apps and those apps can communicate with each other securely over the org's private network.

Expand Down
3 changes: 0 additions & 3 deletions styles/Fly/WordList.yml
Original file line number Diff line number Diff line change
Expand Up @@ -18,19 +18,16 @@ swap:
# below: later|in the following steps
check box: checkbox
click on: click|click in
data are: data is
datatype: data type
datastore: data store
# filesystem: file system
firewalls: firewall rules
free tier: free allowances
functionality: capability|feature
healthcheck: health check
healthchecks: health checks
HTTPs: HTTPS
in order to: to
# instance: Machine
k8s: Kubernetes
leverage: use
Nodejs: Node.js
open-source: open source
Expand Down
Loading