---
rexxpub:
  defaults: rony.yaml
  logo: oorexx
---

<!-- 060_ooRexx_commands_V19.odp (2026-10-15 09:36) -->

<!-- slide # 1 (2026-10-15 09:36) ----------------------------- ODP slide # 1 -->
. slide cover
# Procedural and Object-oriented Programming 6

. subtitle
**Commands**

. cover-art
. picture img/060_ooRexx_commands_V19/p01-diagram-7.png

<!-- slide # 2 (2026-10-15 09:36) ----------------------------- ODP slide # 2 -->
. slide reference="Cf. rexxref.pdf (1.16.2. Commands)"
# Commands

. steps each=after
- Directed to the operating system
. click
- Typed on the command line, e.g.
    - "**dir**" (Windows), "**ls**" (Unix) … list entries
    - "**copy**" (Windows), "**cp**" (Unix) … copy files
    - "**sort**" (Windows, Unix) … sort files
. click
- Commands may have switches and arguments
    - "**dir /s**" (Windows), "**ls -R**" (Unix)
        - … list also entries in subdirectories
    - "**dir a\* /s**" (Windows), "**ls -R a\***" (Unix)
        - … list entries starting with "a"
    - "**sort /R**" (Windows) "**sort -r**" (Unix)
        - … sort in reverse order

<!-- slide # 3 (2026-10-15 09:36) ----------------------------- ODP slide # 3 -->
. slide reference="Cf. rexxref.pdf (1.16.2. Commands)"
# Commands

. after steps
- Commands always have a numeric **r**eturn **c**ode (**RC**)
    - Upon return of a command Rexx sets a Rexx variable named **RC** to the command's return code
        . after
        - It is therefore very easy to learn about return codes in Rexx
    - If the return code is **0**, then the command executed without errors
        . static
        - Any other value for the return code and its meaning is usually documented with the command
- Attention! Commands with file and path names may contain blanks!
    - The command line interpreter splits commands at blanks, unless double quotes get used!
    - Therefore always enquote file/path names with double quotes!
        . after
        - Windows example:  **dir /s** ***"**c:\\abc def\\this is a file with blanks.txt**"***
        . after
        - Unix example:   **ls -al** ***"**/abc def/this is a file with blanks.txt**"***

<!-- slide # 4 (2026-10-15 09:36) ----------------------------- ODP slide # 4 -->
. slide reference="Cf. rexxref.pdf (1.16.2. Commands)"
# Commands

. after steps
- Rexx can run commands directly from strings, e.g.

  . with
  ```rexx
  "dir /s"                -- execute command
  ```

    . after
    - Rexx will submit the string as the command to the system for execution
    . after
    - Upon return the Rexx **RC** variable refers to the command's return code
- Rexx can run commands referred to by variables, e.g.

  . with
  ```rexx
  command="dir /s"        -- assign to variable command
  command                 -- execute command
  ```

- Use the ***ADDRESS*** keyword statement explicitly, e.g.

  . with
  ```rexx
  ADDRESS SYSTEM "dir /s" -- execute command
  -- or
  command="dir /s"        -- assign to variable command
  ADDRESS SYSTEM command  -- execute command
  ```

<!-- slide # 5 (2026-10-15 09:36) ----------------------------- ODP slide # 5 -->
. slide reference="Cf. rexxref.pdf (1.16.2. Commands)"
# Commands

- One can assign the command to a Rexx variable and use that

  . after mark 1-4 pen=1
  ```rexx
   -- get current operating system
  parse source op_sys +1  -- "W"...Windows, everything else is regarded to be Unix
  if op_sys="W" then command="dir /s" -- list directory and subdirectories
                else command="ls -R"  -- list directory and subdirectories
  command           -- execute command via the operating system (command line)
  say "Rexx, RC="rc
  ```

  . click
  Output (Windows), maybe:

  . after
  ```output
  Directory of e:\tmp
  10.11.2020  13:38    <DIR>          .
  10.11.2020  13:38    <DIR>          ..
  10.11.2020  13:40    <DIR>          .idea
  10.11.2020  13:16               546 example1.rex
                 2 File(s)          1 287 bytes

  Directory of e:\tmp\.idea
  …cut…
  Rexx, RC=0
  ```

