1. 1

    Fiction: Season of Migration to the North, in the original Arabic. I’ve read the English translation and it’s one of my favorite books.

    Non-fiction: The Real World of Technology by Ursula Franklin. Read a few of the lectures in my first year of undergrad and figured it was about time to read the rest.

    1. 6

      Go’s treating of errors as first-class citizens is, by far, my favorite way of handling errors. Most of my other work is done in TypeScript, and it’s absolutely bonkers that we’re spending all this time typing functions and return types and the like, but when it comes to errors, we basically throw everything about type checking out the window. Obviously TypeScript can only handle so much given the choices in JavaScript, but it still feels like a huge missing opportunity for the language.

      It’s actually gotten to the point where I’m considering making all my functions return tuple types, with a nullable error component just like Go:

      type Err = Error | null;
      
      async function getUser(): Promise<[string, Err]> {
          try {
              const res = await fetch('/me');
              const data = await res.json();
              return [data, null];
          } catch (err) {
              return ["", err];
          }
      }
      
      (async () => {
          const [user, err] = await getUser();
          if (err !== null) {
              console.error(err);
              return;
          }
      
          console.log(user);
      })();
      
      1. 3

        Someone once said to me they thought java style checked exceptions would have been ok, if they were inferred via type inference.

        1. 7

          The problem with Java isn’t checked exceptions, it’s that exceptions are used for stuff that’s not exceptional, like not finding a result. If exceptions weren’t being used where they shouldn’t, it’d annoy people far less than it does.

          1. 1

            I’m not aware of anything that Java-style checked exceptions can do that you can’t do with result types in a language with ML-style types.

            1. 2

              The only thing I can think of is that Java kinda let’s you combine unrelated exception types, while at least in Rust you would have to define an enum for it.

              Plus, Rust is kinda bad with enums, because the individual enum members are not real types on their own, so you can’t say “only this specific error case of this enum can happen”.

              But on the other hand, Java’s throws clause is basically a union, with exception supertypes mentioned in the throws clause subsuming subtypes, so they can accidentality be thrown away while coding.

              1. 3

                The only thing I can think of is that Java kinda let’s you combine unrelated exception types, while at least in Rust you would have to define an enum for it.

                In OCaml you can combine result types with polymorphic variants which work like a set of constructors and are combined and type-inferred by the compiler. Here’s an explanation and so far it seems to work pretty well. Basically, composable checked exceptions in ML.

                1. 3

                  Really cool, thanks for letting me know this!

          2. 3

            I totally feel your frustration with errors, but I think the tuple approach puts too much faith in the developer not making a mistake. Do you know if Go prevents returning both an error and value?

            I would probably go with something like this:

            type Result<T> = ({success: true} & T) | {success: false, err: Error}
            
            async function getUser(): Promise<Result<{user: string}>> {
                try {
                    const res = await fetch('/me');
                    const user = await res.json() as string;
                    return {success: true, user};
                } catch (err) {
                    return {success: false, err}
                }
            }
            
            (async () => {
                const result = await getUser();
            
                // You can only access result.success here.
            
                if (!result.success) {
                    // Since success === false in this block, err can be accessed
                    console.error(result.err);
                    return;
                }
            
            
                // Because we returned when success === false, TypeScript knows that this
                // has {success: true; user: string}.
            
                console.log(result.user);
            })();
            
            
            1. 4

              Do you know if Go prevents returning both an error and value?

              Of course not! It’s not a bug, it’s a feature.

              1. 1

                Do you know if Go prevents returning both an error and value?

                No, and that’s not really a bad thing IMHO. For example I wrote an email address parsing library which can return an error but also returns the list of email addresses it was able to parse, which is useful in various situations (e.g. “sent email to X, but wasn’t able to send to Y”).

                In general, you probably shouldn’t return a value and an error in most cases though.

                1. 7

                  That sounds like a problem waiting to happen. Like a C function that processes half your data and admittedly returns -1 but if you forget to check you might just go ahead and use the half-processed data thinking you’re done (e.g. who will ever notice that only 999 addresses were processed, not 1000 until 3 months later you’re wondering why there is a large discrepancy in what you excepted and what you got at which point it will be too late).

                  1. 1

                    Well the solution to that is to not forget to check it 🙃 But yeah, I get your point. Perhaps a better way would be to return an error with the mail addresses on the error struct, so you need to do something with the error, and if you’re sure you want to get the email addresses anyway you can still get them from the error 🤔 This way it’s at least explicit.

                    1. 2

                      Alternatively you can make that particular failure case (a partial success) not an error and return some kind of state struct where for each address it would state whether it was able to send it or not individually. Since there was some kind of success presumably. This is a discussion of API design, I am not particularly familiar with how that’s preferred to be done in Go, I just try to design APIs that prevent the user from shooting themselves in the foot.

                      1. 1

                        I just try to design APIs that prevent the user from shooting themselves in the foot.

                        Yeah, that’s a good attitude. In this particular case you really needed to ignore errors on multiple levels for things to really go wrong. I don’t remember the exact details off-hand as I wrote this over 4 years ago (and has been running pretty much bug-free in production ever since processing millions of emails daily, which is actually not a bad accomplishment considering there were many issues before) but I would perhaps do it different if I were to write it today, I was fairly new to Go at the time 😅

                        Generally speaking though the mantra of “check your errors!” in Go is strong enough that you can somewhat rely on it; you can run in to problems if you ignore errors and return empty data too.

                    2. 1

                      There are linters that tell you if you forgot to check.

                2. 1

                  Not sure if you like it but you can use the io-ts-promise library to chain async operations together like this:

                  fetch('http://example.com/api/not-a-person')
                    .then(response => response.json())
                    .then(tPromise.decode(Person))
                    .then(typeSafeData =>
                      console.log(`${typeSafeData.name} is ${typeSafeData.age} years old`),
                    )
                    .catch(error => {
                      if (tPromise.isDecodeError(error)) {
                        console.error('Request failed due to invalid data.');
                      } else {
                        console.error('Request failed due to network issues.');
                      }
                    });
                  
                1. 7

                  Clearly defined layers of abstraction. Good documentation.

                  Tests. I really appreciate a well tested codebase. It’s really nice when you have confidence that the existing tests are good.

                  Consistent patterns in the code. Some codebases have A LOT of experimenting. I think that if a team wants to adopt a new pattern, they should put in the effort to make sure that the old way of doing things is replaced. This isn’t always easy, especially with deadlines and aggressive estimations of work. Keeping up to date documentation of “best practices” is a good first step.

                  1. 2

                    I agree with the tests part. They are kinda all the documentation I need — a lot of code has complicated setup requirements and tests give you minimal working examples and show you how you need to call the methods. I don’t know if you can reasonably expect documentation in real-life software projects but at least if there are tests it’s easier to get familiar and build confidence.

                    Another thing is maybe a build system or process that is not too difficult? Like if you can’t manage to get stuff to build because there’s a million dependencies that all need to be built in the right order, that can also be a problem.

                  1. 4

                    Nice write up! I do understand stringify better now :)

                    In the first example, I would agree with @pilif that the regex is a bit of a dangerous solution. I think I’d go for something like this:

                    const mapObj = {
                        _id: "id",
                        created_at: "createdAt",
                        updated_at: "updatedAt",
                    };
                    
                    Object.entries(todayILearn).reduce((obj, [key, value]) => {
                        key = mapObj[key] || key;
                        return {
                            ...obj,
                            [key]: value,
                        };
                    }, {});
                    
                    
                    1. 2

                      Nice functional solution. I write a lot of JavaScript at the moment that needs to be fast and understandable by people without too much JS experience, so my take would be something like this:

                      function replaceKeys(keyMap, obj) {
                        const output = {};
                      
                        for (let key in obj) {
                          const newKey = keyMap[key] || key;
                      
                          output[newKey] = obj[key];
                        }
                      
                        return output;
                      }
                      

                      This wouldn’t handle every case, off the top of my head it wouldn’t handle symbols or a key of zero, but for the author’s usecase it would work fine.

                    1. 2

                      Company: Honor

                      Company site: https://www.joinhonor.com/careers

                      Position(s): Senior front-end, backend, iOS, Android

                      Location: San Fransisco, CA; Austin, TX. Not remote friendly at the moment.

                      Description: https://www.keyvalues.com/honor

                      Contact: nagee.elghassein@joinhonor.com or DM. Please let me know via DM that you’ve emailed me otherwise it might get lost :(

                      1. 9

                        I recently learned about this:

                        first_match = next((x for x in xs if condition(x)), None)
                        

                        Which returns the first matching element, or None (the default in this case) if nothing was found.

                        1. 2

                          https://isthisnagee.com/

                          it used to be a plain html/css/js site but then i redid it with gatsby. Honestly I hate that it’s a gatsby site and I plan to move away from it one day. It’s just too complex for my usecase.

                          1. -10

                            You definitely seem to have ‘issues’ with this project and your V posts are heavily biased. How about instead of shooting projects down, contribute to them to make them better. That is more in the spirit of open source.

                            1. 26

                              I would, but I’ve been blocked from the V github repo with no option for appeal or reversal.

                              1. 5

                                Do you know what caused you to be blocked?

                                1. 8
                              2. 23

                                The history of V so far has been pretty… interesting. Lots of marketing and sparse substance. It came across to me as frequently “snake oil” like.
                                I think if it hadn’t have been so over-hyped and over-sold to start with, people would be a lot more accepting of shortcomings and date slippages.

                                1. 12

                                  Also wasn’t the author notoriously aggressive with all his skeptics? O remember him attacking Andrew Kelley a whole bunch for calling out some of the wilder claims.

                                  1. 2

                                    Yup, I remember that too.

                                2. 16

                                  Didn’t expect to see this comment here. I’ll post the same reply I have you on the orange site:

                                  It’s perfectly fine to critique without contributing. You’ll also notice this:

                                  I can’t open issues myself because I’ve been banned from the V issue tracker, or I would have already.

                                  Also this from their previous article on V:

                                  I hope this feedback can help make V a productive tool for programming. It’s a shame it seems to have been hyped so much for comparatively so little as a result. The developer has been hyping and selling this language like it’s the new sliced bread. It is not. This is a very alpha product. I bet you could use it for productive development as is if you really stuck your head into it, but as it stands I recommend against using it for anything.

                                  1. 12

                                    I also think that there is value in calling out false and)or overhyped claims. It’s not like this is a student’s first project or something similarly worthy of a gentle hand. It also isn’t like V is providing anything very unique.

                                  1. 2

                                    I’d like to try something like this out… is there a vim ‘theme’ that demonstrates the ‘color free editor setup’?

                                      1. 2

                                        It might be his vim-colors-plain theme:

                                        https://github.com/nerdypepper/vim-colors-plain

                                        1. 2
                                            1. 1

                                              to add to some of the others

                                              Though I use vim-colors-plain. I’ve really enjoyed it.

                                              1. 1

                                                I wrote this for myself: everything is yellow, strings are red, comments are grey.

                                                I remember when I started dipping into that idea – a veteran programmer ridiculed the idea of syntax highlighting. “I know what my language does, I don’t need training wheels for my editor!”

                                                “What a ridiculous idea!” I thought. “Of course it’s better and easier with colours. I’ll try without them for some time just to make sure he’s wrong.” Fast forward a few weeks… he wasn’t really wrong. I’m not convinced syntax highlighting really does anything for clarity and ease of working with code. Syntax is usually instantly recognizable from the code layout alone.

                                                What I’d really like to see is an editor that can highlight stuff that make semantic sense, or are meaningful in runtime. Make my slow code red and fast code green, like a highlighting code profiler, for example. Find the code not covered by unit tests and turn it red. Highlight the variable that was written to, but never read in the last 20 runs, stuff like that.

                                                I can recognize syntax of my “native” programming language just fine – it’s the subtle semantics that elude me.

                                                1. 0
                                                  :syntax off
                                                  

                                                  It disables syntax highlighting.

                                                  1. 2

                                                    Well, sure, but the example in the article doesn’t have all coloring disabled: https://files.nerdypepper.tech/bF.png

                                                    1. 3

                                                      By chance I’ve been doing almost exactly the same as the OP has with my Vim colours. I just can’t stand rainbow vomit in my editor.

                                                      I use it with an xterm using solarized colours.

                                                      As you can see, it’s not really release-ready.

                                                      (The copyright comment is that of the theme template I started with).

                                                      1. 1
                                                  1. 3

                                                    I’m no longer using github (except for work), but I would love to help fund! Is there an alternative to github sponsors, like paypal or something else.

                                                    1. 3

                                                      It depends! I have some donation methods listed here: https://github.com/qutebrowser/qutebrowser/blob/master/README.asciidoc#donating

                                                      However, I haven’t figured out the specifics yet for people who want shirts/stickers - the amounts would be higher because of GitHub’s matching and high fees (at least for Paypal). I plan to set something up, probably using Stripe directly, similar to https://drewdevault.com/donate/ - but that’ll probably take another month or two.

                                                      1. 2

                                                        Thanks for pointing out the alternative donation methods section, just donated. Best of luck in your work! Hopefully I can also help out with some code in the future :)

                                                    1. 3

                                                      I’ve gotten really busy at work so haven’t been able to do the past two advent of code challenges, so I’m going to do that :)

                                                      also i’m planning on making a big batch of harira, since it’s been getting a bit chilly here and I would like to have some soup :)

                                                      1. 2

                                                        setting up a new laptop! Bought a Dell XPS13 from a coworker for very cheap and finally got arch installed on it (took me like 4 tries but I’m finally done with that. Currently typing this from the new laptop :)

                                                        firefox is slow though so I’m looking through the docs and forums trying to figure out how to make it act normal.

                                                        1. 1

                                                          Which version/year of the XPS13? I have a 9370 and after a couple of months still ashamedly running WIndows because I like the idea of properly optimised battery/power management and video drivers, but I haven’t done any work yet to figure out how close Linux is to Windows. My last XPS 13 (the first one they produced) killed batteries pretty regularly, but no idea if this could have been driver issue.

                                                          1. 1

                                                            I run Arch Linux on my 9370 without any problems. The battery lasts all day, and the display is beautiful. I strongly suggest giving the switch to Linux an honest try.

                                                        1. 2

                                                          I have a planck at home (non-split) and I actually like it quite a bit. It does make me wonder if I can go one level deeper with something like a gherkin (3x10). Then if that works well it begs the question to me, how deep can I go?

                                                          1. 2

                                                            I felt the Planck would be too little, and got a Preonic recently… Maybe it’s a gateway drug. :)

                                                            1. 2

                                                              I use a plank at work and at home. keyboards now feel too big haha.

                                                              But honestly it took me a while to get used to it. It was not easy for me to get used to the numbers and symbols being on a different layer. But once you get used to it I feel like it’s hard to not have everything this way. to me, the plank is a gateway drug to more planks :)

                                                              1. 1

                                                                yep it’s pretty chill. I can even game on it, which is wild to me. I’ve won games of apex legends with it lmao. I have custom gateron clears to have an activation curve and sound similar to topre. They were lying around from a input club k-type I had.

                                                            1. 1

                                                              not really a fault of the companies, but I’ve had my laptop password stop working twice. Once on a Mac and another time on a windows machine.

                                                              The Mac one was bizarre. I would boot into recovery mode and run a sudo command in the terminal, which would prompt for my password. Putting that in would work. Would proceed to the login screen and enter my password and that wouldn’t work.

                                                              Honestly it’s one of those issues where I would love to dig into the root cause but i don’t know how and I didn’t have the time :(

                                                              (if anyone has any insight as to why it would happen, or some readings, please comment!)

                                                              1. 5

                                                                I’m not too knowledgeable about enterprise mac stuff, but it’s possible for your account local to the machine to have a different password than your account in some LDAP system, if the laptop is configured to authenticate that way. Maybe something like that happened.

                                                              1. 2

                                                                I really enjoyed Jaron Lanier‘s Ten Arguments for Deleting Your Social Media Accounts Right Now, and I think it’s a good way to get the point across to people who “aren’t really into IT, let alone privacy or security”

                                                                1. 2

                                                                  Thanks for the recommendation. Just bought the audio book.

                                                                1. 6

                                                                  console.count can also be useful in situations where you’re trying to find out how many times things are getting called/rendered/etc.

                                                                  1. 9

                                                                    Glad to hear you are doing what you enjoy and getting paid for it. The industry definitely needs more dedicated, self-directed people.

                                                                    I’m curious to hear about your experience with writing for DigitalOcean? Have you just applied and got accepted? What is the process like?

                                                                    You should learn about algorithms and datastructures though: it’s not just helpful, it’s also a very interesting subject.

                                                                    And so are types: a good type system is really about expresiveness with automated checking rather than just the compiler preventing you from doing things it thinks make no sense. Languages with modern type systems like PureScript or Elm are gaining popularity in the JS ecosystem, and some classic languages can be cross-compiled to it: Facebook Messenger is written in OCaml for example. For a teaser: in https://perl.plover.com/yak/typing/notes.html there’s a live example of type checker finding an infinite loop.

                                                                    1. 8

                                                                      Regarding DigitalOcean, they found some articles I wrote on my own site and asked me if I’d be interested in writing for them, so I agreed to do the “How to Code in JavaScript” tutorial series. As for algorithms and data structures, (and types) I am interested in learning them; they’re on the top of my learning in public list. I’ve been playing around with TypeScript as well, to get familiar with more strict typing.

                                                                      1. 5

                                                                        I started learning typed languages with Elm and I found the experience really nice, even though I eventually “outgrew” it, mostly due to lack of interesting features and feeling like it’s kind of a dead end.

                                                                        OCaml/ReasonML is great but not very beginner-friendly atm, though the community is growing and doing a great job at making it more approachable. TypeScript also has a lot of good points, but I don’t think one can use it to its full potential without “being immersed” in a fully typed language first.

                                                                        So I definitely recommend Elm if you wanna get started with types and all that, but I wouldn’t invest on it for the long term.

                                                                        1. 1

                                                                          I was considering learning Go to get more familiar with a typed language.

                                                                          1. 13

                                                                            Go doesn’t really have much of a type system… If you’re mainly looking to learn Go by all means do it, but to really learn typed languages I suggest you look elsewhere.

                                                                            1. 4

                                                                              Go types aren’t really anything to write home about, and there are special rules for builtins that you don’t get to use (and therefore learn about) properly. If you’re comfortable with JS, I’d suggest TypeScript. You can add it one file at a time, and it’s easy to tell it to shut up and trust your word if you’re doing something magic it can’t grok, or you’re just mid-way through converting a module.

                                                                              1. 2

                                                                                Go’s approach to interfaces are pretty uncommon and worth understanding.

                                                                                1. 2

                                                                                  I agree on both counts. Doesn’t make Go a good place to start getting a handle on typed systems in general though, IMO. And to me, the most interesting thing about Go interfaces is the “static duck typing” aspect, which is exactly how TypeScript interfaces work, and is why you can migrate to TS a module at a time, using module-private typedefs even for inter-module communications. TS will happily let you do that, and still tell you when your structures aren’t compatible, which means you don’t have to have a single source-of-truth for any system-wide object shapes until you’re ready to do so.

                                                                              2. 2

                                                                                A quick example. In Go, the usual approach to functions that may fail is to return a tuple of error value that can be nil and an actual value.

                                                                                err, value := doThings();
                                                                                if err != nil {
                                                                                ...
                                                                                }
                                                                                

                                                                                The caller must always remember to actually check the error.

                                                                                In ML/Haskell, where you can have a “sum type” that can have multiple variants carrying different values, there are types like this:

                                                                                (* 'a and 'b are placeholders for "any type" *)
                                                                                type ('a, 'b) result = Ok of 'a | Error of 'b
                                                                                

                                                                                You cannot unwrap an (Ok x) without explicitly handling the other case without getting glaring compiler warnings (that you can make errors):

                                                                                let result = do_things () in
                                                                                match result with
                                                                                | Ok value -> do_other_things value
                                                                                | Error msg -> log_err "Bad things happened"; do_other_things some_default
                                                                                

                                                                                If you have a bunch of functions that may return errors, you can sequence them with a simple operator that takes a value and a function (the function must also return the Ok|Error type). If the value is Error is just returns it, but if it’s (Ok x) then it returns (f x).

                                                                                let (>>=) x f =
                                                                                  match x with
                                                                                  | Error _ as e -> e 
                                                                                  | Ok value -> f x
                                                                                
                                                                                (* if at least one of these functions returns Error, res will be Error *)
                                                                                let res = do_risky_thing foo >>= do_other_thing >>= do_one_more_thing
                                                                                

                                                                                (Note: OCaml also has exceptions and they are used just as widely as this approach, Haskell uses this approach exclusively)

                                                                            2. 2

                                                                              That learning in public list is really cool, what an awesome idea. Also, thanks for sharing this article :)

                                                                            3. 1

                                                                              I’ve been trying to learn more about expressive type systems as opposed to compilers complaining about nonsensical code.

                                                                              Could you please recommend some resources for further reading?

                                                                              1. 2

                                                                                “OCaml from the very beginning” is a very nice book, and it’s not very expensive. For the non-strict way, http://haskellbook.com is good, but expensive.

                                                                                If you want something free of charge, it’s a more difficult question. Stay away from “Learn You a Haskell”, it’s a very bad pedagody. Robert Harper’s “Programming in StandardML” (https://www.cs.cmu.edu/~rwh/isml/) is great and free, but it’s in, well, StandardML, the Latin of typed functional languages. You will have no problem switching to another syntax from it, but while you are in the SML land, you are on your own, with essentially no libs, no tooling, and not many people to ask for help. Tutorials on https://ocaml.org are good but not very extensive.

                                                                            1. 3

                                                                              I’ve been working on a before/after screenshot tool (site, code). I like to take before/after pics for small UI/css changes at work and attach them to code reviews.

                                                                              Code is very much a result of some late night work where I’m half concentrating on it, but it’s Working (for now), and also intentionally done without a front-end framework.

                                                                              Also finished my first big project at work last week and that was fun :)

                                                                              1. 11

                                                                                I was skeptical that the $5k computer had anything to do with Requests. Requests is a small pure-Python library; if you want to work on it, then any cheap laptop is more than sufficient.

                                                                                This line-item justification that people expect for OSS donations is bizarre.

                                                                                More generally, the post is talking about $30k, which after taxes is about $20k. I.e., the equivalent of a few weeks of FAANG dev salary.

                                                                                While the world goes round, OSS participants tear each other apart over a few scraps, and commonly insist that “real OSS devs work for nothing but the glory”. Sounds like Baptist religion.

                                                                                1. 27

                                                                                  Scraps? That’s a decent year salary for a Bulgarian programmer. Please take your Bay Area blinders off. There are more coders, including plenty of equivalent quality, outside of the US.

                                                                                  1. 8

                                                                                    We’re talking about $30k raised one time for a project with many contributors and millions of users.

                                                                                    In any case your righteous reaction is typical of OSS drive-by analysis, extrapolating one-time fundraising outliers to salary. Ask yourself whether it makes sense that the salary of one Bulgarian programmer is newsworthy as a fundraising target for a top-1% OSS project. Just think about that.

                                                                                    1. 14

                                                                                      It would be nice if the world were such that we wouldn’t have to care about how 30K is spent on an OSS project. Unfortunately 30K is all we’ve got, so we do care.

                                                                                      There are places in the world where people kill each other for food: do you also tell them there is plenty of food in the world and they really shouldn’t need to be killing each other over it?

                                                                                      I don’t see how your comment is helping. Drive-by analysis indeed.

                                                                                    2. 2

                                                                                      I think they meant that 30k is scraps to the companies that donated, not necessarily for them or the individual that received it.

                                                                                    3. 13

                                                                                      More generally, the post is talking about $30k, which after taxes is about $20k. I.e., the equivalent of a few weeks of FAANG dev salary.

                                                                                      This is insanity. If you see someone making in a month more than you do in a year don’t bring them down, find out how to bring yourself up.

                                                                                      The open source community has turned into the crab bucket community. Reading the thread here, hacker news and reddit it seems that without noticing the majority of people left are poor, bitter and mentally ill. If this continues we will end up with open source software imploding, like the Firefox fuckup yesterday, because anyone with any skill ends up in corporate closed source or if were extremely lucky in a walled garden which we can see the source code of - like sqlite.

                                                                                      I have stopped my contributions to anything remotely public under my name because I’ve been, doxxed, stalked and had ddos attacks against my sites from people who demanded line item accounting on where I was spending the money I was charging for open services based on top of other open source/hardware projects.

                                                                                      1. 6

                                                                                        I think the implication was that he was taking 1/4 of the funds and splurging with them, where otherwise they could’ve gone to contributors who were doing more of the actual work and who needed them more in the first place.

                                                                                        1. 1

                                                                                          A lot of it has to do with what kind of expectations were set. If you’re saying “yo, I need a new computer, I spent a lot of spare time on this Requests thing, and it would be great if you could show your gratitude for my work by contributing then that would be awesome” then that’s completely fair and reasonable.

                                                                                          If, on the other hand, you say “I need money to develop this” and then buy a $5k computer with it, then that’s … a bit stranger.

                                                                                          I’ve donated some large amounts of money (>€100) to some projects to make specific certain things happen, but I would never donate that kind of money so someone can buy a new computer. I might donate €5 or €10, but not €150.

                                                                                          As far as I can find, this is the only info about the fundraiser, and it certainly seems to suggest that contributions will be directly used for Requests development, by paying someone (“we lost our sponsored maintainer, we are seeking community financial contributions towards the development of Requests 3.0”). I certainly don’t see a $5k computer mentioned anywhere.

                                                                                          I don’t think it has to do with “tearing each other apart from scraps”, but with “spending money in a different way than you suggested you would”.

                                                                                          1. 2

                                                                                            I don’t think it has to do with “tearing each other apart from scraps”, but with “spending money in a different way than you suggested you would”.

                                                                                            I’m pointing out a macro effect. When resources are scarce, conflict happens. I’m suggesting that OSS as a culture embrace and normalize money instead of the abstinence culture proselytized by the loudmouths. That’s step 1.

                                                                                            It is much too rare for projects to raise money. It should be 1000x more common. This particular case of squabbling over scraps is ghetto violence, something on page 8 that the locals care about while the structural mistakes go ignored.

                                                                                            Even in this thread there is someone blathering on about the evils of money. (Not to mention starting other rumors. Wow. Again: tearing each other apart for scraps.)

                                                                                            1. 1

                                                                                              As a general point I don’t disagree. But in this specific case there are a lot of signals that this person spent the money in a different way than he indicated he would. And that is, regardless of the merits of the general point, pretty darn sketchy.

                                                                                              I don’t think it’s a “local” issue, as it involves a fairly high profile project with a fairly high profile developer. If I steal $5 then that won’t even make the papers but if an MP does it it’ll make the front page.

                                                                                          2. -3

                                                                                            But if you start relying on money, you defy the original purpose of the open-source, that is to be free from profit logic. Yeah, in 2019 it sounds ridicolous because corporate interests invaded and destroyed most of the OSS communities, but many still stick to the same values. Clearly this favours the corporate interests because they get free work from volunteers, but the alternatives are to either abandon OSS as a form of political struggle and contribution to the commons or embrace the dominance of corporations over the OSS. Both of them are unreasonable to many. Maybe one day they will figure out.

                                                                                            1. 23

                                                                                              …the original purpose of the open-source, that is to be free from profit logic…

                                                                                              I don’t think open-source was ever meant to be anti-profit.

                                                                                              1. 22

                                                                                                Stallman even encouraged selling free software.

                                                                                                1. 2

                                                                                                  being free from profit logic doesn’t mean to be anti-profit. If profit is just a mean to keep doing what you’re doing you can be free from profit logic. If you do what you do to maximize your profit, you’re profit driven and profit will be the measure of your success. There’s a huge difference.

                                                                                                  1. 5

                                                                                                    There’s no inherent conflict between being profit-driven and embracing the Free Software or Open Source philosophies. People thought there was back when software was being sold shrink-wrapped in stores on CDs, but everyone has long since realized that that’s not how software should be sold–the real profits are in support fees.

                                                                                                    1. 0

                                                                                                      There’s no more conflict, you’re right. That’s why more and more people are driven away from Open Source as a tool to do good. Now it’s just a tool to make money.

                                                                                                      1. 3

                                                                                                        How do you arrive at the conclusion that people are more motivated by money than ‘good’ in Open Source?

                                                                                                        1. 0

                                                                                                          I’m not saying that. I believe the vast majority of people in open source are still driven by the will to do good. Nonetheless the relationship between positive impact on society and free work for companies is getting more and more imbalanced, leading more and more people to criticize open source as something intrinsically positive and distance themselves from projects that have been colonized by corporations. That said, the form of Free Software is still a reasonable medium to promote an initiative that aims at the common good, but in 2019 the myth that this is sufficient to have a positive impact is becoming weaker and weaker.

                                                                                                        2. 1

                                                                                                          Would you rather it be unprofitable? You have to accept that software is not just a hobby, but also an industry. It’s going to be used as “a tool to make money” no matter what; all we can do is choose whether to view that fact as an obstacle or an asset.

                                                                                                      2. 1

                                                                                                        I agree that having something other than profit in mind is nice. But when it comes down to it, it’s all about money, and so you’ll come across times when you have to choose to compromise one or the other: your morals or your profits. Sometimes profits should come dead-last: there are certainly some projects I’d like to see no work done on at all, such as Google’s various government tie-ins. But for other (less controversial) stuff, such as databases and frameworks, money is what keeps the updates coming. Maybe someday all our software will be developed by altruists. Until then, we’ll just have to settle for the compromises that come with developing software in a primarily capitalist economy.

                                                                                                    2. 11

                                                                                                      The original goal of open source software was to commercialize free software: https://youtu.be/vjMZssWMweA?t=2748

                                                                                                      There’s the people who invented it saying exactly the same thing.

                                                                                                  1. 14

                                                                                                    Nice write up. I actually didn’t know about A, so I’ll be using that today. I usually do $i or $a to insert at the end of a line.

                                                                                                    52gg jump to line 52

                                                                                                    I might be wrong, but I think you can also do :52 to go to line 52.

                                                                                                    1. 10

                                                                                                      And also 52G

                                                                                                      (gg is a vim-ism, so if you’re just using plain old vi you need to use <number>G or :<number>)

                                                                                                      1. 10

                                                                                                        I might be wrong, but I think you can also do :52 to go to line 52.

                                                                                                        I love using this command. It is also possible to copy or move by expanding the command. Using :52co12 will copy line 52 to below 12. Using :52co. will copy below the current line. It even works with ranges :52,55mo. will move 52 through 55 to the current line.

                                                                                                        1. 10

                                                                                                          53,55norm! A; will at a semicolon to the end of every line in that range

                                                                                                        2. 3

                                                                                                          Thank you!

                                                                                                          Yep, I actually prefer the :52 style but I didn’t want to get into explaining : commands for beginners for this article. ;-)

                                                                                                          1. 1

                                                                                                            I usually avoid ‘$’ because I’m less accurate typing it haha!

                                                                                                            1. 3

                                                                                                              I have a very small keyboard so R, $, and 4 are the same key, but with different modifiers.

                                                                                                              1. 2

                                                                                                                is it a Planck?

                                                                                                                1. 2

                                                                                                                  Yup!

                                                                                                                  1. 2

                                                                                                                    I’ve been using one for more than a year now. I like it so much, specially that, by default, the escape key replaces caps lock, it’s perfect for vim.

                                                                                                              2. 1

                                                                                                                Cool kids do nnoremap L $.

                                                                                                                1. 1

                                                                                                                  That’s a good idea. Unfortunately, I work in two separate vim-emulating editors which don’t support these gizmos.

                                                                                                                  1. 1

                                                                                                                    I actually use L M and H quite a bit, especially when I need to look at neighbouring code. I don’t use the split feature very often, though, do you?

                                                                                                                    1. 1

                                                                                                                      Even cooler kids do:

                                                                                                                      " Jump to first character or column
                                                                                                                      noremap <silent> H :call FirstCharOrFirstCol()<cr>
                                                                                                                      
                                                                                                                      function! FirstCharOrFirstCol()
                                                                                                                        let current_col = virtcol('.')
                                                                                                                        normal ^
                                                                                                                        let first_char = virtcol('.')
                                                                                                                        if current_col <= first_char
                                                                                                                          normal 0
                                                                                                                        endif
                                                                                                                      endfunction
                                                                                                                      

                                                                                                                      Explanation.

                                                                                                                      (I realise you were talking about nnoremap L $ and not nnoremap H 0, but I think the two ideas are related and I thought this might useful to somebody out there).

                                                                                                                      1. 2

                                                                                                                        That can be a lot shorter with expression mappings. This is what I map (to Home):

                                                                                                                        noremap <expr> <Home> col('.') is# match(getline('.'), '\S') + 1 ? '0' : '^'
                                                                                                                        imap <silent> <Home> <C-O><Home>
                                                                                                                        

                                                                                                                        Expression mappings are really useful!

                                                                                                                        Some other notes:

                                                                                                                        • normal means that Vim will use the currently mapped key, rather than the default one. So if you nnoremap 0 .... then your mapping may break since normal 0 will run that mapping. Use normal! to always ignore user mappings. You should almost always use normal! unless you have a specific reason not to.

                                                                                                                        • You can create a script-local function with fun s:FirstCharOrFirstCol() and then refer to it with nnoremap H <SID>FirstCharOrFirstCol(). I personally much prefer this as it doesn’t pollute the global namespace so much with what is essentially useless stuff.