1+ /*
2+ * Copyright 2018 Philipp Salvisberg <philipp.salvisberg@trivadis.com>
3+ *
4+ * Licensed under the Apache License, Version 2.0 (the "License");
5+ * you may not use this file except in compliance with the License.
6+ * You may obtain a copy of the License at
7+ *
8+ * http://www.apache.org/licenses/LICENSE-2.0
9+ *
10+ * Unless required by applicable law or agreed to in writing, software
11+ * distributed under the License is distributed on an "AS IS" BASIS,
12+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+ * See the License for the specific language governing permissions and
14+ * limitations under the License.
15+ */
16+ package org.utplsql.sqldev
17+
18+ import java.awt.Desktop
19+ import java.io.File
20+ import java.net.URL
21+ import java.nio.charset.StandardCharsets
22+ import java.nio.file.Files
23+ import java.nio.file.Paths
24+ import java.sql.Connection
25+ import java.util.ArrayList
26+ import java.util.List
27+ import java.util.logging.Logger
28+ import oracle.dbtools.raptor.utils.Connections
29+ import org.utplsql.sqldev.dal.UtplsqlDao
30+
31+ class CodeCoverageReporter {
32+ static val Logger logger = Logger . getLogger(CodeCoverageReporter . name);
33+
34+ var Connection conn
35+ var List<String > pathList
36+ var List<String > includeObjectList
37+ var CodeCoverageReporterWindow frame
38+ var String schemas
39+ var String includeObjects
40+ var String excludeObjects
41+
42+ new (List<String > pathList, List<String > includeObjectList, String connectionName) {
43+ this . pathList = pathList
44+ this . includeObjectList = includeObjectList
45+ setConnection(connectionName)
46+ }
47+
48+ new (List<String > pathList, List<String > includeObjectList, Connection conn) {
49+ this . pathList = pathList
50+ this . includeObjectList = includeObjectList
51+ this . conn = conn
52+ }
53+
54+ private def setConnection (String connectionName ) {
55+ if (connectionName == = null ) {
56+ throw new RuntimeException (" Cannot initialize a CodeCoverageReporter without a ConnectionName" )
57+ } else {
58+ // must be closed manually
59+ this . conn = Connections . instance. cloneConnection(Connections . instance. getConnection(connectionName))
60+ }
61+ }
62+
63+ private def toStringList (String s ) {
64+ val list = new ArrayList<String >
65+ if (s !== null && ! s. empty) {
66+ for (item : s. split(" ," )) {
67+ if (! item. empty) {
68+ list. add(item. trim)
69+ }
70+ }
71+ }
72+ return list
73+ }
74+
75+ private def void run () {
76+ try {
77+ logger. fine(' ' ' Running code coverage reporter for «pathList»...' ' ' )
78+ val dal = new UtplsqlDao (conn)
79+ val content = dal. htmlCodeCoverage(pathList, toStringList(schemas), toStringList(includeObjects), toStringList(excludeObjects))
80+ val file = File . createTempFile(" utplsql_" , " html" )
81+ logger. fine(' ' ' Writing result to «file.absolutePath»...' ' ' )
82+ Files . write(Paths . get(file. absolutePath), content. split(System . lineSeparator), StandardCharsets . UTF_8 );
83+ val url = file. toURI(). toURL(). toExternalForm()
84+ logger. fine(' ' ' Opening «url» in browser...' ' ' )
85+ val Desktop desktop = if (Desktop . isDesktopSupported()) {Desktop . getDesktop()} else {null }
86+ if (desktop !== null && desktop. isSupported(Desktop . Action . BROWSE ) && url !== null ) {
87+ desktop. browse((new URL (url)). toURI)
88+ logger. fine(url + " opened in browser." );
89+ } else {
90+ logger. severe(' ' ' Could not launch «file» in browser. No default browser defined on this system.' ' ' )
91+ }
92+ } catch (Exception e) {
93+ logger. severe(' ' ' Error when running code coverage: «e?.message»' ' ' )
94+ }
95+ finally {
96+ conn. close
97+ if (frame !== null ) {
98+ frame. exit
99+ }
100+ }
101+ }
102+
103+ def setFrame (CodeCoverageReporterWindow frame ) {
104+ this . frame = frame;
105+ }
106+
107+ def getFrame () {
108+ return this . frame
109+ }
110+
111+ def getConnection () {
112+ return conn
113+ }
114+
115+ def getPathList () {
116+ return pathList
117+ }
118+
119+ def getIncludeObjectList () {
120+ if (includeObjectList == = null ) {
121+ return new ArrayList<String >
122+ } else {
123+ return includeObjectList
124+ }
125+ }
126+
127+ def setSchemas (String schemas ) {
128+ this . schemas = schemas
129+ }
130+
131+ def setIncludeObjects (String includeObjects ) {
132+ this . includeObjects = includeObjects
133+ }
134+
135+ def setExcludeObjects (String excludeObjects ) {
136+ this . excludeObjects = excludeObjects
137+ }
138+
139+ def runAsync () {
140+ val Runnable runnable = [|run]
141+ val thread = new Thread (runnable)
142+ thread. name = " code coverage reporter"
143+ thread. start
144+ }
145+
146+ def showParameterWindow () {
147+ CodeCoverageReporterWindow . createAndShow(this )
148+ }
149+
150+ }
0 commit comments