<!-- slide # 6 (2026-10-15 09:36) ----------------------------- ODP slide # 6 -->
. slide logo=rexx kicker=Excursus
# Operating System "Process"

- For each program that needs to be executed Unix or Windows
    . click
    - Creates a management unit named "*process*" and
        . after
        - Reserves memory
        . after
        - Reserves processor time
        . after
        - Sets up the following "standard files"
            - "standard input file ('*stdin*', file descriptor number `0`)": default input via the keyboard
            - "standard output file ('*stdout*', file descriptor number `1`)": default output to the screen (window)
            - "standard error file ('*stderr*', file descriptor number `2`): default output to the screen (window)
        . click
        - Sets up the process "environment"
            - Defines environment variables like
                - `PATH` … determines the directories and the order for seeking programs
                - `JAVA_HOME` … determines the Java directory to use
                - `CLASSPATH` … determines the directories and the order for seeking Java classes
    . click
    - Manages and supervises the program execution (using a single or multiple threads)

<!-- slide # 7 (2026-10-15 09:36) ----------------------------- ODP slide # 7 -->
. slide kicker=Excursus reference="Cf. rexxref.pdf (14.1.4. Default Stream Names)"
# "Redirecting Standard Files"

. steps
. static
- Redirecting the standard files when running a program in a process
    . after
    - Redirection operators: '**\<**' (*stdin*), '**\>**'  (*stdout*, *stderr*) and '**\>\>**' (*stdout*, *stderr*)
        - '**\>**' will delete the output file, whereas '**\>\>**' will append output to the output file
    - Examples
        - Redirect input from the keyboard to the file "*myinput.txt*`"`

          . with
          ```bash
          rexx myprogram.rex  0<myinput.txt
          rexx myprogram.rex   <myinput.txt
          ```

        - Redirect output from the screen to the file "*myoutput.txt*" (will delete file if it exists)

          . with
          ```bash
          rexx myprogram.rex  1>myoutput.txt
          rexx myprogram.rex   >myoutput.txt
          ```

        - Redirect error output from the screen to the file "*myerrors.txt*" (will delete file if it exists)

          . with
          ```bash
          rexx myprogram.rex  2>myerrors.txt
          ```

<!-- slide # 8 (2026-10-15 09:36) ----------------------------- ODP slide # 8 -->
. slide kicker=Excursus
# "Redirecting Standard Files"

- Redirecting standard files when running a program in a process

  . with
  ```bash
  rexx myprogram.rex 0<myinput.txt 1>myoutput.txt 2>myerrors.txt
  rexx myprogram.rex  <myinput.txt  >myoutput.txt 2>myerrors.txt
  ```

    . after
    - Input from file "*myinput.txt*" instead of keyboard, output to "*myoutput.txt*" instead of screen and error output to "*myerrors.txt"* instead of screen
    . click
    - Redirecting *stderr* to *stdout*
        . after
        - Redirect output to a file and also redirect error output to the same file

          . with
          ```bash
          rexx myprogram.rex >myoutput.txt 2>&1
          ```

            . click
            - Output goes to "*myoutput.txt*" instead of screen
            . with
            - Error output goes to where *stdout* goes to, i.e. "*myoutput.txt*" as well
            . with
            - Important note: always redirect *stdout* first and then redirect *stderr* to *stdout*!
        . click
        - Redirecting and *appending* to *stdout* and to *stderr*

          . with
          ```bash
          rexx myprogram.rex >>myoutput.txt 2>>myerrors.txt
          ```

<!-- slide # 9 (2026-10-15 09:36) ----------------------------- ODP slide # 9 -->
. slide kicker=Excursus
# "Redirecting Standard Files"

. after steps
- "Piping"
    . after
    - Redirect *stdout* of one program to *stdin* of the next program
        . after
        - The output of one program becomes the input of another program
    - Piping operator: vertical bar ("**|**")
    - Example

      . with
      ```bash
      rexx myprogram.rex | rexx myfilter.rex
      ```

        . after
        - The output (*stdout*) of "*myprogram.rex*" becomes the input (*stdin*) of "*myfilter.rex*"
    - One can redirect and pipe to/from multiple programs

      . after
      ```bash
      rexx myprogram.rex < myinput.txt | rexx myfilter.rex 2>removed.txt | sort
      ```

        - "*myprogram.rex*": input is taken from the text file "*myinput.txt*", its output (*stdout*) gets piped to the next program's ("*myfilter.rex*") *stdin*
        - "*myfilter.rex*": input is taken from *stdout* of the previous program, *stderr* gets redirected to "removed*.txt*", *stdout* gets piped to next program's ("*sort*") *stdin*
        - "*sort*": input is taken from *stdout* of the previous program, output (*stdout*) goes to the screen

<!-- slide # 10 (2026-10-15 09:36) --------------------------- ODP slide # 10 -->
. slide kicker=Excursus
# "Redirecting Standard Files"

. steps
. static
- "Null device"
    - Any output redirected to the "null device" gets discarded!
        - Unix null device, a file named

          [**/dev/null**]{.fragment .withPrevious}

        - Windows null device, a pseudo file named

          [**nul**]{.fragment .withPrevious}

    - Used in redirections, examples
        . after
        - Show errors only (discard *stdout* output)

          [`rexx myprogram.rex >nul`                       (Windows)]{.fragment .withPrevious}

          [`rexx myprogram.rex >/dev/null`    (Unix)]{.fragment .afterPrevious}

        . after
        - Show output only (discard *stderr* output, i.e. do not show error messages)

          [`rexx myprogram.rex 2>nul`            (Windows)]{.fragment}

          [`rexx myprogram.rex 2>/dev/null`   (Unix)]{.fragment .afterPrevious}

<!-- slide # 11 (2026-10-15 09:36) --------------------------- ODP slide # 11 -->
. slide kicker=Excursus
# "Redirection", Example

```rexx
/* myprogram.rex: write input lines (stdin) to output (stdout) */
do until value=""    -- if empty input, leave
   parse pull value  -- read line from stdin, assign to variable "value"
   say value         -- write to stdout
