How to write to a text file upon creation? - bash

I'm self-learning command line code and can't seem to find an answer.
I'm using the standard MacOS Terminal application to create directories/files for practice.
my question is, can I use a code to include what would get written to the file as I create it?
I've tried:
touch one/texttest.txt echo "Hello"
But this only creates 3 files, one called hello, one called echo, and a third called texttest.txt within the "one" folder
I've also tried these and got the same results:
touch echo "Hello" ~/one/texttest.txt
echo Hello ~/one/texttest.txt
touch one/texttest.txt Hello
I can't seem to find any solutions for the standard terminal app with 0 plugins, is this even possible?

This should work:
echo "Hello" > one/texttest.txt

touch one/texttest.txt echo "Hello"
That is the touch command with three arguments: one/texttest.txt, echo, and Hello (the shell removes the quotes).
touch echo "Hello" ~/one/texttest.txt
touch one/texttest.txt Hello
These are the same as the first one (different arguments but same concept).
echo Hello ~/one/texttest.txt
This is the echo command with two arguments: Hello, and ~/one/texttest.txt (only the ~ will have been expanded to your home directory by the time echo sees it).
touch only creates files (and updates timestamps) it doesn't write content.
You could have a touch command that takes content also but I don't know of one.
Luckily you don't need one because the shell can do this for you.
You use echo Hello to run echo and have it spit out Hello and you tell the shell to "redirect" the text to a file instead of the screen.
echo Hello > texttest.txt
It is worth pointing out that redirection creates the file whether you write anything to it or not (and in fact whether the command works or even exists or even if a command is given).
$ ls /tmp/texttest.txt
ls: /tmp/texttest.txt: No such file or directory
$ flekjfe Hello > /tmp/texttest.txt
$ ls /tmp/texttest.txt
/tmp/texttest.txt
So you can use > file all by itself to create a new empty file for example.

You can use output redirection command_output > file
For more details : http://tldp.org/LDP/abs/html/io-redirection.html

Related

What does !!:2 mean in Mac or Linux?

