kodaek98
kodaek98

Reputation: 473

How to write file to html with beauty?

I would like to write to the test.html file this html:

<h2><strong><a href="http://awesome.com">AwesomeCom</a></strong><span>is awesome</span></h2>

Which will be lokk like:

<h2>
    <strong>
        <a href="http://awesome.com">
            AwesomeCom
        </a>
    </strong>
    <span>
         is awesome
   </span>
</h2>

so it is looks beauty and so on...and i tried this code:

var html = require("html");
var beautify_html = require('js-beautify').html;
var data = '<h2><strong><a href="http://awesome.com">AwesomeCom</a></strong><span>is awesome</span></h2>';
var beautyHtml= beautify_html(data);
fs.writeFile('test.html',beautyHtml, function (err) {});

But it is stays in one line...is it wrong what i wrote? or i have to add something? Thanks for the helps

Upvotes: 6

Views: 1998

Answers (3)

Richard Lovell
Richard Lovell

Reputation: 888

You could read from a file and then write it. It will keep the formatting and it's better practice than writing HTML in strings (unless you have to):

    fs.readFile(fs.realpathSync('input.html'), 'utf8', function (err, data){
        if (err) {
            return console.log(err);
        }
        fs.writeFile('output.html', data, function (err) {
            if (err) return console.log(err);
            console.log('File writing done');
        });
    });

Upvotes: 0

BitwiseMan
BitwiseMan

Reputation: 1937

You're not doing anything wrong. js-beautify definitely has bugs and limitations. It is likely you are encountering one of them. You should file an issue.

That said, whether putting all elements on separate lines is correct is a bit more complex than it seems at first. js-beautify is considerably more accurate than using a series of regular expressions or a tool that treats HTML the same as XML, but it is also does not fully parse the HTML before formatting it, so some behaviors that seem like they should be trivial are not implemented because the tool doesn't have enough information to do so safely.

Example 1: HTML is not XML

For example, if the input were XML, then the desired formatted output shown above would be fine. But, because this is HTML, the desired output HTML shown in the question will display differently than the input.

Given this HTML (the sample input):

<h2><strong><a href="http://awesome.com">AwesomeCom</a></strong><span>is awesome</span></h2>

The displayed text will look like this:

AwesomeComis awesome

Given this HTML (the desired output):

<h2>
  <strong>
    <a href="http://awesome.com">AwesomeCom</a>
  </strong>
  <span>is awesome</span>
</h2>

The displayed text will look like this:

AwesomeCom is awesome

The formatted output HTML for the given input might be either of these:

<h2>
  <strong><a href="http://awesome.com">AwesomeCom</a></strong><span>is awesome</span>
</h2>

<h2><strong><a href="http://awesome.com">AwesomeCom</a></strong><span>is awesome</span></h2>

But it is definitely not the desired output HTML shown in the question, sorry.

Example 2: Adding whitespace to HTML may change layout

Next, let's consider why <strong> and <a> might not be safe to separate. If the input were the following, then adding whitespace between <strong> and <a> would produce different displayed text:

<h2>The<strong><a href="http://awesome.com">AwesomeCom</a></strong><span>is awesome</span>!</h2>

In the case of the original input, adding a newline <strong> and <a> is safe, because there is no text between <h2> and <strong>, but js-beautify isn't smart enough to be sure of that. Even if it were, it is debatable whether that is the right behavior. Doing that would produce the following behavior where formatting differs wildly depending on presence of leading text and/or whitespace:

<!-- Input --> 
<h2><strong><a href="http://awesome.com">AwesomeCom</a></strong><span>is awesome</span>!</h2>
<h2>The<strong><a href="http://awesome.com">AwesomeCom</a></strong><span>is awesome</span>!</h2>

<!-- Output --> 
<h2>
  <strong>
    <a href="http://awesome.com">AwesomeCom</a></strong><span>is awesome</span>!
</h2>
<h2>
  The<strong><a href="http://awesome.com">AwesomeCom</a></strong><span>is awesome</span>!
</h2>

Example 3: Close to "real-world" input

Finally, let's consider an input that is more like what was probably meant, with spaces in reasonable places:

<h2>The <strong><a href="http://awesome.com">AwesomeCom</a></strong> <span>is awesome</span>!</h2>

Example 3-a: Multiple valid "beautified" HTML outputs

There are a number of ways to reformat this. The h2 tag ignores whitespace between it and it's contents and adding more whitespace where there is already whitespace is safe. All of the below examples are reasonable depending on who you ask:

<h2>The <strong><a href="http://awesome.com">AwesomeCom</a></strong> <span>is awesome</span>!</h2>

<h2>
  The <strong><a href="http://awesome.com">AwesomeCom</a></strong>
  <span>is awesome</span>!
</h2>

<h2>
  The 
  <strong><a href="http://awesome.com">AwesomeCom</a></strong>
  <span>is awesome</span>!
</h2>

Example 3b: Invalid "beautified" HTML output

Some would even say that this next example is okay as well, but I'm not so sure.

<h2>
  The 
  <strong>
    <a href="http://awesome.com">AwesomeCom</a>
  </strong>
  <span>is awesome</span>!
</h2>

It adds a whitespace between between <strong> and <a> where there wasn't any before. Will the layout engine merge the space before and after <strong>? What about if there's CSS that changes the font size for all <strong> tags? This might be safe in some cases, but would change the layout in just as many.

Upvotes: 2

Alex
Alex

Reputation: 38499

This problem seems to be isolated to js-beautify

There's a couple of related open issues on the github page:

You can also see this not working if you paste your arbitrary HTML into http://jsbeautifier.org/


If I replace js-beautify for pretty-data I get the desired output, when formatting as XML:

var fs = require('fs');
var pd = require('pretty-data').pd;
var data = '<h2><strong><a href="http://awesome.com">AwesomeCom</a></strong><span>is awesome</span></h2>';
var pdHtml= pd.xml(data);

fs.writeFile('test.html',pdHtml, function (err){});

Results in

<h2>
  <strong>
    <a href="http://awesome.com">AwesomeCom</a>
  </strong>
  <span>is awesome</span>
</h2>

Upvotes: 0

Related Questions