python-3.xflaskchartist.js

How to send two series from Flask to be plotted by Chartist.js


I want to compare the results of the year 2019 with the results of the year 2020. To compare the data I created a chart using Chartist.js; when I use only one series the graph is displayed (as seen in the figure); However, when I send two series, I don't get the graph. For some reason it seems that the instructions in jinja2 are not correct. Any recommendation where the error is in my code will be very helpful.

enter image description here

The source code to obtain the graph using the series [100,200,300] is as follows:

@app.route('/chart')
def chart():
    labels = ["Jan", "Feb", "Mar"] 
    series =  [100, 200, 300]          
    return render_template('chart.html',labels=labels, series=series)

The chart.html file is as follows:

<!DOCTYPE html>
<html>
<head>
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/chartist.js/latest/chartist.min.css">
  <script src="https://cdn.jsdelivr.net/chartist.js/latest/chartist.min.js"></script>
</head>

<style>
  body {
    background-color: #222;
    padding: 20px;
    font-family: arial;
  }

  #chart4 {
    background-color: slategrey;
    border-radius: 10px;
    padding-top: 10px;
  }

  #title{
    color:slategrey;
    margin-bottom: 10px;
  }


  /* Customizing plain Css:  */


  /* First series a */

  .ct-series-a .ct-line {
    stroke: black;
    stroke-width: 4px;
  }

  .ct-series-a .ct-point {
    stroke: red;
    stroke-width: 14px;
  }


  /* Second series b */

  .ct-series-b .ct-line {
    stroke: Orange;
    stroke-width: 4px;
  }

  .ct-series-b .ct-point {
    stroke: black;
    stroke-width: 14px;
  }

  /* Custom Css for the labels */

  #labels{
    padding-top:10px;
    display;block;
    height: 30px;
    width: 100%;
    border-radius:4px;
    margin-bottom: 10px;
    background-color: slategrey;
    text-align:center;
  }

  #series-b{
    float:right;
  }


  .label-series-a{
    stroke:black;
    fill:orange;
    stroke-width: 4px;
  }

  .label-series-b{
    stroke:red;
    fill:black;
    stroke-width: 4px;
  }


</style>

<body>
  <div id="title">Comparative analytics between 2019 and 2020:</div> 
  <div id="labels"> 2019: <svg width="14" height="14" viewBox="0 0 14 14" xmlns="http://www.w3.org/2000/svg">
    <rect x="0" y="0"
          width="14" height="14"
          rx="2" ry="2"
          class="label-series-b"
          />
  </svg> 
  &nbsp;&nbsp;2020:
      <svg width="14" height="14" viewBox="0 0 14 14" xmlns="http://www.w3.org/2000/svg">
    <rect x="0" y="0"
          width="14" height="14"
          rx="2" ry="2"
          class="label-series-a"
          />
  </svg>

  </div>

  <div id="chart4" class="ct-chart"></div>  


<script>
    var data = {
        // A labels array that can contain any sort of values
        // labels: ['Mon', 'Tue', 'Wed', 'Thu', 'Fri'],
        labels: [{% for item in labels %}
                    "{{ item }}",
                {% endfor %}],
        // Our series array that contains series objects or in this case series data arrays

        series: [ [{% for item in series %} 
                    "{{ item }}", 
                   {% endfor %}]
                ]
    };

      var options = {
          width: "640px",
          height: "320px"
      }

      // Create a new line chart object where as first parameter we pass in a selector
      // that is resolving to our chart container element. The Second parameter
      // is the actual data object.
      new Chartist.Line('#chart4', data);
</script>

by modifying my code in @ app.route ('/ chart') with two series [[100, 200, 300], [10,20,30]]

@app.route('/chart')
def chart():
   labels = ["Jan", "Feb", "Mar"] 
   series =  [[100, 200, 300],[10,20,30]]          
   return render_template('chart.html',labels=labels, series=series)

and making changes to the chart.html file in jinja2 (as indicated in the following code):

    <script>
    var data = {
        // A labels array that can contain any sort of values
        // labels: ['Mon', 'Tue', 'Wed', 'Thu', 'Fri'],
        labels: [{% for item in labels %}
                    "{{ item }}",
                {% endfor %}],
        // Our series array that contains series objects or in this case series data arrays
        series: [ [{% for item in series %} 
                    "{{ item }}", 
                   {% endfor %}],

                   [{% for item in series %} 
                   "{{ item }}", 
                    {% endfor %}]
               ]
    };

      var options = {
          width: "640px",
          height: "320px"
      }

      // Create a new line chart object where as first parameter we pass in a selector
      // that is resolving to our chart container element. The Second parameter
      // is the actual data object.
      new Chartist.Line('#chart4', data);
</script>

I get a graph without the trend lines plotted. Where in the code in chart.html am I making the mistake with jinja2?

If I hardcode the series, for example [[1,2,3], [3,2,1]] in the script tag I get the graph correctly. What suggests that the problem is in the coding of jinja2 on the html page. I still do not determine what the cause is, any suggestions will be appreciated.

    <script>
    var data = {
        // A labels array that can contain any sort of values
        // labels: ['Mon', 'Tue', 'Wed', 'Thu', 'Fri'],
        labels: [{% for item in labels %} "{{ item }}", {% endfor %}],
        // Our series array that contains series objects or in this case series data arrays
        series: [ 
                [1,2,3],
                [3,2,1]
        ]
    };

      var options = {
          width: "640px",
          height: "320px"
      }

      // Create a new line chart object where as first parameter we pass in a selector
      // that is resolving to our chart container element. The Second parameter
      // is the actual data object.
      new Chartist.Line('#chart4', data);
    </script>

enter image description here


Solution

  • It's easier than you're thinking.
    Also, you don't need the quotes around {{ item }} for the series.
    Try this out:

        var data = {
            labels: [   {% for item in labels %}
                            "{{ item }}",
                        {% endfor %}
                    ],
            series: [   {% for item in series %} 
                            {{ item }}, 
                        {% endfor %}
                    ]
        };
    

    enter image description here