Initial commit: HPR Knowledge Base MCP Server
- MCP server with stdio transport for local use - Search episodes, transcripts, hosts, and series - 4,511 episodes with metadata and transcripts - Data loader with in-memory JSON storage 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
236
hpr_transcripts/hpr2739.txt
Normal file
236
hpr_transcripts/hpr2739.txt
Normal file
@@ -0,0 +1,236 @@
|
||||
Episode: 2739
|
||||
Title: HPR2739: Bash Tips - 19
|
||||
Source: https://hub.hackerpublicradio.org/ccdn.php?filename=/eps/hpr2739/hpr2739.mp3
|
||||
Transcribed: 2025-10-19 16:04:10
|
||||
|
||||
---
|
||||
|
||||
This episode of HBR is brought to you by Ananasthost.com, get 15% discount on all shared hosting with
|
||||
the offer code HBR15, that's HBR15, better web hosting that's honest and fair at Ananasthost.com.
|
||||
Hello everybody, this is Dave Morris for Hacker Public Radio. Today I'm doing bash tips
|
||||
number 19 and I'm still talking about a raise and this is part 4 but it's the last in the group
|
||||
about a raise. Do I hear a sigh of relief? So in the last show we looked at parameter expansion in
|
||||
the context of a raise. There's more that could be said about that but I think I'll probably not say
|
||||
any more, unless I'm called to do so in the future. But in this episode I want to look at the
|
||||
command we've already seen in brief called declare and it's also got a synonym which is type set
|
||||
and then there's some other related commands read only and local and there's a couple more that
|
||||
allow you to load data into a raise which are called map file with the synonym read array and read
|
||||
which we've seen in passing several times. So declare or type set, it's there because the synonym is
|
||||
there because that's what it's called in the corn shell and so it was been added to bash for
|
||||
that reason. So we've seen how you use declare to create a raise and so forth but it's used
|
||||
generically to create variables and to give them attributes. There are a whole list of options to
|
||||
declare but rather than going through them all which I don't think I need to do really, I thought
|
||||
I'd just spend a little bit of time looking at the ones that relate to a raise partly because I
|
||||
found them quite interesting to discover a few euro two back when I first started playing around
|
||||
of the raise. Now there are, this command is a little odd, there's not many commands do this,
|
||||
the options usually consist of a hyphen followed by a single letter, it's quite common in Unix to do it
|
||||
that way but some of them you can reverse their effect by replacing the hyphen with the plus sign
|
||||
which is all fine and nice and stuff, it's a bit confusing because there's not much else that
|
||||
you can do that with. Anyway, let's start with an option you probably not going to use very much
|
||||
but I think it's quite cool so I thought I'd mention it, it's the hyphen i, lowercase i option,
|
||||
what that does is make the variable you're declaring which would raise what we're thinking about here,
|
||||
behaviors if it's an integer only an integer and whenever you assign anything to it an arithmetic
|
||||
evaluation is performed as if it was inside the double parentheses which we've talked about in
|
||||
this series so I thought the easiest way to explain this was to put together a downloadable script
|
||||
which is called bash19 underscoreex1.sh and it shows what you can do with an array declared this way
|
||||
so just to go through it briefly because I think it's pretty well self-documenting there's
|
||||
little comments in it. I'm declaring two arrays, one is called int i and ts and it's declared with
|
||||
hyphen a and then hyphen i and the name int's, int's or integers. There's not to declare another one
|
||||
hyphen a and I've called the array norm because it's just an ordinary array indexed arrays in both
|
||||
cases. So I put into ints a couple of values in by by putting an an assignment statement ints
|
||||
equals and then open parenthesis and a couple of things being added there and the two things I'm
|
||||
adding are a couple of expressions in quote so they're quoted a strings effectively but they're
|
||||
numeric expressions within them so we've got 38% seven so it's using the modulo operator which
|
||||
divides by seven and gives you the remainder and then the next one is in quotes 38 slash seven which
|
||||
is dividing, doing integers division on 38 and the norm array gets the same stuff then for each of
|
||||
the arrays I add a string to the end of it so I've put the string jellyfish onto the end of each one
|
||||
using the append operator so the plus equals to append another value to the end of the array just so
|
||||
you can see what the effects are then the script echoes the contents of ints and the contents of norm
|
||||
to show you what you get well within ints you get the values three five and zero because the value of
|
||||
38 mod seven is three and 38 divided by seven is five and then the value of the string jellyfish
|
||||
because it's not numeric is treated to zero anything that's not numeric any string that's not
|
||||
numeric is regarded as a zero which seems sensible I think we covered this reasonably comprehensively
|
||||
in when we were talking about arithmetic expressions and stuff when you come to look at the contents
|
||||
of the array norm then it's just got the string 38 space percent space seven in one element 38
|
||||
space slash base seven in the next and jellyfish in the last one so that's all really it's pretty
|
||||
pretty straightforward stuff but quite useful I would say then we come to the hyphen L and the
|
||||
hyphen U both lowercase letters these options force any alphabetic characters that you store in
|
||||
this array it forces them to lowercase in the case of hyphen L or uppercase in the case of hyphen
|
||||
U so obviously when you declare these things you don't need to declare one of these at a time
|
||||
so this is mildly useful I don't I've never used it myself I don't see a use for it personally
|
||||
there you go the last one last option I want to mention is hyphen lowercase R now what this
|
||||
does is it makes whatever you declare read only so when you are declaring you also have to initialize
|
||||
them because you can't change their contents at all afterwards so it's a way of declaring
|
||||
constants and I've got an example that sets a simple variable not on array in this case but
|
||||
the same applies to arrays I've declared hyphen I R you can concatenate these options by the way
|
||||
so the I means it's an integer the R means it's read only and I've called it sixth prime and I
|
||||
set it to 13 of course I use the sixth prime then I try and set sixth prime to 17 I get back the
|
||||
the error message bash call on sixth prime call on read only variable now you think well can I turn
|
||||
off the read only capability so try to declare plus lowercase R sixth prime which by rights should
|
||||
turn off the read only thing but because it's read only I guess the logic is you can't do it
|
||||
and you get back an error message just in passing there is a command which is which comes from
|
||||
the born shell which is equivalent to declare hyphen R and it is read only so it takes some of the
|
||||
options that declare takes and it lets you create arrays and variables and stuff which I read only
|
||||
so it's doing the same thing it's just that bash is a sort of a blend of the older born shell
|
||||
so I call born again shell of course I think I've said this before the next command is the local
|
||||
command it takes the same options and types of arguments as declare but you're only allowed to use
|
||||
it within a function so if you're if you're creating a function declaring a function then you can
|
||||
use the local command to create variables and stuff within it now I have demonstrated this when I've
|
||||
talked in other shows about creating functions but I've in this particular sub-series I haven't
|
||||
really explained functions in detail so I'll leave the rest of the use of local to that when I get
|
||||
to that but the point of it is that it makes the variables that you declare local to the function
|
||||
so they work within the function but as soon as the function exits they vanish so it's like other
|
||||
programming languages now we move on to what I think is a very very useful command which I didn't
|
||||
know about until maybe earlier this year I think never used it much myself but now I've discovered
|
||||
it and understood it find it extremely useful and it's map file which has the synonym read array so
|
||||
what this does is it reads lines from standard input and puts them in an indexed array it can also
|
||||
read from a file descriptor which is a way of connecting bits of a script to a file but I haven't
|
||||
looked at this yet I plan to talk about this in an upcoming show it's on the to-do list anyway so
|
||||
I'll leave that I won't talk about it here just to mention that it exists so I've prepared a command
|
||||
syntax diagram he thing which shows all the options and what you can follow them with which I've
|
||||
grabbed from the GNU bash manual included in the long notes here and all of the options and
|
||||
arguments are optional in fact I also made a table of all of these options where I explain what
|
||||
they do just to talk about them briefly you can change what delimiter terminates each input line
|
||||
in other words define a different end of line bit like the way you can do stuff like that in
|
||||
orc you can control how many and that's with the the hyphen d delimiter option you can define how
|
||||
many lines are to be read so if you're offering map file a file you want to read the first few
|
||||
lines from it then you can control that if that is with the hyphen n option with a numerical count
|
||||
if the count is zero then all the lines are are read and if the hyphen n option is not
|
||||
I used it all then it reads the entirety of the file you can change where the lines are written
|
||||
into your array because normally they will clear the array and we'll start at zero to write
|
||||
values in and that's done with hyphen capital O and then the numerical origin that you want to write to
|
||||
you can if you wish skip a number of lines from your data source from your file with hyphen
|
||||
lowercase s and then a number count and here's the thing I think it's quite nice the hyphen t
|
||||
option she doesn't have an parameter to it you can remove whatever the the delimiter is from
|
||||
each line so if you're reading stuff separated by new lines which is a pretty common scenario using
|
||||
hyphen t will throw away the new line so when you come to list out contents your array you don't
|
||||
end up with new lines after each element the hyphen lowercase u is followed by a file descriptor
|
||||
but I'll not talk about that for now but it changes what what source the map file reads from
|
||||
rather than from standard input then there are two things that I have played around with but I
|
||||
don't know how useful they're going to be there's hyphen capital C followed by a callback a callback
|
||||
is either an expression or a function which is going to be called by the map file command every
|
||||
time a certain number of lines are read the number of lines is called the quantum and that's to find
|
||||
by the next option which is hyphen lowercase c and a number so if you don't have the lowercase c
|
||||
then it's every 5,000 lines that you've read in but you can change that I've got an example coming
|
||||
up to demonstrate this so the final argument to the map file command is the name of the array
|
||||
that's where the lines can be written you need to have created the array first if you don't
|
||||
specify an array then there's a built-in array called map file in uppercase into which stuff will
|
||||
be written it's quite an interesting thing that when the callback is invoked whether it be a
|
||||
function or whatever then it is given two values the first where is the index of the next array
|
||||
element that's going to be assigned and then the line that's going to be assigned to it the callback
|
||||
functional expression is evaluated after the line is read but before the array element is assigned
|
||||
so you could use that to filter stuff out if you really wanted to you could do some quite clever
|
||||
stuff in there I haven't experimented with that very much but I do have an example of using it
|
||||
coming up so there's a downloadable script that demonstrates some of the features of map file
|
||||
and that's bash 19 underscore EX2 which is moderately long actually now I come to look at it
|
||||
a bit carried away but I just threw in a bunch of things that you could do to fill an array using
|
||||
map file and I've alluded to this along the way because I've been filling arrays in loops and
|
||||
it's not necessarily the best way of doing it so in my script I've got I'm declaring an index
|
||||
array called map and then call map file with the hyphen t option and the array name map and I'm
|
||||
feeding it through a redirection so it's using a less than sign to redirect from the next thing
|
||||
and I'm using one of these process substitution things which is a less than sign and then commands
|
||||
in parentheses and what I've got in the parentheses is a for loop which goes for i in and then a
|
||||
brace expansion of 1 to 10 so it's it's going to iterate through values 1 to 10 setting i to each one
|
||||
and then semicolon do then the the actual meat of this loop is an echo echoing dollar random
|
||||
being the uppercase variable name which gives you a different random number each time you call it
|
||||
semicolon done and that's the closed parentheses so what that will do is it will fill the array
|
||||
with 10 random numbers and it because we're using echo in the loop it will be generating a new line
|
||||
but map file needs the new line in order to tell where one line ends and the next begins but I've
|
||||
told map file to throw it away when it stores so then use an echo to print out the contents of
|
||||
this map array using the syntax for printout and entire array using the asterisk as the index
|
||||
and you you can see that later on in the in the notes just I just run it and put the result
|
||||
just a list of 10 random numbers on one line next thing define a string just put in a
|
||||
simple variable called words and what I did was I put few lines from words worth poem in there
|
||||
where all the spaces had been replaced by underscores really just to demonstrate how you could use
|
||||
alternative delimitors so I wondered lonely as a cloud and all that stuff is in there then the
|
||||
map file command that plays with that uses hyphen lowercase d and follows that with an underscore so
|
||||
the delimiter is the underscore between each word and I use underscure hyphen t to strip off
|
||||
the underscores and I put it into an array called dafts d a double f s because it's about daftedals
|
||||
so I forgot to say I declared it before so what that does is another process substitution which
|
||||
simply echoes the string called words without a trailing new line uses echo hyphen in to do so that
|
||||
will load up map using map file that will load up dafts with all of these words one per element
|
||||
and will have removed the underscores that's doing it and there you go and now echo the contents
|
||||
out again and you can see after the script there's some example output from it
|
||||
where it prints out the words of the poem on online the final demonstration in this script
|
||||
is to declare another index array which I call big in this case because it's going to contain
|
||||
many contents many elements well hundreds but then I use map file with hyphen t located t that is
|
||||
and then hyphen capital c and following capital c is a print f so the print f statement has a format
|
||||
which consists of percent zero to d space percent s backslash n and what that will do is it it will
|
||||
expect two arguments first of which it will treat as a number we print it out with two decimal
|
||||
places leading zero and the second one that will just treat as a string so that's all in double
|
||||
quotes then the next option is hyphen locc followed by the number ten so the quantum is going to be
|
||||
ten every ten lines that it gets it will invoke that call back then the name of the array is big
|
||||
we're using the same structure again of a less than sign to redirect and then process substitution
|
||||
less than sign and then bracketed list we're using the ever present printing or extraction of words
|
||||
from user shared dict words this time I've used shuff and ask for 100 words so the final bit of
|
||||
this script simply echoes the contents of the array we should have been seeing stuff going
|
||||
into the array as it as if the the map file was being invoked but I'm printing them out as a while
|
||||
so the first thing that's printed out is the number of elements that we got in this array
|
||||
called big and then the second thing is a for loop which begins setting i to nine and iterating
|
||||
until it reaches the number of elements in the big array and then we're we're incrementing
|
||||
the number by ten to each iteration and inside we're using pretty much the same print f command
|
||||
where we're same format anyway so read it out again it's printing a number and then a string
|
||||
and the the number is coming from the variable i and the string is coming from the array element
|
||||
the i the rail so when you run this you get remember we're getting random words out of it so
|
||||
what I'm seeing on the screen won't necessarily be what you'll see in the notes because I probably
|
||||
probably run them again before I before I write some at the show but there's a list of elements
|
||||
that are going into the array every every tenth element so the first one is zero the first one
|
||||
will be the added theory will be the zero and that won't be shown but then the next one the
|
||||
tenth element will be the one with the index of nine and we get a word out and then the 19th
|
||||
another word and so forth up to word number 99 and the loop does pretty much the same it says
|
||||
there are a hundred elements and it prints out the same stuff so that was just really a demonstration
|
||||
of what you can do with map file personally I now use map file to load load arrays pretty much
|
||||
all the time and I'm doing this type of thing so I find it amazing useful hope you feel the same way
|
||||
about it so the final bit of this show is to mention the read command we've used read loads loads
|
||||
time and all sorts of examples in this bash tip series we haven't looked at the option which is
|
||||
hyphen lock case a followed by a name what that does is to load an array and the array is named with
|
||||
whatever you put instead of name but because read reads one line at a time then we're assuming that
|
||||
all of the words that are going to the array are all on that on on a line and more to the point
|
||||
the array is if you keep nominating the same array then the array will be overwritten each time
|
||||
read is called with the same array so if you were doing this in a loop you'd have to be very careful
|
||||
doing for that reason all of the words to go into the array need to be on the one line and the
|
||||
work the the words on the line are split up using the word splitting process that we described
|
||||
in episode 2045 that was we were talking about the whole subject of expansion and word splitting is
|
||||
one of the things that happens when a command or a file spec is being expanded and it was described
|
||||
in so I've created a third downloadable script bash 19 underscore EX3.sh which has a little demonstration
|
||||
of the use of read with this particular option I'll talk more about the other options later on
|
||||
I think I don't have a particular slot to do this but I'll talk about them in passing I think
|
||||
as I go forward with this series so in this script we start by declaring an index to array which in
|
||||
this case I've called read test now I thought there are ways in which you could present a read with
|
||||
a single line but read is normally reading from standard in which means you would have to type
|
||||
this stuff it's not not a straightforward thing to put it within the script but it is possible
|
||||
but we haven't really covered what this would require yet so I'm not doing it the way that you
|
||||
might do if you're doing this for real I've just done a sort of demonstration of generating some
|
||||
data on standard in and poking it into an array the read consists of read space hyphen
|
||||
lowercase r that's the thing that takes away the meta status of backslash things like backslash
|
||||
n and so forth basically ignores them in the it doesn't give them their special meaning
|
||||
and that's followed by space hyphen lowercase a and then read test is the name of the array so that's
|
||||
the read command we want to do we're going to read a line and put it into read test which is an array
|
||||
so this one is using the same stuff as we've been using in previous examples in this
|
||||
episode it's using a less than sign to redirect some stuff from a data source and the data source
|
||||
is another one of these process substitution less than sign open parenthesis some stuff inside
|
||||
the parenthesis close parenthesis and what we have inside this inside these parenthesis is a
|
||||
for loop we're setting for c in and then we're using a double brace expansion the first brace
|
||||
expansion is capital A to capital J that's first 10 that's the alphabet of a case then in the next
|
||||
set of braces 1 dot dot three so you'll recall from when we talked about brace expansion that this
|
||||
will generate sequences like a 1 a 2 a 3 b 1 b 2 b 3 etc each time round this loop
|
||||
not reading out the minute details of this we echo the contents of dollar c the variable c
|
||||
but we do it with echo hyphen n which suppresses the new line because we want just one line to come
|
||||
out this thing okay so this will generate this list of a 1 a 2 a 3 stuff which will then be fed
|
||||
into the array so to demonstrate what actually happens simply echo out the number of elements
|
||||
that are in the array which will be 30 it's 10 times 3 is 30 and then echo out the contents
|
||||
so as I said we get a 1 a 2 a 3 b 1 b 2 b 3 c 1 c 2 c 3 etc add north here so hopefully that
|
||||
demonstrates the purpose of this quite well so with that said that is the end of this particular
|
||||
episode and of the sub sub sub section talking about arrays and i'm going to give the
|
||||
bash tips series a little bit of a rest now for a for a month or two well i do something else
|
||||
because you probably bored sick of it and i could do the bit of a change as well so
|
||||
but i'll come back to it in due course okay then bye bye
|
||||
you've been listening to hecka public radio at hecka public radio dot org
|
||||
we are a community podcast network that releases shows every weekday Monday through Friday
|
||||
today's show like all our shows was contributed by an hbrlist snare like yourself
|
||||
if you ever thought of recording a podcast then click on our contributing to find out how easy it
|
||||
really is hecka public radio was founded by the digital dot pound and the infonomicon computer
|
||||
club and it's part of the binary revolution at binwreff.com if you have comments on today's show
|
||||
please email the host directly leave a comment on the website or record a follow up episode yourself
|
||||
unless otherwise status today's show is released on the creative comments
|
||||
attribution share a light 3.0 license
|
||||
Reference in New Issue
Block a user