Build beautiful and interactive API documentation for ORDS

Image
In this blog post, I will show you how to quickly build beautiful and interactive API documentation for your Oracle APEX REST data sources using  swagger hub . Using APEX v23.1. I downloaded the  titanic data set  and loaded them into tables in my APEX instance, created some authorized restful services and published them using swagger hub. You can create a free account on swagger hub.   Check out my titanic swagger hub here ; Press Authorize. Username REST, password Glasgow123! I won't go through creating RESTful services and just show you the four I created that sit on top of the titanic data set; The GET is a very simple SQL query;      select * from TITANIC_DATA_SET_NEW A handy tip is to add comments, as there will appear on swagger hub, making your API self documenting; Once you have created your modules, press the Generate Swagger Doc button; This will generate an open API for you.  Copy the API and paste it into swagger hub This will generate the documentation; As mentioned b

Add a time-series chart to your APEX app - Part 3 of the HighChart Series

Add a time-series chart to your APEX app using HighCharts and JQuery.  This is the third in the series of blog posts showing you how to add HighCharts to your APEX application.

This is the most useful of the HighCharts in the series so far, easily turn your date data into an animated time series chart with a couple of lines of JavaScript



The chart reads the data points from an Interactive Report on the page. Create the Interactive Region with static ID IR_STATIC_ID using the following SQL source;

