# Line wrapping utilities, Linux fmt -s equivalent



## eldaemon (May 16, 2020)

I'm looking for a better way to wrap lines. I have Markdown Hugo source to my website and haven't been wrapping the lines for a while. One of the problems I ran into was things like lists getting messed up if I formatted with `fmt`.

For example:


```
please wrap this really long set of words. one two, three, four, five; six, seven, eight

1. don't
2. wrap
3. this

aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
```

Becomes:


```
please wrap this really long set of words. one two, three, four,
five; six, seven, eight

1. don't 2. wrap 3. this

aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
```

I'd like to keep the 1, 2, 3, all on separate lines but wrap the first line (as it does) and leave the last line alone (as it also does).

So effectively, only splitting a line if it's longer than the maximum.

`fold` does this, but it's a hard wrap that doesn't account for words. So it will split a word in half.

`fmt` on Linux has a -s argument that tells it not to split lines shorter than the maximum. It operates exactly how I would hope.

On FreeBSD, -s is a whitespace collapsing argument. If -s wasn't used on FreeBSD, I'd be tempted to rewrite the feature and just use -s. I could still do it with a different argument name, although not certain which one.

Is there another utility which does this? Maybe something in Ports? If I did write a patch for FreeBSD's `fmt`, do you think it would be accepted? What should the argument name be? Or should I write something new altogether?

Thank you for your time.


----------



## memreflect (May 16, 2020)

Install sysutils/coreutils, and you can use gfmt(1) and many other GNU tools.


----------



## aragats (May 17, 2020)

Linux `fmt` (as well as gfmt()) with _-s_ option doesn't perform the required functionality, e.g. this file:
	
	



```
please wrap this really long set of words. one two, three, four, five; six, seven, eight
 
1. don't
2. wrap
3. this

please wrap this really long set of words. one two, three, four, five; six, seven, eight
please wrap this really long set of words. one two, three, four, five; six, seven, eight
please wrap this really long set of words. one two, three, four, five; six, seven, eight
```
becomes:
	
	



```
% gfmt -s foo
please wrap this really long set of words. one two, three, four, five;
six, seven, eight

1. don't
2. wrap
3. this

please wrap this really long set of words. one two, three, four, five;
six, seven, eight
please wrap this really long set of words. one two, three, four, five;
six, seven, eight
please wrap this really long set of words. one two, three, four, five;
six, seven, eight
```
The multiple long lines are split, but not joined, the idea of formatting is lost. Maybe in your particular case it's okay, but IMO that option is useless since can be achieved with a simple sed() script:
	
	



```
#!/bin/sh
 
GOAL=65
MAX=10
sed 's/\(.\{'$GOAL'\}[^\ ]\{0,'$MAX'\}\ \)\(.*\)$/\1\
\2/' $1
```


----------



## eldaemon (May 17, 2020)

memreflect said:


> Install sysutils/coreutils, and you can use gfmt(1) and many other GNU tools.



That is probably the easiest option, thank you. Great suggestion.

Do you think this is a feature worthy of being merged into FreeBSD's `fmt`, though? I wonder if it'd be worth implementing it.


----------



## eldaemon (May 17, 2020)

aragats, I'm not sure it's possible to support lines like 1. test, 2. test, etc, and still have line joining.

The nice thing is that if you have formatted your file, it makes it a bit more idempotent. I'm looking for something I can run safely and always have sane output without having to look it over carefully, even if some lines are shorter than they could be.

Interesting sed script though, haven't tried that yet.


----------



## gpw928 (May 17, 2020)

eldaemon said:


> I'm not sure it's possible to support lines like 1. test, 2. test, etc, and still have line joining.


I agree.  The arithmetic list items need to be easily identifiable for fmt(1).

If you indent the arithmetic list items and separate them with a newline, then `fmt -$MAX -p` will do the job you want.
	
	



```
please wrap this really long set of words. one two, three, four, five; six, seven, eight
 
  1. don't wrap this very long list item to join the next arithmetic list item because I don't want that;

  2. wrap; and

  3. this.

please wrap this really long set of words. one two, three, four, five; six, seven, eight
please wrap this really long set of words. one two, three, four, five; six, seven, eight
please wrap this really long set of words. one two, three, four, five; six, seven, eight
```


```
$ fmt -60 -p
please wrap this really long set of words. one two, three,
four, five; six, seven, eight

  1. don't wrap this very long list item to join the next
  list item because I don't want that;

  2. wrap; and

  3. this.

please wrap this really long set of words. one two, three,
four, five; six, seven, eight please wrap this really long
set of words. one two, three, four, five; six, seven, eight
please wrap this really long set of words. one two, three,
four, five; six, seven, eight
```
You could use sed for pre- and post- processing of the arithmetic list items to achieve the outcome you want.


----------



## gpw928 (May 17, 2020)

On re-reading your original post, I'm not sure if this is what you want.  Maybe it progresses the discussion.


----------

