Threads for eterps

  1.  

    Is there some nice way to add “task running” functionality directly to shell.nix? For example, I have the following shell.nix for my blog:

    λ bat shell.nix
    # rm ./vendor -rf && nix-shell --run 'bundle install'
    # nix-shell --run 'bundle exec jekyll serve --livereload'
    with import <nixpkgs> {}; mkShell {
      packages = [ ruby ];
    }
    

    The “task running” functionality are the two comments above, which I just copy-paste in the shell.

    Is there some short, non-horrible way to allow me to type nix shell --run serve and have that to what I want? Preferably with something like nix shell --run list-available-tasks.

    1.  

      I believe you could do something like this in a flake file:

       apps."<system>".task-name = { type = "app"; program = lib.writeScript... ; };
      

      And then run it with “nix run task-name”. I can’t remember the actual definition, so may need some fixing.

      Similar https://www.ertt.ca/nix/shell-scripts/

      1.  

        Indeed!

        Now the shell.nix has

        with import <nixpkgs> {}; mkShell {
          packages = [ 
            (writeShellScriptBin "serve" "bundle exec jekyll serve --livereload")
            (writeShellScriptBin "install" "rm ./vendor -rf && bundle install")
            ruby libffi pkg-config
          ];
        }
        

        and nix-shell --run serve does what I need, many thank!

      2.  

        Why not just put those tasks as separate scripts in a subdirectory?

        Like: https://github.blog/2015-06-30-scripts-to-rule-them-all/

        1.  

          That can work, but I’d love too keep this scoped to a single file, to reduce fs clutter, and scoped to a single CLI entry point (nix shell) to reduce mental clutter (cc @grahamc, this actually sounds like a user pain potentially relevant to determinate systems).

        2.  

          Sure thing, you can just put these little scripts into derivations and make them available in the shell environment:

          let pkgs = import <nixpkgs> {};
              installScript = pkgs.writeScriptBin "install" "rm ./vendor -rf && bundle install";
              serveScript = pkgs.writeScriptBin "serve" "bundle exec jekyll serve --livereload"
          in with pkgs; mkShell {
            packages = [ installScript serveScript ruby ];
          }
          

          With this, you can use nix-shell --run install and nix-shell --run serve.

          If you put a little more sophistication into it, I’m sure you can define the scripts in a way that you can also generate a list-available-tasks script. Something like:

          let pkgs = import <nixpkgs> {};
              makeScripts = scriptDefinitions:
                  let scripts = map ({name, source}: pkgs.writeScriptBin name source) scriptDefinitions;
                      listTasksScript =
                          pkgs.writeScriptBin "list-available-tasks"
                              (concatStringSep "" (map ({name}: "echo ${name}\n") scriptDefinitions));
                  in scripts ++ [ listTasksScript ];
              scripts = makeScripts [
                  {name = "install", source = "rm ./vendor -rf && bundle install"}
                  {name = "serve", source = "bundle exec jekyll serve --livereload"}
              ];
          in with pkgs; mkShell {
            packages = scripts ++ [ ruby ];
          }
          

          I didn’t test any of this, so there is probably a little bit of debugging required to make it work, but I’m confident it can work like this.

        1. 2

          semi-pascal blocks are worse than either full pascal, curly braces, or semantic indentation

          1. 3

            I agree; it’s a small thing but pervasive, and one of the first things anyone will notice about the language. I suppose Rubyists will feel at home, but no one else.

            IMO the reasonable choices would be either curly-braces like nearly every mainstream language, or indentation-based like Python and Nim. But I’m not the one writing the parser :)

            1. 2

              Feel free to open an issue or submit a patch.

              1. 2

                Anything is better than semantic indentation. Even LISP is better :P

                1. 5

                  Anything is better than braces*

                  1. 4

                    For those keeping score at home, everything is terrible and we are all doomed.

                2. 2

                  You mean having loads of ‘begin’ statements everywhere? Pascal’s successors don’t have that either. Only on the unit/proc level

                1. 2

                  Nice, you usually don’t see much going on in this niche. This UX seems comfortable and innovative, even though it’s based on existing concepts.

                  1. 42

                    I’m getting married :)

                    1. 4

                      Congrats!!! May you dodge the traditional post wedding covid and have much marital bliss.

                      1. 3

                        congrats!

                        1. 3

                          WOW congratulations! I hope you enjoy married life even half as much as I do :)

                          1. 3

                            Congratulations!! Enjoy the day and be as present as possible, it goes by so fast!

                          1. 4

                            In most (all?) programming languages specifying a type also implies choosing a particular layout in memory. That’s a pragmatic choice. But they could be separate concerns [1], but that would have an impact on source code readability (at least for as long as source code is plain text).

                            [1] Check out https://www.janestreet.com/tech-talks/unboxed-types-for-ocaml/ to get an impression how these can be separate concerns.

                            1. 10

                              But they could be separate concerns [1], but that would have an impact on source code readability (at least for as long as source code is plain text).

                              Could you describe this in more details? Ada lets you specify type and representation separately in a fairly readable manner in my opinion:

                              -- Create a type Small on two bits where -7 is represented as 0b00, -6 as 0b01...
                              type Small is range -7 .. -4 with Size => 2;
                              
                              -- Create a array type of 8 Booleans, packing it into a single byte
                              type Arr is array (1 .. 8) of Boolean;
                              pragma Pack (Arr);
                              
                              -- Create a struct where the fields span arbitrary ranges of bits
                              type MyRec is record
                                A : Boolean;
                                B : Integer;
                                C : Integer;
                              end record;
                              for MyRec use record
                                 A at 0 range 00 .. 04;
                                 B at 0 range 05 .. 37;
                                 C at 0 range 38 .. 128;
                              end record;
                              
                              1. 5

                                Wow, that is really elegant. Somehow I missed that Ada could do that. Rust could learn a lot from that level of clarity IMO. Thank you for this example!

                              2. 3

                                Rust actually has a bit of flexibility there. Not a huge amount, and less than the compiler actually uses in a practical sense, but some. Notable examples: References to small structures passed to a function may pass the function a pointer, or more likely will just copy the structure into registers and copy it back afterwards. Struct fields do not have any set order, so the compiler will reorder structs to squish out unnecessary padding. There’s not even any promise that two instances of the same struct will have the same representation, as far as I know. And of course, Option<NonNull<T>> may decide to use a null pointer to represent the None variant of the option.

                                On the other hand, contrast Rust with the very first line of your link: “OCaml has a well-deserved reputation for compiling quickly…” :-P (Also wow that’s an excellent talk.)

                              1. 1

                                Does anything recent exist that can be considered a holistic system?

                                1. 12

                                  For personal computing, I would say that the Apple M1 is definitely a holistic system – and there are many instances of personal devices.

                                  1. 6

                                    I agree about Apple Silicon Macs. Asahi Linux’s description of the Apple Silicon boot process is interesting. My favorite part:

                                    One consequence of the boot picker being implemented as a macOS application behind the scenes is that is has full accessibility support (including VoiceOver), which is rather unique.

                                  2. 4

                                    Precursor comes close in the mobile space: https://www.crowdsupply.com/sutajio-kosagi/precursor

                                    1. 2

                                      Thank you for this. This looks a lot like a vague idea that I’ve had, have seen some related discussion on, and have been interested in exploring myself as part of my work on Dawn. This seems like a considerably better basis for a portable runtime (and, potentially, OS) than WebAssembly, and I look forward to experimenting with the concept.

                                    1. 3

                                      This is satire right?

                                      1. 2

                                        Well, the best satire is hard to distinguish from being serious, so I guess it is. :-)

                                        1. 1

                                          Poe’s law in full effect.

                                      1. 3

                                        Scripts to Rule Them All is such an effective and underestimated solution, I get the impression that some people consider the technique ‘dirty’, or too simplistic (as if professional developers wouldn’t do it that way). It’s really powerful though.

                                        1. 3

                                          Start migrating from Arch to NixOS.

                                          1. 2

                                            A write up of that process would be interesting!

                                            1. 2

                                              Hope all goes smooth and well. I went through the same migration around 6 months ago. Haven’t looked back!

                                            1. 2

                                              An intelligent tiling window manager that can automatically re-arrange (on demand) based on the content of its windows (i.e. it would be aware where your browser / terminal has no significant content).

                                              An open educational computing system with OS & compiler (+ simple hardware) that can be understood in its entirety by a single human being. http://www.projectoberon.com comes close, but a bit more modern and less archaic.

                                              A reimagined web browser that builds on itself (i.e. starts with some SVG/PDF level primitives and creates higher level webcomponents with increasing complexity from that, all with a single coherent logical syntax (like s-expressions f.i.)).

                                              A UI framework targeted to power users, like a modern age ncurses that isn’t restricted to the terminal with excellent support for extensible and scriptable apps, supports (but also limits) graphics, lot’s of focus on keybindings an layered VI-like modes.

                                              1. 2

                                                Also wondering if this flow would be done differently in 2020.

                                                1. 6

                                                  I don’t really see the point of the initial pull request. A pull request is a request for changes to be pulled, but if you don’t want changes to be pulled, creating a pull request seems wrong. If it is something to do with being able to ‘review’ code through GitHub’s pull request screen, I recommend avoiding trying to do that: every experience I’ve had trying to review code through GitHub’s pull request/review feature was a total nightmare honestly.

                                                  This just seems like a really unwieldy way of emulating a patch series. This is why mailing list-based git collaboration makes so much more sense than the ‘pull request’ system: you end up emulating the features of mailing lists anyway. If your work flow involves reacting to email notifications about changes to ‘stacked pull requests’ then I’d suggest that you might want to investigate a work flow where people just use email to respond to a patch series.

                                                  Even if you insist on using GitHub’s pull requests, why not just review the changes commit-by-commit instead of breaking each commit out into its own separate pull request?

                                                  1. 3

                                                    Interesting point of view, thank you. I’ll delve into this a bit more. But I’m affraid that patch by email isn’t used for many projects.

                                                      1. 2

                                                        Thanks, I found the first link a minute ago ;-)

                                                    1. 2

                                                      There is a way to create draft pull requests on github, which can’t be merged.

                                                    1. 2

                                                      I admit that I don’t have much experience in a ‘professional’ setting, but at first glance, this seems unwieldy. Submitting diffs in that many pieces, and requesting independent review seems like it would require MORE cognitive load to keep track of. Also, the ‘seems fine’ comment on the monolithic PR seems like a straw man.

                                                      1. 6

                                                        Also, the ‘seems fine’ comment on the monolithic PR seems like a straw man.

                                                        Having a lot of experience with participating in and/or leading teams using PR workflows in professional shops: it’s absolutely not a straw man.

                                                        1. 5

                                                          Also, the ‘seems fine’ comment on the monolithic PR seems like a straw man.

                                                          Could be, but that is how I experienced it in a professional setting.

                                                        1. 2

                                                          How would humor be different in this language? You can’t hide the punchline while you’re setting it up. Are there jokes that are just as funny read backwards as forwards?

                                                          1. 3

                                                            I guess it would be somewhat similar as looking at a single frame cartoon: https://www.google.com/search?q=single+frame+cartoon&tbm=isch

                                                            I am sure humor would work differently in this language, but it might introduce alternative ways to express it?

                                                            1. 2

                                                              I’d also add that, while Sapir-Whorf is in general…well, um, provably wrong, to be blunt…there are certain things, especially around humour, that are language-dependent. Puns are only available in some languages, for example; German can’t really do them. Or they’re available spoken, but not written (for example, Japanese, which has many cognates, but uses a Chinese writing system in part to avoid ambiguity in written forms).

                                                              In this case, I can imagine an almost reverse of the Japanese situation: some of these sentences would be recognizable as drawings, and could have a unique form of written-only pun depending on how that worked out.

                                                              1. 4

                                                                German can do puns. Maybe Germans can’t, though. ;)

                                                                1. 2

                                                                  I speak German okay, not great, so I confess I’m forwarding what I was told. Can you give me a German pun? I love them in English.

                                                                  1. 5

                                                                    Germans can definitely do puns, and puns are in fact pretty common in German (though generally considered to be “lame” jokes). The German name is Kalauer. A classic one: “Es wird nie wieder ein Kalauer über meine Lippen kommen, und wenn du lauerst, bist du kahl wirst.” (Of course it doesn’t work in English, but the translation would be “Never again shall a pun cross my lips, even if you lurk till you turn bald”).

                                                                    1. 1

                                                                      Ooh, nice! Thanks! I’ll need to ask my buddy what he actually meant.

                                                                    2. 4

                                                                      Most famous German pun (at least among English speakers): https://genius.com/Rammstein-du-hast-lyrics

                                                                      The phrases ‘du hast’ and ‘du hast mich’ when spoken can mean either ‘you have’ or ‘you hate’ and ‘you have … me’ and ‘you hate me’ respectively. When written hate is spelled differently, i.e. hast -> hasst.

                                                                      In effect the song tricks the hearer into believing that the singer is accusing them of being hateful towards him. Only when the complete sentence is sung is it clear that the much tamer meaning ‘You asked me’ is meant the whole time.

                                                                      I am not a huge fan but its such a famous example I thought it worth bringing up.

                                                                      1. 1

                                                                        Google for “Wortspiele”.

                                                                        Wikipedia has a few: https://de.m.wikipedia.org/wiki/Wortspiel

                                                                  2. 1

                                                                    That’s a good comparison! I think Scalar families is in part what prompted this thought. You could make the glyph for “big” be comically big, like 10x bigger than the rest of the sentence.

                                                                    Maybe you could show irony by making a big glyph that says “small”, or vice versa. Like the trope of a big guy named “Tiny”.

                                                                  3. 1

                                                                    An ironic situation is ironic no matter which order you learn about it.

                                                                    1. 2

                                                                      Interesting to imagine how this would be with:

                                                                      • emoji like icons
                                                                      • along 3 axis (i.e. in 3D)

                                                                      Obviously handwriting isn’t viable anymore in those cases.

                                                                      1. 1

                                                                        Since mirror reflection has meaning, you might need your glyphs to all have a 3D depth and a handedness, to avoid ambiguity.

                                                                      1. 1

                                                                        The author mentions ‘the tests’ several times, as if all tests are equal. I agree with the author to some degree if he solely means unit tests.

                                                                        1. 2

                                                                          The first 2 minutes are interesting even if you’re not interested in OCaml at all.

                                                                          1. 1

                                                                            That’s exactly what I thought, I never had given much thought on the subtle distinction between types and memory layout.