1
0
mirror of https://github.com/jbranchaud/til synced 2026-01-04 23:58:01 +00:00

Compare commits

...

19 Commits

Author SHA1 Message Date
sandeep singh negi
ab46fef965 Merge cea4ffc0a3 into db07125ba9 2025-03-27 11:15:07 +00:00
jbranchaud
db07125ba9 Add Output CLI Results In Different Formats as an AWS TIL 2025-03-25 10:53:22 -05:00
jbranchaud
b6cf4ba0ad Add Search Tabs With The Vimium Vomnibar as a Chrome TIL 2025-03-24 20:22:52 -05:00
jbranchaud
e4d695e465 Add Show Reconstructed Constraints For A Table as a Postgres TIL 2025-03-22 12:02:03 -05:00
jbranchaud
5c9a3888fd Add Find And Copy A Value From Large JSON Output as a Unix TIL 2025-03-21 10:22:50 -05:00
jbranchaud
22541826d6 Add Go To Beginning And End Of Line as a Vim TIL 2025-03-19 11:50:10 -05:00
jbranchaud
b39ee94c90 Add Run SQL Script Against Postgres Container as a Docker TIL 2025-03-19 09:50:23 -05:00
jbranchaud
efad7da916 Add Turn Off Output Pager For A Command as an AWS TIL 2025-03-18 18:34:11 -05:00
jbranchaud
ca3327bda3 Add Show The Bundler Location Of An Installed Gem as a Ruby TIL 2025-03-18 11:05:38 -05:00
jbranchaud
595ac85f17 Add Fetch Data From An Endpoint In SQL as a Postgres TIL 2025-03-17 17:31:32 -05:00
jbranchaud
92d732c769 Add Check Postgres Version Running In Docker Container as a Docker TIL 2025-03-15 14:03:55 -05:00
jbranchaud
d6ebe52523 Add Run A Command With Specific Tool Version as a Mise TIL 2025-03-14 16:34:39 -05:00
jbranchaud
93398ab950 Add Add Color To The IRB Console Prompt as a Rails TIL 2025-03-13 10:31:32 -05:00
jbranchaud
b1b2aa8982 Add Break Debugger On First Line Of Program as a Python TIL 2025-03-12 10:35:08 -05:00
jbranchaud
6cbf1cb974 Add Download A Google Doc As Specific Format as an Internet TIL 2025-03-11 17:03:40 -05:00
jbranchaud
79faae1047 Add Create Umbrella Task For All Test Tasks as a Mise TIL 2025-03-10 18:07:38 -05:00
sandeep singh negi
cea4ffc0a3 Update README.md 2021-03-27 23:24:13 +05:30
sandeep singh negi
b325522d06 Update README.md 2021-03-27 23:22:35 +05:30
sandeep singh negi
f9efe3174f Update README.md 2021-03-27 23:21:48 +05:30
16 changed files with 583 additions and 3 deletions

View File