end
```

[Command (Unix, Windows):]{.fragment}

. columns 9 3

. after id=#p11x16

```output
rexx myprogram.rex < myinput.txt
```



. next column

. after id=#p11x15

. file=myinput.txt:
```output
Max
und
Moritz
konnt
der
Lehrer ...
```


. end columns

. after arrow #p11x15 -> #p11x16

. columns 9 3 tight

. click label
Output:

. after
```output
Max
und
Moritz
konnt
der
Lehrer ...
```


. next column

. end columns

<!-- slide # 12 (2026-10-15 09:36) --------------------------- ODP slide # 12 -->
. slide kicker=Excursus
# "Redirection", Example

```rexx
/* myprogram.rex: write input lines (stdin) to output (stdout) */
do until value=""    -- if empty input, leave
   parse pull value  -- read line from stdin, assign to variable "value"
   say value         -- write to stdout
end
```

. after
```rexx
/* myfilter.rex: if value contains 'r' then write it to stdout, else to stderr */
do until value=""
   parse pull value           -- read line from stdin, assign to variable "value"
   if pos('r',value)>0 then say value -- write value to stdout
                       else call lineout 'stderr',value   -- write value to stderr
end
```

. click
Command (Windows):

. columns 9 3

. after id=#p12x18

```output
rexx myprogram.rex < myinput.txt | rexx myfilter.rex >nul
```


[Command (Unix):]{.fragment .afterPrevious}

. after id=#p12x19

```output
rexx myprogram.rex < myinput.txt | rexx myfilter.rex >/dev/null
```



. next column

. after id=#p12x17

. file=myinput.txt:
```output
Max
und
Moritz
konnt
der
Lehrer ...
```


. end columns

. after arrow #p12x17 -> #p12x18

. with arrow #p12x17 -> #p12x19

. click label
Output:

. after
```output
Max
und
konnt
```

<!-- slide # 13 (2026-10-15 09:36) --------------------------- ODP slide # 13 -->
. slide kicker=Excursus
# "Redirection", Example

```rexx
/* myprogram.rex: write input lines (stdin) to output (stdout) */
do until value=""    -- if empty input, leave
   parse pull value  -- read line from stdin, assign to variable "value"
   say value         -- write to stdout
