1. 23

    This seems kind of neat in concept but I’m befuddled by several aspects of this product/company(?).

    First, this blog post emphasizes that they’ll never sell our data, but I’m unclear why this terminal add on would need to connect to the internet or collect any end user data in the first place. They want to make money on hosting but uh what are we hosting exactly?

    Also, I thought to myself oh cool do postmodern terminal emulators like iterm2 and kitty provide enough wacky hooks through escape codes that you can build complicated software with them? Sadly no, this thing just uses macos’ accessibility APIs for now apparently. Which…isn’t a bad solution for certain problems, like at least we aren’t loading kernel modules with input managers in them anymore I guess, but it’s not, like, a terminal-centric solution. They should’ve written their own terminal after all.

    1. 4

      They explain why they don’t want to build their own terminal on the linked page: https://fig.io/blog/post/launching-fig#-why-hasnt-fig-built-its-own-terminal

      If integrating with existing terminals works well that’s preferable. Getting people to switch terminals and integrating with everything that has a built in terminal (eg vs code) sounds hard. How many people have iTerm2 configured in some weird way to make mosh have a better scrollback buffer, for example? Who wants to support all that while adding friction to adoption?

      1. 5

        I’d be curious about the market research that led them here. It sounds as if they are targeting people who are not familiar with the terminal and want a more discoverable interface. I would not have expected that set of folks to have a large intersection with the set of people who have weird iTerm2 configurations.

        Writing a custom terminal would also give them a potentially interesting target market: folks building products that need an integrated terminal but want something easier to use for novices. They mention the VS Code terminal, and that’s exactly the kind of thing where I can imagine a terminal with custom helpers for the programs that it wants to run being a differentiating feature and the tooling for building those being something that you could sell.

        That said, I type passwords into a terminal so an application that is network connected being able to snoop them makes me incredibly nervous.

        1. 3

          That’s like suggesting intellisense is only for people who are not familiar with coding

          1. 2

            The problem with a solution like “We’ll integrate using a custom terminal” is that the advantage breaks down when your users are inside SSH, GNU Screen, tmux, or mosh - potentially all at once. You need to either be a client of the user’s shell (there are a lot of shells, though…) or otherwise do your thing by querying a process tree and figuring out how to read an arbitrary process’s character data, ie by parsing a PTY. and if you need to query the process tree or parse a PTY… why build your own terminal?

        2. 3

          but I’m unclear why this terminal add on would need to connect to the internet or collect any end user data in the first place

          Makes me very confident to use this for anything administrative.

        1. 9

          This workflow is just bringing (client-side) Git up to parity with Mercurial as used at Google/Facebook:

          • Adds in-memory rebases (for performance reasons).
          • Adds changeset evolution.
          • Encourages of a “patch-stack”/“stacked-diff” workflow with trunk-based development.
          • Discourages the use of branches/stashes/staged changes, in favor of commits for everything (where possible).

          Unfortunately, I’ve found it hard to motivate the collection of features as a whole. But most people can use at least one of the following in their workflow:

          • git undo to undo operations on the commit graph.
          • git move as a saner, faster replacement for git rebase.
          1. 3

            I have looked at this project a few weeks ago and I seem to not get it. Maybe it is something with the naming, but how is it branchless? All work in git is on a branch. What is the difference if I have a local checkout and work on feature-xyz instead of main? I still do git fetch && git rebase origin/main regardless of the local branch name. I could not figure it out from the README tbh.

            Note that I am from the “rebase, squash and “no-merge-commits” school of thought, so maybe this is going in a similar direction, but I don’t really understand what the usp here is. Maybe it makes more sense to people who have used mercurial?

            1. 11

              All work in git is on a branch.

              Under git-branchless, this is no longer necessary. There are three main ways to not use a branch:

              • Run git checkout --detach explicitly.
              • Use one of git next/git prev to move along a stack.
              • Use git checkout with a commit hash (or git co from the latest source build).

              Why is this useful? It helps you make experimental changes to various parts of the commit graph without dealing with the overhead of branch management. Suppose I have a feature feature made of three commits, and I get feedback on the first commit and want to try out various approaches to addressing it. My session might look like this:

              $ git checkout -b feature
              $ git commit -m A
              $ git commit -m B
              $ git commit -m C
              $ git sl
              ⋮
              ◇ fcba6182 7d (main) Create foo
              ┃
              ◯ 9775f9a6 4m A
              ┃
              ◯ 97b8d332 4m B
              ┃
              ● 67fa26af 4m (feature) C
              
              $ git prev 2
              $ git sl
              ⋮
              ◇ fcba6182 7d (main) Create foo
              ┃
              ● 9775f9a6 6m A
              ┃
              ◯ 97b8d332 6m B
              ┃
              ◯ 67fa26af 6m (feature) C
              
              $ git commit -m 'temp: try approach 1'
              $ git sl
              ⋮
              ◇ fcba6182 7d (main) Create foo
              ┃
              ◯ 9775f9a6 7m A
              ┣━┓
              ┃ ◯ 97b8d332 7m B
              ┃ ┃
              ┃ ◯ 67fa26af 7m (feature) C
              ┃
              ● 9dba147f 1s temp: try approach 1
              
              $ git prev
              $ git commit -m 'temp: try approach 2'
              $ git sl
              ⋮
              ◇ fcba6182 7d (main) Create foo
              ┃
              ◯ 9775f9a6 8m A
              ┣━┓
              ┃ ◯ 97b8d332 8m B
              ┃ ┃
              ┃ ◯ 67fa26af 7m (feature) C
              ┣━┓
              ┃ ◯ 9dba147f 58s temp: try approach 1
              ┃
              ● ef9ea69a 1s temp: try approach 2
              
              # Check out "temp: try approach 1".
              # Note that there is no branch attached to it,
              # so we use the commit hash directly.
              # (Or we can use the interactive commit selector
              # with `git co`.)
              $ git checkout 9dba147f
              $ git commit -m 'temp: more approach 1'
              $ git sl
              ⋮
              ◇ fcba6182 7d (main) Create foo
              ┃
              ◯ 9775f9a6 10m A
              ┣━┓
              ┃ ◯ 97b8d332 10m B
              ┃ ┃
              ┃ ◯ 67fa26af 10m (feature) C
              ┣━┓
              ┃ ◯ 9dba147f 3m temp: try approach 1
              ┃ ┃
              ┃ ● 60ad3014 4s temp: more approach 1
              ┃
              ◯ ef9ea69a 2m temp: try approach 2
              
              # Settle on approach 1.
              # Hide "temp: try approach 2" from the smartlog.
              $ git hide ef9ea69a
              $ git sl
              ⋮
              ◇ fcba6182 7d (main) Create foo
              ┃
              ◯ 9775f9a6 11m A
              ┣━┓
              ┃ ◯ 97b8d332 11m B
              ┃ ┃
              ┃ ◯ 67fa26af 11m (feature) C
              ┃
              ◯ 9dba147f 4m temp: try approach 1
              ┃
              ● 60ad3014 1m temp: more approach 1
              
              # Squash approach 1 into `main`:
              $ git rebase -i main
              ...
              branchless: This operation abandoned 1 commit!
              branchless: Consider running one of the following:
              branchless:   - git restack: re-apply the abandoned commits/branches
              branchless:     (this is most likely what you want to do)
              branchless:   - git smartlog: assess the situation
              branchless:   - git hide [<commit>...]: hide the commits from the smartlog
              branchless:   - git undo: undo the operation
              branchless:   - git config branchless.restack.warnAbandoned false: suppress this message
              Successfully rebased and updated detached HEAD.
              $ git sl
              ⋮
              ◇ fcba6182 7d (main) Create foo
              ┣━┓
              ┃ ✕ 9775f9a6 12m (rewritten as 14450270) A
              ┃ ┃
              ┃ ◯ 97b8d332 12m B
              ┃ ┃
              ┃ ◯ 67fa26af 12m (feature) C
              ┃
              ● 14450270 32s A
              
              # Move B and C and branch "feature" on top of A,
              # where they belong
              $ git restack
              $ git sl
              ⋮
              ◇ fcba6182 7d (main) Create foo
              ┃
              ● 14450270 1m A
              ┃
              ◯ 7d592eae 3s B
              ┃
              ◯ fec8f0ba 3s (feature) C
              

              So the value for the above workflow is:

              • No thinking about branch names, especially since they’re ephemeral and going to be deleted shortly anyways.
                • Some people don’t find this an impediment to their workflow anyways.
              • Automatic fix up of descendant commits and branches.
                • Works even if there are multiple descendant branches (git rebase moves at most one branch).
                • Works even if one of the descendants has multiple children, causing a tree structure.
              1. 1

                Maybe a dumb question, is there an equivalent to hg heads in git-branchless?

                1. 1

                  Not yet, but it should be pretty easy as part of the task to add revset support (https://github.com/arxanas/git-branchless/issues/175).

                2. 1

                  Thanks for the explanation! This is very different from the git I use. I don’t think I ever had a use case for this sort of workflow, but I can see how people might find it useful. I will keep a bookmark and revisit this again in the future. Maybe it turns out useful.

              2. 3

                Seems like this workflow tries to avoid interactive rebase (and other tools are recommended to do that in-memory). I… can’t exactly imagine not using it all the time. Especially in situations like maintaining a constantly rebased “patchset” on top of an upstream, occasionally submitting patches to it. In my mind “restack” means “reorder in interactive rebase”, not what the restack tool does.

                What does changeset evolution mean btw?

                1. 2

                  It’s not that the workflow tries to avoid interactive rebase, but that it simply doesn’t offer a good replacement for interactive rebase at present. (It should handle in-memory rebasing, rebasing/editing tree structures, and referencing commits without branches.) It’s on the roadmap: cl https://github.com/arxanas/git-branchless/issues/177

                  Changeset evolution is this feature from Mercurial: https://www.mercurial-scm.org/wiki/ChangesetEvolution. In short, it tracks the history of a commit/patch as it gets rewritten with commands like git commit --amend or git rebase (or their equivalents in git-branchless). It means that we can automatically recover from situations where descendant commits are “abandoned”:

                  $ git commit -m A
                  $ git commit -m B
                  $ git commit -m C
                  $ git prev 2  # same as git checkout HEAD^^
                  $ git commit --amend -m A2
                  # now commits B and C are based on A instead of A2,
                  # which is probably not what you intended
                  $ git restack  # moves B and C onto A2
                  
                2. 1

                  I’ve been interested in this toolkit since I first came across it but I’m reluctant to set up rust on my laptop to install it. Do you have any enthusiasm for packaging releases yourself?

                  1. 1

                    Maybe, I haven’t looked into it too much. What platform are you using? Some kind folks have already packaged it for Nix, if you can use that.

                    1. 2

                      macOS for the most part. Mac users as a whole would probably most readily try this out if it were in Homebrew. (I have a bit of a grudge against Homebrew for being slow and pulling in outlandish dependency closures with stuff so I tend to prefer graphical installers or copying things into ~/bin when those are provided options.)

                      (Really if I had ever set up Rust for something else on my work computer I’d probably be trying it out as is instead of griping but y’know.)

                      1. 2

                        Something like https://github.com/emk/rust-musl-builder makes building static binaries very easy, if you want to go that way.

                  1. 1

                    Work desktop:

                    ~$ echo "'$PS1'"
                    '\W\$ '
                    

                    Work servers:

                    peach-dev01 ~$ echo "'$PS1'"
                    '\h \W\$ '
                    
                    1. 9

                      Hey, mods? For the last five years or so, I’ve titled these articles “Jepsen: [Database Name] [Version]”. I’ve been informed that that’s no longer an acceptable title for Jepsen reports, because “Jepsen” is also the name of the site. Can I get a policy clarification here? Do I need to make up a lobste.rs-friendly title that doesn’t include the word “Jepsen” for each submission from now on?

                      1. 7

                        The story submission guidelines state, in part: “Please remove extraneous components from titles such as the name of the site, blog, section, and author.” The story was originally submitted with the story title “Jepsen: YugaByte DB 1.3.1” from the domain jepsen.io. Given that the site name appears in the story title, and consistent with the story submission guidelines, I replaced “Jepsen: “ with “Testing “ as the best operational description of the article I could find.

                        It has since been brought to my attention that Jepsen is also the name of a Clojure library. As a site name, the story submission guidelines are clear. As a library or tool name, they are mute. As Jepsen is both, but given the existence of an interpretation of the article title that does not violate the site guidelines, I have restored the story title as originally submitted.

                        1. 4

                          It has since been brought to my attention that Jepsen is also the name of a Clojure library. As a site name, the story submission guidelines are clear. As a library or tool name, they are mute. As Jepsen is both, but given the existence of an interpretation of the article title that does not violate the site guidelines, I have restored the story title as originally submitted.

                          This is such a wacky justification! Somewhere, a lawyer smiles without knowing why.

                          But I like the “Jepsen: WebscaleDB 0.1.1-alpha2” titles, so I’ll take it.

                          1. 3

                            Absent a Damas-Hindley-Milner typechecker for story titles, it’s just us manually splitting hairs to try to keep up their signal:noise ratio. I was also surprised by Jepsen being the name of the tool used for the analysis as well as the project and consulting company I knew about. I can only ask that @aphyr disambiguate with Hungarian Notation - perhaps he’d like to adopt Jepsen_clj, Jepsen_blog, and Jepsen_LLC so we can more efficiently mangle his titles in the future.

                            1. 5

                              I like to think the usage in the submission title here is a fourth meaning of “Jepsen”, being a proper name not of the blog itself but of the kind of article the blog contains, i.e. “a Jepsen of YugaByte DB”

                          2. 3

                            Thank you. For what it’s worth, I prefer to see Jepsen in the title, because in my mind, it adds a ton of credibility for the content.

                        1. 6

                          Kyle Mitchell’s writing on software licensing have influenced my thinking a lot this year. His lead role in drafting a variety of plain language form licenses, both open source (Blue Oak, Parity) and otherwise (Polyform) is to be commended as well.

                          1. 1

                            Same here. Here’s the link to his other, non-licensezero writings in case anyone is interested: https://writing.kemitchell.com/

                            I’m using Parity for the project I’m working on at the moment, it’s going to be interesting how that will shake out.

                          1. 10

                            End of an era, I suppose. There’s no such thing as a healthy monoculture, just monocultures that haven’t found their blight yet.

                            1. 33

                              According to that Stack Overflow survey there are plenty of popular alternatives, such as “ZIP file back-ups”, “Copying and pasting files to network shares”, and “I don’t use version control”.

                              1. 18

                                Did the ever popular “Final FINAL Copy 2” make it in? That’s got to be the number one version control system, right?

                                1. 9

                                  My first programming job was like that. I was working as a repair tech at a computer shop, at some point they needed someone to clean up the intranet, and that someone was me.

                                  First thing I did was set up svn and get rid of all the “foo.orig”, “foo.orig2”, etc directories. This was trickier as it might seem as some of the projects were being served from those .orig2 dirs.

                                  All was going well, and then half a year later the guy who had been doing this asked me if knew what happened to the “cms.orig” directory. After I told him I deleted it he said he had been storing the company outings photos there for the last 15 years. By the time we discovered it was too late to recover from backup, so … all lost.

                                  I still don’t understand why you would store pictures in a deeply nested subdir of an otherwise unused cms.orig …. 🤨 from what I heard he ditched svn and went back to his “system” after I left.

                              2. 13

                                Well, just to play a devil’s advocate… Some things are so good exactly because they are ubiquitous. Like Unicode, for example. Or POSIX. They have their flaws for sure, but they made writing interoperable software much easier.

                                There are already other tools that work with the same repository format as the Torvalds’ git. Maybe git format becoming the standard repo format is a good thing after all. No one has to use the reference implementation if they prefer different UI and abstractions.

                                1. 14

                                  Maybe git format becoming the standard repo format is a good thing after all.

                                  No, it’s definitely not. It doesn’t scale. The git “API” is literally the local filesystem. Microsoft has valiantly hacked the format into functioning at scale with VFS for Git, but the approach is totally bananas.

                                  How does it work?

                                  VFS for Git virtualizes the filesystem beneath your Git repository so that Git tools see what appears to be a normal repository when, in fact, the files are not actually present on disk. VFS for Git only downloads files as they are needed.

                                  VFS for Git also manages Git’s internal state so that it only considers the files you have accessed, instead of having to examine every file in the repository. This ensures that operations like status and checkout are as fast as possible.

                                  - vfsforgit.org

                                  Microsoft had to implement an entire virtual filesystem that, through smoke and mirrors, tricks git to behave sanely. More details in this GVFS architecture overview.

                                  1. 4

                                    Isn’t the same true for Mercurial and every other DVCS in existence?

                                    1. 17

                                      No. Git’s remote repository API is nothing more than a specialized rsync implementation (git-send-pack and git-receive-pack).

                                      Mercurial uses a semantic API for exchanging changes with the server. It doesn’t need local files in the same way git does. That opens up a lot of doors for scaling large repositories, because you can implement optimizations in the client, protocol, and server.

                                      For git repos, where local filesystem operations are the protocol, there really is no alternative to Microsoft’s smoke and mirrors, virtualize the world approach. You’d have to just reimplement git, which defeats the point.

                                      1. 1

                                        Ah, that is interesting. Thanks for the information, I should look into the way mercurial actually works.

                                        1. 3

                                          If you’re curious about the actual on-disk formats (which should be irrelevant, as hg tries to compartmentalise them), you can read about Mercurial’s internals.

                                    2. 4

                                      I don’t see anything wrong with git using the local file system API.

                                      There are multiple implementations of such file systems – Linux, FreeBSD, OS X, Minix, etc. git works fine on all those systems, and the code is portable AFAICT.

                                      1. 8

                                        So, I personally love how git transparently exposes its internal data structures for direct manipulation by the user. It gives you tons of power and freedom. Back when I used git, I considered it just as much a development tool as my editor.

                                        But that transparency is problematic for scaling. To the point where you really do need to implement a virtual remote filesystem tailored for git to support huge repos. Whether you like git or not, that’s bananas.

                                        1. 5

                                          There’s nothing bananas about that: scaling is a feature and it’s not surprising that you need more code/engineering to scale. It would be surprising if you didn’t!

                                          To make a very close analogy, two companies I worked at used Perforce (the proprietary VCS). At one company we used it out of the box, and it worked great. Thousands of companies use Perforce like this, and Perforce is a very profitable company because as a result.

                                          The second company (Google) also used Perforce out of the box. Then we needed to scale more, so we wrote a FUSE-based VFS (which I imagine the git VFS is very similar to). That doesn’t mean Perforce is “bananas”. It works for 99% of companies.

                                          It’s just designed for a certain scale, just like git is. Scale requires a lot of tradeoffs, often higher latency, decreased throughput, etc. git seems to have made all the right tradeoffs for its targeted design space. That it succeeded beyond the initial use case is a success story, not an indication of problems with its initial design.


                                          Also, I don’t see any evidence that Mercurial reached the same scale. It probably has different problems – you don’t really know until you try it. I heard some teams were working on scaling Mercurial quite awhile ago [1], but I’m not sure what happened.

                                          https://engineering.fb.com/core-data/scaling-mercurial-at-facebook/

                                          1. 4

                                            Then we needed to scale more, so we wrote a FUSE-based VFS

                                            I currently work at Google. CitC has nothing to do with Piper performance, it’s more about the utility of sharing your workspace, both between dev machines and tools (desktop, cloudtop, cider, critique), as well as blaze.

                                            (which I imagine the git VFS is very similar to).

                                            Not at all. The git “protocol” is filesystem operations. Microsoft made VFS for Git because they need to intercept filesystem operations to interface with the git toolchain. Perforce and Mercurial have actual remote APIs, git does not.

                                            That doesn’t mean Perforce is “bananas”. It works for 99% of companies.

                                            I don’t think Perforce is bananas. I don’t think git is bananas either. I specifically think “git format becoming the standard repo format” is NOT a good thing. The git toolchain and the repo format are inseparable, leading to Microsoft’s bananas implementation of a scalable git server. Clever and impressive, but bananas.

                                            1. 2

                                              What I’m reading from your comments is: “If only git had decoupled its repo format and push/pull protocol, then it would be more scalable”.

                                              I don’t think that’s true. You would just run into DIFFERENT scalability limits with different design decisions. For example: Perforce and Mercurial don’t share that design decision, as you say, but they still have scalability limits. Those designs just have different bottlenecks.

                                              Designing for scale you don’t have is an antipattern. If literally the only company that has to use a git VFS is Microsoft, then that’s a fantastic tradeoff!!!

                                              IMO Google’s dev tools are a great example of the tradeoff. They suffer from scalability. They scale and solve unique problems, but are slow as molasses in the common case (speaking from my experience as someone who worked both on the dev tools team and was a user of those tools for 11 years)

                                              1. 2

                                                I don’t think that’s true. You would just run into DIFFERENT scalability limits with different design decisions.

                                                Git was probably strongly tied to the filesystem because it was made in 2005 (Pentium 4 era) for a lower-performance scenario by someone who understood the Linux filesystem better than high-performance, distributed applications. It worked for his and their purposes of managing their one project at their pace. Then, wider adoption and design inertia followed.

                                                It’s 2019. Deploying new capabilities backwards compatible with the 2005 design requires higher, crazier efforts with less-exciting results delivered than better or more modern designs.

                                                1. 1

                                                  “If only git had decoupled its repo format and push/pull protocol, then it would be more scalable”.

                                                  It would be easier to scale. When the simplest and easiest way to scale genuinely is implementing a client-side virtual filesystem to intercept actions performed by git clients, that’s bananas. To be clear, VFS for Git is more than a simple git-aware network filesystem, there’s some gnarly smoke and mirrors trickery to make it actually work. The git core code is so tightly coupled to the file format, there’s little else you could do, especially if don’t want to break other tooling using libraries like libgit2 or jgit.

                                                  Designing for scale you don’t have is an antipattern.

                                                  Designing tightly coupled components with leaky abstractions is an antipattern. Mercurial supports Piper at Google through a plugin. Doing the same with git just isn’t possible, there’s no API boundary to work with.

                                          2. 3

                                            To the best of my knowledge it still uses the intricate knowledge of filesystem behaviour to avoid (most?) fsync calls — and the behaviour it expects is ext3 (which is better at preserving operation order in case of crash than most other filesystems).

                                            I actually had a hard poweroff during/just after commit corrupt a git repository.

                                            So, in a way, the API it actually expects is often not provided…

                                            1. 1

                                              Do you mean its reliance on atomic rename when managing refs? Or some other behavior?

                                              1. 3

                                                I would hope that atomic renames are actually expected from a fullu-featured POSIX FS (promised by rename manual page etc).

                                                But Git also assumes some ordering of file content writes without using fsync.

                                                1. 2

                                                  Renames are only atomic with respect to visibility in a running filesystem, not crash safety, though. So I guess it’s not surprising you’ve seen corruption on crash.

                                                  I’ve been trying to find a way to run a small-scale HA Git server at work — as far as I can tell the only viable option is to replace the whole backend as a unit (e.g., GitHub DGit/Spokes, GitLab’s Gitaly plans). Both GitHub and GitLab started by replicating at a lower level (drbd and NFS, respectively), but moved on. I can say from experience that GlusterFS doesn’t provide whatever Git requires, either.

                                                  1. 1

                                                    There is at least some pressure to provide metadata atomicity on crash (you cannot work around needing that, and journalled filesystems have a natural way to provide it), but obviously data consistency is often the same as without rename. And indeed there are no persistency order guarantees.

                                                    Systems like Monotone or Fossil outsources the consistency problem to SQLite — which uses carefully ordered fsync calls to make sure things are consistent — but Git prioritised speed over portability outside ext3. (Mercurial is also not doing fsync, though)

                                                    And if ext4 doesn’t provide what Git needs, of course GlusterFS won’t…

                                    1. 2

                                      Once again, my unwillingness to learn about new things has paid off.

                                        1. 9

                                          Well, opengit describes itself as a clone of Git, which Got is not, so that’s probably why not.

                                          1. 10

                                            Farhan already has commit access to Got. But he hasn’t used it much yet.