select TO_DATE('2003/07/09''yyyy/mm/dd'as VALUE_110 as VALUE_220 as VALUE_3 from DUAL
UNION
select TO_DATE('2003/07/11''yyyy/mm/dd'as VALUE_120 as VALUE_240 as VALUE_3 from DUAL
UNION
select TO_DATE('2003/07/13''yyyy/mm/dd'as VALUE_130 as VALUE_220 as VALUE_3 from DUAL
UNION
select TO_DATE('2003/07/10''yyyy/mm/dd'as VALUE_199 as VALUE_280 as VALUE_3 from DUAL
UNION
select TO_DATE('2003/08/01''yyyy/mm/dd'as VALUE_15 as VALUE_280 as VALUE_3 from DUAL
UNION
select TO_DATE('2003/08/02''yyyy/mm/dd'as VALUE_110 as VALUE_230 as VALUE_3 from DUAL
UNION
select TO_DATE('2003/08/03''yyyy/mm/dd'as VALUE_115 as VALUE_220 as VALUE_3 from DUAL
UNION
select TO_DATE('2003/08/04''yyyy/mm/dd'as VALUE_14 as VALUE_210 as VALUE_3 from DUAL
UNION
select TO_DATE('2003/08/05''yyyy/mm/dd'as VALUE_117 as VALUE_220 as VALUE_3 from DUAL
UNION
select TO_DATE('2003/08/06''yyyy/mm/dd'as VALUE_120 as VALUE_240 as VALUE_3 from DUAL
UNION
select TO_DATE('2003/08/07''yyyy/mm/dd'as VALUE_13 as VALUE_22 as VALUE_3 from DUAL
UNION
select TO_DATE('2003/08/08''yyyy/mm/dd'as VALUE_120 as VALUE_230 as VALUE_3 from DUAL
UNION
select TO_DATE('2003/08/10''yyyy/mm/dd'as VALUE_118 as VALUE_220 as VALUE_3 from DUAL
UNION
select TO_DATE('2004/07/09''yyyy/mm/dd'as VALUE_110 as VALUE_220 as VALUE_3 from DUAL
UNION
select TO_DATE('2004/07/11''yyyy/mm/dd'as VALUE_120 as VALUE_240 as VALUE_3 from DUAL
UNION
select TO_DATE('2004/07/13''yyyy/mm/dd'as VALUE_130 as VALUE_220 as VALUE_3 from DUAL
UNION
select TO_DATE('2004/07/10''yyyy/mm/dd'as VALUE_199 as VALUE_270 as VALUE_3 from DUAL
UNION
select TO_DATE('2004/08/01''yyyy/mm/dd'as VALUE_15 as VALUE_220 as VALUE_3 from DUAL
UNION
select TO_DATE('2004/08/02''yyyy/mm/dd'as VALUE_110 as VALUE_220 as VALUE_3 from DUAL
UNION
select TO_DATE('2004/08/03''yyyy/mm/dd'as VALUE_115 as VALUE_240 as VALUE_3 from DUAL
UNION
select TO_DATE('2004/08/04''yyyy/mm/dd'as VALUE_14 as VALUE_22 as VALUE_3 from DUAL
UNION
select TO_DATE('2004/08/05''yyyy/mm/dd'as VALUE_117 as VALUE_220 as VALUE_3 from DUAL
UNION
select TO_DATE('2004/08/06''yyyy/mm/dd'as VALUE_120 as VALUE_230 as VALUE_3 from DUAL
UNION
select TO_DATE('2004/08/07''yyyy/mm/dd'as VALUE_13 as VALUE_22 as VALUE_3 from DUAL
UNION
select TO_DATE('2004/08/08''yyyy/mm/dd'as VALUE_120 as VALUE_210 as VALUE_3 from DUAL
UNION
select TO_DATE('2004/08/10''yyyy/mm/dd'as VALUE_118 as VALUE_22 as VALUE_3 from DUAL
order by VALUE_1 asc

Create a static region which will display the timeline diagram chart in the Header and Footer section header text

<div id="container" style="height: 400px; min-width: 600px"></div>

<script src="https://code.highcharts.com/stock/highstock.js"></script>
<script src="https://code.highcharts.com/stock/modules/exporting.js"></script>

(reading directly from HighCharts, if it works for you download them to static application files)

Add the following code to execute when page loads. This is the code that contains the configuration of the chart and loads the data from the Interactive Report;

let period = 1000//1sec

Highcharts.stockChart('container', {

    legend: {
            enabled: true,
            labelFormatter: function() {
        return this.name +' (click to hide)';
      }
        },

    chart: {
        borderColor: 'black',
        borderWidth: 0.2,
        
        borderRadius: 10
    },
       tooltip: {
        xDateFormat: '%d-%m-%Y',
        shared: true
    },


    series: [{
        animation: {
        defer: period*0,
        duration : 4000
      },
        name: 'Product sales 2017',
        data: getDataFromInteractiveReport('IR_STATIC_ID',1)
    },{
        animation: {
        defer: period*1,
        duration : 4000
      },
        name: 'Product sales 2018',
        data: getDataFromInteractiveReport('IR_STATIC_ID',2)
    }]
});

(You can have a play with configuration options in HighCharts Fiddle and then change the options in the code)

the chart reads the data from the Interactive Report to display on the chart;

function getDataFromInteractiveReport(staticIDcolumn){
    var result = []; // array of [date, value] to pass to HighCharts
    
    // For each row in the IR
    var data =$.each($('#'+staticID+' tr'), function(indextr){  
        var data = []; // holds the date-value
        var dateColumnValue =  Date.parse($(this).find("td:eq(0)").text());
        var value =  Number($(this).find("td:eq("+column+")").text());
  
        if (value){
            data.push(dateColumnValuevalue);
            result.push(data);
        }
  });
  return result;
}

Highcharts needs the Interactive Report to be present on the page to get the values to plot on the graph. In this case I  don't need the Interactive report displayed on the page, so I will hide the interactive report using the following CSS;

#IR_STATIC_ID {
    displaynone;
}

If you want to add another series for 2019 add a new column to the SQL then add the series to the JavaScript code. This time column 3;

series: [{
    animation: {
    defer: period*0,
    duration : 4000
  },
    name: 'Product sales 2017',
    data: getDataFromInteractiveReport('IR_STATIC_ID',1// column number 1
},{
    animation: {
    defer: period*1,
    duration : 4000
  },
    name: 'Product sales 2018',
    data: getDataFromInteractiveReport('IR_STATIC_ID',2)// column number 2
},{
    animation: {
    defer: period*2,
    duration : 4000
  },
    name: 'Product sales 2019',
    data: getDataFromInteractiveReport('IR_STATIC_ID',3)// column number 3
}]

The example shown is using dummy SQL. To create an Interactive Region from your table that contains dates you can use something like this, where I am getting completion date counts from my table which will work with the JS code shown above when we have 1 series.

select TRUNC(UPDATED_DATE), 
           COUNT(*)  from pdr WHERE  
                status_comm='COMPLETE' GROUP BY TRUNC(UPDATED_DATE
                     ORDER BY TRUNC(UPDATED_DATE)

To work with the source above, for one series you would have this;

series: [{
    animation: {
    defer: period*0,
    duration : 4000
  },
    name: 'PDR Completion Count',
    data: getDataFromInteractiveReport('IR_STATIC_ID',1// column number 1
}]

Highcharts is free to use for personal projects, school websites, and non-profit organizations. For commercial applications you must purchase a license.

Part 1 - Dumbell Chart

Part 2 - Timeline Diagram Chart



Comments

Popular posts from this blog

Oracle APEX Interactive Grid colour cells based on a condition using JavaScript and CSS

Oracle APEX pretty checkbox item plugin

Build beautiful and interactive API documentation for ORDS