end
```

. after
```rexx
/* myfilter.rex: if value contains 'r' then write it to stdout, else to stderr */
do until value=""
   parse pull value           -- read line from stdin, assign to variable "value"
   if pos('r',value)>0 then say value -- write value to stdout
                       else call lineout 'stderr',value   -- write value to stderr
end
```

. click
Command (Windows):

. columns 9 3

. after group id=#p13x21

. after mark 1 "2>nul" pen=1
```output
rexx myprogram.rex < myinput.txt | rexx myfilter.rex 2>nul
```

. end group

[Command (Unix):]{.fragment .afterPrevious}

. after group id=#p13x22

. after mark 1 "2>/dev/null" pen=1
```output
rexx myprogram.rex < myinput.txt | rexx myfilter.rex 2>/dev/null
```

. end group


. next column

. after id=#p13x20

. file=myinput.txt:
```output
Max
und
Moritz
konnt
der
Lehrer ...
```


. end columns

. after arrow #p13x20 -> #p13x21

. with arrow #p13x20 -> #p13x22

. click label
Output:

. after
```output
Moritz
der
Lehrer ...
```

<!-- slide # 14 (2026-10-15 09:36) --------------------------- ODP slide # 14 -->
. slide kicker=Excursus
# "Redirection", Example, 4a (PARSE PULL)

```rexx
/* myprogram.rex: write input lines (stdin) to output (stdout) */
do until value=""    -- if empty input, leave
   parse pull value  -- read line from stdin, assign to variable "value"
   say value         -- write to stdout
end
```

. after
```rexx
/* myfilter.rex: if value contains 'r' then write it to stdout, else to stderr */
do until value=""
   parse pull value           -- read line from stdin, assign to variable "value"
   if pos('r',value)>0 then say value -- write value to stdout
                       else call lineout 'stderr',value   -- write value to stderr
end
```

. click
Command (Windows):

. columns 9 3

. after group id=#p14x24

. after mark 1 "2>nul | sort" pen=1
```output
rexx myprogram.rex < myinput.txt | rexx myfilter.rex 2>nul | sort
```

. end group

. after
Command (Unix):

. after group id=#p14x25

. after mark 1 "2>/dev/null | sort -f" pen=1
```output
rexx myprogram.rex < myinput.txt | rexx myfilter.rex 2>/dev/null | sort -f
```

. end group


. next column

. after id=#p14x23

. file=myinput.txt:
```output
Max
und
Moritz
konnt
der
Lehrer ...
```


. after arrow #p14x23 -> #p14x24

. with arrow #p14x23 -> #p14x25

. click label
Output:

. after
```output
der
Lehrer ...
Moritz
```

. end columns


<!-- slide # 15 (2026-10-15 09:36) --------------------------- ODP slide # 15 -->
. slide kicker=Excursus
# "Redirection", Example, 4b (PARSE LINEIN)

. click mark 2-4 pen=1
. after mark 7 "notready:" pen=1
```rexx
/* myprogram2.rex: write input lines (stdin) to output (stdout) */
signal on notready      -- raised, if no input data anymore
loop                    -- loop eternally, same as: do forever
  parse linein value    -- get line from stdin, raises notready if no data anymore
  say value             -- write to stdout
end
notready:               -- label to signal, if no input anymore
```

. after
. after mark 2-4 pen=2
. after mark 8 "notready:" pen=2
. after mark 5-6 pen=2
```rexx
/* myfilter2.rex: if value contains 'r' then write it to stdout, else to stderr */
signal on notready      -- raised, if no input data anymore
do forever              -- loop eternally, same as: loop
   parse linein value   -- get line from stdin, raises notready if no data anymore
   if pos('r',value)>0 then .output~say(value)  -- write value to stdout
                       else .error ~say(value)  -- write value to stderr
