It doesn't even have a logical history. Despite having used it for many years, I still don't understand why when I type one command (eg make), and then another (eg out.exe), I have to toggle between pressing up or pressing down from the new command-prompt to access the previous commands.
I can't make the window more than 80-characters wide dynamically. (I don't want to change settings and restart the program to get the width to change.) So any time I want to copy and paste one of the infamous wall-of-text C++ template errors, I have to waste a lot of time reformatting the text.
Copy-and-paste as well is just complete garbage that takes forever.
I have to dump batch files into a folder in PATH because there's no alias support nor .profile startup script.
I can't color-code the prompt separately for visibility. There's no tab-completion. There's no shell escaping backticks. On and on.
Batch scripts are just hopelessly broken. It really feels like we're abusing the hell out of them to do things they were never intended to do. The language is closer to Malbolge than C.
PowerShell is a whole other can of worms. I don't care for it either, but that'd be a separate discussion.
Bash on Windows sounded promising, up until "Windows 10 only" and "doesn't play nice with the regular Windows environment."
> It doesn't even have a logical history. Despite having used it for many years, I still don't understand why when I type one command (eg make), and then another (eg out.exe), I have to toggle between pressing up or pressing down from the new command-prompt to access the previous commands.
With readline-style editing, as in bash, when you go back to an earlier command and re-run it, it is added to the end of the history and your "position" in the history is reset to the end. So if you want to go back to an earlier command again, you always hit "up".
In cmd.exe, when you go back to an earlier command and re-run it, you are simply going back to that earlier position in the history. When you run it, your location in the history is now immediately after the command you just ran. So to run the following command again, you now hit "down" rather than "up".
I think it's pretty logical and I actually quite like it (after the first half an hour of familiarisation, each time I have to use it). It's just different.
I also genuinely like PowerShell, but I'm with you on everything else.
Interesting! I never realized the logic behind it, thanks for expanding on it.
I definitely don't care for it at all. Much easier for my mind to think of the list of previous commands as a straight list, than trying to conceptualize 'where I am at' in my list of previous commands, and how executing a new command would then jump me somewhere else entirely. But I'll respect your difference of opinion.
> I also genuinely like PowerShell
To expand on this. As a Unix user with decades of experience writing shell, I find it easier to write a shell script than a PowerShell one for any given job. But I am a lot more confident that the PowerShell one will work correctly.
I take care with argument handling and the like in my scripts, but I still feel that testing a shell script with a specific set of inputs only really tells me whether it works with that set of inputs. It's almost certainly possible to craft an alternative set of inputs that will break it. I don't feel that way about PowerShell.
On the other hand, I do find it much easier to reason about performance with shell scripts. Their simple streaming structure parallelises well and the individual commands have generally predictable performance and scaling characteristics. I'm a lot less confident about that aspect of PowerShell.
https://msdn.microsoft.com/en-us/library/windows/desktop/ms6...:
"Console aliases are used to map source strings to target strings. For example, you can define a console alias that maps "test" to "cd \a_very_long_path\test". When you type "test" at the command line, the console subsystem expands the alias and executes the specified cd command. To define a console alias, use Doskey.exe to create a macro, or use the AddConsoleAlias function."
https://www.microsoft.com/resources/documentation/windows/xp...:
"Executing registry subkeys
If you do not specify /d in string, Cmd.exe looks for the following registry subkeys: HKEY_LOCAL_MACHINE\Software\Microsoft\Command Processor\AutoRun\REG_SZ HKEY_CURRENT_USER\Software\Microsoft\Command Processor\AutoRun REG_EXPAND_SZ If either one or both registry subkeys are present, they are executed before all other variables."
"There's no shell escaping backticks."
https://technet.microsoft.com/en-us/library/bb490909.aspx:
"Iterating and file parsing Use file parsing to process command output, strings and file content. […] for /F ["ParsingKeywords"] {%% | %}variable in ('command') do command [CommandLineOptions]"
Good UI? I've seen better. It also doesn't affect the conclusion that the cmd shell is bad, but the functionality does exist in some, often weirdly limited, form.
> I can't make the window more than 80-characters wide dynamically.
Windows 10 fixes this. You can resize the window and it wraps text better than any other terminal out there.
> Copy-and-paste as well is just complete garbage that takes forever.
Turn on Quick Edit. Now drag to select and right click to copy.
> There's no tab-completion.
Tab completion for filepaths works quite well for me.
Don't want to derail with Windows 10 arguments, but for me, that's a total deal breaker at this time. But thanks for pointing it out! Now if I find out Windows 10 can handle LF-formatted text in Notepad, I'll have to check and see if Hell froze over :P
> Turn on Quick Edit. Now drag to select and right click to copy.
It's not just having to go to the menu to click edit, it's that it bounds selections as a rectangular box when you paste the results. I also don't like the way quick-edit is so quick to select white blocks just by clicking in the window without dragging. Then to get rid of it, I have to right-click and kill whatever was in my clipboard. A bit OCD there, but ... I like bash a whole lot more. Normal text highlight, middle-click to paste what was highlighted elsewhere, and it's formatted properly. This is especially important when copying those 200-character long C++ template error messages.
> Tab completion for filepaths works quite well for me.
...... indeed there is. How in the world did I miss this?! Very sorry, I can't edit the parent post to fix this now.
Command line + mouse = GUI, not command line.
It is because the shell history has its own completely invisible cursor, and the cursor is not reset after a command. So when you press <up> three times, then press <enter>, your history cursor is still at -3 (actually, -4). If you then want to move to command -2, you need to press <down> instead of <up>.
The real fun comes when you edit commands in your history (so press <up>, then edit the command line). I'm still not quite sure how Microsoft handles that.
Also, you can use F7 to browse your command history - that may help a bit.
1. The parser allows modifying a .bat file during its execution and having those changes execute without restarting the Batch interperter. [1] This is in keeping with the rationale for batch processing -- facilitating serial execution of computationally expensive operations.
2. The Batch interpreter allows self modifying code.[2] In the early 1980's when Batch was designed, sophisticated COBOL programmers might have felt right at home. Lisper's were probably more hit and miss.
This is a case where historical context is useful. Today, it might perhaps be worth mentioning Powershell in a discussion of the Windows command line. Batch was the DOS command line and exists in Windows for evolutionary reasons.
In the days when abundant RAM and fast CPU speeds were prefixed with "mega" and distributed computing often happened at BAUD rates, not restarting a process was a big deal. More importantly, then as today, the execution speed of the batch interpreter was not a critical section of a batch process.
[1]: https://stackoverflow.com/questions/906586/changing-a-batch-...
http://www.os2museum.com/wp/dos/dos-1-0-and-1-1/dos-1-0-dir/
To a first approximation, I'd expect that 1980's Unix programmers would generally be working in environments more accepting of restarting a batch process when there was an error in the code, i.e. significantly less likely to hold a clerical or secretarial "TCP report" job in a regular commercial office. Though that split has become less likely, it's still pretty uncommon for a computer user with little control of their work environment and deadlines to be using *nix rather than Windows.
Batch was restricted by DOS, I wish I had never learned it, but it did come in handy for launching games.
Easy enough to fix by having the menu program put the run script (.bat file) into the Novell equivalent of each user's home directory, but it was a real WTF moment at first :-)
Try type utf8Encoded.txt > out.txt in cmd.exe and posh. Cmd works and posh fs it up.
And after you do figure out utf8 encoding in posh, it'll always add a BOM just to screw you
[IO.File]::WriteAllLines($filename, $content)
(from https://stackoverflow.com/questions/5596982/using-powershell...)
Powershell is like a poor Java/C# interpreter instead of a quick and dirty shell.
You can see the difference in philosophy here, cmd (and bash, to a certain extent) are simple and don't try to do sneaky things silently, even if it means you might have to do a little more yourself e.g. performing character set translations explicitly. The behaviour is straightforward and predictable. PS attempts to be more "user-friendly" by doing some hidden conversions presumably so the user doesn't have to explicitly do character set translations, and when it works it works well; but when it fails, it fails spectacularly.
http://steve-yegge.blogspot.ca/2006/03/execution-in-kingdom-...
I don't deny that it is much more powerful than cmd, but it feels a lot like "emacs rather than vi" in its design, and I much prefer the latter (which would be more (ba)sh-like.)
* usable tab-completion: scrolling through all available cmdlets is a poor substitute, and usually increases my keypresses instead of decreasing it.
* workable history editing: if I edit a previous command, I must remember to never use tab completion again, because pressing <tab> halfway in a command erases everything following the cursor
* consistent interface: In a powershell shell window, I can use left mouse button to select and copy, right mouse button to paste. In command shell window, I must use right mouse button to select "Mark" in context menu before even left-mouse selection works. In powershell ISE, left mouse button selects but does not copy, right mouse button still opens a context menu.
My first impression of it? It went like this:
Task: you need to connect to Hyper-V VM console via Remote Desktop.
Hiccup: for that, you need to know it's GUID. How to find it out? Just run this handy posh script... (https://blogs.msdn.microsoft.com/virtual_pc_guy/2014/11/25/u...)
Another hiccup: That script does not work, it needs some library that's not loaded by default. Try to find out how.
Another hiccup: It does not load, because it breaks some policy, that's off by default. Investigate, what to do.
How it ended: forget it, I have better things to do than solve problems with Powershell. Look into VM files and find out, that it's one of the GUIDs there.
Result: Won't touch posh again and anyone singing about its virtues is getting promptly ignored.
Maybe it's not fair to Powershell, but the first impression counts.
I was trying to run a Bash script from a Git repo mounted in a Docker container. When running the Bash script, I kept getting all kinds of errors. I ran the exact same script in the same Docker container on a different Linux computer that had cloned the repo. It turns out the \r Windows line endings (which I later normalized in Git settings) caused my script to barf.
Though honestly, Windows just doesn't even matter any more to me, I haven't needed to touch an MS product in years...
I've never gotten into PowerShell but I have absolute respect for the concept behind it, and how much more advanced it is than any shell you can find on UNIX. Think about it: instead of piping several commands through an unspecified string protocol that varies between each command (essentially what UNIX does), you are now piping real language objects in a uniform binary protocol defined by the shell itself.
Which is in fact a bad idea, because in order for stdin to accept objects and stdout to output objects, now those commands have to be powered by PowerShell and .NET. In other words you're in a very finite and closed environment that does not interoperate with the outside world.
You know, love or hate Unix, but the fact remains that this family of operating systems, including its command line, has survived the test of time. And it has done so because it has at its core a set of philosophical principles. And one of those is that programs that handle text streams are preferred, being highly interoperable, as text is a universal interface [1]. And you know it's funny how people loathe Unix, but at the same time rediscover its principles (and often implement them badly) again and again.
Configuration customization isn't really needed, only the usual date.timezone to get rid of the warning (and hell, this is annoying! can't PHP just use the OS-provided time zone?!), and in extremely rare cases the memory limit and max_execution_time.
You dont even need to give your software a ".exe" extension to run code.
Just rename a program removing its .exe extension, then call it from the command line. It will run!
Its perhaps better to compare dos BATch files with bash.
only 600kb to enjoy your sanity back
For the moment, I'm still stuck with Cygwin, shaking my head a bit too.
I'm a Microsoft fanboy and I find Python far more structured and faster than any of the above for anything beyond the most simple shell scripts. (If only the inventor of PowerShell had spent ten minutes outside the Microsoft ecosystem before locking himself in a seafoam green office for two years...)
Doesn't solve the IT admin scenarios PowerShell is good for but I don't go there. And if I did, I'd use C# anyway. No need to learn a new language to loop and call objects, that's solved.
With the .NET Core stuff, I'm using C# and Microsoft.DotNet.Cli.Utils and the end result is briefer and saner than Python argparse, and file operations work great cross platform. Less issues than even Python, plus I can use LINQ to sort and remove dupes. Handy.
As for the "Windows command line" (cmd.exe) well, it still sucks. Console2 plus Clink and ... well, you'll still miss zsh on cygwin or what just works out of box on Mac... but, hey, it's a start.
... and it's all true.