@@ -2,15 +2,15 @@
> Today I Learned
A collection of concise write-ups on small things I learn day to day across a
variety of languages and technologies. These are things that don't really
A collection of concise write-ups on small things I learn day to day across a
variety of languages and technologies. These are things that don't
warrant a full blog post. These are things I've picked up by [Learning In
Public™](https://dev.to/jbranchaud/how-i-built-a-learning-machine-45k9) and
pairing with smart people at Hashrocket.
For a steady stream of TILs, [sign up for my newsletter](https://crafty-builder-6996.ck.page/e169c61186).
_1613 TILs and counting..._
_1628 TILs and counting..._
See some of the other learning resources I work on:
- [Ruby Operator Lookup](https://www.visualmode.dev/ruby-operators)
@@ -114,8 +114,10 @@ If you've learned something here, support my efforts writing daily TILs by
- [AWS CLI Requires Groff Executable](aws/aws-cli-requires-groff-executable.md)
- [Find And Follow Server Logs](aws/find-and-follow-server-logs.md)
- [Output CLI Results In Different Formats](aws/output-cli-results-in-different-formats.md)
- [Sign Up User With Email And Password](aws/sign-up-user-with-email-and-password.md)
- [SSH Into An ECS Container](aws/ssh-into-an-ecs-container.md)
- [Turn Off Output Pager For A Command](aws/turn-off-output-pager-for-a-command.md)
- [Use Specific AWS Profile With CLI](aws/use-specific-aws-profile-with-cli.md)
### Brew
@@ -136,6 +138,7 @@ If you've learned something here, support my efforts writing daily TILs by
- [Navigate The Browser History With Vimium](chrome/navigate-the-browser-history-with-vimium.md)
- [Pretty Print Tabular Data](chrome/pretty-print-tabular-data.md)
- [Reference The Selected Node](chrome/reference-the-selected-node.md)
- [Search Tabs With The Vimium Vomnibar](chrome/search-tabs-with-the-vimium-vomnibar.md)
- [Selecting DOM Elements Faster Than Ever](chrome/selecting-dom-elements-faster-than-ever.md)
- [Simulating Various Connection Speeds](chrome/simulating-various-connection-speeds.md)
- [Toggle Device Mode](chrome/toggle-device-mode.md)
@@ -224,10 +227,12 @@ If you've learned something here, support my efforts writing daily TILs by
### Docker
- [Check Postgres Version Running In Docker Container](docker/check-postgres-version-running-in-docker-container.md)
- [Configure Different Host And Container Ports](docker/configure-different-host-and-container-ports.md)
- [List Running Docker Containers](docker/list-running-docker-containers.md)
- [Prevent Containers From Running On Startup](docker/prevent-containers-from-running-on-startup.md)
- [Run A Basic PostgreSQL Server In Docker](docker/run-a-basic-postgresql-server-in-docker.md)
- [Run SQL Script Against Postgres Container](docker/run-sql-script-against-postgres-container.md)
### Drizzle
@@ -495,6 +500,7 @@ If you've learned something here, support my efforts writing daily TILs by
- [Analyze Your Website Performance](internet/analyze-your-website-performance.md)
- [Check Your Public IP Address](internet/check-your-public-ip-address.md)
- [Digraph Unicode Characters Have A Titlecase](internet/digraph-unicode-characters-have-a-titlecase.md)
- [Download A Google Doc As Specific Format](internet/download-a-google-doc-as-specific-format.md)
- [Enable Keyboard Shortcuts In Gmail](internet/enable-keyboard-shortcuts-in-gmail.md)
- [Exclude AI Overview From Google Search](internet/exclude-ai-overview-from-google-search.md)
- [Exclude Whitespace Changes From GitHub Diffs](internet/exclude-whitespace-changes-from-github-diffs.md)
@@ -692,9 +698,11 @@ If you've learned something here, support my efforts writing daily TILs by
### Mise
- [Create Umbrella Task For All Test Tasks](mise/create-umbrella-task-for-all-test-tasks.md)
- [List The Files Being Loaded By Mise](mise/list-the-files-being-loaded-by-mise.md)
- [Preserve Color Output For Task Command](mise/preserve-color-output-for-task-command.md)
- [Read Existing Dot Env File Into Env Vars](mise/read-existing-dot-env-file-into-env-vars.md)
- [Run A Command With Specific Tool Version](mise/run-a-command-with-specific-tool-version.md)
### MongoDB
@@ -834,6 +842,7 @@ If you've learned something here, support my efforts writing daily TILs by
- [Escaping String Literals With Dollar Quoting](postgres/escaping-string-literals-with-dollar-quoting.md)
- [Export Query Results To A CSV](postgres/export-query-results-to-a-csv.md)
- [Extracting Nested JSON Data](postgres/extracting-nested-json-data.md)
- [Fetch Data From An Endpoint In SQL](postgres/fetch-data-from-an-endpoint-in-sql.md)
- [Fetch Specific Number Of Results](postgres/fetch-specific-number-of-results.md)
- [Find Duplicate Records In Table Without Unique Id](postgres/find-duplicate-records-in-table-without-unique-id.md)
- [Find Records That Contain Duplicate Values](postgres/find-records-that-contain-duplicate-values.md)
@@ -905,6 +914,7 @@ If you've learned something here, support my efforts writing daily TILs by
- [Sets With The Values Command](postgres/sets-with-the-values-command.md)
- [Shorthand Absolute Value Operator](postgres/shorthand-absolute-value-operator.md)
- [Show All Versions Of An Operator](postgres/show-all-versions-of-an-operator.md)
- [Show Reconstructed Constraints For A Table](postgres/show-reconstructed-constraints-for-a-table.md)
- [Show The Hidden Queries Behind Backslash Commands](postgres/show-the-hidden-queries-behind-backslash-commands.md)
- [Sleeping](postgres/sleeping.md)
- [Special Math Operators](postgres/special-math-operators.md)
@@ -957,6 +967,7 @@ If you've learned something here, support my efforts writing daily TILs by
### Python
- [Access Instance Variables](python/access-instance-variables.md)
- [Break Debugger On First Line Of Program](python/break-debugger-on-first-line-of-program.md)
- [Create A Dummy DataFrame In Pandas](python/create-a-dummy-dataframe-in-pandas.md)
- [Dunder Methods](python/dunder-methods.md)
- [Override The Boolean Context Of A Class](python/override-the-boolean-context-of-a-class.md)
@@ -974,6 +985,7 @@ If you've learned something here, support my efforts writing daily TILs by
- [Add A Generated Column To A PostgreSQL Table](rails/add-a-generated-column-to-a-postgresql-table.md)
- [Add A Reference Column With An Index](rails/add-a-reference-column-with-an-index.md)
- [Add ActiveRecord Error Not Tied To Any Attribute](rails/add-activerecord-error-not-tied-to-any-attribute.md)
- [Add Color To The IRB Console Prompt](rails/add-color-to-the-irb-console-prompt.md)
- [Add React With Webpacker To A New Rails App](rails/add-react-with-webpacker-to-a-new-rails-app.md)
- [Add timestamptz Columns With The Migration DSL](rails/add-timestamptz-columns-with-the-migration-dsl.md)
- [Adjust The Production Log Level](rails/adjust-the-production-log-level.md)
@@ -1375,6 +1387,7 @@ If you've learned something here, support my efforts writing daily TILs by
- [Set RVM Default Ruby](ruby/set-rvm-default-ruby.md)
- [Shift The Month On A Date Object](ruby/shift-the-month-on-a-date-object.md)
- [Show Public Methods With Pry](ruby/show-public-methods-with-pry.md)
- [Show The Bundler Location Of An Installed Gem](ruby/show-the-bundler-location-of-an-installed-gem.md)
- [Silence The Output Of A Ruby Statement In Pry](ruby/silence-the-output-of-a-ruby-statement-in-pry.md)
- [Single And Double Quoted String Notation](ruby/single-and-double-quoted-string-notation.md)
- [Skip Specific CVEs When Auditing Your Bundle](ruby/skip-specific-cves-when-auditing-your-bundle.md)
@@ -1546,6 +1559,7 @@ If you've learned something here, support my efforts writing daily TILs by
- [Find All Files Matching A Name With fd](unix/find-all-files-matching-a-name-with-fd.md)
- [Find All Files With A Specific Extension With fd](unix/find-all-files-with-a-specific-extension-with-fd.md)
- [Find All Tool Version Files Containing Postgres](unix/find-all-tool-version-files-containing-postgres.md)
- [Find And Copy A Value From Large JSON Output](unix/find-and-copy-a-value-from-large-json-output.md)
- [Find Any Dotfiles That Modify Path Env Var](unix/find-any-dotfiles-that-modify-path-env-var.md)
- [Find A File Installed By Brew](unix/find-a-file-installed-by-brew.md)
- [Find Duplicate Lines In A File](unix/find-duplicate-lines-in-a-file.md)
@@ -1722,6 +1736,7 @@ If you've learned something here, support my efforts writing daily TILs by
- [Generate and Edit Rails Migration](vim/generate-and-edit-rails-migration.md)
- [Get The pid Of The Session](vim/get-the-pid-of-the-session.md)
- [Go Back To The Previous Window](vim/go-back-to-the-previous-window.md)
- [Go To Beginning And End Of Line](vim/go-to-beginning-and-end-of-line.md)
- [Go To File With Line Number](vim/go-to-file-with-line-number.md)
- [Grepping Through The Vim Help Files](vim/grepping-through-the-vim-help-files.md)
- [Head of File Name](vim/head-of-file-name.md)

View File

@@ -0,0 +1,49 @@
# Output CLI Results In Different Formats
The AWS CLI can output the results of commands in three different formats.
- Text
- JSON
- Table
The _default_ output format for my AWS CLI is currently configured to `json`.
```bash
$ aws configure get output
json
```
I can either accept the default or I can override it with the `--output` flag.
```bash
$ aws rds describe-db-instances \
--query 'DBInstances[*].Endpoint' \
--no-cli-pager
[
{
"Address": "fc-database-abcefg-ab1c23de.asdfgh4zxcvb.us-east-2.rds.amazonaws.com",
"Port": 5432,
"HostedZoneId": "A1BCDE2FG345H6"
}
]
$ aws rds describe-db-instances \
--query 'DBInstances[*].Endpoint' \
--no-cli-pager \
--output table
----------------------------------------------------------------------------------------------------
| DescribeDBInstances |
+-----------------------------------------------------------------------+-----------------+--------+
| Address | HostedZoneId | Port |
+-----------------------------------------------------------------------+-----------------+--------+
| fc-database-abcefg-ab1c23de.asdfgh4zxcvb.us-east-2.rds.amazonaws.com | A1BCDE2FG345H6 | 5432 |
+-----------------------------------------------------------------------+-----------------+--------+
$ aws rds describe-db-instances \
--query 'DBInstances[*].Endpoint' \
--no-cli-pager \
--output text
fc-database-abcefg-ab1c23de.asdfgh4zxcvb.us-east-2.rds.amazonaws.com A1BCDE2FG345H6 5432
```
[source](https://docs.aws.amazon.com/cli/v1/userguide/cli-usage-output-format.html)

View File

@@ -0,0 +1,38 @@
# Turn Off Output Pager For A Command
It is not uncommon for an AWS CLI command to return a ton of output. When that
happens, it is nice that the results end up in pager program (like `less`)
where you can search and review them, copy a value of interest, and then exit.
The pager prevents that wall of output from cluttering your terminal history.
However, sometimes I am running a command that I know is going to return a
small result. I'd rather have the results go to stdout where I can see them in
the terminal history rather than to an ephemeral pager.
For that situation I can tack on the `--no-cli-pager` flag.
```bash
$ aws rds describe-db-instances \
--query 'DBInstances[*].EngineVersion' \
--output json \
--no-cli-pager
[
"13.15",
"16.8"
]
```
Here I've asked the AWS CLI to tell me the engine versions of all my RDS
Postgres databases. Because I know the results are only going to include a
couple results for my couple of DBs, I'd like to skip the pager —
`--no-cli-pager`.
Though I think it is better to do this on a case by case basis, it is also
possible to turn off the pager via the CLI configuration file.
```bash
$ aws configure set cli_pager ""
```
[source](https://docs.aws.amazon.com/cli/latest/userguide/cli-usage-pagination.html#cli-usage-pagination-clientside)

View File

@@ -0,0 +1,22 @@
# Search Tabs With The Vimium Vomnibar
If you use Chrome like I do, then you eventually end up with several windows
with dozens if not 100+ tabs open. It can start to get tedius with that many
tabs to find and navigate to a given tab. Someone might suggest closing a few
dozen tabs as a solution to this predicament. However, Vimium offers a solution
that doesn't require I [_kill my
darlings_](https://en.wiktionary.org/wiki/kill_one%27s_darlings).
The Vomnibar, a Vimium-powered search bar, can be summoned with `T` to only
search through open tabs.
When I hit `T`, I see a text area (for refining the search) and then a bunch of
entries populate below that which I immediately recognize as many of those tabs
that I'm going to get back to one of these days.
To narrow down to the specific thing I'm looking for, I type something into the
input. Then I arrow to the result I'm looking for and hit enter. And I'm
transported to that tab.
If I don't like where I ended up, I can also go back to the tab I had been on
with `^`.

View File

@@ -0,0 +1,28 @@
# Check Postgres Version Running In Docker Container
I have a docker container that I'm using to run a PostgreSQL development
database on my local machine. It was a while ago when I set it up, so I can't
remember specifically which major version of PostgreSQL I am using.
I use `docker ps` to list the names of each container.
```bash
$ docker ps --format "{{.Names}}"
still-postgres-1
better_reads-postgres-1
```
I grab the one I am interested in. In this case, that is `still-postgres-1`.
Then I can execute a `select version()` statement with `psql` against the
container with that name like so:
```bash
$ docker exec still-postgres-1 psql -U postgres -c "select version()";
version
---------------------------------------------------------------------------------------------------------------------
PostgreSQL 16.2 (Debian 16.2-1.pgdg120+2) on x86_64-pc-linux-gnu, compiled by gcc (Debian 12.2.0-14) 12.2.0, 64-bit
(1 row)
```
And there I have it. I'm running Postgres v16 in this container.

View File

@@ -0,0 +1,42 @@
# Run SQL Script Against Postgres Container
I've been using dockerized Postgres for local development with several projects
lately. This is typically with framework tooling (like Rails) where schema
migrations and query execution are handled by the tooling using the specified
connection parameters.
However, I was experimenting with and iterating on some Postgres functions
outside of any framework tooling. I needed a way to run the SQL script that
(re)creates the function via `psql` on the docker container.
With a local, non-containerized Postgres instance, I'd redirect the file to
`psql` like so:
```bash
$ psql -U postgres -d postgres < experimental-functions.sql
```
When I tried doing this with `docker exec` though, it was silently failing /
doing nothing. As far as I can tell, there was a mismatch with redirection
handling across the bounds of the container.
To get around this, I first copy the file into the `/tmp` directory on the
container:
```bash
$ docker cp experimental-functions.sql still-postgres-1:/tmp/experimental-functions.sql
```
Then the `psql` command that docker executes can be pointed directly at a
local-to-it SQL file.
```bash
$ docker exec still-postgres-1 psql \
-U postgres \
-d postgres \
-f /tmp/experimental-functions.sql
```
There are probably other ways to handle this, but I got into a nice rhythm with
this file full of `create or replace function ...` definitions where I could
modify, copy over, execute, run some SQL to verify, and repeat.

View File

@@ -0,0 +1,34 @@
# Download A Google Doc As Specific Format
I was recently given a public Google Doc URL and I was curious if I could
download it from the command line. I didn't want to have to install special CLI
though. I was hoping to use something like `curl`.
A brief chat with Claude and I learned that not only can I use `curl`, but I
can specify the format in the _export_ URL.
```bash
$ export GOOGLE_DOC_URL="https://docs.google.com/document/d/157rMgHeBf76T9TZnUjtrUyyS2XPwG0tObr-OjYNfMaI"
$ echo $GOOGLE_DOC_URL
https://docs.google.com/document/d/157rMgHeBf76T9TZnUjtrUyyS2XPwG0tObr-OjYNfMaI
$ curl -L "$GOOGLE_DOC_URL/export?format=pdf" -o doc.pdf
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
100 414 0 414 0 0 2763 0 --:--:-- --:--:-- --:--:-- 2895
100 16588 0 16588 0 0 56214 0 --:--:-- --:--:-- --:--:-- 167k
$ ls doc.pdf
doc.pdf
```
I append `/export` and then include the `?format=pdf` query param to specify
that I want the document to be exported in PDF format. With the `-o` flag I can
specify the name and extension of the output file.
This is a handy on its own, but noticing that Google Docs supports other export
formats, I thought it would be useful to go back-and-forth with Claude to
sketch out a script that can do this and prompt me (with `fzf`) for the file
type -- [here is the gist for
`gdoc-download`](https://gist.github.com/jbranchaud/cf3d2028107a1bd8484eed7cca0fcdab).

View File

@@ -0,0 +1,53 @@
# Create Umbrella Task For All Test Tasks
When I was first sketching out the [`mise`
tasks](https://mise.jdx.dev/tasks/running-tasks.html) for a Rails app, I added
the following two tasks. One is for running all the `rspec` tests. The Other is
for running all the `vitest` (JavaScript) tests.
```toml
[tasks."test:rspec"]
run = "unbuffer bundle exec rspec"
description = "Run RSpec tests"
depends = ["bundle-install"]
[tasks."test:vitest"]
run = "unbuffer yarn test run"
description = "Run Vitest tests"
depends = ["node-install"]
```
I didn't want to have to invoked both of this individually every time I wanted
to run the full suite. So I added a `test:all` task to do it all.
```toml
[tasks."test:all"]
description = "Run all tests (RSpec and Vitest)"
run = [
"unbuffer bundle exec rspec",
"unbuffer yarn test run",
]
description = "Run RSpec tests"
depends = ["bundle-install", "node-install"]
```
This worked (for now). But it ate at me, for a couple reasons. I had to
duplicate everything about the existing `test:rspec` and `test:vitest` tasks.
And this didn't account for a new kind of test task being added (e.g.
`test:e2e`).
Instead, I can rely on `depends` and wildcards to achieve this without the
duplication which makes it more future-proof.
```toml
[tasks."test:all"]
description = "Run all tests (RSpec and Vitest)"
depends = ["test:*"]
```
Running `mise run test:all` won't execute its own command, but because it
depends on all other `test:*` tasks, the tests will get run through those
dependencies.
This task naming pattern also allows for calling all tests with `mise run
"test:**"`.

View File

@@ -0,0 +1,39 @@
# Run A Command With Specific Tool Version
Because I'm using `mise` to manage the versions of tools like Node, I can
execute commands in the context of specific versions. Behind the scenes `mise`
makes sure I have the necessary tool(s) installed at the desired version(s).
So, [`mise exec` command](https://mise.jdx.dev/cli/exec.html) will default to
using the latest version of a tool if I haven't been more specific. At the time
of this writing, for Node, that is v23.
```bash
$ mise exec node -- node --version
v23.9.0
```
To be specific I could specify the major version with `node@23` like so:
```bash
mise exec node@23 -- npx repomix
Need to install the following packages:
repomix@0.2.39
Ok to proceed? (y) y
...
```
Or if I wanted to use a different, older version of Node, I could specify that
as well. We can see it will first install that and then execute the command:
```bash
$ mise exec node@22 -- npx repomix
gpg: Signature made Tue Feb 11 04:44:53 2025 CST
gpg: using RSA key C0D6248439F1D5604AAFFB4021D900FFDB233756
gpg: Good signature from "Antoine du Hamel <duhamelantoine1995@gmail.com>" [unknown]
📦 Repomix v0.2.39
...
```

View File

@@ -0,0 +1,49 @@
# Fetch Data From An Endpoint In SQL
The [`pgsql-http` extension](https://github.com/pramsey/pgsql-http) provides a
variety of functions for allowing PostgreSQL to act as an HTTP client. This is
a bit unorthodox and may not be a good idea in production systems. That said,
it is cool that it is possible. Let's look at an example of it.
First, I've installed the extension on the Docker container running my local
Postgres server.
```bash
$ docker exec -it still-postgres-1 bash
$ apt-get update
$ apt-get install postgres-16-http # I'm running Postgres v16
$ exit
```
Then I'll connect to a `psql` session in that container for the `postgres` database.
```bash
$ docker exec still-postgres-1 psql -U postgres -d postgres
```
Then I enable the extension.
```sql
> create extension if not exists http;
CREATE EXTENSION
```
Now I can point a PostgreSQL statement at a live endpoint like
[https://httpbun.com/ip](https://httpbun.com/ip) which will respond with a
chunk of JSON including the IP address for that project's server. I do this
using `http_get` which makes a `GET` request to the given endpoint. The body is
included in the result set.
```bash
> select content from http_get('http://httpbun.com/ip');
content
-----------------------------
{ +
"origin": "73.75.236.101"+
} +
(1 row)
```

View File

@@ -0,0 +1,35 @@
# Show Reconstructed Constraints For A Table
The [`pg_get_constraintdef`
function](https://pgpedia.info/p/pg_get_constraintdef.html) can be used to
reconstruct the command for creating a given constraint. This isn't necessarily
the command (or commands) that originally created the constraint, but rather a
reconstruction.
We have to pass it an `oid` that corresponds to the constraint which we can get
from the `pg_constraint` table. These results can be further narrowed down by
the `conname` (constraint name) and `conrelid` (table name).
Here is an example of listing the constraints on a `reading_statuses` table.
```sql
> select
conname,
pg_get_constraintdef(oid)
from pg_constraint
where conrelid = 'reading_statuses'::regclass;
conname | pg_get_constraintdef
-------------------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
reading_statuses_pkey | PRIMARY KEY (id)
fk_rails_17ee7cb2c4 | FOREIGN KEY (user_id) REFERENCES users(id)
fk_rails_0d3729339f | FOREIGN KEY (book_id) REFERENCES books(id)
reading_statuses_valid_status_check | CHECK (((status)::text = ANY ((ARRAY['started'::character varying, 'completed'::character varying, 'abandoned'::character varying, 'already_read'::character varying])::text[])))
(4 rows)
```
I came across this while experimenting with [an idea for a fail-fast Rails
initializer
check](https://gist.github.com/jbranchaud/12813a0558f9cd06bcc24b7d8706550c)
that verifies the values of the `reading_statuses_valid_status_check` stay in
sync with the Rails version of those values that live in a constant.

View File

@@ -0,0 +1,35 @@
# Break Debugger On First Line Of Program
One of the things I appreciate about how
[Delve](https://github.com/go-delve/delve) (the debugger for Go) works by
default is that when you start it up, it immediately breaks on the first line
of the program. This is as good a starting point as any regardless of whether
you have other breakpoints set.
As I was reading through the VS Code Python Debugger configuration docs, I
noticed [an option called
`stopOnEntry`](https://code.visualstudio.com/docs/python/debugging#_stoponentry).
It is turned off by default, but if you turn it on, then you get the same
behavior as I described for Delve. Nice!
This can be configured in a `.vscode/launch.json` file:
```json
{
"version": "0.2.0",
"configurations": [
{
"name": "Python Debugger: Current File",
"type": "debugpy",
"request": "launch",
"program": "${file}",
"console": "integratedTerminal",
"stopOnEntry": true
}
]
}
```
Now, when running this debugger configuration profile, you'll break the
debugger on the first line of the program. From there add more breakpoints,
start stepping through, etc.

View File

@@ -0,0 +1,62 @@
# Add Color To The IRB Console Prompt
IRB has a little-known [`Color`
module](https://docs.ruby-lang.org/en/3.2/IRB/Color.html) with some helpers for
adding a splash of color to the IRB prompt. I like to clearly differentiate the
environment I'm in when connecting to the `rails console`, so I have a
customize the prompt to display and colorize the current environment.
I can wrap any string in ANSI escape codes that instruct the terminal to style
the text with color. For instance, here is how I can style the word `DEV` to be
inverted against a blue background.
```ruby
IRB::Color.colorize("DEV", [:BLUE, :BOLD, :REVERSE])
```
which will clearly stand out from `PROD` against a red background:
```ruby
IRB::Color.colorize("PROD", [:RED, :BOLD, :REVERSE])
```
Here is a full example of customizing the prompt from the
`config/application.rb` file.
```ruby
module MyApp
class Application < Rails::Application
# ...
console do
# Get the application module name and convert to kebab-case
app_name = Rails.application.class.module_parent.name
kebab_name = app_name.underscore.dasherize
# Environment color coding
env_colors = {
"development" => IRB::Color.colorize("DEV", [:BLUE, :BOLD, :REVERSE]),
"production" => IRB::Color.colorize("PROD", [:RED, :BOLD, :REVERSE]),
"test" => IRB::Color.colorize("TEST", [:YELLOW, :BOLD, :REVERSE]),
}
colored_env = "(#{env_colors[Rails.env]})"
# Docs: https://docs.ruby-lang.org/en/3.2/IRB.html#module-IRB-label-Customizing+the+IRB+Prompt
IRB.conf[:PROMPT][:RAILS_APP] = {
PROMPT_I: "#{kebab_name}#{colored_env}> ",
PROMPT_N: "#{kebab_name}#{colored_env}* ",
PROMPT_S: "#{kebab_name}#{colored_env}% ",
PROMPT_C: "#{kebab_name}#{colored_env}? ",
RETURN: "=> %s\n"
}
# Set it as the current prompt
IRB.conf[:PROMPT_MODE] = :RAILS_APP
end
end
end
```
The Ruby docs have more about [IRB Prompt
Customization](https://docs.ruby-lang.org/en/3.2/IRB.html#module-IRB-label-Customizing+the+IRB+Prompt).

View File

@@ -0,0 +1,24 @@
# Show The Bundler Location Of An Installed Gem
When you run `bundle install` with a project, it is going to install all the
gems specified by your project in a vendored location relative to the location
of your Ruby version install.
If you want to find the location of a specific gem, you can ask bundler with
`bundle show <gem-name>`.
Here I ask where the `rspec` gem is.
```bash
$ bundle show rspec
/Users/jbranchaud/.asdf/installs/ruby/3.1.3/lib/ruby/gems/3.1.0/gems/rspec-3.12.0
```
I could `cd` into that directory to have a look around at the source. That's a
great way to learn more about how our dependencies work.
I could even inject some debugging statements (e.g. `binding.irb`) which the
program using these gems will break on. Not often, but sometimes you need to
dig in this deep to understand what is causing a tricky bug or why code isn't
behaving like you'd hoped. Just remember to remove those statements when you're
done.

View File

@@ -0,0 +1,22 @@
# Find And Copy A Value From Large JSON Output
I've been using [`fx`](https://github.com/antonmedv/fx) for years as a sidekick
to [`jq`](https://jqlang.org/) when I want to explore a JSON document or JSON
output that I'm not yet familiar with. A more recent version of `fx` added the
ability to _yank_ (copy) values and keys you find in the document.
For instance, I may be looking for some info about my AWS RDS instances, so I
pipe that command to `fx`.
```bash
$ aws rds describe-db-instances --output json | fx
```
This takes a moment to process and then the `fx` viewer is populated with a
large blob of JSON. I can then hit `/` to start a document search, type in
something like `Endpoint`, and then look around for the specific key-value pair
I'm interested in.
I can then hit `y` to indicate that I want to copy the element under my cursor.
If it is a key-value pair I will then be prompted to pick whether I want the
value (`v`), the key (`k`), or the JSON path to this value (`p`).

View File

@@ -0,0 +1,33 @@
# Go To Beginning And End Of Line
There are two movements that I often find useful in Vim when trying to position
my cursor relative to the current line.
- `0` - go to the first character of the line
- `$` - go to the end of the line
For instance, I may use `0` to jump to beginning of a line so that I can then
make a block-visual selection of several lines to insert some text in front of
each line.
Or perhaps I'm already in visual mode and I want to move the cursor (and visual
selection) to the end of the line. I hit `$` to do that. Then I might `y`
(yank) or `c` (delete into insert mode).
It's also worth noting that with code indentation, `0` moves the cursor to the
very first position of the line whereas `^` moves the cursor to the first
non-whitespace character. The former essentially accounts for code indentation.
For example, imagine you're in the middle of line 3 in the following example.
Depending on what you're trying to do, you may want to jump to one or the other
position.
```ruby
class Greeting
def hello(name)
puts "Hello, #{name || 'world'}!" # say hi
end
end
```
See `:h 0` for Vim help files on these motions. They are all located near each
other.