end
notready:               -- label to signal, if no input anymore
```

. columns 9 3

[Command (Windows):]{.fragment}

. after group id=#p15x27

. after mark 1 "2>nul | sort" pen=3
```output
rexx myprogram2.rex < myinput.txt | rexx myfilter2.rex 2>nul | sort
```

. end group

. after
Command (Unix):

. after group id=#p15x28

. after mark 1 "2>/dev/null | sort -f" pen=3
```output
rexx myprogram2.rex < myinput.txt | rexx myfilter2.rex 2>/dev/null | sort -f
```

. end group


. next column

. after id=#p15x26

. file=myinput.txt:
```output
Max
und
Moritz
konnt
der
Lehrer ...
```


. after arrow #p15x26 -> #p15x27

. with arrow #p15x26 -> #p15x28

. click label
Output:

. after
```output
der
Lehrer ...
Moritz
```

. end columns


<!-- slide # 16 (2026-10-15 09:36) --------------------------- ODP slide # 16 -->
. slide logo=oorexx reference="Cf. rexxref.pdf (1.16.2. Commands)"
# Commands, 5

. after
- Commands may include all desired redirections and pipes!
. click
- Possible to redirect the command's standard files to and from ooRexx!
. click
- Use the ***ADDRESS … WITH*** statement for redirections

  . plain steps each=after level=2
  | | |
  |---|---|
  | **INPUT** option: | command's *stdin* provided by an ooRexx collection object |
  | **OUTPUT** option: | command's *stdout* gets appended to an ooRexx collection object |
  | **ERROR** option: | command's *stderr* gets appended to an ooRexx collection object |

. click
- Example
    - Use two ooRexx arrays to receive *stdout* and *stderr* output from command

      . after
      ```rexx
      outArr=.array~new
      errArr=.array~new
      ADDRESS SYSTEM "some command" WITH OUTPUT USING (outArr) ERROR USING (errArr)
      ```

<!-- slide # 17 (2026-10-15 09:36) --------------------------- ODP slide # 17 -->
. slide reference="Cf. rexxref.pdf (1.16.2. Commands)"
# Commands, 6

- Redirecting command's *stdout* to an ooRexx array

. after group level=1
. click mark 1-4 pen=1
. click mark 10 pen=2
. after mark 12 pen=2
. after mark 14 pen=2
```rexx
-- get current operating system
parse source op_sys +1  -- "W"...Windows, everything else is regarded to be Unix
if op_sys="W" then command="dir /s" -- list directory and subdirectories
              else command="ls -R"  -- list directory and subdirectories

say "Rexx, command:" quote(command)
say "Rexx, current directory:" quote(directory())

   -- redirect standard output to the 'arrOut' array
arrOut=.array~new -- create Rexx array for fetching standard output
   -- execute command, redirect output to Rexx array
ADDRESS SYSTEM command WITH OUTPUT USING (arrOut)
say "Rexx, RC="rc
say "Rexx, arrOut~items:" arrOut~items "(lines)"

::routine quote   -- enquote argument in double quotes
  return '"' || arg(1) || '"'
