153 karma · joined May 9, 2016
I do very much like that by introducing aria attributes, the CSS reacts to it and styles it appropriately. As opposed to a full-blown react component library which does all of that for you. It would be a good exercise for developers to think aria-first and let the library just help with styling.
Lastly, I think the best part is that this component library has a native sidebar. So many of these I see and they have a nice web page which showcases all the components and I want to replicate their layout and nav/sidebars but they only focus on smaller re-usable components and not the layout. So that's a nice touch, I think. And, as someone who keeps an eye on but doesn't do a lot of frontend, the fact that a sidebar is an aside > nav > ul next to a main just makes so much sense and doesn't have a lot of cruft around it.
This is a blog. Blog posts are a way to show the voice of the author, share their thoughts on the matter, perhaps work through their own thought processes and come to a nice conclusion for themselves that they choose to share with the public.
I would find the internet and the community incredibly dull if the first person to post a criticism was it and everyone else always referred to their article. There'd be no further discussion whatsoever.
I found this article to be enlightening and a wonderful way to frame my disdain for AI-generated art and other content in a framing that I hadn't thought of so explicitly before. The analogy to alchemy is a welcomed and fresh take. I appreciate this article. Perhaps I'm one of today's lucky 10,000 to have made this connection.
I also appreciate this article because the author put effort into it and voiced their opinion. Voicing opinions don't have to be novel, since this isn't academia necessarily where you have to fight for uniqueness and new takes.
The fact that you are receiving multiple kinds of ads from Anthropic does signify more of a marketing push, though.
I would have thought that this method of organizing documentation is preferred, as I assumed The Grand Unified Theory of Documentation[0] was well known and liked.
SCIM allows clients to ignore the group membership lists via `?excludeAttributes=groups` (or members on the group resource). But not all clients send that by default. Entra does well to only ask for a list of groups or members on resources when it's really needed in my experience.
Some enterprise customers use SCIM with tons of users. Querying for the users themselves is simple because querying users is paginated and you can constrain the results. But returning a single group with 10,000 users in a single response can be a lot. It only really contains the user's identifier and optionally their display name, but if you have to pull this data from a paginated API it'll take a while to respond. Or it could still be taxing on some databases.
It'd be nice to query `/Users/:id/groups` or `/Groups/:id/members in a paginated fashion similar to `/Users`.
In reality, most systems expect you to have the full default schema present without modifications and might complain when items are missing. Do you provide scim support without passwords (only SSO)? Okta will send a password anyway (random and unused). Does your application not differentiate between username and email? IdPs will complain if they can't set them separately. Do you not store the user's `costCenter`? IdPs will get mad and keep trying to set it because it never sticks.
Some of the time, you'll have to store SCIM attributes on your user objects which have no effect on your system at all.
The other side is making custom schema items. SCIM has you present these in the `/Schema` endpoints. But, no system (that I know of) actually looks at your schema to autopopulate items for mapping. Entra and Okta are great at letting your provide mapping from an IdP user to a SCIM user, and then you map SCIM users back to your app's users. But you typically have to follow app documentation to map things properly if it's not using the default schema entirely.
Whereas in Go, the error is visible everywhere. As a developer I see its path more easily since it's always there, and so I have a better mind to handle it right there.
Additionally, it's less easy to group errors together. A try/catch with multiple throwable functions catches an error...which function threw it though? If you want to actually handle an error, I'd prefer handling it from a particular function and not guessing which it came from.
Java with type-checked exceptions is nice. I wish Swift did that a bit better.
This is where languages diverge. Many languages use exceptions to throw the error until someone explicitly catches it and you have a stack trace of sorts. This might tell you where the error was thrown but doesn't provide a lot of helpful insight all of the time. In Go, I like how I can have some options that I always must choose from when writing code:
1. Ignore the error and proceed onward (`foo, _ := doSomething()`)
2. Handle the error by ending early, but provide no meaningful information (`return nil, err`)
3. Handle the error by returning early with helpful context (return a general wrapped error)
4. Handle the error by interpreting the error we received and branching differently on it. Perhaps our database couldn't find a row to alter, so our service layer must return a not found error which gets reflected in our API as a 404. Perhaps our idempotent deletion function encountered a not found error, and interprets that as a success.
In Go 2, or another language, I think the only changes I'd like to see are a `Result<Value, Failure>` type as opposed to nillable tuples (a la Rust/Swift), along with better-typed and enumerated error types as opposed to always using `error` directly to help with error type discoverability and enumeration.
This would fit well for Go 2 (or a new language) because adding Result types on top of Go 1's entrenched idiomatic tuple returns adds multiple ways to do the same thing, which creates confusion and division on Go 1 code.
I want to start with the fact that building FlowRipples is a monumental feat of its own. Generic tools that are adaptable to lots of situations is a difficult task, and it's impressive what was built.
But the supporting functionality in any service like this is also so important. It's one thing to have a low friction setup and way to get started, with simple steps and a quick showcase video, so that someone can get to tinkering. It's another thing to fully adopt this as a tool within your team that would be integrated into a published product.
Suddenly, like you say, you have multiple environments (Dev, QA, Staging/Pre-prod, Prod) that you have to move changes into and out of. Replicating the same changes manually will inevitably lead to human error and what worked in QA will no longer work in Staging or Production. Even a simple export + import helps with this.
I think one thing that also needs attention is parallel changes. Two people are wokring on different changes in the dev environment. Promoting the current state of the Dev environment to QA requires that both tasks have to be dev-complete, or else unfinished changes could make its way to QA and cause confusion. This is difficult when the different tasks aren't synchronized in their testing (i.e. start testing one ticket but not necessarily the other). It's almost like you need branching and merging and diffing, a la git, to help resolve this. That's difficult to do in low-code visual programming apps.
Though to be fair I've only read Temporal docs, and this Restate blog post, without much experience in either. Temporal may not have as much on the distributed locking (or concept of) side of things that Restate does, in this post.
It's janky. And I would know because we had to implement that at work.
Actually no, that's on the spec for not enforcing they're in the ID token, and only must be available in the userinfo endpoint.
Location: San Diego, United States
Remote: Yes
Willing to relocate: No
Technologies: Senior Software Engineer, backend and cloud, Go, .NET, Swift, AWS, Terraform, Web (HTML + frameworks), Okta/IAM/OAuth/OIDC
Résumé/CV: https://jamesnl.com/resume.pdf
Email: james.n.linnell@gmail.comHowever, wouldn't putting the input inside of the label (before the label text) be a better solution than fiddling too much with CSS and flexbox? It's more foolproof to ensure clicks within the label activate the input, and eliminates the need for the "for" reference.
Location: San Diego, United States
Remote: Yes
Willing to relocate: No
Technologies: Senior Software Engineer, backend and cloud, Go, .NET, Swift, AWS, Terraform, Web (HTML + frameworks), Okta/IAM/OAuth/OIDC
Résumé/CV: https://jamesnl.com/resume.pdf
Email: james.n.linnell@gmail.comI suppose sometimes it makes sense to boycott, but not all the time.
1. Hash word, retrieve the value from the counts map
2. Increment the value
3. Hash word, store the value into the counts map
By change counts to a map of strings to pointers of ints, you only need to perform #3 once per unique word. Once you've read the int pointer, you need only write to the pointer and not re-hash the word and write that to the map, which can be expensive.https://github.com/benhoyt/countwords/blob/master/optimized....
It seems built-in to Swift, as opposed to a dynamically executed crate like with serde. I wonder how it's implemented in Swift and if it leads to any significant slowdowns.
[0] https://developer.apple.com/documentation/foundation/archive...
$ otool -L AdventOfCode2022
AdventOfCode2022:
/usr/lib/libobjc.A.dylib (compatibility version 1.0.0, current version 228.0.0)
/usr/lib/libSystem.B.dylib (compatibility version 1.0.0, current version 1319.0.0)
/usr/lib/swift/libswiftCore.dylib (compatibility version 1.0.0, current version 5.7.1)
/usr/lib/swift/libswiftCoreFoundation.dylib (compatibility version 1.0.0, current version 120.100.0, weak)
/usr/lib/swift/libswiftDarwin.dylib (compatibility version 1.0.0, current version 0.0.0, weak)
/usr/lib/swift/libswiftDispatch.dylib (compatibility version 1.0.0, current version 17.0.0, weak)
/usr/lib/swift/libswiftIOKit.dylib (compatibility version 1.0.0, current version 1.0.0, weak)
/usr/lib/swift/libswiftObjectiveC.dylib (compatibility version 1.0.0, current version 6.0.0, weak)
/usr/lib/swift/libswiftXPC.dylib (compatibility version 1.0.0, current version 6.0.0, weak)
/usr/lib/swift/libswiftFoundation.dylib (compatibility version 1.0.0, current version 1.0.0, weak)
Not only does it say that libswiftcore is 5.7.1, but that /usr/lib/swift folder doesn't have any of those files there. Very very confusing. I don't like any of this.I appreciate your write-up and research into all of this though! I tried googling for what runtime version of Swift is installed in Monterey and couldn't find anything. This is incredibly opaque.
$ swift -v
Apple Swift version 5.7.1 (swiftlang-5.7.1.135.3 clang-1400.0.29.51)
Target: arm64-apple-macosx12.0
I love Swift as a language, but the lack of release notes for 5.7.1 (aside from a blog post for 5.7 as a whole), OS-specific releases (especially for SwiftUI), Xcode removing old toolchains when it upgrades (making me re-download tvOS 15.4 runtime for no reason), and all these other little things are starting to weigh on me.