Today I saw a command in Mac:
touch !!:2/{f1.txt, f2.txt}
I know the use of touch command but what does !!:2 does in this command. I don't have Mac and tried in Linux It is giving some weird output. If anyone could explain more expression like this it would be great.
touch updates file timestamp (to current time, given no arguments)
!! is 'History expansion' operation, retrieving previous command from bash history log in this form (two exclamation dots), alias for '!-1'
:2 is word specifier, retrieving 2nd command argument. E.g. if previous history command was ls -l /tmp, !!:2 will render to '/tmp'
{f1.txt,f2.txt} is called 'Brace expansion'. Brace expansion requires single word string without unescaped white spaces (it's definitely a typo in the question). For example, foo{bar,baz} will be expanded to 'foobar foobaz'
So, let's assume we run bash command
ls -l /tmp
Now, touch !!:2/{f1.txt,f2.txt} will produce
touch /tmp/f1.txt /tmp/f2.txt
https://tiswww.case.edu/php/chet/bash/bashref.html
!! refers to the previous command. This is a synonym for ‘!-1’.
:2 refers to the second argument.
So for example :
echo "content" > foo
cp foo bar
cat !!:2
Displays the content of bar.
!!:2 is the second argument of the previous command.
Which one was it in your example?

What command makes a new file in terminal?

If mkdir creates a new directory, what creates a new file? for example "something.text".
I tried couple of commands mkdir (FileName) -- works fine. But I didn't know how to create a new file inside a directory. I know that I can always go to my project folder then create my new file but I want to know how to do that using terminal to increase productivity.
On Linux there are mutiple options
The typical used one is touch
touch bar.txt
However you may also use echo if you want to create and write to the file right away
The following command tells to create bar.txt and put foo inside of it
echo foo > bar.txt
You may also use >> which appends to an existing file
The following command puts bar at the end of bar.txt, in a other words, bar will display after foo inside bar.txt
echo bar >> bar.txt
You can either use touch:
$ touch something.txt
or > operator to redirect nothing to a file and effectively creating it:
$ > something.txt
or
$ : > something.txt
Note that last 2 commands will truncate file contents if file already exists.
If you mean on Linux so the command is touch.

How do I call rename successfully from a bash script on Ubuntu?

I have a bash script #!/usr/bin/env bash that is called part of a make process. This script creates a directory with the files pertinent to a realise and then tars them up. I would like to take a copy of the directory and rename some of the files to replace the version identifier with the word "latest". This will make it simple to script the acquisition of the latest file from a web-server. When I run my script, the call to rename seems to do nothing, why is that?
#!/usr/bin/env bash
DATE_NOW="$(date +'%Y%m%d')"
product_id_base="$1"
firmware_dir="${product_id_base}-full-${DATE_NOW}"
# ...rest of file ommitted to protest the innocent
# It creates and fills the ${firmware_dir} with some files that end in
# -$DATE_NOW.<extention> and I would like to rename the copies of them so that they end in
# -latest.<extention>
cp -a "./${firmware_dir}" "./${product_id_base}-full-latest"
# see what there is in pwd
cd "./${product_id_base}-full-latest"
list_output=`ls`
echo $list_output
# Things go OK until this point.
replacment="'s/${DATE_NOW}/latest/'"
rename_path=$(which rename)
echo $replacment
perl $rename_path -v $replacment *
echo $cmd
pwd
$cmd
echo "'s/-${DATE_NOW}/-latest/g'" "${product_id_base}-*"
echo $a
# check what has happened
list_output=`ls`
echo $list_output
I call the above with ./rename.sh product-id and get the expected output from ls that indicates the present working directory is the one full of files that I want renamed.
$ ./rename.sh product-id ET-PIC-v1.1.dat ET-PIC-v1.1.hex
product-id-20160321.bin product-id-20160321.dat
product-id-20160321.elf product-id-20160321.gz 's/20160321/latest/'
/home/thomasthorne/work/product-id/build/product-id-full-latest
's/-20160321/-latest/g' product-id-*
ET-PIC-v1.1.dat ET-PIC-v1.1.hex product-id-20160321.bin
product-id-20160321.dat product-id-20160321.elf product-id-20160321.gz
What I hopped to see was some renamed files. When I directly call the rename function from a terminal emulator I see the rename occur.
~/work/product-id/build/product-id-full-latest$ rename -vn
's/-20160321/-latest/g' * product-id-20160321.bin renamed as
product-id-latest.bin product-id-20160321.dat renamed as
product-id-latest.dat product-id-20160321.elf renamed as
product-id-latest.elf ...
I have tried a few variations on escaping the strings, using ` or $(), removing all the substitutions from the command line. So far nothing has worked so I must be missing something fundamental.
I have read that #!/usr/bin/env bash behaves much like #!/bin/bash so I don't think that is at play. I know that Ubuntu and Debian have different versions of the rename script to some other distributions and I am running on Ubuntu. That lead me to try calling perl /usr/bin/rename ... instead of just rename but that seems to have made no perceivable difference.
This string:
replacment="'s/${DATE_NOW}/latest/'"
will be kept exactly the same because you put it between single quotes.
Have you tried with:
replacment="s/${DATE_NOW}/latest/"
This one worked on my Ubuntu, without perl:
$ ./test_script
filename_20160321 renamed as filename_latest
filename2_20160321 renamed as filename2_latest
filename3_20160321 renamed as filename3_latest
test_script content being:
#!/bin/bash
DATE_NOW="$(date +'%Y%m%d')"
replacment="s/${DATE_NOW}/latest/"
rename -v $replacment *

Using cat in a bash script : escaping troubles

I'm very bad at regex and escaping characters.
I want to use the 'cat' command in a bash script like this :
echo `cat working-dir/*OUTPUT` ;
That should print on screen, every files in the working-dir that end with "OUTPUT" but this is not working
Later in that program, i would like to do this :
cat working-dir/*OUTPUT >> result_file.txt
But is not working either :(
Can you help me please?
Why are you using echo, or backticks, at all?
cat working-dir/*OUTPUT
Similarly,
cat working-dir/*OUTPUT >> result_file.txt
...certainly should work. Please provide a complete script for reproducing any failure that you see, including setup (creating working-dir, putting at least one file ending with OUTPUT into it, running the cat, and observing it to fail).

invoking a Bash script indirectly - and a puzzle about how to use `source` appropriately

I have a script called greeting_script as follows:
GREETING='Top O the Morning to Ya!'
export GREETING
echo $GREETING
If I run this script from the command line, I see the following result:
> export GREETING='hello'
> echo $GREETING
hello
> source greeting_script
Top O the Morning to Ya!
> echo $GREETING
Top O the Morning to Ya!
This is what I expect. I have another script called 'indirect_greeting_script' as follows:
#!/bin/bash
source greeting_script
If I run this script from the command line, I see the following:
> export GREETING='hello'
> echo $GREETING
hello
> indirect_greeting_script
Top O the Morning to Ya!
> echo $GREETING
hello
Note that I have the permissions set on indirect_greeting_script in order to enable it to be executed directly at the command line. I also have the first line that #!/bin/bash
Obviously when I invoke greeting_script indirectly the results are not being stored in my current environment properly. I would like for the indirect_greeting_script to be an executable at the command line and not a file that I have to source. What is it that I don't understand?
NOTE: it works as expected if I make indirect_greeting_script a normal file (i.e., not executable), remove the leading line that reads #!/bin/bash and invoke it with the source command.
A child process cannot modify the environment of its parent. export simply marks a parameter to be included in the environment of any children processes. When you call it in your script, it does not cause the value to be sent back to the parent.

Resources