```

. end group

. click level=1
Output (Windows), maybe:

. after group level=1
. with mark 4 pen=3
```output
Rexx, command: "dir /s"
Rexx, current directory: "e:\tmp"
Rexx, RC=0
Rexx, arrOut~items: 26 (lines)
```

. end group

<!-- slide # 18 (2026-10-15 09:36) --------------------------- ODP slide # 18 -->
. slide kicker="Command, 7" reference="Cf. rexxref.pdf (1.16.2. Commands)"
# "curl" Command

. after
- "curl"
    . after
    - Command "Client URL (cURL)" to allow accessing web resources
        . after
        - A Utility originating from Unix available for Windows 10, Linux and MacOS as well
        . click
        - Very powerful, very popular, quite easy to use
        . click
        - Uses standard files
            - *stdin* e.g. for data to upload
            - *stdout* for the fetched data from the server
            - *stderr* for information about the operation and errors, if any
        . click
        - Links for more information on "curl"
            . after
            - Wikipedia: [https://en.wikipedia.org/wiki/CURL](https://en.wikipedia.org/wiki/CURL)
            . after
            - Tutorials:
                - [https://curl.se/docs/httpscripting.html](https://curl.se/docs/httpscripting.html)
                - [https://curl.se/docs/manual.html](https://curl.se/docs/manual.html)
                - [https://www.baeldung.com/curl-rest](https://www.baeldung.com/curl-rest)

<!-- slide # 19 (2026-10-15 09:36) --------------------------- ODP slide # 19 -->
. slide kicker="Command, 8" reference="Cf. rexxref.pdf (1.16.2. Commands)"
# "curl" Example 1, Extracting Link from HTML Text

. after group id=#p19x31

. picture img/060_ooRexx_commands_V19/p19-diagram-10.png width=100%

. end group

. click arrow #p19x31:36,60 -> #p19x31:84,69

. after arrow #p19x31:14,93 -> #p19x31:60,73

<!-- slide # 20 (2026-10-15 09:36) --------------------------- ODP slide # 20 -->
. slide kicker="Command, 9" reference="Cf. rexxref.pdf (1.16.2. Commands)"
# "curl" Example 1, Extracting Link from HTML Text

. after
- Extracting WU's Directory URL (as of 2022-05-24)
    . after
    - Get WU BACH's home page from the URL: [https://bach.wu.ac.at/z/start](https://bach.wu.ac.at/z/start)
    . with
    - Parse the received data for the WU directory URL and display it

. after group level=2
. after mark 5 "<h2>WU</h2>" pen=1
. with mark 5 '<a href="' pen=1
. with mark 5 '">WU Directory<' pen=1
```rexx
command="curl https://bach.wu.ac.at/z/start"
outArr=.array~new          -- array for stdout
ADDRESS SYSTEM command WITH OUTPUT USING (outArr)
source=outArr~makeString   -- turn array into string
parse var source '<h2>WU</h2>' . '<a href="' url '">WU Directory<'
say "Current URL of BACH-WU Directory:" url
```

. end group

. click label level=2
Output:

. group level=2
. with group id=#p20x32

. after mark 1-3 pen=2
```output
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
100 15583  100 15583    0     0   423k      0 --:--:-- --:--:-- --:--:--  434k
Current URL of BACH-WU Directory: http://bach.wu.ac.at/d/directory/
```

. with callout --> #p20x32:1-3 at=right
from curl's stderr

. end group

. end group

<!-- slide # 21 (2026-10-15 09:36) --------------------------- ODP slide # 21 -->
. slide kicker="Command, 10" reference="Cf. rexxref.pdf (1.16.2. Commands)"
# "curl" Example 1, Extracting Link from HTML Text

. after
- Extracting WU's Directory URL (as of 2022-04-03)
    . after
    - Version that intercepts *stderr* output from *curl* to inhibit it to be displayed

. click group level=2
. after mark 3 pen=1
. after mark 4 "ERROR USING (errArr)" pen=1
```rexx
command="curl https://bach.wu.ac.at/z/start"
outArr=.array~new          -- array for stdout
errArr=.array~new          -- array for stderr: curl's information goes here
ADDRESS SYSTEM command WITH OUTPUT USING (outArr) ERROR USING (errArr)
source=outArr~makeString   -- turn array into string
parse var source '<h2>WU</h2>' . '<a href="' url '">WU Directory<'
say "Current URL of BACH-WU Directory:" url
```

. end group

. click label level=2
Output:

. after level=2
```output
Current URL of BACH-WU Directory: http://bach.wu.ac.at/d/directory/
```

<!-- slide # 22 (2026-10-15 09:36) --------------------------- ODP slide # 22 -->
. slide kicker="Command, 11" reference="Cf. rexxref.pdf (1.16.2. Commands)" presenter="Till Winkler"
# "curl" Example 2 – Using a Weather API (wttr.in)

. with
- Most websites have APIs (**A**pplication **P**rogramming **I**nterface**s**), which allow to specify the response cURL gets using **URL query strings**.
. click
- Websites describe what responses can be delivered:
    . after
    - [https://github.com/chubin/wttr.in#one-line-output](https://github.com/chubin/wttr.in#one-line-output)

. after level=2
```bash
curl https://wttr.in/Vienna?format="%l:+%t+%w"
```

. after group level=2
. after mark 1 pen=1
```rexx
command='curl https://wttr.in/Vienna?format="%l:+%t+%w"'
outArr=.array~new          -- array for stdout
errArr=.array~new          -- array for stderr: curl's information goes here
ADDRESS SYSTEM command WITH OUTPUT USING (outArr) ERROR USING (errArr)
SAY outArr
```

. end group

. click label level=2
Output:

. after level=2
```output
Vienna: +15°C →33km/h
```

. drawing id=#p22d33 ratio=3.16 width=22% size=1.21
. after box bare square bottom id=#p22x34 at=0,0,33.8,99.9 style="--skin-box-bg: rgba(114,159,207,0.20); color: #067d17"
`%l:`

. after box bare square bottom id=#p22x35 at=37.9,0.1,26.6,99.9 style="--skin-box-bg: rgba(114,159,207,0.20); color: #067d17"
`+%t`

. after box bare square bottom id=#p22x36 at=66.7,0.1,33.3,99.9 style="--skin-box-bg: rgba(114,159,207,0.20); color: #067d17"
`+%w`

. end drawing

<!-- slide # 23 (2026-10-15 09:36) --------------------------- ODP slide # 23 -->
. slide kicker="Command, 12" reference="Cf. rexxref.pdf (1.16.2. Commands)" presenter="Till Winkler"
# "curl" Example 3 – Using a Translation API (Deepl.com)

. steps each=after
- Many websites require an authorization key, which is often free and available under certain conditions.
    - Get the Deepl.com authorization key (2026-10-18): [https://www.deepl.com/pro#developer](https://www.deepl.com/pro#developer)
    - A list of websites for inspiration (2026-10-18): [https://github.com/public-apis/public-apis](https://github.com/public-apis/public-apis)

. after group level=2
. click mark 1 "url" pen=1
. with mark 5 "url" pen=1
. after mark 2 "key" pen=1
. with mark 5 "key" pen=1
. after mark 3 "original_text" pen=1
. with mark 5 '"quote(original_text)' pen=1
. after mark 4 "translate_to" pen=1
. with mark 5 "translate_to" pen=1
```rexx
url = "https://api-free.deepl.com/v2/translate"
key = "yourAuthorizationKey"     -- you need to obtain a valid key from deepl.com!
original_text = "ooRexx die Sprache der unbegrenzten Möglichkeiten."
translate_to = "EN"
command="curl" url "-d auth_key="key "-d text="quote(original_text) "-d target_lang="translate_to
outArr=.array~new          -- array for stdout
ADDRESS SYSTEM command WITH OUTPUT USING (outArr) ERROR USING (.array~new)
parse var outArr . ':"' translated_from '","text":"' translated_text '"' -- parse turns array into string
say "Translated by Deepl.com from" translated_from "to" translate_to
say "Translated text:" translated_text

