Take the 2-minute tour ×
Code Review Stack Exchange is a question and answer site for peer programmer code reviews. It's 100% free, no registration required.

I am using Bootstrap for a front-end project. I would like feedback concerning my HTML markup. I have spent quite some time polishing it, and I feel it is somewhat "mature". I have run the W3C HTML validator on it, and it only complains about three things:

  1. My use of center tags (consider this a "known issue")
  2. "Element legend not allowed as child of element div in this context." (I do not understand this error.)
  3. My use of X-UA-Compatible in the meta tag (common practice, but not standard)

Here are other things I am aware of:

  1. All the JavaScript should be bundled in just one file to reduce the number of requests. (I will do this for production.)
  2. The same as above, but for CSS.
  3. The code is a little lengthy, but I prefer to keep everything in just one file.
  4. The code is not commented.

What are best practices I have not followed in my code?

<!doctype html>

<!-- Bootstrap customisations:
    No responsiveness
    @navbarBackground: #568FB6
    @navbarBackgroundHighlight: lighten(#568FB6, 12%)
-->

<head>
    <meta charset='utf-8'>
    <meta http-equiv='X-UA-Compatible' content='IE=edge,chrome=1'>
    <title>DeepFlow</title>

    <link href='./img/favicon.ico' rel='icon'>

    <link href='./css/bootstrap.css' rel='stylesheet'>
    <link href='./css/font-awesome.css' rel='stylesheet'>
    <link href='./css/global.css' rel='stylesheet'>
    <link href='./css/login.css' rel='stylesheet'>
    <link href='./css/custom.css' rel='stylesheet'>

    <script src='./RGraph/libraries/RGraph.common.core.js'></script>
    <script src='./RGraph/libraries/RGraph.common.annotate.js'></script>
    <script src='./RGraph/libraries/RGraph.common.effects.js'></script>
    <script src='./RGraph/libraries/RGraph.common.dynamic.js'></script>
    <script src='./RGraph/libraries/RGraph.gauge.js'></script>
    <script src='./RGraph/libraries/RGraph.line.js'></script>

    <script src='./js/jquery.js'></script>
    <script>jQuery.fx.speeds._default = 800;</script>
    <script src='./js/underscore.js'></script>
    <script src='./js/bootstrap.js'></script>

    <script src='./js/ajax.js'></script>
    <script src='./js/navbar.js'></script>
    <script src='./js/login.js'></script>

    <script src='./js/users.js'></script>
    <script src='./js/editUser.js'></script>
    <script src='./js/addUser.js'></script>

    <script src='./js/statistics.js'></script>
    <script src='./js/protocols.js'></script>
    <script src='./js/export.js'></script>
    <script src='./js/tuple.js'></script>
    <script src='./js/network.js'></script>
</head>

<div class='navbar navbar-fixed-top' style='display:none'>
    <div class='navbar-inner'>
        <div class='container'>
            <div class='brand'>DeepFlow</div>
            <div id='navbar-container'>
                <ul class='nav panes-nav'>
                    <li id='statistics-label'><a>Statistics</a></li>
                    <li id='protocols-label'><a>Protocols</a></li>
                    <li id='tuples-label'><a>Tuples</a></li>
                    <li id='exports-label'><a>Exports</a></li>
                    <li id='users-label'><a>Users</a></li>
                    <li id='network-label'><a>Network</a></li>
                </ul>
                <ul class='nav pull-right'>
                    <li id='sign-out'><a>Log out</a></li>
                </ul>
            </div>
        </div>
    </div>
</div>

<div id='wrap'>
    <br>
    <br>
    <br>

    <div class='container'>
        <div class='alert alert-error' style='display:none'>
            <span id='error-message'></span>
            <button type='button' class='close' data-dismiss='alert'>×</button>
        </div>

        <div class='hero-unit' id='login-unit'>
            <h2>Welcome to DeepFlow</h2>
            <p>Please log in</p>
            <center id='login-box' class='pull-right control-group'>
                <div class='clearfix'>
                    <input type='text' placeholder='Username' id='login-username'/>
                </div>
                <div class='clearfix'>
                    <input type='password' placeholder='Password' id='login-password'/>
                </div>
                <button class='btn btn-primary' type='submit' id='login-button'>Log in</button>
            </center>
        </div>

        <div class='row pane' id='statistics-pane' style='display:none'>
            <legend>Network</legend>

            <div class='form-horizontal well'>
                <div class='offset1'>
                    <div class='control-group statistics-group'>
                        <label class='control-label graph-label'>
                            <div>Packets per second</div>
                            <p class='live-statistic' data-ending='' data-precision='0'></p>
                        </label>
                        <div class='controls'>
                            <canvas id='pps_graph' width='500' height='100'>[No canvas support]</canvas>
                        </div>
                    </div>
                    <div class='control-group statistics-group'>
                        <label class='control-label graph-label'>
                            <div>Throughput</div>
                            <p class='live-statistic' data-ending='&nbsp;kB/s' data-precision='0'></p>
                        </label>
                        <div class='controls'>
                            <canvas id='throughput_graph' width='500' height='100'>[No canvas support]</canvas>
                        </div>
                    </div>
                    <div class='statistics-group'>
                        <label class='control-label graph-label'id='packets-dropped-group'>
                            <div>Packets dropped</div>
                            <p class='live-statistic' data-ending='' data-precision='0'></p>
                        </label>
                        <div class='controls'>
                            <canvas id='packets_dropped_graph' width='500' height='100'>[No canvas support]</canvas>
                        </div>
                    </div>
                </div>
            </div>

            <legend>System</legend>
            <div class='form-horizontal well'>
                <div class='offset1'>
                    <div class='control-group statistics-group'>
                        <label class='control-label graph-label'>
                            <div>CPU usage</div>
                            <p class='live-statistic' data-ending='&nbsp;%' data-precision='2'></p>
                        </label>
                        <div class='controls'>
                            <canvas id='cpu_graph' width='500' height='100'>[No canvas support]</canvas>
                        </div>
                    </div>
                    <div class='statistics-group'>
                        <label class='control-label graph-label'>
                            <div>Memory usage</div>
                            <p class='live-statistic' data-ending='&nbsp;k' data-precision='0'></p>
                        </label>
                        <div class='controls'>
                            <canvas id='memory_graph' width='500' height='100'>[No canvas support]</canvas>
                        </div>
                    </div>
                </div>
            </div>
        </div>

        <div class='row pane' id='protocols-pane' style='display:none'>
            <legend>Protocol list</legend>
            <table class='table table-hover table-condensed offset3' id='protocol-table'>
                <thead>
                    <tr>
                        <th>Protocol</th>
                        <th id='protocol-status-column'></th>
                    </tr>
                </thead>
                <tbody id='protocol-rows'>
                </tbody>
            </table>
        </div>

        <div class='row pane' id='tuples-pane' style='display:none'>
            <legend>List of tuples</legend>
            <table class='table table-hover offset3' id='tuple-table'>
                <thead>
                    <tr>
                        <th>Name</th>
                        <th>Total</th>
                        <th id='tuples-status-column'></th>
                    </tr>
                </thead>
                <tbody id='tuples-rows'>
                </tbody>
            </table>
        </div>

        <div class='row pane' id='exports-pane' style='display:none'>
            <legend>Configure export destinations</legend>
            <table class='table table-hover' id='exports-table'>
                <thead>
                    <tr>
                        <th>Name</th>
                        <th>URL</th>
                        <th>IP</th>
                        <th>Port</th>
                        <th>Format</th>
                        <th id='exports-edit-column'></th>
                    </tr>
                </thead>
                <tbody id='exports-rows'>
                </tbody>
            </table>

            <div class='modal hide fade' id='edit-export-modal'>
                <div class='modal-header'>
                    <span type='button' class='close' data-dismiss='modal' aria-hidden='true'>&times;</span>
                    <h3>Edit export <code id='edit-export-old'></code></h3>
                </div>
                <div class='modal-body'>
                    <form class='form-horizontal'>
                        <div class='control-group'>
                            <label class='control-label'>New IP</label>
                            <div class='controls'>
                                <input type='text' id='edit-export-ip' placeholder='IP'/>
                            </div>
                        </div>
                        <div class='control-group'>
                            <label class='control-label'>New port</label>
                            <div class='controls'>
                                <input type='text' id='edit-export-port' placeholder='Port'/>
                            </div>
                        </div>
                        <label class='control-label'>New format</label>
                        <div class='controls'>
                            <input type='text' id='edit-export-format' placeholder='Format'/>
                        </div>
                    </form>
                </div>
                <div class='modal-footer'>
                    <span class='btn' id='edit-export-close'>Close</span>
                    <span class='btn btn-primary' id='edit-export-save'>Save changes</span>
                </div>
            </div>
        </div>

        <div class='row pane' id='users-pane' style='display:none'>
            <div class='span6'>
                <legend>List of users</legend>
                <table class='table table-hover' id='users-table'>
                    <thead>
                        <tr>
                            <th>User</th>
                            <th>Rights</th>
                            <th id='users-edit-column'></th>
                        </tr>
                    </thead>
                    <tbody id='user-rows'>
                    </tbody>
                </table>
            </div>

            <div id='new-user-box' class='span6'>
                <legend>Add a new user</legend>
                <form class='form-horizontal well'>
                    <div class='control-group'>
                        <label class='control-label'>Username</label>
                        <div class='controls'>
                            <input type='text' class='username' id='new-user-username' placeholder='Username'/>
                        </div>
                    </div>
                    <div class='control-group'>
                        <label class='control-label'>Password</label>
                        <div class='controls'>
                            <input type='password' class='password' id='new-user-password' placeholder='Password'/>
                        </div>
                    </div>
                    <div class='control-group'>
                        <label class='control-label'>Rights</label>
                        <div class='controls'>
                            <div class='btn-group' data-toggle='buttons-radio' id='new-user-rights'/>
                                <span class='btn'>Administrator</span>
                                <span class='btn' id='new-user-operator'>Operator</span>
                            </div>
                        </div>
                    </div>
                    <div class='controls'>
                        <span class='btn btn-primary' id='new-user-button'>Add new user</span>
                    </div>
                </form>
            </div>

            <div class='modal hide fade' id='edit-user-modal'>
                <div class='modal-header'>
                    <span class='close' data-dismiss='modal' aria-hidden='true'>&times;</span>
                    <h3>Edit user <code id='edit-user-old-username'></code></h3>
                </div>
                <div class='modal-body'>
                    <form class='form-horizontal'>
                        <div class='control-group'>
                            <label class='control-label'>New username</label>
                            <div class='controls'>
                                <input type='text' class='username' id='edit-user-username' placeholder='(Leave unchanged)'/>
                            </div>
                        </div>
                        <div class='control-group'>
                            <label class='control-label'>New password</label>
                            <div class='controls'>
                                <input type='password' class='password' id='edit-user-password' placeholder='(Leave unchanged)'/>
                            </div>
                        </div>
                        <label class='control-label'>New rights</label>
                        <div class='controls'>
                            <div class='btn-group' data-toggle='buttons-radio' id='edit-user-rights'>
                                <span class='btn'>Administrator</span>
                                <span class='btn'>Operator</span>
                            </div>
                        </div>
                    </form>
                </div>
                <div class='modal-footer'>
                    <span class='btn btn-danger pull-left' data-action='remove'><i class='icon-trash'></i> Remove</span>
                    <span class='btn' data-action='close'>Close</span>
                    <span class='btn btn-primary' data-action='save'>Save changes</span>
                </div>
            </div>
        </div>

        <div class='pane' id='network-pane' style='display:none'>
            <div class='row'>
                <div class='alert alert-info' style='display:none'>
                    Use this pane to configure the server network. Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.
                </div>
                <form class='span6 form-horizontal'>
                    <legend>Basic configurations</legend>
                    <div class='control-group'>
                        <label class='control-label'>IP address</label>
                        <div class='controls'>
                            <input type='text' id='network-ip' placeholder='IP address'/>
                        </div>
                    </div>
                    <div class='control-group'>
                        <label class='control-label'>Subnet mask</label>
                        <div class='controls'>
                            <input type='text' id='network-mask' placeholder='Subnet mask'/>
                        </div>
                    </div>
                    <div class='control-group'>
                        <label class='control-label'>Default gateway</label>
                        <div class='controls'>
                            <input type='text' id='network-gateway' placeholder='Default gateway'/>
                        </div>
                    </div>
                </form>
                <form class='span6 form-horizontal'>
                    <legend>Optional fields</legend>
                    <div class='control-group'>
                        <label class='control-label'>DNS hostname</label>
                        <div class='controls'>
                            <input type='text' id='network-dns' placeholder='DNS hostname'/>
                        </div>
                    </div>
                    <div class='control-group'>
                        <label class='control-label'>NTP server hostname</label>
                        <div class='controls'>
                            <input type='text' id='network-ntp' placeholder='NTP server hostname'/>
                        </div>
                    </div>
                </form>
            </div>

            <br>
            <br>
            <br>
            <center>
                <span class='btn btn-large btn-primary' id='network-save'>Save and reboot server now</span>
            </center>
        </div>

        <div id='push'></div>
    </div>
</div>

<div id='footer'>
    <div class='container'>
        <span class='muted credit'>&copy; Copyright 2013 Qosmos SA. All rights reserved.</span>
        <img id='logo' src='./img/logo_grey.png' alt='logo'/>
    </div>
</div>
share|improve this question
add comment

1 Answer

Other items to consider:

  • Place JavaScript at the bottom (before the closing body tag).
  • Find other ways to avoid the flash of unstyled content.
  • Avoid hard-coding text (e.g., "DeepFlow", "System") with an eye to internationalization.
  • Use CSS to change layout, not multiple <br /> tags.
  • Leave "style='display:none'" in CSS; change the class instead.
  • Accessibility and its corresponding mark-up.
  • Use tools like JSLint, CSSLint, in addition to the W3C validation tool.
  • Good use of unique id attributes.
  • Wrap input fields with label elements when possible; this allows users to click the label associated with the input field to give that field focus.
  • "logo" should probably be "Qosmos Logo".
  • Technically, you don't need &copy; and the word Copyright.
  • Add a body tag to help ensure consistency across all browsers.
share|improve this answer
    
The reason I have the style in the HTML is because the CSS could load after the HTML, which might cause some elements to appear briefly before the CSS is fully loaded. –  Randomblue Jan 11 '13 at 20:31
    
Regarding accessibility, I have made sure to have an alt attribute for the only image. What else do you suggest? –  Randomblue Jan 11 '13 at 20:31
    
Regarding your note (before the closing body tag) I do not have a body tag. Well, at least it is implicit. –  Randomblue Jan 11 '13 at 20:42
    
Regarding the doctype, I grabbed it from HTML5 boilerplate. –  Randomblue Jan 11 '13 at 20:47
    
The doctype should be fine as is; Google and StackOveflow also use such a minimal declaration. –  Dave Jarvis Jan 11 '13 at 20:52
show 2 more comments

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.