{"id":15045263,"url":"https://github.com/jenkinsci/data-tables-api-plugin","last_synced_at":"2026-04-18T21:07:45.326Z","repository":{"id":37037325,"uuid":"220562342","full_name":"jenkinsci/data-tables-api-plugin","owner":"jenkinsci","description":"Jenkins plug-that provides JQuery DataTables","archived":false,"fork":false,"pushed_at":"2026-03-01T15:40:42.000Z","size":1692,"stargazers_count":4,"open_issues_count":6,"forks_count":15,"subscribers_count":1,"default_branch":"main","last_synced_at":"2026-03-01T18:37:54.444Z","etag":null,"topics":["api-plugin","datatables","jenkins-plugin","jquery"],"latest_commit_sha":null,"homepage":"https://plugins.jenkins.io/data-tables-api/","language":"Java","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/jenkinsci.png","metadata":{"files":{"readme":"README.adoc","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null},"funding":{"community_bridge":"jenkins","custom":["https://www.jenkins.io/donate/#why-donate"]}},"created_at":"2019-11-08T23:15:02.000Z","updated_at":"2026-03-01T15:40:46.000Z","dependencies_parsed_at":"2024-01-26T12:13:23.400Z","dependency_job_id":"d102d897-2a3b-4c6e-bf80-3b5fb39c7d2f","html_url":"https://github.com/jenkinsci/data-tables-api-plugin","commit_stats":{"total_commits":808,"total_committers":12,"mean_commits":67.33333333333333,"dds":0.4554455445544554,"last_synced_commit":"d1302ab385fdedacbf93c50c651a5df7b3566170"},"previous_names":[],"tags_count":83,"template":false,"template_full_name":null,"purl":"pkg:github/jenkinsci/data-tables-api-plugin","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jenkinsci%2Fdata-tables-api-plugin","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jenkinsci%2Fdata-tables-api-plugin/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jenkinsci%2Fdata-tables-api-plugin/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jenkinsci%2Fdata-tables-api-plugin/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/jenkinsci","download_url":"https://codeload.github.com/jenkinsci/data-tables-api-plugin/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jenkinsci%2Fdata-tables-api-plugin/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":30098124,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-03-04T22:49:54.894Z","status":"ssl_error","status_checked_at":"2026-03-04T22:49:48.883Z","response_time":59,"last_error":"SSL_read: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["api-plugin","datatables","jenkins-plugin","jquery"],"created_at":"2024-09-24T20:51:39.187Z","updated_at":"2026-03-04T23:05:05.058Z","avatar_url":"https://github.com/jenkinsci.png","language":"Java","funding_links":["https://funding.communitybridge.org/projects/jenkins","https://www.jenkins.io/donate/#why-donate"],"categories":[],"sub_categories":[],"readme":":tip-caption: :bulb:\n:imagesdir: etc/images\n\n= jQuery DataTables Jenkins Plugin\n\nimage:https://github.com/jenkinsci/data-tables-api-plugin/workflows/GitHub%20CI/badge.svg[GitHub Actions, link=https://github.com/jenkinsci/data-tables-api-plugin/actions]\nimage:https://img.shields.io/github/issues-pr/jenkinsci/data-tables-api-plugin.svg[GitHub pull requests, link=https://github.com/jenkinsci/data-tables-api-plugin/pulls]\n\nProvides https://datatables.net[jQuery DataTables] for Jenkins Plugins. DataTables is a plug-in for the jQuery Javascript library. It is a highly flexible tool, built upon the foundations of progressive enhancement, that adds all of these advanced features to any HTML table:\n\n** Previous, next and page navigation\n** Filter results by text search\n** Sort data by multiple columns at once\n** DOM, Javascript, Ajax and server-side processing\n** Easily theme-able\n** Mobile friendly\n\nThis plugin contains JS and CSS files of the latest https://datatables.net[DataTables] release and corresponding Jenkins UI elements (Java data model). It also contains some additional DataTables plugins.\n\n== How to use the plugin\n\nA common UI element to show plugin details is a table control. Most plugins (and Jenkins core) typically use\nplain HTML tables. However, if the table should show a large number of rows then using a more sophisticated control\nlike  https://datatables.net[DataTables] makes more sense.\n\nIn order to use https://datatables.net[DataTables] in a view there are two options, you can either decorate existing\nstatic HTML tables (see \u003c\u003ctables-static\u003e\u003e) or populate the table content using Ajax (see \u003c\u003ctables-dynamic\u003e\u003e). Both\noption require that you add a maven dependency to your pom:\n\n[source,xml]\n----\n\u003cdependency\u003e\n  \u003cgroupId\u003eio.jenkins.plugins\u003c/groupId\u003e\n  \u003cartifactId\u003edata-tables-api\u003c/artifactId\u003e\n  \u003cversion\u003e[latest version]\u003c/version\u003e\n\u003c/dependency\u003e\n----\n\n[#tables-static]\n=== Tables with static HTML content\n\nThe easiest way of using DataTables is by creating a static HTML table that will be decorated by simply calling the\nconstructor of the datatable. This approach involves no special handling on the Java and Jelly side, so I think it is\nsufficient to follow the https://datatables.net/examples/basic_init/zero_configuration.html[example] in the DataTables\ndocumentation. Just make sure that after building the table in your Jelly file you need to decorate the table\nwith the following piece of code:\n\n[source,xml]\n----\n\u003cj:jelly xmlns:j=\"jelly:core\" xmlns:st=\"jelly:stapler\" \u003e\n\n  \u003cst:adjunct includes=\"io.jenkins.plugins.jquery3\"/\u003e\n  \u003cst:adjunct includes=\"io.jenkins.plugins.data-tables\"/\u003e\n\n  [...]\n\n    \u003cdiv class=\"table-responsive\"\u003e\n        \u003ctable\n          class=\"table table-striped display\" id=\"id\"\u003e\n            [...]\n        \u003c/table\u003e\n    \u003c/div\u003e\n\n  [...]\n  \u003cscript\u003e\n     $('#id').DataTable(); \u003c1\u003e\n  \u003c/script\u003e\n\n\u003c/j:jelly\u003e\n----\n\u003c1\u003e replace `id` with the ID of your HTML table element\n\nIn the Forensics plugin no such static table is used so far, but you can have a look at the\nhttps://github.com/jenkinsci/warnings-ng-plugin/blob/master/plugin/src/main/resources/io/jenkins/plugins/analysis/core/model/FixedWarningsDetail/index.jelly[table that shows fixed warnings]\nin the warnings plugin to see how such a table can be decorated.\n\n[#tables-dynamic]\n=== Tables with dynamic model based content\n\nWhile static HTML tables are easy to implement, they have several limitations. So it makes sense to follow a more\nsophisticating approach. Typically, tables in user interfaces are defined by using a corresponding table (and row) model.\nJava Swing successfully provides such a\nhttps://docs.oracle.com/javase/tutorial/uiswing/components/table.html[table model] concept since the early days of Java.\nI adapted these concepts for Jenkins and DataTables as well. In order to create a table in a Jenkins view a plugin\nneeds to provide a table model class, that provides the following information:\n\n- the ID of the table (since there might be several tables in the view)\n- the model of the columns (i.e., the number, type, and header labels of the columns)\n- the content of the table (i.e. the individual row objects)\n\nYou will find an example of such a table in the Forensics plugin: here a table lists\nthe files in your Git repository combined with the corresponding commit statistics (number of authors,\nnumber of commits, last modification, first commit). A screenshot of that table is shown in \u003c\u003cimg-table\u003e\u003e.\n\n.Dynamic Table in the Forensics plugin\n[#img-table]\nimage::table.png[Table example]\n\nIn order to create such a table in Jenkins, you need to create a table model class that derives from `TableModel`.\nIn \u003c\u003cforensics-table-model\u003e\u003e a diagram of the corresponding classes in the Forensics plugin is shown.\n\n[#forensics-table-model]\n.Table model of the Forensics plugin\nimage::table-model.png[Tabel model]\n\n==== Table column model\n\nThis first thing a table model class defines is a model of the available columns by creating corresponding\n `TableColumn` instances. For each column you need to specify a header label and the name of the bean property that\nshould be shown in the corresponding column (the row elements are actually Java beans: each column will\nshow one distinct property of such a bean, see next section). You can\nuse any of the https://datatables.net/reference/option/columns.type[supported column types] by simply providing a\n`String` or `Integer` based column.\n\n==== Table rows content\n\nAdditionally, a table model class provides the content of the rows. This `getRows()` method\nwill be invoked asynchronously using an Ajax call. Typically, this method simply returns a list of Java Bean instances,\nthat provide the properties of each column (see previous section). These objects will be converted automatically\nto an array of JSON objects, the basic data structure required for the DataTables API.\nYou will find a fully working example table model\nimplementation in the Git repository of the forensics plugin in the class\nhttps://github.com/jenkinsci/forensics-api-plugin/blob/plugin-util/src/main/java/io/jenkins/plugins/forensics/miner/ForensicsTableModel.java[ForensicsTableModel].\n\nIn order to use such a table in your plugin view you need to create the table in the associated\nJelly file using the new `table` tag:\n\n[source,xml]\n.index.jelly\n----\n\u003cj:jelly xmlns:j=\"jelly:core\" xmlns:dt=\"/data-tables\" \u003e\n    [...]\n    \u003cst:adjunct includes=\"io.jenkins.plugins.data-tables\"/\u003e\n\n    \u003cdt:table model=\"${it.getTableModel('id')}\"/\u003e \u003c1\u003e\n    [...]\n\u003c/j:jelly\u003e\n----\n\u003c1\u003e replace `id` with the id of your table\n\nThe only parameter you need to provide for the table is the model -- it is typically part of the corresponding\nJenkins view model class (this object is referenced with `+${it}+` in the view).\nIn order to connect the corresponding Jenkins view model class with the table, the view model class needs to\nimplement the `AsyncTableContentProvider` interface. Or even simpler, let your view model class derive from\n`DefaultAsyncTableContentProvider`. This relationship is required, so that Jenkins can automatically create\nand bind a proxy for the Ajax calls that will automatically fill the table content after the HTML page has been created.\n\nIf we put all those pieces together, we are required to define a model similar to the model of the Forensics plugin,\nthat is shown in \u003c\u003cjenkins-view-model\u003e\u003e.\n\n[#jenkins-view-model]\n.Jenkins reporter design - high level view of the model for reporter plugins\nimage::forensics-view-model.png[Forensics view model]\n\nAs already described in \u003c\u003cjenkins-reporter-model\u003e\u003e the plugin needs to attach a `BuildAction` to each build. The\nForensics plugin attaches a `ForensicBuildAction` to the build. This action stores a `RepositoryStatistics` instance,\nthat contains the repository results for a given build. This action delegates all Stapler requests to a new\nhttps://stapler.kohsuke.org/apidocs/org/kohsuke/stapler/StaplerProxy.html[Stapler proxy instance] so we can keep the\naction clean of user interface code. This `ForensicsViewModel` class then acts as view model that provides the server\nside model for the corresponding Jelly view given by the file `index.jelly`.\n\nWhile this approach looks quite complex at a first view, you will see that the actual implementation part\nis quite small. Most of the boilerplate code is already provided by the base classes and you need to implement\nonly a few methods. Using this concept also provides some additional features, that are part of the DataTables plugin:\n\n- Ordering of columns is persisted automatically in the browser local storage.\n- Paging size is persisted automatically in the browser local storage.\n- The Ajax calls are actually invoked only if a table will become visible. So if you have\nseveral tables hidden in tabs then the content will be loaded on demand only, reducing the amount of data\nto be transferred.\n- There is an option available to provide an additional details row that can be expanded with a + symbol,\nsee https://github.com/jenkinsci/warnings-ng-plugin/blob/master/doc/images/details.png[warnings plugin table] for details.\n\nYou can find several examples of Jenkins views that use jQuery in the\nhttps://github.com/jenkinsci/warnings-ng-plugin[Warnings Next Generation plugin]\nand in the https://github.com/jenkinsci/forensics-api-plugin[Forensics plugin].\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjenkinsci%2Fdata-tables-api-plugin","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjenkinsci%2Fdata-tables-api-plugin","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjenkinsci%2Fdata-tables-api-plugin/lists"}