::routine quote -- encloses text in quotes, such that it may contain blanks
  return '"' || arg(1) || '"'
```

. end group

. click level=2
Output (if authorization key is correct):

. after level=2
```output
Translated by Deepl.com from DE to EN
Translated text: ooRexx the language of unlimited possibilities.
```

<!-- slide # 24 (2026-10-15 09:36) --------------------------- ODP slide # 24 -->
. slide reference="Cf. rexxref.pdf (1.16.2. Commands)"
# "curl"-Related Links (as of 2025-10-24)

. after
- Documentation and examples
    - [https://curl.se/](https://curl.se/)
. after
- cURL for websites that support "clear URLs" a.k.a. "RESTful URLs"
    - Wikipedia
        - [https://en.wikipedia.org/wiki/Clean\_URL](https://en.wikipedia.org/wiki/Clean\_URL)
        - [https://en.wikipedia.org/wiki/Query\_string](https://en.wikipedia.org/wiki/Query\_string)
        - [https://en.wikipedia.org/wiki/Representational\_state\_transfer](https://en.wikipedia.org/wiki/Representational\_state\_transfer)
    . after
    - Tutorial
        - [https://www.baeldung.com/curl-rest](https://www.baeldung.com/curl-rest)
. after
- A directory of RESTful sites and their APIs: [https://publicapis.io/](https://publicapis.io/)
    - A Star Wars RESTful site: [https://swapi.dev/](https://swapi.dev/)

<!-- slide # 25 (2026-10-15 09:36) ----------- business card (not in the ODP) -->
. slide card logo=none
# Contact