summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--.gitignore13
-rw-r--r--LICENSE.txt6
-rw-r--r--dcaeapplib/ChangeLog.md6
-rw-r--r--dcaeapplib/LICENSE.txt17
-rw-r--r--dcaeapplib/README.md64
-rw-r--r--dcaeapplib/dcaeapplib/__init__.py152
-rw-r--r--dcaeapplib/pom.xml241
-rw-r--r--dcaeapplib/setup.py39
-rw-r--r--dcaeapplib/tests/test_dcaeapplib.py112
-rw-r--r--dcaeapplib/tox-local.ini11
-rw-r--r--dcaeapplib/tox.ini13
-rw-r--r--eelf-logger/cpd-exclude.properties21
-rw-r--r--eelf-logger/eelf-logger-api/pom.xml48
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/AppLogInfo.java101
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/CodeLogInfo.java55
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/CustomFieldsLogInfo.java62
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/ErrorLogInfo.java76
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/LogInfo.java30
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/LogLevelCategory.java36
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/MessageLogInfo.java62
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/MiscLogInfo.java45
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/NagiosAlertLevel.java52
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/RequestIdLogInfo.java44
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/RequestStatusCode.java32
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/RequestTimingLogInfo.java64
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/ResponseLogInfo.java81
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/ServiceLogInfo.java61
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/TargetServiceLogInfo.java54
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/package-info.java28
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/AuditLog.java130
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/DebugLog.java76
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/EELFLogFactory.java85
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/EELFLogger.java67
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/EELFLoggerContext.java56
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/ErrorLog.java93
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/MetricLog.java130
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/package-info.java23
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpAuditLog.java90
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpDebugLog.java56
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpEELFLogger.java77
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpErrorLog.java68
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpMetricLog.java89
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/package-info.java26
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/AppLogSpec.java32
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/AuditLogSpec.java42
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/DebugLogSpec.java34
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/ErrorLogSpec.java42
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/MetricLogSpec.java36
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/OptionalLogSpec.java39
-rw-r--r--eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/package-info.java28
-rw-r--r--eelf-logger/eelf-logger-logback-impl/pom.xml62
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/EELFLoggerDefaults.java105
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/filter/MarkerFilter.java71
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/AuditLogLayout.java81
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/ConsoleLayout.java56
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/DebugLogLayout.java54
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/ErrorLogLayout.java64
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/MetricLogLayout.java83
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/listener/LogbackStartupListener.java128
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/AuditLogImpl.java119
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/DebugLogImpl.java88
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/EELFLoggerContextImpl.java57
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/EELFLoggerImpl.java81
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/ErrorLogImpl.java98
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/MetricLogImpl.java120
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/CompositePropertyResolver.java53
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/EnvironmentPropertyResolver.java46
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/PropertyResolver.java41
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/SystemPropertyResolver.java59
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/utils/LogUtils.java590
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/resources/META-INF/services/org.onap.dcae.utils.eelf.logger.api.log.EELFLogger20
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-async-appenders.xml55
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-defaults.xml51
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-logback.xml45
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-optional-appenders.xml68
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-required-appenders.xml112
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/BaseLogbackUnitTest.java157
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/AuditLogImplTest.java66
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/DebugLogImplTest.java53
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/ErrorLogImplTest.java61
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/MetricLogImplTest.java67
-rw-r--r--eelf-logger/eelf-logger-logback-impl/src/test/resources/logback.xml41
-rw-r--r--eelf-logger/eelf-logger-model/pom.xml77
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/AppLogInfoImpl.java53
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/CodeLogInfoImpl.java48
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/CustomFieldsLogInfoImpl.java51
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/ErrorLogInfoImpl.java47
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/MessageLogInfoImpl.java54
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/MiscLogInfoImpl.java47
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/RequestIdLogInfoImpl.java45
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/RequestTimingLogInfoImpl.java51
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/ResponseLogInfoImpl.java47
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/ServiceLogInfoImpl.java49
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/TargetServiceLogInfoImpl.java48
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/package-info.java23
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/AppLogSpecImpl.java47
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/AuditLogSpecImpl.java61
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/DebugLogSpecImpl.java48
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/ErrorLogSpecImpl.java61
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/MetricLogSpecImpl.java64
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/OptionalLogSpecImpl.java60
-rw-r--r--eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/package-info.java23
-rw-r--r--eelf-logger/findbugs-exclude.xml30
-rw-r--r--eelf-logger/pmd-exclude.properties22
-rw-r--r--eelf-logger/pom.xml476
-rw-r--r--eelf-logger/version.properties25
-rwxr-xr-xmvn-phase-script.sh20
-rw-r--r--onap-dcae-cbs-docker-client/.coveragerc5
-rw-r--r--onap-dcae-cbs-docker-client/.gitignore1
-rw-r--r--onap-dcae-cbs-docker-client/Changelog.md16
-rw-r--r--onap-dcae-cbs-docker-client/README.md7
-rw-r--r--onap-dcae-cbs-docker-client/onap_dcae_cbs_docker_client/__init__.py4
-rw-r--r--onap-dcae-cbs-docker-client/onap_dcae_cbs_docker_client/client.py97
-rw-r--r--onap-dcae-cbs-docker-client/pom.xml10
-rw-r--r--onap-dcae-cbs-docker-client/requirements.txt1
-rw-r--r--onap-dcae-cbs-docker-client/setup.py27
-rw-r--r--onap-dcae-cbs-docker-client/tests/test_client.py67
-rw-r--r--onap-dcae-cbs-docker-client/tox-local.ini12
-rw-r--r--onap-dcae-cbs-docker-client/tox.ini17
-rw-r--r--onap-dcae-dcaepolicy-lib/.coveragerc4
-rw-r--r--onap-dcae-dcaepolicy-lib/LICENSE.txt4
-rw-r--r--onap-dcae-dcaepolicy-lib/README.md93
-rw-r--r--onap-dcae-dcaepolicy-lib/onap_dcae_dcaepolicy_lib/__init__.py9
-rw-r--r--onap-dcae-dcaepolicy-lib/onap_dcae_dcaepolicy_lib/dcae_policy.py420
-rw-r--r--onap-dcae-dcaepolicy-lib/onap_dcae_dcaepolicy_lib/policies_output.py148
-rw-r--r--onap-dcae-dcaepolicy-lib/pom.xml7
-rw-r--r--onap-dcae-dcaepolicy-lib/setup.py10
-rw-r--r--onap-dcae-dcaepolicy-lib/tests/__init__.py19
-rw-r--r--onap-dcae-dcaepolicy-lib/tests/log_ctx.py15
-rw-r--r--onap-dcae-dcaepolicy-lib/tests/mock_cloudify_ctx.py7
-rw-r--r--onap-dcae-dcaepolicy-lib/tests/test_dcae_policy.py1270
-rw-r--r--onap-dcae-dcaepolicy-lib/tox-local.ini3
-rw-r--r--onap-dcae-dcaepolicy-lib/tox.ini9
-rw-r--r--pom.xml20
-rw-r--r--python-discovery-client/pom.xml2
-rw-r--r--python-discovery-client/setup.py2
-rw-r--r--python-discovery-client/tox.ini6
-rw-r--r--python-dockering/pom.xml2
-rw-r--r--python-dockering/tox.ini6
-rw-r--r--scripts/mvn-phase-lib.sh201
-rw-r--r--scripts/pom.xml2
141 files changed, 9362 insertions, 535 deletions
diff --git a/.gitignore b/.gitignore
index 3b3b613..59bb4de 100644
--- a/.gitignore
+++ b/.gitignore
@@ -68,3 +68,16 @@ docs/_build/
target/
logs/
+
+
+# Intellij Files & Dir #
+*.iml
+*.ipr
+*.iws
+*.uml
+
+atlassian-ide-plugin.xml
+out/
+.DS_Store
+./lib/
+.idea
diff --git a/LICENSE.txt b/LICENSE.txt
index 69d5fc1..9536f0b 100644
--- a/LICENSE.txt
+++ b/LICENSE.txt
@@ -1,11 +1,11 @@
/*
* ============LICENSE_START==========================================
* ===================================================================
-* Copyright © 2017 AT&T Intellectual Property. All rights reserved.
+* Copyright (c) 2017 AT&T Intellectual Property. All rights reserved.
* ===================================================================
*
* Unless otherwise specified, all software contained herein is licensed
-* under the Apache License, Version 2.0 (the “License”);
+* under the Apache License, Version 2.0 (the "License");
* you may not use this software except in compliance with the License.
* You may obtain a copy of the License at
*
@@ -20,7 +20,7 @@
*
*
* Unless otherwise specified, all documentation contained herein is licensed
-* under the Creative Commons License, Attribution 4.0 Intl. (the “License”);
+* under the Creative Commons License, Attribution 4.0 Intl. (the "License");
* you may not use this documentation except in compliance with the License.
* You may obtain a copy of the License at
*
diff --git a/dcaeapplib/ChangeLog.md b/dcaeapplib/ChangeLog.md
new file mode 100644
index 0000000..0942537
--- /dev/null
+++ b/dcaeapplib/ChangeLog.md
@@ -0,0 +1,6 @@
+# Change Log
+
+All notable changes to this project will be documented in this file.
+
+The format is based on [Keep a Changelog](http://keepachangelog.com/)
+and this project adheres to [Semantic Versioning](http://semver.org/).
diff --git a/dcaeapplib/LICENSE.txt b/dcaeapplib/LICENSE.txt
new file mode 100644
index 0000000..8bdab89
--- /dev/null
+++ b/dcaeapplib/LICENSE.txt
@@ -0,0 +1,17 @@
+============LICENSE_START=======================================================
+Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+================================================================================
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+============LICENSE_END=========================================================
+
+ECOMP is a trademark and service mark of AT&T Intellectual Property.
diff --git a/dcaeapplib/README.md b/dcaeapplib/README.md
new file mode 100644
index 0000000..81fd825
--- /dev/null
+++ b/dcaeapplib/README.md
@@ -0,0 +1,64 @@
+# dcaeapplib
+
+Library for building DCAE analytics applications
+
+# Example use:
+
+```
+
+class myapp:
+ def __init__(self):
+ # get the environment, and register callbacks for health checks and
+ # configuration changes
+ self.dcaeenv = dcaeapplib.DcaeEnv(healthCB=self.isHealthy, reconfigCB=self.reconfigure)
+ # simulate a configuration change - we want the initial configuration
+ self.reconfigure()
+ # start the environment (to wait for health checks and config changes)
+ self.dcaeenv.start()
+ # begin processing loop
+ while True:
+ if self.configchanged:
+ # fetch the updated configuration
+ self.conig = self.dcaeenv.getconfig()
+ self.configchanged = False
+ # do any setup relevant to the configuration
+ data = self.dcaeenv.getdata('myinputstream')
+ # Data is a UTF-8 string, 'myinputstream' is this application's logical
+ # name for this (one of potentially several) data sources.
+ # Can also specify timeout_ms and limit as arguments.
+ # timeout_ms (default 15,000) is the maximum time getdata() will block
+ # limit is the maximum number of records retrieved at a time.
+ # If no data is retrieved (timeout) the return will be None.
+ if data is not None:
+ # do something to process the data
+ self.dcaeenv.senddata('myoutputstream', 'somepartitionkey', data)
+ # data is a string, 'myoutputstream' is the application's logical
+ # name for this (one of potentially several) data sinks.
+ # somepartitionkey is used, by Kafka, to assign the data to a partition.
+
+ def isHealthy(self):
+ # return the health of the application (True/False)
+ return True
+
+ def reconfigure(self):
+ # Do whatever needs to be done to handle a configuration change
+ self.configchanged = True
+```
+
+# Environment Variables
+
+This library uses the onap-dcae-cbs-docker-client library to fetch
+configuration. That library relies on the HOSTNAME and CONSUL_HOST
+environment variables to find the configuration.
+
+This library provides an HTTP interface for health checks. By default this
+listens on port 80 but can be overridden to use another port by setting the
+DCAEPORT environment variable. The HTTP interface supports getting 2 URLs:
+/healthcheck, which will return a status of 202 (Accepted) for healthy,
+and 503 (Service Unavailable) for unhealthy, and /reconfigure, which triggers
+the library to check for updated configuration.
+
+# Console Commands
+
+This library provides a single console command "reconfigure.sh" which
+performs an HTTP get of the /reconfigure URL
diff --git a/dcaeapplib/dcaeapplib/__init__.py b/dcaeapplib/dcaeapplib/__init__.py
new file mode 100644
index 0000000..18b60fe
--- /dev/null
+++ b/dcaeapplib/dcaeapplib/__init__.py
@@ -0,0 +1,152 @@
+# org.onap.dcae
+# ============LICENSE_START====================================================
+# Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+# =============================================================================
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+# ============LICENSE_END======================================================
+#
+# ECOMP is a trademark and service mark of AT&T Intellectual Property.
+
+import base64
+import json
+import os
+import requests
+from threading import Thread
+import uuid
+from onap_dcae_cbs_docker_client.client import get_config
+
+try:
+ from http.server import BaseHTTPRequestHandler, HTTPServer
+except ImportError:
+ from BaseHTTPServer import BaseHTTPRequestHandler, HTTPServer
+
+_httpport = int(os.environ['DCAEPORT']) if 'DCAEPORT' in os.environ else 80
+_clientid = uuid.uuid4().hex
+_groupid = uuid.uuid4().hex
+
+class _handler(BaseHTTPRequestHandler):
+ def do_GET(self):
+ if '/healthcheck' == self.path:
+ if self.server.env._health():
+ self.send_response(202)
+ self.end_headers()
+ else:
+ self.send_error(503)
+ elif '/reconfigure' == self.path:
+ self.server.env._loadconfig()
+ self.server.env._reconf()
+ self.send_response(202)
+ self.end_headers()
+ else:
+ self.send_error(404)
+
+def _genauth(sinfo):
+ """
+ Return authentication parameters for stream, if present.
+ """
+ user = sinfo['aaf_username'] if 'aaf_username' in sinfo else None
+ password = sinfo['aaf_password'] if 'aaf_password' in sinfo else None
+ if user and password:
+ return { 'auth': (user, password) }
+ else:
+ return {}
+
+class DcaeEnv:
+ def __init__(self, healthCB = lambda:True, reconfigCB = lambda:None):
+ """
+ Initialize environment, but don't start web server or invoke any callbacks.
+ """
+ self._health = healthCB
+ self._reconf = reconfigCB
+ self._unread = {}
+ self._server = None
+ self._loadconfig()
+
+ def start(self):
+ """
+ Start web server to receive health checks and reconfigure requests
+ """
+ if self._server is not None:
+ return
+ self._server = HTTPServer(('', _httpport), _handler)
+ self._server.env = self
+ th = Thread(target=self._server.serve_forever, name='webserver')
+ th.daemon = True
+ th.start()
+
+ def stop(self):
+ """
+ Stop web server
+ """
+ if self._server is None:
+ return
+ self._server.shutdown()
+ self._server.env = None
+ self._server = None
+
+ def _loadconfig(self):
+ self._config = get_config()
+
+ def hasdata(self, stream):
+ """
+ Return whether there is any unprocessed received data for the specified
+ data stream. That is, if an earlier getdata() call returned more than
+ one record, and the additional records have not yet been retrieved.
+ """
+ return stream in self._unread
+
+ def getdata(self, stream, timeout_ms = 15000, limit = 10):
+ """
+ Try to retrieve data from Message Router for the specified data stream.
+ If no data is retrieved, within the specified timeout, return None.
+ """
+ sinfo = self._config['streams_subscribes'][stream]
+ if stream in self._unread:
+ x = self._unread[stream]
+ ret = x.pop()
+ if len(x) == 0:
+ del self._unread[stream]
+ return ret
+ gid = sinfo['client_id'] if 'client_id' in sinfo and sinfo['client_id'] else _groupid
+ resp = requests.get('{0}/{1}/{2}?timeout={3}&limit={4}'.format(sinfo['dmaap_info']['topic_url'], gid, _clientid, timeout_ms, limit), **_genauth(sinfo))
+ resp.raise_for_status()
+ x = resp.json()
+ if len(x) == 0:
+ return None
+ if len(x) == 1:
+ return x[0]
+ x.reverse()
+ ret = x.pop()
+ self._unread[stream] = x
+ return ret
+
+ def senddata(self, stream, partition, data):
+ """
+ Publish data to the specified stream.
+ """
+ sinfo = self._config['streams_publishes'][stream]
+ body = '{0}.{1}.{2}{3}'.format(len(partition), len(data), partition, data)
+ resp = requests.post('{0}'.format(sinfo['dmaap_info']['topic_url']), headers={'Content-Type': 'application/cambria'}, data=body, **_genauth(sinfo))
+ resp.raise_for_status()
+
+ def getconfig(self):
+ """
+ Get the latest version of the configuration data.
+ """
+ return self._config
+
+def reconfigure():
+ """
+ Make the web request to reconfigure (locally)
+ """
+ requests.get('http://localhost:{0}/reconfigure'.format(_httpport))
diff --git a/dcaeapplib/pom.xml b/dcaeapplib/pom.xml
new file mode 100644
index 0000000..66e73da
--- /dev/null
+++ b/dcaeapplib/pom.xml
@@ -0,0 +1,241 @@
+<?xml version="1.0"?>
+<!--
+================================================================================
+Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+================================================================================
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+============LICENSE_END=========================================================
+
+ECOMP is a trademark and service mark of AT&T Intellectual Property.
+-->
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+ <modelVersion>4.0.0</modelVersion>
+ <parent>
+ <groupId>org.onap.dcaegen2.utils</groupId>
+ <artifactId>utils</artifactId>
+ <version>1.2.0-SNAPSHOT</version>
+ </parent>
+ <groupId>org.onap.dcaegen2.utils</groupId>
+ <artifactId>dcaeapplib</artifactId>
+ <name>dcaeapplib</name>
+ <version>0.0.3-SNAPSHOT</version>
+ <url>http://maven.apache.org</url>
+
+ <properties>
+ <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
+
+ <sonar.sources>.</sonar.sources>
+ <sonar.junit.reportsPath>xunit-results.xml</sonar.junit.reportsPath>
+ <sonar.python.coverage.reportPath>coverage.xml</sonar.python.coverage.reportPath>
+ <sonar.language>py</sonar.language>
+ <sonar.pluginName>Python</sonar.pluginName>
+ <sonar.inclusions>**/*.py</sonar.inclusions>
+ <sonar.exclusions>tests/*,setup.py</sonar.exclusions>
+ </properties>
+ <build>
+ <finalName>${project.artifactId}-${project.version}</finalName>
+ <pluginManagement>
+ <plugins>
+ <!-- the following plugins are invoked from oparent, we do not need them -->
+ <plugin>
+ <groupId>org.sonatype.plugins</groupId>
+ <artifactId>nexus-staging-maven-plugin</artifactId>
+ <version>1.6.7</version>
+ <configuration>
+ <skipNexusStagingDeployMojo>true</skipNexusStagingDeployMojo>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-deploy-plugin</artifactId>
+ <!-- This version supports the "deployAtEnd" parameter -->
+ <version>2.8</version>
+ <configuration>
+ <skip>true</skip>
+ </configuration>
+ </plugin>
+ <!-- first disable the default Java plugins at various stages -->
+ <!-- maven-resources-plugin is called during "*resource" phases by default behavior. it prepares
+ the resources dir. we do not need it -->
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-resources-plugin</artifactId>
+ <version>2.6</version>
+ <configuration>
+ <skip>true</skip>
+ </configuration>
+ </plugin>
+ <!-- maven-compiler-plugin is called during "compile" phases by default behavior. we do not need it -->
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-compiler-plugin</artifactId>
+ <version>3.1</version>
+ <configuration>
+ <skip>true</skip>
+ </configuration>
+ </plugin>
+ <!-- maven-jar-plugin is called during "compile" phase by default behavior. we do not need it -->
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-jar-plugin</artifactId>
+ <version>2.4</version>
+ <executions>
+ <execution>
+ <id>default-jar</id>
+ <phase/>
+ </execution>
+ </executions>
+ </plugin>
+ <!-- maven-install-plugin is called during "install" phase by default behavior. it tries to copy stuff under
+ target dir to ~/.m2. we do not need it -->
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-install-plugin</artifactId>
+ <version>2.4</version>
+ <configuration>
+ <skip>true</skip>
+ </configuration>
+ </plugin>
+ <!-- maven-surefire-plugin is called during "test" phase by default behavior. it triggers junit test.
+ we do not need it -->
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-surefire-plugin</artifactId>
+ <version>2.12.4</version>
+ <configuration>
+ <skipTests>true</skipTests>
+ </configuration>
+ </plugin>
+ </plugins>
+ </pluginManagement>
+ <plugins>
+ <!-- plugin>
+ <artifactId>maven-assembly-plugin</artifactId>
+ <version>2.4.1</version>
+ <configuration>
+ <descriptors>
+ <descriptor>assembly/dep.xml</descriptor>
+ </descriptors>
+ </configuration>
+ <executions>
+ <execution>
+ <id>make-assembly</id>
+ <phase>package</phase>
+ <goals>
+ <goal>single</goal>
+ </goals>
+ </execution>
+ </executions>
+ </plugin -->
+ <!-- now we configure custom action (calling a script) at various lifecycle phases -->
+ <plugin>
+ <groupId>org.codehaus.mojo</groupId>
+ <artifactId>exec-maven-plugin</artifactId>
+ <version>1.2.1</version>
+ <executions>
+ <execution>
+ <id>clean phase script</id>
+ <phase>clean</phase>
+ <goals>
+ <goal>exec</goal>
+ </goals>
+ <configuration>
+ <arguments>
+ <argument>${project.artifactId}</argument>
+ <argument>clean</argument>
+ </arguments>
+ </configuration>
+ </execution>
+ <execution>
+ <id>generate-sources script</id>
+ <phase>generate-sources</phase>
+ <goals>
+ <goal>exec</goal>
+ </goals>
+ <configuration>
+ <arguments>
+ <argument>${project.artifactId}</argument>
+ <argument>generate-sources</argument>
+ </arguments>
+ </configuration>
+ </execution>
+ <execution>
+ <id>compile script</id>
+ <phase>compile</phase>
+ <goals>
+ <goal>exec</goal>
+ </goals>
+ <configuration>
+ <arguments>
+ <argument>${project.artifactId}</argument>
+ <argument>compile</argument>
+ </arguments>
+ </configuration>
+ </execution>
+ <execution>
+ <id>package script</id>
+ <phase>package</phase>
+ <goals>
+ <goal>exec</goal>
+ </goals>
+ <configuration>
+ <arguments>
+ <argument>${project.artifactId}</argument>
+ <argument>package</argument>
+ </arguments>
+ </configuration>
+ </execution>
+ <execution>
+ <id>test script</id>
+ <phase>test</phase>
+ <goals>
+ <goal>exec</goal>
+ </goals>
+ <configuration>
+ <arguments>
+ <argument>${project.artifactId}</argument>
+ <argument>test</argument>
+ </arguments>
+ </configuration>
+ </execution>
+ <execution>
+ <id>install script</id>
+ <phase>install</phase>
+ <goals>
+ <goal>exec</goal>
+ </goals>
+ <configuration>
+ <arguments>
+ <argument>${project.artifactId}</argument>
+ <argument>install</argument>
+ </arguments>
+ </configuration>
+ </execution>
+ <execution>
+ <id>deploy script</id>
+ <phase>deploy</phase>
+ <goals>
+ <goal>exec</goal>
+ </goals>
+ <configuration>
+ <arguments>
+ <argument>${project.artifactId}</argument>
+ <argument>deploy</argument>
+ </arguments>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+ </plugins>
+ </build>
+</project>
diff --git a/dcaeapplib/setup.py b/dcaeapplib/setup.py
new file mode 100644
index 0000000..b985be9
--- /dev/null
+++ b/dcaeapplib/setup.py
@@ -0,0 +1,39 @@
+# org.onap.dcae
+# ============LICENSE_START====================================================
+# Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+# =============================================================================
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+# ============LICENSE_END======================================================
+#
+# ECOMP is a trademark and service mark of AT&T Intellectual Property.
+
+from setuptools import setup, find_packages
+
+setup(
+ name='dcaeapplib',
+ version='0.0.5',
+ packages=find_packages(),
+ author = 'Andrew Gauld',
+ author_email = 'ag1282@att.com',
+ description = ('Library for building DCAE analytics applications'),
+ license = 'Apache 2.0',
+ keywords = '',
+ url = '',
+ zip_safe = True,
+ install_requires=[ 'onap-dcae-cbs-docker-client>=0.0.5' ],
+ entry_points = {
+ 'console_scripts': [
+ 'reconfigure.sh=dcaeapplib:reconfigure'
+ ]
+ }
+)
diff --git a/dcaeapplib/tests/test_dcaeapplib.py b/dcaeapplib/tests/test_dcaeapplib.py
new file mode 100644
index 0000000..9995264
--- /dev/null
+++ b/dcaeapplib/tests/test_dcaeapplib.py
@@ -0,0 +1,112 @@
+# org.onap.dcae
+# ============LICENSE_START====================================================
+# Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+# =============================================================================
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+# ============LICENSE_END======================================================
+#
+# ECOMP is a trademark and service mark of AT&T Intellectual Property.
+
+import dcaeapplib
+import requests
+import json
+
+class Stubs:
+ def __init__(self):
+ self.toreturn = [ 's1', 's2', 's3' ]
+ self.config = {
+ "anotherparameter": 1,
+ "streams_subscribes": {
+ "myinputstream": {
+ "aaf_username": "user1",
+ "aaf_password": "pass1",
+ "dmaap_info": {
+ "topic_url": "http://messagerouter.example.com:3904/events/topic1"
+ }
+ }
+ },
+ "streams_publishes": {
+ "myoutputstream": {
+ "aaf_username": None,
+ "aaf_password": None,
+ "dmaap_info": {
+ "topic_url": "http://messagerouter.example.com:3904/events/topic2"
+ }
+ }
+ }
+ }
+ self.health = True
+ self.cc = False
+
+ def raise_for_status(self):
+ pass
+
+ def json(self):
+ return self.toreturn
+
+def test_todo(monkeypatch):
+ stuff = Stubs()
+ def stub_config():
+ return json.loads(json.dumps(stuff.config))
+ def stub_hc():
+ return stuff.health
+ def stub_cc():
+ stuff.cc = True
+ monkeypatch.setattr(dcaeapplib, 'get_config', stub_config)
+ monkeypatch.setattr(dcaeapplib, '_httpport', 0)
+ env = dcaeapplib.DcaeEnv(healthCB=stub_hc, reconfigCB=stub_cc)
+ env.stop() # exercise stop when not running
+ env.start()
+ print('Port is {0}'.format(env._server.server_port))
+ monkeypatch.setattr(dcaeapplib, '_httpport', env._server.server_port)
+ stuff.config['anotherparameter'] = 2
+ assert env.getconfig()['anotherparameter'] == 1
+ dcaeapplib.reconfigure()
+ assert stuff.cc is True
+ assert env.getconfig()['anotherparameter'] == 2
+ resp = requests.get('http://localhost:{0}/healthcheck'.format(dcaeapplib._httpport))
+ assert resp.status_code < 300
+ stuff.health = False
+ resp = requests.get('http://localhost:{0}/healthcheck'.format(dcaeapplib._httpport))
+ assert resp.status_code >= 500
+ resp = requests.get('http://localhost:{0}/invalid'.format(dcaeapplib._httpport))
+ assert resp.status_code == 404
+ env.start() # exercise start when already running
+ env.stop()
+ def stub_get(*args, **kwargs):
+ stuff.auth = 'auth' in kwargs
+ return stuff
+ def stub_post(url, data, *args, **kwargs):
+ assert data == '4.11.asdfhello world'
+ stuff.auth = 'auth' in kwargs
+ stuff.posted = True
+ return stuff
+ monkeypatch.setattr(requests, 'post', stub_post)
+ stuff.posted = False
+ stuff.auth = True
+ env.senddata('myoutputstream', 'asdf', 'hello world')
+ assert stuff.posted == True
+ assert stuff.auth == False
+ monkeypatch.setattr(requests, 'get', stub_get)
+ assert env.hasdata('myinputstream') is False
+ assert env.getdata('myinputstream') == 's1'
+ assert stuff.auth == True
+ stuff.toreturn = [ 'a1' ]
+ assert env.getdata('myinputstream') == 's2'
+ assert env.hasdata('myinputstream') is True
+ assert env.getdata('myinputstream') == 's3'
+ assert env.hasdata('myinputstream') is False
+ assert env.getdata('myinputstream') == 'a1'
+ stuff.toreturn = []
+ assert env.hasdata('myinputstream') is False
+ assert env.getdata('myinputstream') is None
diff --git a/dcaeapplib/tox-local.ini b/dcaeapplib/tox-local.ini
new file mode 100644
index 0000000..935a5d6
--- /dev/null
+++ b/dcaeapplib/tox-local.ini
@@ -0,0 +1,11 @@
+[tox]
+envlist = py27
+[testenv]
+deps=
+ onap-dcae-cbs-docker-client>=0.0.2
+ pytest
+ coverage
+ pytest-cov
+setenv =
+ PYTHONPATH={toxinidir}
+commands=pytest --cov dcaeapplib --cov-report html
diff --git a/dcaeapplib/tox.ini b/dcaeapplib/tox.ini
new file mode 100644
index 0000000..653ac3f
--- /dev/null
+++ b/dcaeapplib/tox.ini
@@ -0,0 +1,13 @@
+[tox]
+envlist = py27,py35
+[testenv]
+deps=
+ onap-dcae-cbs-docker-client>=0.0.5
+ pytest
+ coverage
+ pytest-cov
+setenv =
+ PYTHONPATH={toxinidir}
+commands=
+ pytest --junitxml xunit-results.xml --cov dcaeapplib --cov-report xml
+ coverage xml
diff --git a/eelf-logger/cpd-exclude.properties b/eelf-logger/cpd-exclude.properties
new file mode 100644
index 0000000..399fb30
--- /dev/null
+++ b/eelf-logger/cpd-exclude.properties
@@ -0,0 +1,21 @@
+#
+# ================================================================================
+# Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+# ================================================================================
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+# ============LICENSE_END=========================================================
+#
+#
+
+# Ignored as there are different log specs
+org.onap.dcae.utils.eelf.logger.model.spec.AuditLogSpecImpl,org.onap.dcae.utils.eelf.logger.model.spec.MetricLogSpecImpl
diff --git a/eelf-logger/eelf-logger-api/pom.xml b/eelf-logger/eelf-logger-api/pom.xml
new file mode 100644
index 0000000..1d7fa1b
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/pom.xml
@@ -0,0 +1,48 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ ~ ================================================================================
+ ~ Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ ~ ================================================================================
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License.
+ ~ ============LICENSE_END=========================================================
+ ~
+ -->
+
+<project xmlns="http://maven.apache.org/POM/4.0.0"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+
+ <modelVersion>4.0.0</modelVersion>
+
+ <parent>
+ <groupId>org.onap.dcaegen2.utils</groupId>
+ <artifactId>eelf-logger</artifactId>
+ <version>1.0.0-SNAPSHOT</version>
+ </parent>
+
+ <artifactId>eelf-logger-api</artifactId>
+ <packaging>jar</packaging>
+
+ <!-- EELF LOGGING API CONTAINS VARIOUS INTERFACES REQUIRED TO SUPPORT SUPPORT EELF LOGGING SPECIFICATIONS -->
+ <name>dcaegen2-utils-eelf-logger-api</name>
+ <description>API contracts for EELF Logging Framework</description>
+
+ <properties>
+ <main.basedir>${project.parent.basedir}</main.basedir>
+ <!-- SONAR SETTINGS : EXCLUDE TEST COVERAGE AS API ONLY CONTAINS INTERFACES AND NO BUSINESS LOGIC-->
+ <sonar.coverage.exclusions>**/api/**</sonar.coverage.exclusions>
+ </properties>
+
+ <!-- NOTE: THIS API MODULE MUST NOT HAVE ANY DEPENDENCIES IN COMPILE SCOPE-->
+
+</project>
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/AppLogInfo.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/AppLogInfo.java
new file mode 100644
index 0000000..bdce8d1
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/AppLogInfo.java
@@ -0,0 +1,101 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+/**
+ * Captures information about application which is doing the logging. All app log fields must remain same for
+ * the whole duration of the application once its instance is created.
+ *
+ * @author Rajiv Singla
+ */
+public interface AppLogInfo extends LogInfo {
+
+ /**
+ * Required field contains UUID which identifies this service instance inside an inventory management system
+ * (e.g. A&AI) to reference/manage this service as a unit
+ *
+ * @return remote VM Name or service the request is acting upon.
+ */
+ String getServiceInstanceID();
+
+ /**
+ * Required field contains a universally unique identifier used to differentiate between multiple instances of
+ * the same (named), log writing service/application. Its value is set at instance creation time (and read by it,
+ * e.g. at start/initialization time from the environment). This value should be picked up by the component
+ * instance from its configuration file and subsequently used to enable differentiating log records created by
+ * multiple, locally load balanced EELF component or sub component instances that are otherwise identically
+ * configured.
+ *
+ * @return instance UUID
+ */
+ String getInstanceUUID();
+
+ /**
+ * Optional field contains VM Name where app is deployed.
+ * DCAE sub components should populate this field but it can be empty if
+ * determined that its value can be added by the log files collecting agent itself (e.g. Splunk).
+ * <p>
+ * <b> Example: host.vm.name.com</b>
+ * </p>
+ *
+ * @return virtual server name
+ */
+ String getVirtualServerName();
+
+ /**
+ * Optional field contains the logging component host server’s IP address.
+ * <p>
+ * <b>Example: 127.0.0.100</b>
+ * </p>
+ *
+ * @return server ip address
+ */
+ String getServerIPAddress();
+
+ /**
+ * Required field for VM's fully qualified domain name or hosting machine fully qualified domain name.
+ * <p>
+ * <b> Example: host.fqdn.com</b>
+ * </p>
+ *
+ * @return server host fully qualified domain name
+ */
+ String getServerFQDN();
+
+
+ /**
+ * Contains default values for {@link AppLogInfo}
+ */
+ interface Defaults {
+
+ String DEFAULT_SERVICE_INSTANCE_ID = "UNKNOWN_INSTANCE_ID";
+
+ String DEFAULT_INSTANCE_UUID = "";
+
+ String DEFAULT_VIRTUAL_SERVER_NAME = "";
+
+ String DEFAULT_SERVER_IP_ADDRESS = "UNKNOWN_IP_ADDRESS";
+
+ String DEFAULT_SERVER_FQDN = "UNKNOWN_SERVER_FQDN";
+
+ }
+
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/CodeLogInfo.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/CodeLogInfo.java
new file mode 100644
index 0000000..bea195d
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/CodeLogInfo.java
@@ -0,0 +1,55 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+/**
+ * Capture field required to log details about code which is generating the log message.
+ * <p>
+ * <b>NOTE: When using a logging framework(e.g. logback) implementation these fields may be automatically deduced - so
+ * settings these fields is not required by the application and even if application sets these fields the logging
+ * framework may ignore it
+ * </b>
+ * </p>
+ *
+ * @author Rajiv Singla
+ */
+public interface CodeLogInfo extends LogInfo {
+
+
+ /**
+ * Optional field used if wanting to trace processing of a request over a number of sub-components of a single EELF
+ * component. It should be preceded by a log record that establishes its chaining back to the corresponding
+ * requestID.
+ *
+ * @return thread ID used to trace processing of request over number of sub-components of single EELF Component.
+ */
+ String getThreadId();
+
+
+ /**
+ * Optional field: If available for OO programing languages that support this concept. This is the name of the
+ * class that has caused the log record to be created.
+ *
+ * @return name of the class that has the caused the log record to be created
+ */
+ String getClassName();
+
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/CustomFieldsLogInfo.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/CustomFieldsLogInfo.java
new file mode 100644
index 0000000..634afa6
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/CustomFieldsLogInfo.java
@@ -0,0 +1,62 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+/**
+ * Captures fields required to log Custom fields
+ *
+ * @author Rajiv Singla
+ */
+public interface CustomFieldsLogInfo extends LogInfo {
+
+ /**
+ * Optional field that can be used by developers to include additional application-specific
+ * information to support operations and troubleshooting of the system.
+ *
+ * @return additional application-specific information to support operations and troubleshooting of the system.
+ */
+ String getCustomField1();
+
+ /**
+ * Optional field that can be used by developers to include additional application-specific
+ * information to support operations and troubleshooting of the system.
+ *
+ * @return additional application-specific information to support operations and troubleshooting of the system.
+ */
+ String getCustomField2();
+
+ /**
+ * Optional field that can be used by developers to include additional application-specific
+ * information to support operations and troubleshooting of the system.
+ *
+ * @return additional application-specific information to support operations and troubleshooting of the system.
+ */
+ String getCustomField3();
+
+ /**
+ * Optional field that can be used by developers to include additional application-specific
+ * information to support operations and troubleshooting of the system.
+ *
+ * @return additional application-specific information to support operations and troubleshooting of the system.
+ */
+ String getCustomField4();
+
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/ErrorLogInfo.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/ErrorLogInfo.java
new file mode 100644
index 0000000..876037c
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/ErrorLogInfo.java
@@ -0,0 +1,76 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+/**
+ * Captures fields required to log error related information
+ *
+ * @author Rajiv Singla
+ */
+public interface ErrorLogInfo extends LogInfo {
+
+
+ /**
+ * Required field contains an error code representing the error condition. The codes can be chose by
+ * the logging application but they should adhere to the guidelines embodied in the table below:
+ * <table summary="Error Codes" cellspacing=0 border=1>
+ * <tr>
+ * <td style=min-width:50px>Error type</td>
+ * <td style=min-width:50px>Notes</td>
+ * </tr>
+ * <tr>
+ * <td style=min-width:50px>100</td>
+ * <td style=min-width:50px>Permission errors</td>
+ * </tr>
+ * <tr>
+ * <td style=min-width:50px>200</td>
+ * <td style=min-width:50px>Availability errors/Timeouts</td>
+ * </tr>
+ * <tr>
+ * <td style=min-width:50px>300</td>
+ * <td style=min-width:50px>Data errors</td>
+ * </tr>
+ * <tr>
+ * <td style=min-width:50px>400</td>
+ * <td style=min-width:50px>Schema errors</td>
+ * </tr>
+ * <tr>
+ * <td style=min-width:50px>500</td>
+ * <td style=min-width:50px>Business process errors</td>
+ * </tr>
+ * <tr>
+ * <td style=min-width:50px>900</td>
+ * <td style=min-width:50px>Unknown Errors</td>
+ * </tr>
+ * </table>
+ *
+ * @return error Code
+ */
+ Integer getErrorCode();
+
+
+ /**
+ * Required field contains a human readable description of the error condition.
+ *
+ * @return human readable description of the error condition
+ */
+ String getErrorDescription();
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/LogInfo.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/LogInfo.java
new file mode 100644
index 0000000..4a3680f
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/LogInfo.java
@@ -0,0 +1,30 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+import java.io.Serializable;
+
+/**
+ * Marker interface for all EELF Logging Information Components
+ *
+ * @author Rajiv Singla
+ */
+public interface LogInfo extends Serializable {
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/LogLevelCategory.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/LogLevelCategory.java
new file mode 100644
index 0000000..665a280
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/LogLevelCategory.java
@@ -0,0 +1,36 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+/**
+ * Captures various logging levels.
+ * NOTE: Enum ordered signifies low to high log level severity
+ *
+ * @author Rajiv Singla
+ */
+public enum LogLevelCategory implements LogInfo {
+
+ DEBUG,
+ INFO,
+ WARN,
+ ERROR,
+ FATAL;
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/MessageLogInfo.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/MessageLogInfo.java
new file mode 100644
index 0000000..cd53ccf
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/MessageLogInfo.java
@@ -0,0 +1,62 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+import java.util.Date;
+
+/**
+ * Captures fields required for message level logging. These fields are mostly derived fields. For example: creation
+ * timestamp can be auto generated based on system time, {@link RequestStatusCode} and {@link NagiosAlertLevel} can be
+ * derived based on {@link LogLevelCategory}
+ *
+ * @author Rajiv Singla
+ */
+public interface MessageLogInfo extends LogInfo {
+
+
+ /**
+ * Required field to capture when the message was created
+ * The value should be represented in UTC and formatted according to ISO 8601.
+ * <p>
+ * <b>Example: 2015-06-03T13:21:58+00:00</b>
+ * </p>
+ *
+ * @return message creation creationTimestamp
+ */
+ Date getCreationTimestamp();
+
+ /**
+ * Required field contains a value of COMPLETE or ERROR to indicate high level success or failure of the
+ * request related activities.
+ *
+ * @return value to indicate high level success or failure of the request related activities
+ */
+ RequestStatusCode getStatusCode();
+
+
+ /**
+ * Optional field for Nagios monitoring/alerting severity code
+ *
+ * @return nagios monitoring/alerting severity code
+ */
+ NagiosAlertLevel getAlertSeverity();
+
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/MiscLogInfo.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/MiscLogInfo.java
new file mode 100644
index 0000000..bf1e451
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/MiscLogInfo.java
@@ -0,0 +1,45 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+/**
+ * Captures optional / deprecated fields that can be populated as per EELF Logging Requirements
+ *
+ * @author Rajiv Singla
+ */
+public interface MiscLogInfo extends LogInfo {
+
+ /**
+ * Optional field that can can be used to capture the flow of a transaction through the system by
+ * indicating the components and operations involved in processed. If present, it can be denoted by a comma
+ * separated list of components and applications.
+ *
+ * @return list of comma separated components and operations involved in processing
+ */
+ String getProcessId();
+
+ /**
+ * This field is deprecated and should be left empty.
+ *
+ * @return deprecated field value - should be empty
+ */
+ String getUnused();
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/NagiosAlertLevel.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/NagiosAlertLevel.java
new file mode 100644
index 0000000..3da5fc3
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/NagiosAlertLevel.java
@@ -0,0 +1,52 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+/**
+ * Enum for Nagios monitoring/alerting codes as per table below.
+ * <p>
+ * <table cellspacing=0 border=1>
+ * <tr><th>Return Code</th><th>Service State</th><th>Host State</th></tr>
+ * <tr><td>0</td><td>OK</td><td>UP</td></tr>
+ * <tr><td>1</td><td>WARNING</td><td>UP or DOWN/UNREACHABLE*</td></tr>
+ * <tr><td>2</td><td>CRITICAL</td><td>DOWN/UNREACHABLE</td></tr>
+ * <tr><td>3</td><td>UNKNOWN</td><td>DOWN/UNREACHABLE</td></tr>
+ * </table>
+ *
+ * @author Rajiv Singla
+ */
+public enum NagiosAlertLevel implements LogInfo {
+
+ OK("0"),
+ WARNING("1"),
+ CRITICAL("2"),
+ UNKNOWN("3");
+
+ private String severityCode;
+
+ NagiosAlertLevel(final String severityCode) {
+ this.severityCode = severityCode;
+ }
+
+ public String getSeverityCode() {
+ return severityCode;
+ }
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/RequestIdLogInfo.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/RequestIdLogInfo.java
new file mode 100644
index 0000000..68d5a17
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/RequestIdLogInfo.java
@@ -0,0 +1,44 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+/**
+ * Captures fields required for logging request information
+ *
+ * @author Rajiv Singla
+ */
+public interface RequestIdLogInfo extends LogInfo {
+
+ /**
+ * Required field containing requestID which uniquely that identifies a single transaction request within the EELF
+ * platform. Its value is conforms to RFC4122 UUID. The requestID value is passed using a REST API from one
+ * EELF component to another via HTTP Headers named X-RequestID
+ * <p>
+ * <b>724229c0-9945-11e5-bcde-0002a5d5c51b:1234</b>
+ * </p>
+ * If receiving a composite requestID value, e.g. something of the form UUID-1:UUID-2, the receiving component
+ * should only use the UUID-1 portion (i.e. remove the “:” and any trailing suffix, e.g. UUID-2) as the requestID
+ * field value for its log files.
+ *
+ * @return requestID which uniquely that identifies a single transaction request within the EELF
+ */
+ String getRequestId();
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/RequestStatusCode.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/RequestStatusCode.java
new file mode 100644
index 0000000..b022b80
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/RequestStatusCode.java
@@ -0,0 +1,32 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+/**
+ * Enum to indicate high level success or failure of the request related activities
+ *
+ * @author Rajiv Singla
+ */
+public enum RequestStatusCode {
+
+ ERROR,
+ COMPLETE;
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/RequestTimingLogInfo.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/RequestTimingLogInfo.java
new file mode 100644
index 0000000..7448e69
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/RequestTimingLogInfo.java
@@ -0,0 +1,64 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+import java.util.Date;
+
+/**
+ * Captures Logging fields required for request timing related information
+ *
+ * @author Rajiv Singla
+ */
+public interface RequestTimingLogInfo extends LogInfo {
+
+ /**
+ * Required field containing creationTimestamp when the request processing started.
+ * The value should be represented in UTC and formatted according to ISO 8601.
+ * <p>
+ * <b>Example: 2015-06-03T13:21:58+00:00</b>
+ * </p>
+ *
+ * @return request activity begin creationTimestamp
+ */
+ Date getBeginTimestamp();
+
+
+ /**
+ * Required field containing creationTimestamp when the request processed stopped.
+ * The value should be represented in UTC and formatted according to ISO 8601.
+ * <p>
+ * <b>Example: 2015-06-03T13:21:58+00:00</b>
+ * </p>
+ *
+ * @return request activity end creationTimestamp
+ */
+ Date getEndTimestamp();
+
+
+ /**
+ * Required field contains the elapsed time to complete processing of an API call or transaction request (e.g.,
+ * processing of a message that was received). This value should be the difference between EndTimestamp and
+ * BeginTimestamp fields and should be expressed in milliseconds.
+ *
+ * @return request processing elapsed time in milliseconds
+ */
+ Long getElapsedTime();
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/ResponseLogInfo.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/ResponseLogInfo.java
new file mode 100644
index 0000000..1929e7f
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/ResponseLogInfo.java
@@ -0,0 +1,81 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+/**
+ * Captures field required for logging Response information
+ *
+ * @author Rajiv Singla
+ */
+public interface ResponseLogInfo extends LogInfo {
+
+ /**
+ * Required field contains application-specific response codes. While error codes are
+ * application-specific, they
+ * should conform categories mentioned in table below in order to provide consistency
+ * <p>
+ * <table cellspacing=0 border=1>
+ * <tr>
+ * <th style=min-width:50px><b>Error type</b></th>
+ * <th style=min-width:50px><b>Notes</b></th>
+ * </tr>
+ * <tr>
+ * <td style=min-width:50px>0</td>
+ * <td style=min-width:50px>Success</td>
+ * </tr>
+ * <tr>
+ * <td style=min-width:50px>100</td>
+ * <td style=min-width:50px>Permission errors</td>
+ * </tr>
+ * <tr>
+ * <td style=min-width:50px>200</td>
+ * <td style=min-width:50px>Availability errors/Timeouts</td>
+ * </tr>
+ * <tr>
+ * <td style=min-width:50px>300</td>
+ * <td style=min-width:50px>Data errors</td>
+ * </tr>
+ * <tr>
+ * <td style=min-width:50px>400</td>
+ * <td style=min-width:50px>Schema errors</td>
+ * </tr>
+ * <tr>
+ * <td style=min-width:50px>500</td>
+ * <td style=min-width:50px>Business process errors</td>
+ * </tr>
+ * <tr>
+ * <td style=min-width:50px>900</td>
+ * <td style=min-width:50px>Unknown Errors</td>
+ * </tr>
+ * </table>
+ *
+ * @return application-specific error code
+ */
+ Integer getResponseCode();
+
+
+ /**
+ * Required field contains a human readable description of the {@link #getResponseCode()}.
+ *
+ * @return human readable description of the response code
+ */
+ String getResponseDescription();
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/ServiceLogInfo.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/ServiceLogInfo.java
new file mode 100644
index 0000000..0287cef
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/ServiceLogInfo.java
@@ -0,0 +1,61 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+/**
+ * Captures information about logging fields for application acting as service and handling requests from other
+ * applications
+ *
+ * @author Rajiv Singla
+ */
+public interface ServiceLogInfo extends LogInfo {
+
+ /**
+ * Required field contains the developer given name of the ecomp component's exposed api (~='method', function')
+ * invoked. For example if the application is exposing a REST interface and exposing runtime metrics then the
+ * service name can be: appName-getMetrics
+ *
+ * @return name of the API invoked by the application
+ */
+ String getServiceName();
+
+
+ /**
+ * Optional field contains the name of the client or user invoking the service.
+ * It may be an application, user name or mech id.
+ *
+ * @return name of the client or user invoking the API if known
+ */
+ String getPartnerName();
+
+
+ /**
+ * Optional field contains requesting remote client application’s IP address. Use UNKNOWN or an empty string if not
+ * available.
+ *
+ * @return remote client application’s IP address
+ */
+ String getClientIPAddress();
+
+
+}
+
+
+
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/TargetServiceLogInfo.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/TargetServiceLogInfo.java
new file mode 100644
index 0000000..d9b1f98
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/TargetServiceLogInfo.java
@@ -0,0 +1,54 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.info;
+
+/**
+ * Captures fields for logging application which is calling an external/target service
+ *
+ * @author Rajiv Singla
+ */
+public interface TargetServiceLogInfo extends LogInfo {
+
+ /**
+ * Required field containing name of EELF component/sub component or non-EELF entity which is invoked by the
+ * logging application
+ *
+ * @return target entity name which is invoked by the logging application
+ */
+ String getTargetEntity();
+
+
+ /**
+ * Required field containing name of External API/operation activities invoked on {@link #getTargetEntity()}
+ *
+ * @return target service name invoked by the logging application
+ */
+ String getTargetServiceName();
+
+
+ /**
+ * Optional field containing target VNF or VM being acted upon by the logging application. This field contains the
+ * virtual entity that is the target of the action for example the FQDN of the target virtual entity
+ *
+ * @return target Virtual Entity
+ */
+ String getTargetVirtualEntity();
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/package-info.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/package-info.java
new file mode 100644
index 0000000..45bddd1
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/info/package-info.java
@@ -0,0 +1,28 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+/**
+ * Captures EELF logging information about various types.
+ * <p>
+ * The logging information is segregated into various information different types as to their relevance in particular
+ * cases.
+ *
+ * @author Rajiv Singla
+ */
+package org.onap.dcae.utils.eelf.logger.api.info;
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/AuditLog.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/AuditLog.java
new file mode 100644
index 0000000..952176e
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/AuditLog.java
@@ -0,0 +1,130 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.log;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.spec.AuditLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+
+/**
+ * Audit Log captures all log levels supported by audit specifications
+ *
+ * @author Rajiv Singla
+ */
+public interface AuditLog {
+
+ /**
+ * Logs audit message with provided {@link LogLevelCategory}
+ *
+ * @param logLevelCategory log level category
+ * @param message log message
+ * @param auditLogSpec audit log spec
+ * @param optionalLogSpec optional log spec
+ * @param args argument values for log message interpolation
+ */
+ void log(LogLevelCategory logLevelCategory, String message, AuditLogSpec auditLogSpec,
+ OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs audit message with provided {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param logLevelCategory log level category
+ * @param message log message
+ * @param auditLogSpec audit log spec
+ * @param args argument values for log message interpolation
+ */
+ void log(LogLevelCategory logLevelCategory, String message, AuditLogSpec auditLogSpec, String... args);
+
+
+ /**
+ * Logs audit message with provided INFO {@link LogLevelCategory}
+ *
+ * @param message log message
+ * @param auditLogSpec audit log spec
+ * @param args argument values for log message interpolation
+ */
+ void info(String message, AuditLogSpec auditLogSpec, OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs audit message with provided INFO {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param message log message
+ * @param auditLogSpec audit log spec
+ * @param args argument values for log message interpolation
+ */
+ void info(String message, AuditLogSpec auditLogSpec, String... args);
+
+
+ /**
+ * Logs audit message with provided WARN {@link LogLevelCategory}
+ *
+ * @param message log message
+ * @param auditLogSpec audit log spec
+ * @param args argument values for log message interpolation
+ */
+ void warn(String message, AuditLogSpec auditLogSpec, OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs audit message with provided WARN {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param message log message
+ * @param auditLogSpec audit log spec
+ * @param args argument values for log message interpolation
+ */
+ void warn(String message, AuditLogSpec auditLogSpec, String... args);
+
+ /**
+ * Logs audit message with provided ERROR {@link LogLevelCategory}
+ *
+ * @param message log message
+ * @param auditLogSpec audit log spec
+ * @param args argument values for log message interpolation
+ */
+ void error(String message, AuditLogSpec auditLogSpec, OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs audit message with provided ERROR {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param message log message
+ * @param auditLogSpec audit log spec
+ * @param args argument values for log message interpolation
+ */
+ void error(String message, AuditLogSpec auditLogSpec, String... args);
+
+ /**
+ * Logs audit message with provided FATAL {@link LogLevelCategory}
+ *
+ * @param message log message
+ * @param auditLogSpec audit log spec
+ * @param args argument values for log message interpolation
+ */
+ void fatal(String message, AuditLogSpec auditLogSpec, OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs audit message with provided FATAL {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param message log message
+ * @param auditLogSpec audit log spec
+ * @param args argument values for log message interpolation
+ */
+ void fatal(String message, AuditLogSpec auditLogSpec, String... args);
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/DebugLog.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/DebugLog.java
new file mode 100644
index 0000000..98a0921
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/DebugLog.java
@@ -0,0 +1,76 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.log;
+
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.spec.DebugLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+
+/**
+ * Debug Log captures all log levels supported by debug specifications.
+ * <p>
+ * <b>NOTE: DEBUG Log is optional as per EELF Specifications</b>
+ *
+ * @author Rajiv Singla
+ */
+public interface DebugLog {
+
+ /**
+ * Logs debug message with provided {@link LogLevelCategory}
+ *
+ * @param logLevelCategory log level category
+ * @param message log message
+ * @param debugLogSpec debug log spec
+ * @param optionalLogSpec optional log spec
+ * @param args argument values for log message interpolation
+ */
+ void log(LogLevelCategory logLevelCategory, String message, DebugLogSpec debugLogSpec,
+ OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs debug message with provided {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param logLevelCategory log level category
+ * @param message log message
+ * @param debugLogSpec debug log spec
+ * @param args argument values for log message interpolation
+ */
+ void log(LogLevelCategory logLevelCategory, String message, DebugLogSpec debugLogSpec, String... args);
+
+
+ /**
+ * Logs debug message with provided DEBUG {@link LogLevelCategory}
+ *
+ * @param message log message
+ * @param debugLogSpec debug log spec
+ * @param args argument values for log message interpolation
+ */
+ void debug(String message, DebugLogSpec debugLogSpec, OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs debug message with provided DEBUG {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param message log message
+ * @param debugLogSpec debug log spec
+ * @param args argument values for log message interpolation
+ */
+ void debug(String message, DebugLogSpec debugLogSpec, String... args);
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/EELFLogFactory.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/EELFLogFactory.java
new file mode 100644
index 0000000..2cfb2ec
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/EELFLogFactory.java
@@ -0,0 +1,85 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.log;
+
+
+import org.onap.dcae.utils.eelf.logger.api.noop.NoOpEELFLogger;
+
+import java.lang.reflect.InvocationTargetException;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+import java.util.ServiceLoader;
+import java.util.WeakHashMap;
+
+/**
+ * EELF Log Factory uses {@link ServiceLoader} to load implementations of {@link EELFLogger} in application
+ * classpath. If no EELF Logging implementations are found - eelf logging is disabled and {@link NoOpEELFLogger}
+ * is used.
+ *
+ * @author Rajiv Singla
+ */
+public class EELFLogFactory {
+
+ private static final ServiceLoader<EELFLogger> SERVICE_LOADER = ServiceLoader.load(EELFLogger.class);
+ private static final Map<Class<?>, EELFLogger> LOGGER_CACHE = new WeakHashMap<>(64);
+
+ private static List<EELFLogger> loggerImplementations = new LinkedList<>();
+
+ static {
+
+ for (EELFLogger loggerImplementation : SERVICE_LOADER) {
+ loggerImplementations.add(loggerImplementation);
+ }
+
+ if (loggerImplementations.isEmpty()) {
+ System.err.println(
+ "EELF LOGGING ERROR: Unable to find any EELF Logger Implementations in the classpath.");
+ System.err.println("=============EELF LOGGING IS DISABLED================");
+ loggerImplementations.add(NoOpEELFLogger.getInstance());
+ }
+
+ }
+
+ private EELFLogFactory() {
+ // private constructor
+ }
+
+ public static <T> EELFLogger getLogger(Class<T> clazz) {
+
+ if (LOGGER_CACHE.get(clazz) != null) {
+ return LOGGER_CACHE.get(clazz);
+ }
+
+ EELFLogger EELFLogger = null;
+ try {
+ EELFLogger = loggerImplementations.get(0).getClass().getConstructor(Class.class)
+ .newInstance(clazz);
+ return EELFLogger;
+
+ } catch (
+ InstantiationException | IllegalAccessException | InvocationTargetException | NoSuchMethodException e) {
+ throw new IllegalStateException("Error while Creating EELF Logger", e);
+ }
+
+ }
+
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/EELFLogger.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/EELFLogger.java
new file mode 100644
index 0000000..500d814
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/EELFLogger.java
@@ -0,0 +1,67 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.log;
+
+/**
+ * EELF Logger is main abstraction which applications use to log EELF Compliant log messages
+ *
+ * @author Rajiv Singla
+ */
+public interface EELFLogger {
+
+ /**
+ * Provides Audit Log
+ *
+ * @return Audit log
+ */
+ AuditLog auditLog();
+
+
+ /**
+ * Provides Metric Log
+ *
+ * @return metric log
+ */
+ MetricLog metricLog();
+
+ /**
+ * Provides Error Log
+ *
+ * @return error log
+ */
+ ErrorLog errorLog();
+
+
+ /**
+ * Provides Debug Log
+ *
+ * @return debug log
+ */
+ DebugLog debugLog();
+
+ /**
+ * Provides logging context
+ *
+ * @return logging context
+ */
+ EELFLoggerContext loggingContext();
+
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/EELFLoggerContext.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/EELFLoggerContext.java
new file mode 100644
index 0000000..5910da5
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/EELFLoggerContext.java
@@ -0,0 +1,56 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.log;
+
+
+import org.onap.dcae.utils.eelf.logger.api.spec.AppLogSpec;
+
+/**
+ * EELF Logger Context contains fields are set during application creation time and are fixed for the entire
+ * duration of the application lifetime
+ *
+ * @author Rajiv Singla
+ */
+public interface EELFLoggerContext {
+
+ /**
+ * Returns App Log Spec
+ *
+ * @return current app log spec
+ */
+ AppLogSpec getAppLogSpec();
+
+
+ /**
+ * Sets new App Log Spec
+ *
+ * @param appLogSpec new app log spec
+ */
+ void setAppLogSpec(AppLogSpec appLogSpec);
+
+
+ /**
+ * Returns true if logging context is already initialized
+ *
+ * @return true if logger context is already initialized
+ */
+ boolean isInitialized();
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/ErrorLog.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/ErrorLog.java
new file mode 100644
index 0000000..6b27755
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/ErrorLog.java
@@ -0,0 +1,93 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.log;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.spec.ErrorLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+
+/**
+ * @author Rajiv Singla
+ */
+public interface ErrorLog {
+
+ /**
+ * Logs error message with provided {@link LogLevelCategory}
+ *
+ * @param logLevelCategory log level category
+ * @param message log message
+ * @param errorLogSpec error log spec
+ * @param optionalLogSpec optional log spec
+ * @param args argument values for log message interpolation
+ */
+ void log(LogLevelCategory logLevelCategory, String message, ErrorLogSpec errorLogSpec,
+ OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs error message with provided {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param logLevelCategory log level category
+ * @param message log message
+ * @param errorLogSpec error log spec
+ * @param args argument values for log message interpolation
+ */
+ void log(LogLevelCategory logLevelCategory, String message, ErrorLogSpec errorLogSpec, String... args);
+
+
+ /**
+ * Logs error message with ERROR {@link LogLevelCategory}
+ *
+ * @param message log message
+ * @param errorLogSpec error log spec
+ * @param args argument values for log message interpolation
+ */
+ void error(String message, ErrorLogSpec errorLogSpec, OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs error message with ERROR {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param message log message
+ * @param errorLogSpec error log spec
+ * @param args argument values for log message interpolation
+ */
+ void error(String message, ErrorLogSpec errorLogSpec, String... args);
+
+
+ /**
+ * Logs error message with WARN {@link LogLevelCategory}
+ *
+ * @param message log message
+ * @param errorLogSpec error log spec
+ * @param args argument values for log message interpolation
+ */
+ void warn(String message, ErrorLogSpec errorLogSpec, OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs error message with WARN {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param message log message
+ * @param errorLogSpec error log spec
+ * @param args argument values for log message interpolation
+ */
+ void warn(String message, ErrorLogSpec errorLogSpec, String... args);
+
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/MetricLog.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/MetricLog.java
new file mode 100644
index 0000000..ebc33ca
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/MetricLog.java
@@ -0,0 +1,130 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.log;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.spec.MetricLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+
+/**
+ * Metric Log captures all log levels supported by metric specifications
+ *
+ * @author Rajiv Singla
+ */
+public interface MetricLog {
+
+ /**
+ * Logs metric message with provided {@link LogLevelCategory}
+ *
+ * @param logLevelCategory log level category
+ * @param message log message
+ * @param metricLogSpec metric log spec
+ * @param optionalLogSpec optional log spec
+ * @param args argument values for log message interpolation
+ */
+ void log(LogLevelCategory logLevelCategory, String message, MetricLogSpec metricLogSpec,
+ OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs metric message with provided {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param logLevelCategory log level category
+ * @param message log message
+ * @param metricLogSpec metric log spec
+ * @param args argument values for log message interpolation
+ */
+ void log(LogLevelCategory logLevelCategory, String message, MetricLogSpec metricLogSpec, String... args);
+
+
+ /**
+ * Logs metric message with provided INFO {@link LogLevelCategory}
+ *
+ * @param message log message
+ * @param metricLogSpec metric log spec
+ * @param args argument values for log message interpolation
+ */
+ void info(String message, MetricLogSpec metricLogSpec, OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs metric message with provided INFO {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param message log message
+ * @param metricLogSpec metric log spec
+ * @param args argument values for log message interpolation
+ */
+ void info(String message, MetricLogSpec metricLogSpec, String... args);
+
+
+ /**
+ * Logs metric message with provided WARN {@link LogLevelCategory}
+ *
+ * @param message log message
+ * @param metricLogSpec metric log spec
+ * @param args argument values for log message interpolation
+ */
+ void warn(String message, MetricLogSpec metricLogSpec, OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs metric message with provided WARN {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param message log message
+ * @param metricLogSpec metric log spec
+ * @param args argument values for log message interpolation
+ */
+ void warn(String message, MetricLogSpec metricLogSpec, String... args);
+
+ /**
+ * Logs metric message with provided ERROR {@link LogLevelCategory}
+ *
+ * @param message log message
+ * @param metricLogSpec metric log spec
+ * @param args argument values for log message interpolation
+ */
+ void error(String message, MetricLogSpec metricLogSpec, OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs metric message with provided ERROR {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param message log message
+ * @param metricLogSpec metric log spec
+ * @param args argument values for log message interpolation
+ */
+ void error(String message, MetricLogSpec metricLogSpec, String... args);
+
+ /**
+ * Logs metric message with provided FATAL {@link LogLevelCategory}
+ *
+ * @param message log message
+ * @param metricLogSpec metric log spec
+ * @param args argument values for log message interpolation
+ */
+ void fatal(String message, MetricLogSpec metricLogSpec, OptionalLogSpec optionalLogSpec, String... args);
+
+ /**
+ * Logs metric message with provided FATAL {@link LogLevelCategory} and with default {@link OptionalLogSpec}
+ *
+ * @param message log message
+ * @param metricLogSpec metric log spec
+ * @param args argument values for log message interpolation
+ */
+ void fatal(String message, MetricLogSpec metricLogSpec, String... args);
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/package-info.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/package-info.java
new file mode 100644
index 0000000..e24ccc9
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/log/package-info.java
@@ -0,0 +1,23 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+/**
+ * Contains Logging API contracts for various EELF Logs (e.g. Audit, Metric, Error, Debug etc)
+ */
+package org.onap.dcae.utils.eelf.logger.api.log;
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpAuditLog.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpAuditLog.java
new file mode 100644
index 0000000..6c1c583
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpAuditLog.java
@@ -0,0 +1,90 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.noop;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.log.AuditLog;
+import org.onap.dcae.utils.eelf.logger.api.spec.AuditLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+
+/**
+ * A no operation implementation of AuditLog
+ *
+ * @author Rajiv Singla
+ */
+public class NoOpAuditLog implements AuditLog {
+
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final AuditLogSpec auditLogSpec,
+ final OptionalLogSpec optionalLogSpec, final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final AuditLogSpec auditLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void info(final String message, final AuditLogSpec auditLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void info(final String message, final AuditLogSpec auditLogSpec, final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void warn(final String message, final AuditLogSpec auditLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void warn(final String message, final AuditLogSpec auditLogSpec, final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void error(final String message, final AuditLogSpec auditLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void error(final String message, final AuditLogSpec auditLogSpec, final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void fatal(final String message, final AuditLogSpec auditLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void fatal(final String message, final AuditLogSpec auditLogSpec, final String... args) {
+ // no operation
+ }
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpDebugLog.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpDebugLog.java
new file mode 100644
index 0000000..dd36b52
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpDebugLog.java
@@ -0,0 +1,56 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.noop;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.log.DebugLog;
+import org.onap.dcae.utils.eelf.logger.api.spec.DebugLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+
+/**
+ * A no operation implementation of Debug Log
+ *
+ * @author Rajiv Singla
+ */
+public class NoOpDebugLog implements DebugLog {
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final DebugLogSpec debugLogSpec,
+ final OptionalLogSpec optionalLogSpec, final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final DebugLogSpec debugLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void debug(final String message, final DebugLogSpec debugLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void debug(final String message, final DebugLogSpec debugLogSpec, final String... args) {
+ // no operation
+ }
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpEELFLogger.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpEELFLogger.java
new file mode 100644
index 0000000..c761ba1
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpEELFLogger.java
@@ -0,0 +1,77 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.noop;
+
+
+import org.onap.dcae.utils.eelf.logger.api.log.AuditLog;
+import org.onap.dcae.utils.eelf.logger.api.log.DebugLog;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLogger;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLoggerContext;
+import org.onap.dcae.utils.eelf.logger.api.log.ErrorLog;
+import org.onap.dcae.utils.eelf.logger.api.log.MetricLog;
+
+/**
+ * A no operation implementation of {@link EELFLogger}
+ *
+ * @author Rajiv Singla
+ */
+public class NoOpEELFLogger implements EELFLogger {
+
+ private static final AuditLog NO_OP_AUDIT_LOG = new NoOpAuditLog();
+ private static final MetricLog NO_OP_METRIC_LOG = new NoOpMetricLog();
+ private static final ErrorLog NO_OP_ERROR_LOG = new NoOpErrorLog();
+ private static final DebugLog NO_OP_DEBUG_LOG = new NoOpDebugLog();
+
+ private static final NoOpEELFLogger NO_OP_EELF_LOGGER = new NoOpEELFLogger();
+
+ private NoOpEELFLogger() {
+ // private constructor
+ }
+
+ public static NoOpEELFLogger getInstance() {
+ return NO_OP_EELF_LOGGER;
+ }
+
+ @Override
+ public AuditLog auditLog() {
+ return NO_OP_AUDIT_LOG;
+ }
+
+ @Override
+ public MetricLog metricLog() {
+ return NO_OP_METRIC_LOG;
+ }
+
+ @Override
+ public ErrorLog errorLog() {
+ return NO_OP_ERROR_LOG;
+ }
+
+ @Override
+ public DebugLog debugLog() {
+ return NO_OP_DEBUG_LOG;
+ }
+
+ @Override
+ public EELFLoggerContext loggingContext() {
+ return null;
+ }
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpErrorLog.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpErrorLog.java
new file mode 100644
index 0000000..c1b4e13
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpErrorLog.java
@@ -0,0 +1,68 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.noop;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.log.ErrorLog;
+import org.onap.dcae.utils.eelf.logger.api.spec.ErrorLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+
+/**
+ * A no operation implementation of Error Log
+ *
+ * @author Rajiv Singla
+ */
+public class NoOpErrorLog implements ErrorLog {
+
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final ErrorLogSpec errorLogSpec,
+ final OptionalLogSpec optionalLogSpec, final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final ErrorLogSpec errorLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void error(final String message, final ErrorLogSpec errorLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void error(final String message, final ErrorLogSpec errorLogSpec, final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void warn(final String message, final ErrorLogSpec errorLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void warn(final String message, final ErrorLogSpec errorLogSpec, final String... args) {
+ // no operation
+ }
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpMetricLog.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpMetricLog.java
new file mode 100644
index 0000000..1c67862
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/NoOpMetricLog.java
@@ -0,0 +1,89 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.noop;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.log.MetricLog;
+import org.onap.dcae.utils.eelf.logger.api.spec.MetricLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+
+/**
+ * A no operation implementation of Metric Log
+ *
+ * @author Rajiv Singla
+ */
+public class NoOpMetricLog implements MetricLog {
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final MetricLogSpec metricLogSpec,
+ final OptionalLogSpec optionalLogSpec, final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final MetricLogSpec metricLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void info(final String message, final MetricLogSpec metricLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void info(final String message, final MetricLogSpec metricLogSpec, final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void warn(final String message, final MetricLogSpec metricLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void warn(final String message, final MetricLogSpec metricLogSpec, final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void error(final String message, final MetricLogSpec metricLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void error(final String message, final MetricLogSpec metricLogSpec, final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void fatal(final String message, final MetricLogSpec metricLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ // no operation
+ }
+
+ @Override
+ public void fatal(final String message, final MetricLogSpec metricLogSpec, final String... args) {
+ // no operation
+ }
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/package-info.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/package-info.java
new file mode 100644
index 0000000..f7ed917
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/noop/package-info.java
@@ -0,0 +1,26 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+/**
+ * Contains no operation implementation of EELF Logging API. Generally used as a fallback when no EELF Logging
+ * implementation is detected in the application classpath
+ *
+ * @author Rajiv Singla
+ */
+package org.onap.dcae.utils.eelf.logger.api.noop;
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/AppLogSpec.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/AppLogSpec.java
new file mode 100644
index 0000000..83643fb
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/AppLogSpec.java
@@ -0,0 +1,32 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.spec;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.AppLogInfo;
+
+/**
+ * App Log spec captures fields which are fixed for the duration of application once its instance is created. They
+ * should be populated for all specifications regardless of if they are relevant to that specification
+ *
+ * @author Rajiv Singla
+ */
+public interface AppLogSpec extends AppLogInfo {
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/AuditLogSpec.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/AuditLogSpec.java
new file mode 100644
index 0000000..46360b1
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/AuditLogSpec.java
@@ -0,0 +1,42 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.spec;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.RequestIdLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestTimingLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.ResponseLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.ServiceLogInfo;
+
+/**
+ * Captures fields required for EELF Audit Log Specification.
+ *
+ * @author Rajiv Singla
+ */
+public interface AuditLogSpec extends
+ // request id must be preset for all log specifications
+ RequestIdLogInfo,
+ // duration related fields
+ RequestTimingLogInfo,
+ // app acting as a service fields
+ ServiceLogInfo, ResponseLogInfo {
+
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/DebugLogSpec.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/DebugLogSpec.java
new file mode 100644
index 0000000..ac4bd64
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/DebugLogSpec.java
@@ -0,0 +1,34 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.spec;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.RequestIdLogInfo;
+
+/**
+ * Captures fields required for EELF Debug Log Specification.
+ * NOTE: As per specification debug log is optional
+ *
+ * @author Rajiv Singla
+ */
+public interface DebugLogSpec extends
+ // request id must be preset for all log specifications
+ RequestIdLogInfo {
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/ErrorLogSpec.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/ErrorLogSpec.java
new file mode 100644
index 0000000..455f433
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/ErrorLogSpec.java
@@ -0,0 +1,42 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.spec;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.ErrorLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestIdLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.ServiceLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.TargetServiceLogInfo;
+
+/**
+ * Captures fields required for EELF Error Log Specification
+ *
+ * @author Rajiv Singla
+ */
+public interface ErrorLogSpec extends
+ // request id must be preset for all log specifications
+ RequestIdLogInfo,
+ // app acting as a service fields
+ ServiceLogInfo,
+ // app calling external service fields
+ TargetServiceLogInfo,
+ // error details fields
+ ErrorLogInfo {
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/MetricLogSpec.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/MetricLogSpec.java
new file mode 100644
index 0000000..5b5f698
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/MetricLogSpec.java
@@ -0,0 +1,36 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.spec;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.TargetServiceLogInfo;
+
+/**
+ * Captures fields required for EELF Metric Log Specification.
+ *
+ * @author Rajiv Singla
+ */
+public interface MetricLogSpec extends
+ // Audit log spec
+ AuditLogSpec,
+ // App calling external service fields
+ TargetServiceLogInfo {
+
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/OptionalLogSpec.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/OptionalLogSpec.java
new file mode 100644
index 0000000..dac08ab
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/OptionalLogSpec.java
@@ -0,0 +1,39 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.api.spec;
+
+import org.onap.dcae.utils.eelf.logger.api.info.CodeLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.CustomFieldsLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.MessageLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.MiscLogInfo;
+
+/**
+ * Captures fields which are optional or derived from other fields
+ *
+ * @author Rajiv Singla
+ */
+public interface OptionalLogSpec extends
+ // message fields are mostly auto generated or can be derived from other fields
+ MessageLogInfo,
+ // Code log info can be derived by the underlying logging framework or provided optionally by the app
+ CodeLogInfo,
+ // custom and misc log info are mostly optional
+ CustomFieldsLogInfo, MiscLogInfo {
+}
diff --git a/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/package-info.java b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/package-info.java
new file mode 100644
index 0000000..b4c1df8
--- /dev/null
+++ b/eelf-logger/eelf-logger-api/src/main/java/org/onap/dcae/utils/eelf/logger/api/spec/package-info.java
@@ -0,0 +1,28 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+/**
+ * Contains various EELF Logging Specifications.
+ * <p>
+ * Some specifications are fixed for the whole duration of the
+ * application, some specification are either optional or derived and some are required for particular EELF Logging
+ * specification. These logging specification are composed of various logging information in
+ * {@link org.onap.dcae.utils.eelf.logger.api.info} package
+ */
+package org.onap.dcae.utils.eelf.logger.api.spec;
diff --git a/eelf-logger/eelf-logger-logback-impl/pom.xml b/eelf-logger/eelf-logger-logback-impl/pom.xml
new file mode 100644
index 0000000..165d216
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/pom.xml
@@ -0,0 +1,62 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ ~ ================================================================================
+ ~ Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ ~ ================================================================================
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License.
+ ~ ============LICENSE_END=========================================================
+ ~
+ -->
+
+<project xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xmlns="http://maven.apache.org/POM/4.0.0"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+
+ <modelVersion>4.0.0</modelVersion>
+
+ <parent>
+ <groupId>org.onap.dcaegen2.utils</groupId>
+ <artifactId>eelf-logger</artifactId>
+ <version>1.0.0-SNAPSHOT</version>
+ </parent>
+
+ <artifactId>eelf-logger-logback-impl</artifactId>
+ <packaging>jar</packaging>
+
+ <!-- EELF LOGGING IMPLEMENTATION BACKED BY LOGBACK LOGGING FRAMEWORK-->
+ <name>dcaegen2-utils-eelf-logger-logback-impl</name>
+ <description>Implements EEL Logging Specification using Logback</description>
+
+ <properties>
+ <main.basedir>${project.parent.basedir}</main.basedir>
+ </properties>
+
+ <dependencies>
+
+ <!-- ECOMP LOGGER MODEL -->
+ <dependency>
+ <groupId>${project.groupId}</groupId>
+ <artifactId>eelf-logger-model</artifactId>
+ <version>${project.version}</version>
+ </dependency>
+
+ <!-- LOGBACK -->
+ <dependency>
+ <groupId>ch.qos.logback</groupId>
+ <artifactId>logback-classic</artifactId>
+ </dependency>
+
+ </dependencies>
+
+
+</project>
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/EELFLoggerDefaults.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/EELFLoggerDefaults.java
new file mode 100644
index 0000000..eceaf20
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/EELFLoggerDefaults.java
@@ -0,0 +1,105 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.LogInfo;
+import org.onap.dcae.utils.eelf.logger.model.info.AppLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.CustomFieldsLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.ErrorLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.MiscLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.RequestTimingLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.ResponseLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.ServiceLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.TargetServiceLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.OptionalLogSpecImpl;
+
+import java.util.Date;
+
+import static org.onap.dcae.utils.eelf.logger.logback.utils.LogUtils.createDefaultAppLogInfo;
+
+
+/**
+ * This utility class various default implementations for EELF Logger. Users should use these default rather then
+ * creating their own {@link LogInfo} objects.
+ *
+ * @author Rajiv Singla
+ */
+public class EELFLoggerDefaults {
+
+ private static final String UNKNOWN_FIELD_VALUE = "UNKNOWN";
+
+ // =============== APP LOG SPEC ======================//
+ /**
+ * Provides Default {@link AppLogInfoImpl}
+ */
+ public static final AppLogInfoImpl DEFAULT_APP_LOG_INFO = createDefaultAppLogInfo();
+
+
+ // =============== AUDIT LOG SPEC ===================== //
+
+ private static final String DEFAULT_PARTNER_NAME =
+ System.getProperty("user.name") != null ? System.getProperty("user.name") : UNKNOWN_FIELD_VALUE;
+
+ public static final ServiceLogInfoImpl DEFAULT_SERVICE_LOG_INFO =
+ new ServiceLogInfoImpl(UNKNOWN_FIELD_VALUE, DEFAULT_PARTNER_NAME, "");
+
+
+ public static final RequestTimingLogInfoImpl DEFAULT_REQUEST_TIMING_LOG_INFO =
+ new RequestTimingLogInfoImpl(new Date(), new Date(), null);
+
+
+ public static final ResponseLogInfoImpl DEFAULT_RESPONSE_LOG_INFO =
+ new ResponseLogInfoImpl(900, "UNDEFINED");
+
+
+ // =============== METRIC LOG SPEC ===================== //
+
+ public static final TargetServiceLogInfoImpl DEFAULT_TARGET_SERVICE_LOG_INFO =
+ new TargetServiceLogInfoImpl(UNKNOWN_FIELD_VALUE, UNKNOWN_FIELD_VALUE, UNKNOWN_FIELD_VALUE);
+
+ // =============== ERROR LOG SPEC ===================== //
+
+ public static final ErrorLogInfoImpl DEFAULT_ERROR_LOG_INFO =
+ new ErrorLogInfoImpl(900, "UNDEFINED ERROR");
+
+
+ // ============= OPTIONAL LOG SPEC =================== //
+
+ /**
+ * Provides Default {@link CustomFieldsLogInfoImpl}
+ */
+ public static final CustomFieldsLogInfoImpl DEFAULT_CUSTOM_FIELDS_LOG_INFO =
+ new CustomFieldsLogInfoImpl("", "", "", "");
+
+ /**
+ * Provides Default {@link MiscLogInfoImpl}
+ */
+ public static final MiscLogInfoImpl DEFAULT_MISC_LOG_INFO = new MiscLogInfoImpl("", "");
+
+
+ /**
+ * Provides Default {@link OptionalLogSpecImpl}
+ */
+ public static final OptionalLogSpecImpl DEFAULT_OPTIONAL_LOG_SPEC = new OptionalLogSpecImpl(null, null,
+ DEFAULT_CUSTOM_FIELDS_LOG_INFO, DEFAULT_MISC_LOG_INFO);
+
+
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/filter/MarkerFilter.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/filter/MarkerFilter.java
new file mode 100644
index 0000000..a664190
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/filter/MarkerFilter.java
@@ -0,0 +1,71 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.filter;
+
+import ch.qos.logback.classic.spi.ILoggingEvent;
+import ch.qos.logback.core.filter.AbstractMatcherFilter;
+import ch.qos.logback.core.spi.FilterReply;
+import org.slf4j.Marker;
+import org.slf4j.MarkerFactory;
+
+import java.util.HashSet;
+import java.util.Set;
+
+/**
+ * Logback Marker filter
+ *
+ * @author Rajiv Singla
+ */
+public class MarkerFilter extends AbstractMatcherFilter<ILoggingEvent> {
+
+ private String markersString;
+ private Set<Marker> markersToAccept = new HashSet<>();
+
+ @Override
+ public FilterReply decide(final ILoggingEvent event) {
+
+ if (!isStarted()) {
+ return FilterReply.NEUTRAL;
+ }
+
+ if (markersToAccept.contains(event.getMarker())) {
+ return onMatch;
+ } else {
+ return onMismatch;
+ }
+ }
+
+ public void setMarkers(String markersString) {
+ this.markersString = markersString;
+ }
+
+
+ public void start() {
+
+ if (markersString != null && markersString.trim().split(",").length > 0) {
+
+ final String[] markerStrings = markersString.trim().split(",");
+ for (String markerString : markerStrings) {
+ markersToAccept.add(MarkerFactory.getMarker(markerString.trim()));
+ }
+ super.start();
+ }
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/AuditLogLayout.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/AuditLogLayout.java
new file mode 100644
index 0000000..5d848ac
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/AuditLogLayout.java
@@ -0,0 +1,81 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.layout;
+
+import ch.qos.logback.classic.spi.ILoggingEvent;
+import ch.qos.logback.core.LayoutBase;
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.spec.AppLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.AuditLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+import org.onap.dcae.utils.eelf.logger.logback.utils.LogUtils;
+
+
+/**
+ * Audit log layout generates log messages as per EELF Audit Log Specifications
+ *
+ * @author Rajiv Singla
+ */
+public class AuditLogLayout extends LayoutBase<ILoggingEvent> {
+
+ @Override
+ public String doLayout(final ILoggingEvent event) {
+
+ final AppLogSpec appLogSpec = LogUtils.getAppLogSpec();
+ final LogLevelCategory logLevelCategory = LogUtils.getLogLevelCategory();
+ final Class<?> loggerClass = LogUtils.getLoggerClass();
+ final OptionalLogSpec optionalLogSpec = LogUtils.getOptionalLogSpec(loggerClass, logLevelCategory);
+ final AuditLogSpec auditLogSpec = LogUtils.getAuditLogSpec();
+
+ final String beginTimestamp = LogUtils.formatDate(auditLogSpec.getBeginTimestamp());
+ final String endTimestamp = LogUtils.formatDate(auditLogSpec.getEndTimestamp());
+
+ final String[] auditLogValues = {
+ beginTimestamp,
+ endTimestamp,
+ auditLogSpec.getRequestId(),
+ appLogSpec.getServiceInstanceID(),
+ event.getThreadName(),
+ appLogSpec.getVirtualServerName(),
+ auditLogSpec.getServiceName(),
+ auditLogSpec.getPartnerName(),
+ optionalLogSpec.getStatusCode().name(),
+ auditLogSpec.getResponseCode().toString(),
+ auditLogSpec.getResponseDescription(),
+ appLogSpec.getInstanceUUID(),
+ logLevelCategory != null ? logLevelCategory.name() : "",
+ optionalLogSpec.getAlertSeverity().getSeverityCode(),
+ appLogSpec.getServerIPAddress(),
+ auditLogSpec.getElapsedTime().toString(),
+ appLogSpec.getServerFQDN(),
+ auditLogSpec.getClientIPAddress(),
+ optionalLogSpec.getClassName(),
+ optionalLogSpec.getUnused(),
+ optionalLogSpec.getProcessId(),
+ optionalLogSpec.getCustomField1(),
+ optionalLogSpec.getCustomField2(),
+ optionalLogSpec.getCustomField3(),
+ optionalLogSpec.getCustomField4(),
+ event.getFormattedMessage()
+ };
+
+ return LogUtils.createLogMessageString(auditLogValues);
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/ConsoleLayout.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/ConsoleLayout.java
new file mode 100644
index 0000000..589d863
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/ConsoleLayout.java
@@ -0,0 +1,56 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.layout;
+
+import ch.qos.logback.classic.spi.ILoggingEvent;
+import ch.qos.logback.core.LayoutBase;
+import org.onap.dcae.utils.eelf.logger.logback.utils.LogUtils;
+import org.slf4j.Marker;
+
+/**
+ * Console layout is used to log messages on the console for debugging purposes.
+ *
+ * @author Rajiv Singla
+ */
+public class ConsoleLayout extends LayoutBase<ILoggingEvent> {
+
+ private static final MetricLogLayout METRIC_LOG_LAYOUT = new MetricLogLayout();
+ private static final AuditLogLayout AUDIT_LOG_LAYOUT = new AuditLogLayout();
+ private static final ErrorLogLayout ERROR_LOG_LAYOUT = new ErrorLogLayout();
+ private static final DebugLogLayout DEBUG_LOG_LAYOUT = new DebugLogLayout();
+
+ @Override
+ public String doLayout(final ILoggingEvent event) {
+
+ final Marker eventMarker = event.getMarker();
+
+ if (eventMarker.equals(LogUtils.AUDIT_LOG_MARKER)) {
+ return AUDIT_LOG_LAYOUT.doLayout(event);
+ } else if (eventMarker.equals(LogUtils.METRIC_LOG_MARKER)) {
+ return METRIC_LOG_LAYOUT.doLayout(event);
+ } else if (eventMarker.equals(LogUtils.ERROR_LOG_MARKER)) {
+ return ERROR_LOG_LAYOUT.doLayout(event);
+ } else if (eventMarker.equals(LogUtils.DEBUG_LOG_MARKER)) {
+ return DEBUG_LOG_LAYOUT.doLayout(event);
+ }
+
+ return "Console Layout not defined for Marker: " + eventMarker;
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/DebugLogLayout.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/DebugLogLayout.java
new file mode 100644
index 0000000..e7b1cd4
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/DebugLogLayout.java
@@ -0,0 +1,54 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.layout;
+
+import ch.qos.logback.classic.spi.ILoggingEvent;
+import ch.qos.logback.core.LayoutBase;
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.spec.DebugLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+import org.onap.dcae.utils.eelf.logger.logback.utils.LogUtils;
+
+
+/**
+ * @author Rajiv Singla
+ */
+public class DebugLogLayout extends LayoutBase<ILoggingEvent> {
+
+ @Override
+ public String doLayout(final ILoggingEvent event) {
+
+ final LogLevelCategory logLevelCategory = LogUtils.getLogLevelCategory();
+ final Class<?> loggerClass = LogUtils.getLoggerClass();
+ final OptionalLogSpec optionalLogSpec = LogUtils.getOptionalLogSpec(loggerClass, logLevelCategory);
+
+ final DebugLogSpec debugLogSpec = LogUtils.getDebugLogSpec();
+
+ final String creationTimestamp = LogUtils.formatDate(optionalLogSpec.getCreationTimestamp());
+
+ final String[] debugLogValues = {
+ creationTimestamp,
+ debugLogSpec.getRequestId(),
+ event.getFormattedMessage()
+ };
+
+ return LogUtils.createLogMessageString(debugLogValues);
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/ErrorLogLayout.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/ErrorLogLayout.java
new file mode 100644
index 0000000..4eefe36
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/ErrorLogLayout.java
@@ -0,0 +1,64 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.layout;
+
+import ch.qos.logback.classic.spi.ILoggingEvent;
+import ch.qos.logback.core.LayoutBase;
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.spec.ErrorLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+import org.onap.dcae.utils.eelf.logger.logback.utils.LogUtils;
+
+
+/**
+ * Error Log Layout generates log messages as per EELF Error Log Specifications
+ *
+ * @author Rajiv Singla
+ */
+public class ErrorLogLayout extends LayoutBase<ILoggingEvent> {
+
+ @Override
+ public String doLayout(final ILoggingEvent event) {
+
+ final LogLevelCategory logLevelCategory = LogUtils.getLogLevelCategory();
+ final Class<?> loggerClass = LogUtils.getLoggerClass();
+ final OptionalLogSpec optionalLogSpec = LogUtils.getOptionalLogSpec(loggerClass, logLevelCategory);
+
+ final ErrorLogSpec errorLogSpec = LogUtils.getErrorLogSpec();
+
+ final String creationTimestamp = LogUtils.formatDate(optionalLogSpec.getCreationTimestamp());
+
+ final String[] errorLogValues = {
+ creationTimestamp,
+ errorLogSpec.getRequestId(),
+ event.getThreadName(),
+ errorLogSpec.getServiceName(),
+ errorLogSpec.getPartnerName(),
+ errorLogSpec.getTargetEntity(),
+ errorLogSpec.getTargetServiceName(),
+ logLevelCategory != null ? logLevelCategory.name() : "",
+ errorLogSpec.getErrorCode() != null ? errorLogSpec.getErrorCode().toString() : "",
+ errorLogSpec.getErrorDescription(),
+ event.getFormattedMessage()
+ };
+
+ return LogUtils.createLogMessageString(errorLogValues);
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/MetricLogLayout.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/MetricLogLayout.java
new file mode 100644
index 0000000..509ff8f
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/layout/MetricLogLayout.java
@@ -0,0 +1,83 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.layout;
+
+import ch.qos.logback.classic.spi.ILoggingEvent;
+import ch.qos.logback.core.LayoutBase;
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.spec.AppLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.MetricLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+import org.onap.dcae.utils.eelf.logger.logback.utils.LogUtils;
+
+/**
+ * Metric Log Layout generates log messages as per EELF Metric Log Specifications
+ *
+ * @author Rajiv Singla
+ */
+public class MetricLogLayout extends LayoutBase<ILoggingEvent> {
+
+ @Override
+ public String doLayout(final ILoggingEvent event) {
+
+ final AppLogSpec appLogSpec = LogUtils.getAppLogSpec();
+ final LogLevelCategory logLevelCategory = LogUtils.getLogLevelCategory();
+ final Class<?> loggerClass = LogUtils.getLoggerClass();
+ final OptionalLogSpec optionalLogSpec = LogUtils.getOptionalLogSpec(loggerClass, logLevelCategory);
+ final MetricLogSpec metricLogSpec = LogUtils.getMetricLogSpec();
+
+ final String beginTimestamp = LogUtils.formatDate(metricLogSpec.getBeginTimestamp());
+ final String endTimestamp = LogUtils.formatDate(metricLogSpec.getEndTimestamp());
+
+ final String[] metricLogValues = {
+ beginTimestamp,
+ endTimestamp,
+ metricLogSpec.getRequestId(),
+ appLogSpec.getServiceInstanceID(),
+ event.getThreadName(),
+ appLogSpec.getVirtualServerName(),
+ metricLogSpec.getServiceName(),
+ metricLogSpec.getPartnerName(),
+ metricLogSpec.getTargetEntity(),
+ metricLogSpec.getTargetServiceName(),
+ optionalLogSpec.getStatusCode().name(),
+ metricLogSpec.getResponseCode().toString(),
+ metricLogSpec.getResponseDescription(),
+ appLogSpec.getInstanceUUID(),
+ logLevelCategory != null ? logLevelCategory.name() : "",
+ optionalLogSpec.getAlertSeverity().getSeverityCode(),
+ appLogSpec.getServerIPAddress(),
+ metricLogSpec.getElapsedTime().toString(),
+ appLogSpec.getServerFQDN(),
+ metricLogSpec.getClientIPAddress(),
+ optionalLogSpec.getClassName(),
+ optionalLogSpec.getUnused(),
+ optionalLogSpec.getProcessId(),
+ metricLogSpec.getTargetVirtualEntity(),
+ optionalLogSpec.getCustomField1(),
+ optionalLogSpec.getCustomField2(),
+ optionalLogSpec.getCustomField3(),
+ optionalLogSpec.getCustomField4(),
+ event.getFormattedMessage()
+ };
+
+ return LogUtils.createLogMessageString(metricLogValues);
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/listener/LogbackStartupListener.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/listener/LogbackStartupListener.java
new file mode 100644
index 0000000..b02c471
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/listener/LogbackStartupListener.java
@@ -0,0 +1,128 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.listener;
+
+import ch.qos.logback.classic.Level;
+import ch.qos.logback.classic.Logger;
+import ch.qos.logback.classic.LoggerContext;
+import ch.qos.logback.classic.spi.LoggerContextListener;
+import ch.qos.logback.core.Context;
+import ch.qos.logback.core.spi.ContextAwareBase;
+import ch.qos.logback.core.spi.LifeCycle;
+import ch.qos.logback.core.status.InfoStatus;
+import ch.qos.logback.core.status.WarnStatus;
+import org.onap.dcae.utils.eelf.logger.api.info.AppLogInfo;
+import org.onap.dcae.utils.eelf.logger.model.spec.AppLogSpecImpl;
+
+
+import java.io.File;
+
+import static org.onap.dcae.utils.eelf.logger.logback.EELFLoggerDefaults.DEFAULT_APP_LOG_INFO;
+import static org.onap.dcae.utils.eelf.logger.logback.utils.LogUtils.APP_LOG_SPEC_KEY;
+import static org.onap.dcae.utils.eelf.logger.logback.utils.LogUtils.CUSTOM_MDC_MAP;
+
+
+/**
+ * Logback Startup Listener is used to inject {@link AppLogInfo}
+ *
+ * @author Rajiv Singla
+ */
+public class LogbackStartupListener extends ContextAwareBase implements LoggerContextListener, LifeCycle {
+
+ private static final String APP_LOG_INFO_KEY_IN_CONTEXT = "APP_LOG_INFO";
+ private static final String CONTEXT_COMPONENT_NAME_PROPERTY_KEY = "componentName";
+ private static final String CONTEXT_MODIFY_WINDOWS_LOG_PATH_PROPERTY_KEY = "modifyLogPathInWindows";
+ private static final String CONTEXT_LOG_DIRECTORY_PROPERTY_KEY = "logDirectory";
+ private static final String CONTEXT_DEBUG_LOG_DIRECTORY_PROPERTY_KEY = "debugLogDirectory";
+ private static final String CONTEXT_APPEND_DIRECTORY_PROPERTY_KEY = "appendDirectory";
+
+ private boolean started = false;
+
+ @Override
+ public boolean isResetResistant() {
+ return true;
+ }
+
+ @Override
+ public void onStart(final LoggerContext context) {
+
+ }
+
+ @Override
+ public void onReset(final LoggerContext context) {
+
+ }
+
+ @Override
+ public void onStop(final LoggerContext context) {
+
+ }
+
+ @Override
+ public void onLevelChange(final Logger logger, final Level level) {
+
+ }
+
+ @Override
+ public void start() {
+ if (started) {
+ return;
+ }
+
+ Context context = getContext();
+
+ CUSTOM_MDC_MAP.put(APP_LOG_SPEC_KEY, new AppLogSpecImpl(DEFAULT_APP_LOG_INFO));
+ context.putObject(APP_LOG_INFO_KEY_IN_CONTEXT, DEFAULT_APP_LOG_INFO);
+ context.getStatusManager().add(new InfoStatus("Initialized APP LOG INFO", DEFAULT_APP_LOG_INFO));
+
+ // if Component name is not set derive from jar file name
+ if (context.getProperty(CONTEXT_COMPONENT_NAME_PROPERTY_KEY) == null) {
+ final String appName =
+ new File(getClass().getProtectionDomain().getCodeSource().getLocation().getPath()).getName();
+ context.putProperty(CONTEXT_COMPONENT_NAME_PROPERTY_KEY, appName);
+ context.getStatusManager().add(new WarnStatus(
+ "No componentName Property found. Deriving it from jar name", appName));
+ }
+
+ // if modify windows log path is enabled - then append target before log directories
+ if (context.getProperty(CONTEXT_MODIFY_WINDOWS_LOG_PATH_PROPERTY_KEY).equalsIgnoreCase("true")) {
+ final String os = System.getProperty("os.name");
+ if (os != null && os.startsWith("Windows")) {
+ final String logDirectory = context.getProperty(CONTEXT_LOG_DIRECTORY_PROPERTY_KEY);
+ final String debugLogDirectory = context.getProperty(CONTEXT_DEBUG_LOG_DIRECTORY_PROPERTY_KEY);
+ final String appendDir = context.getProperty(CONTEXT_APPEND_DIRECTORY_PROPERTY_KEY);
+ context.putProperty(CONTEXT_LOG_DIRECTORY_PROPERTY_KEY, appendDir + "/" + logDirectory);
+ context.putProperty(CONTEXT_DEBUG_LOG_DIRECTORY_PROPERTY_KEY, appendDir + "/" + debugLogDirectory);
+ }
+ }
+
+ started = true;
+ }
+
+ @Override
+ public void stop() {
+
+ }
+
+ @Override
+ public boolean isStarted() {
+ return started;
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/AuditLogImpl.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/AuditLogImpl.java
new file mode 100644
index 0000000..947b4c2
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/AuditLogImpl.java
@@ -0,0 +1,119 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.log;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.log.AuditLog;
+import org.onap.dcae.utils.eelf.logger.api.spec.AuditLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+import org.onap.dcae.utils.eelf.logger.logback.utils.LogUtils;
+import org.slf4j.Logger;
+
+
+/**
+ * Audit Log Logback Implementation
+ *
+ * @author Rajiv Singla
+ */
+public class AuditLogImpl implements AuditLog {
+
+ private final Logger logger;
+ private final Class<?> clazz;
+
+ public AuditLogImpl(final Logger logger, final Class<?> clazz) {
+ this.logger = logger;
+ this.clazz = clazz;
+ }
+
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final AuditLogSpec
+ auditLogSpec, final OptionalLogSpec optionalLogSpec, final String... args) {
+ // if audit log spec or log level category is null throw an exception
+ if (auditLogSpec == null || logLevelCategory == null) {
+ throw new IllegalArgumentException("Audit Log Spec and Log level category must not be null");
+ }
+ // required fields
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.LOG_LEVEL_CATEGORY_KEY, logLevelCategory);
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.AUDIT_LOG_SPEC_KEY, auditLogSpec);
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.LOGGER_CLASS_KEY, clazz);
+ // optional fields
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.OPTIONAL_LOG_SPEC_KEY, optionalLogSpec);
+
+ // log with normalized log level category
+ LogUtils.logWithLogLevel(logLevelCategory, logger, LogUtils.AUDIT_LOG_MARKER, message, args);
+
+ // clean up
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.LOG_LEVEL_CATEGORY_KEY);
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.AUDIT_LOG_SPEC_KEY);
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.LOGGER_CLASS_KEY);
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.OPTIONAL_LOG_SPEC_KEY);
+ }
+
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final AuditLogSpec auditLogSpec,
+ final String... args) {
+ log(logLevelCategory, message, auditLogSpec, null, args);
+ }
+
+ @Override
+ public void info(final String message, final AuditLogSpec auditLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ log(LogLevelCategory.INFO, message, auditLogSpec, optionalLogSpec, args);
+ }
+
+ @Override
+ public void info(final String message, final AuditLogSpec auditLogSpec, final String... args) {
+ info(message, auditLogSpec, null, args);
+ }
+
+ @Override
+ public void warn(final String message, final AuditLogSpec auditLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ log(LogLevelCategory.WARN, message, auditLogSpec, optionalLogSpec, args);
+ }
+
+ @Override
+ public void warn(final String message, final AuditLogSpec auditLogSpec, final String... args) {
+ warn(message, auditLogSpec, null, args);
+ }
+
+ @Override
+ public void error(final String message, final AuditLogSpec auditLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ log(LogLevelCategory.ERROR, message, auditLogSpec, optionalLogSpec, args);
+ }
+
+ @Override
+ public void error(final String message, final AuditLogSpec auditLogSpec, final String... args) {
+ error(message, auditLogSpec, null, args);
+ }
+
+ @Override
+ public void fatal(final String message, final AuditLogSpec auditLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ log(LogLevelCategory.FATAL, message, auditLogSpec, optionalLogSpec, args);
+ }
+
+ @Override
+ public void fatal(final String message, final AuditLogSpec auditLogSpec, final String... args) {
+ fatal(message, auditLogSpec, null, args);
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/DebugLogImpl.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/DebugLogImpl.java
new file mode 100644
index 0000000..1e17f3b
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/DebugLogImpl.java
@@ -0,0 +1,88 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.log;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.log.DebugLog;
+import org.onap.dcae.utils.eelf.logger.api.spec.DebugLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+import org.onap.dcae.utils.eelf.logger.logback.utils.LogUtils;
+import org.slf4j.Logger;
+
+
+/**
+ * Debug Log Logback Implementation
+ *
+ * @author Rajiv Singla
+ */
+public class DebugLogImpl implements DebugLog {
+
+ private final Logger logger;
+ private final Class<?> clazz;
+
+ public DebugLogImpl(final Logger logger, final Class<?> clazz) {
+ this.logger = logger;
+ this.clazz = clazz;
+ }
+
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final DebugLogSpec debugLogSpec,
+ final OptionalLogSpec optionalLogSpec, final String... args) {
+
+ // if log level category is null throw an exception
+ if (logLevelCategory == null) {
+ throw new IllegalArgumentException("Log level category must not be null");
+ }
+
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.LOG_LEVEL_CATEGORY_KEY, logLevelCategory);
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.DEBUG_LOG_SPEC_KEY, debugLogSpec);
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.LOGGER_CLASS_KEY, clazz);
+ // optional fields
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.OPTIONAL_LOG_SPEC_KEY, optionalLogSpec);
+
+ // log with normalized log level category
+ LogUtils.logWithLogLevel(logLevelCategory, logger, LogUtils.DEBUG_LOG_MARKER, message, args);
+
+ // clean up
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.LOG_LEVEL_CATEGORY_KEY);
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.DEBUG_LOG_SPEC_KEY);
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.LOGGER_CLASS_KEY);
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.OPTIONAL_LOG_SPEC_KEY);
+
+ }
+
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final DebugLogSpec debugLogSpec,
+ final String... args) {
+ log(logLevelCategory, message, debugLogSpec, null, args);
+ }
+
+ @Override
+ public void debug(final String message, final DebugLogSpec debugLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ log(LogLevelCategory.DEBUG, message, debugLogSpec, optionalLogSpec, args);
+ }
+
+ @Override
+ public void debug(final String message, final DebugLogSpec debugLogSpec, final String... args) {
+ debug(message, debugLogSpec, null, args);
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/EELFLoggerContextImpl.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/EELFLoggerContextImpl.java
new file mode 100644
index 0000000..e5be1d8
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/EELFLoggerContextImpl.java
@@ -0,0 +1,57 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.log;
+
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLoggerContext;
+import org.onap.dcae.utils.eelf.logger.api.spec.AppLogSpec;
+import org.onap.dcae.utils.eelf.logger.model.spec.AppLogSpecImpl;
+
+import static org.onap.dcae.utils.eelf.logger.logback.EELFLoggerDefaults.DEFAULT_APP_LOG_INFO;
+import static org.onap.dcae.utils.eelf.logger.logback.utils.LogUtils.APP_LOG_SPEC_KEY;
+import static org.onap.dcae.utils.eelf.logger.logback.utils.LogUtils.CUSTOM_MDC_MAP;
+
+
+/**
+ * Default EELF Logger Context which contains EELF Specs which are usually constant for entire life cycle of the
+ * application
+ *
+ * @author Rajiv Singla
+ */
+public class EELFLoggerContextImpl implements EELFLoggerContext {
+
+ @Override
+ public AppLogSpec getAppLogSpec() {
+ return CUSTOM_MDC_MAP.get(APP_LOG_SPEC_KEY) == null ? null : (AppLogSpec) CUSTOM_MDC_MAP.get(APP_LOG_SPEC_KEY);
+ }
+
+ @Override
+ public void setAppLogSpec(final AppLogSpec appLogSpec) {
+ if (appLogSpec == null) {
+ CUSTOM_MDC_MAP.put(APP_LOG_SPEC_KEY, new AppLogSpecImpl(DEFAULT_APP_LOG_INFO));
+ } else {
+ CUSTOM_MDC_MAP.put(APP_LOG_SPEC_KEY, appLogSpec);
+ }
+ }
+
+ @Override
+ public boolean isInitialized() {
+ return CUSTOM_MDC_MAP.get(APP_LOG_SPEC_KEY) == null;
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/EELFLoggerImpl.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/EELFLoggerImpl.java
new file mode 100644
index 0000000..3f1e716
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/EELFLoggerImpl.java
@@ -0,0 +1,81 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.log;
+
+
+import org.onap.dcae.utils.eelf.logger.api.log.AuditLog;
+import org.onap.dcae.utils.eelf.logger.api.log.DebugLog;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLogger;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLoggerContext;
+import org.onap.dcae.utils.eelf.logger.api.log.ErrorLog;
+import org.onap.dcae.utils.eelf.logger.api.log.MetricLog;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * EELF Logger Logback Implementation
+ *
+ * @author Rajiv Singla
+ */
+public class EELFLoggerImpl implements EELFLogger {
+
+ private Logger logger;
+ private Class<?> clazz;
+
+ public EELFLoggerImpl() {
+ // no arg constructor required for Service Loader discovery
+ }
+
+ public EELFLoggerImpl(final Class<?> clazz) {
+ logger = LoggerFactory.getLogger(clazz);
+ this.clazz = clazz;
+ }
+
+
+ @Override
+ public AuditLog auditLog() {
+ return new AuditLogImpl(logger, clazz);
+ }
+
+ @Override
+ public MetricLog metricLog() {
+ return new MetricLogImpl(logger, clazz);
+ }
+
+ @Override
+ public ErrorLog errorLog() {
+ return new ErrorLogImpl(logger, clazz);
+ }
+
+ @Override
+ public DebugLog debugLog() {
+ return new DebugLogImpl(logger, clazz);
+ }
+
+ @Override
+ public EELFLoggerContext loggingContext() {
+ return new EELFLoggerContextImpl();
+ }
+
+ @Override
+ public String toString() {
+ return "EELF LOGBACK IMP";
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/ErrorLogImpl.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/ErrorLogImpl.java
new file mode 100644
index 0000000..5d8f272
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/ErrorLogImpl.java
@@ -0,0 +1,98 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.log;
+
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.log.ErrorLog;
+import org.onap.dcae.utils.eelf.logger.api.spec.ErrorLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+import org.onap.dcae.utils.eelf.logger.logback.utils.LogUtils;
+import org.slf4j.Logger;
+
+
+/**
+ * Error Log Logback Implementation
+ *
+ * @author Rajiv Singla
+ */
+public class ErrorLogImpl implements ErrorLog {
+
+ private final Logger logger;
+ private final Class<?> clazz;
+
+ public ErrorLogImpl(final Logger logger, final Class<?> clazz) {
+ this.logger = logger;
+ this.clazz = clazz;
+ }
+
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final ErrorLogSpec errorLogSpec,
+ final OptionalLogSpec optionalLogSpec, final String... args) {
+
+ // if error log spec or log level category is null throw an exception
+ if (errorLogSpec == null || logLevelCategory == null) {
+ throw new IllegalArgumentException("Error Log Spec and Log level category must not be null");
+ }
+
+ // required fields
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.LOG_LEVEL_CATEGORY_KEY, logLevelCategory);
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.ERROR_LOG_SPEC_KEY, errorLogSpec);
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.LOGGER_CLASS_KEY, clazz);
+ // optional fields
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.OPTIONAL_LOG_SPEC_KEY, optionalLogSpec);
+
+ // log with normalized log level category
+ LogUtils.logWithLogLevel(logLevelCategory, logger, LogUtils.ERROR_LOG_MARKER, message, args);
+
+ // clean up
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.LOG_LEVEL_CATEGORY_KEY);
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.ERROR_LOG_SPEC_KEY);
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.LOGGER_CLASS_KEY);
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.OPTIONAL_LOG_SPEC_KEY);
+ }
+
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final ErrorLogSpec errorLogSpec,
+ final String... args) {
+ log(logLevelCategory, message, errorLogSpec, null, args);
+ }
+
+ @Override
+ public void error(final String message, final ErrorLogSpec errorLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ log(LogLevelCategory.ERROR, message, errorLogSpec, null, args);
+ }
+
+ @Override
+ public void error(final String message, final ErrorLogSpec errorLogSpec, final String... args) {
+ error(message, errorLogSpec, null, args);
+ }
+
+ @Override
+ public void warn(final String message, final ErrorLogSpec errorLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ log(LogLevelCategory.WARN, message, errorLogSpec, null, args);
+ }
+
+ @Override
+ public void warn(final String message, final ErrorLogSpec errorLogSpec, final String... args) {
+ warn(message, errorLogSpec, null, args);
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/MetricLogImpl.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/MetricLogImpl.java
new file mode 100644
index 0000000..5857835
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/log/MetricLogImpl.java
@@ -0,0 +1,120 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.log;
+
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.log.MetricLog;
+import org.onap.dcae.utils.eelf.logger.api.spec.MetricLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+import org.onap.dcae.utils.eelf.logger.logback.utils.LogUtils;
+import org.slf4j.Logger;
+
+/**
+ * Metric Log Logback Implementation
+ *
+ * @author Rajiv Singla
+ */
+public class MetricLogImpl implements MetricLog {
+
+ private final Logger logger;
+ private final Class<?> clazz;
+
+ public MetricLogImpl(final Logger logger, final Class<?> clazz) {
+ this.logger = logger;
+ this.clazz = clazz;
+ }
+
+
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final MetricLogSpec metricLogSpec,
+ final OptionalLogSpec optionalLogSpec, final String... args) {
+
+ // if metric log spec or log level category is null throw an exception
+ if (metricLogSpec == null || logLevelCategory == null) {
+ throw new IllegalArgumentException("Metric Log Spec and Log level category must not be null");
+ }
+
+ // required fields
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.LOG_LEVEL_CATEGORY_KEY, logLevelCategory);
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.METRIC_LOG_SPEC_KEY, metricLogSpec);
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.LOGGER_CLASS_KEY, clazz);
+ // optional fields
+ LogUtils.CUSTOM_MDC_MAP.put(LogUtils.OPTIONAL_LOG_SPEC_KEY, optionalLogSpec);
+
+ // log with normalized log level category
+ LogUtils.logWithLogLevel(logLevelCategory, logger, LogUtils.METRIC_LOG_MARKER, message, args);
+
+ // clean up
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.LOG_LEVEL_CATEGORY_KEY);
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.METRIC_LOG_SPEC_KEY);
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.LOGGER_CLASS_KEY);
+ LogUtils.CUSTOM_MDC_MAP.remove(LogUtils.OPTIONAL_LOG_SPEC_KEY);
+ }
+
+ @Override
+ public void log(final LogLevelCategory logLevelCategory, final String message, final MetricLogSpec metricLogSpec,
+ final String... args) {
+ log(logLevelCategory, message, metricLogSpec, null, args);
+ }
+
+ @Override
+ public void info(final String message, final MetricLogSpec metricLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ log(LogLevelCategory.INFO, message, metricLogSpec, optionalLogSpec, args);
+ }
+
+ @Override
+ public void info(final String message, final MetricLogSpec metricLogSpec, final String... args) {
+ log(LogLevelCategory.INFO, message, metricLogSpec, args);
+ }
+
+ @Override
+ public void warn(final String message, final MetricLogSpec metricLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ log(LogLevelCategory.WARN, message, metricLogSpec, optionalLogSpec, args);
+ }
+
+ @Override
+ public void warn(final String message, final MetricLogSpec metricLogSpec, final String... args) {
+ warn(message, metricLogSpec, null, args);
+ }
+
+ @Override
+ public void error(final String message, final MetricLogSpec metricLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ log(LogLevelCategory.ERROR, message, metricLogSpec, optionalLogSpec, args);
+ }
+
+ @Override
+ public void error(final String message, final MetricLogSpec metricLogSpec, final String... args) {
+ error(message, metricLogSpec, null, args);
+ }
+
+ @Override
+ public void fatal(final String message, final MetricLogSpec metricLogSpec, final OptionalLogSpec optionalLogSpec,
+ final String... args) {
+ log(LogLevelCategory.FATAL, message, metricLogSpec, optionalLogSpec, args);
+ }
+
+ @Override
+ public void fatal(final String message, final MetricLogSpec metricLogSpec, final String... args) {
+ fatal(message, metricLogSpec, null, args);
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/CompositePropertyResolver.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/CompositePropertyResolver.java
new file mode 100644
index 0000000..e5f1bc1
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/CompositePropertyResolver.java
@@ -0,0 +1,53 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.resolver;
+
+import java.util.Arrays;
+import java.util.List;
+
+/**
+ * A composite property resolver can look under different resolvers in order of given property resolvers
+ *
+ * @author Rajiv Singla
+ */
+public class CompositePropertyResolver implements PropertyResolver {
+
+ private static final long serialVersionUID = 1L;
+
+ private final List<PropertyResolver> propertyResolvers;
+
+ public CompositePropertyResolver(PropertyResolver... propertyResolvers) {
+ this.propertyResolvers = Arrays.asList(propertyResolvers);
+ }
+
+ @Override
+ public String resolve(final List<String> propertyNames) {
+ // resolver property in given resolvers in the same order they are defined
+ for (PropertyResolver propertyResolver : propertyResolvers) {
+ final String propertyValue = propertyResolver.resolve(propertyNames);
+ if (propertyValue != null) {
+ return propertyValue;
+ }
+ }
+
+ return null;
+ }
+
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/EnvironmentPropertyResolver.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/EnvironmentPropertyResolver.java
new file mode 100644
index 0000000..8f3d59f
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/EnvironmentPropertyResolver.java
@@ -0,0 +1,46 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.resolver;
+
+import java.util.List;
+
+/**
+ * Looks up Property values inside HOST environment variables
+ *
+ * @author Rajiv Singla
+ */
+public class EnvironmentPropertyResolver implements PropertyResolver {
+
+ private static final long serialVersionUID = 1L;
+
+ @Override
+ public String resolve(final List<String> propertyNames) {
+
+ // check if system environment variables have property names set
+ for (final String propertyName : propertyNames) {
+ final String propertyValue = System.getenv(propertyName);
+ if (propertyValue != null) {
+ return propertyValue;
+ }
+ }
+
+ return null;
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/PropertyResolver.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/PropertyResolver.java
new file mode 100644
index 0000000..758de61
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/PropertyResolver.java
@@ -0,0 +1,41 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.resolver;
+
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * A resolver is used to resolve properties
+ *
+ * @author Rajiv Singla
+ */
+public interface PropertyResolver extends Serializable {
+
+ /**
+ * Returns resolved property value
+ *
+ * @param propertyNames names under which property can be found
+ *
+ * @return property value
+ */
+ String resolve(List<String> propertyNames);
+
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/SystemPropertyResolver.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/SystemPropertyResolver.java
new file mode 100644
index 0000000..674b00b
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/resolver/SystemPropertyResolver.java
@@ -0,0 +1,59 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.resolver;
+
+import java.util.List;
+import java.util.Map;
+import java.util.Properties;
+
+/**
+ * Resolve System Properties passed in by -DpropertyName=propertyValue when invoking
+ * via java command line arguments
+ *
+ * @author Rajiv Singla
+ */
+public class SystemPropertyResolver implements PropertyResolver {
+
+ private static final long serialVersionUID = 1L;
+
+ @Override
+ public String resolve(final List<String> propertyNames) {
+
+ // Get all system Properties
+ final Properties systemProperties = System.getProperties();
+
+ for (Map.Entry<Object, Object> systemEntries : systemProperties.entrySet()) {
+
+ if (systemEntries.getKey() instanceof String) {
+ final String systemKey = (String) systemEntries.getKey();
+
+ // if system properties contain any of the property names - ignoring case then return its value
+ for (String propertyName : propertyNames) {
+ if (propertyName.equalsIgnoreCase(systemKey)) {
+ return (String) systemEntries.getValue();
+ }
+ }
+
+ }
+ }
+
+ return null;
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/utils/LogUtils.java b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/utils/LogUtils.java
new file mode 100644
index 0000000..f5c558b
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/java/org/onap/dcae/utils/eelf/logger/logback/utils/LogUtils.java
@@ -0,0 +1,590 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.utils;
+
+import ch.qos.logback.core.CoreConstants;
+import org.onap.dcae.utils.eelf.logger.api.info.AppLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.LogLevelCategory;
+import org.onap.dcae.utils.eelf.logger.api.info.NagiosAlertLevel;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestIdLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestStatusCode;
+import org.onap.dcae.utils.eelf.logger.api.spec.AppLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.AuditLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.DebugLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.ErrorLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.MetricLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+import org.onap.dcae.utils.eelf.logger.logback.EELFLoggerDefaults;
+import org.onap.dcae.utils.eelf.logger.logback.resolver.CompositePropertyResolver;
+import org.onap.dcae.utils.eelf.logger.logback.resolver.EnvironmentPropertyResolver;
+import org.onap.dcae.utils.eelf.logger.logback.resolver.SystemPropertyResolver;
+import org.onap.dcae.utils.eelf.logger.model.info.AppLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.CodeLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.MessageLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.RequestIdLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.RequestTimingLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.AppLogSpecImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.AuditLogSpecImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.DebugLogSpecImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.ErrorLogSpecImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.MetricLogSpecImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.OptionalLogSpecImpl;
+import org.slf4j.Logger;
+import org.slf4j.Marker;
+import org.slf4j.MarkerFactory;
+
+import java.net.InetAddress;
+import java.net.UnknownHostException;
+import java.text.SimpleDateFormat;
+import java.util.Arrays;
+import java.util.Date;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.TimeZone;
+import java.util.UUID;
+
+
+
+/**
+ * Contains various logging utility methods
+ *
+ * @author Rajiv Singla
+ */
+public abstract class LogUtils {
+
+ private static final String LOG_MESSAGE_DELIMITER = "|";
+ private static final String DATE_FORMAT = "yyyy-MM-dd'T'HH:mm:ss.SSSZ";
+ private static final String DATE_TIMEZONE = "UTC";
+ // property resolver which looks up system property and the environment properties
+ private static final CompositePropertyResolver COMPOSITE_PROPERTY_RESOLVER =
+ new CompositePropertyResolver(new SystemPropertyResolver(), new EnvironmentPropertyResolver());
+
+ // Custom MDC Map Keys
+ public static final String APP_LOG_SPEC_KEY = "APP_LOG_SPEC";
+ public static final String AUDIT_LOG_SPEC_KEY = "AUDIT_LOG_SPEC";
+ public static final String METRIC_LOG_SPEC_KEY = "METRIC_LOG_SPEC";
+ public static final String ERROR_LOG_SPEC_KEY = "ERROR_LOG_SPEC";
+ public static final String DEBUG_LOG_SPEC_KEY = "DEBUG_LOG_SPEC";
+ public static final String OPTIONAL_LOG_SPEC_KEY = "OPTIONAL_LOG_SPEC";
+ public static final String LOG_LEVEL_CATEGORY_KEY = "LOG_LEVEL_CATEGORY";
+ public static final String LOGGER_CLASS_KEY = "LOGGER_CLASS_KEY";
+
+ // markers
+ public static final Marker AUDIT_LOG_MARKER = MarkerFactory.getMarker("AUDIT_LOG");
+ public static final Marker METRIC_LOG_MARKER = MarkerFactory.getMarker("METRIC_LOG");
+ public static final Marker ERROR_LOG_MARKER = MarkerFactory.getMarker("ERROR_LOG");
+ public static final Marker DEBUG_LOG_MARKER = MarkerFactory.getMarker("DEBUG_LOG");
+
+
+ public static final Map<String, Object> CUSTOM_MDC_MAP = new ThreadLocal<Map<String, Object>>() {
+ @Override
+ protected Map<String, Object> initialValue() {
+ return new HashMap<>();
+ }
+ }.get();
+
+ public static final ThreadLocal<SimpleDateFormat> SIMPLE_DATE_FORMAT = new ThreadLocal<SimpleDateFormat>() {
+ @Override
+ protected SimpleDateFormat initialValue() {
+ final SimpleDateFormat simpleDateFormat = new SimpleDateFormat(DATE_FORMAT);
+ simpleDateFormat.setTimeZone(TimeZone.getTimeZone(DATE_TIMEZONE));
+ return simpleDateFormat;
+ }
+ };
+
+
+ private LogUtils() {
+ // private constructor
+ }
+
+
+ /**
+ * Logs eomp message with normalized log level category
+ *
+ * @param logLevelCategory ecomp log level category
+ * @param logger logback logger
+ * @param marker logback marker
+ * @param message log message
+ * @param args log message arguments for interpolation
+ */
+ public static void logWithLogLevel(final LogLevelCategory logLevelCategory,
+ final Logger logger, final Marker marker,
+ final String message, final String... args) {
+ switch (logLevelCategory) {
+ case DEBUG:
+ logger.debug(marker, message, args);
+ break;
+ case INFO:
+ logger.info(marker, message, args);
+ break;
+ case WARN:
+ logger.warn(marker, message, args);
+ break;
+ default:
+ // fatal log level is treated as error also as logback does not have fatal level
+ logger.error(marker, message, args);
+ }
+ }
+
+
+ /**
+ * Returns value for {@link AppLogSpec}. If no {@link AppLogSpec} is defined a default app log spec is passed
+ *
+ * @return app log spec
+ */
+ public static AppLogSpec getAppLogSpec() {
+ final AppLogSpec appLogSpec = getCustomMapValue(APP_LOG_SPEC_KEY, AppLogSpec.class);
+ return appLogSpec == null ? new AppLogSpecImpl(EELFLoggerDefaults.DEFAULT_APP_LOG_INFO) : appLogSpec;
+ }
+
+ /**
+ * Populate default values of {@link OptionalLogSpec} if not present
+ *
+ * @param loggerClass logger class
+ * @param logLevelCategory log level category
+ *
+ * @return optional log spec with default values if not present
+ */
+ public static OptionalLogSpec getOptionalLogSpec(final Class<?> loggerClass, final LogLevelCategory
+ logLevelCategory) {
+
+ OptionalLogSpecImpl optionalLogSpec =
+ getCustomMapValue(OPTIONAL_LOG_SPEC_KEY, OptionalLogSpecImpl.class);
+
+ if (optionalLogSpec != null) {
+ // if message log info is empty populate default values
+ if (optionalLogSpec.getMessageLogInfo() == null ||
+ optionalLogSpec.getCreationTimestamp() == null && optionalLogSpec.getAlertSeverity() == null &&
+ optionalLogSpec.getStatusCode() == null) {
+ optionalLogSpec = optionalLogSpec.withMessageLogInfo(createDefaultMessageLogInfo(logLevelCategory));
+ }
+ // if code log info is empty populate default values
+ if (optionalLogSpec.getCodeLogInfo() == null ||
+ optionalLogSpec.getClassName() == null && optionalLogSpec.getThreadId() == null) {
+ optionalLogSpec = optionalLogSpec.withCodeLogInfo(createDefaultCodeLogInfo(loggerClass));
+ }
+ // if custom fields log info is empty populate default values
+ if (optionalLogSpec.getCustomFieldsLogInfo() == null) {
+ optionalLogSpec =
+ optionalLogSpec.withCustomFieldsLogInfo(EELFLoggerDefaults.DEFAULT_CUSTOM_FIELDS_LOG_INFO);
+ }
+ // if misc fields log info is empty populate default values
+ if (optionalLogSpec.getMiscLogInfo() == null) {
+ optionalLogSpec = optionalLogSpec.withMiscLogInfo(EELFLoggerDefaults.DEFAULT_MISC_LOG_INFO);
+ }
+ } else {
+ // optional log spec is null so create new optional log spec
+ optionalLogSpec = createDefaultOptionalLogSpec(loggerClass, logLevelCategory);
+ }
+
+ return optionalLogSpec;
+ }
+
+
+ /**
+ * Formats given date in ISO 8601 format
+ *
+ * @param date Date object
+ *
+ * @return formatted date string
+ */
+ public static String formatDate(final Date date) {
+ if (date == null) {
+ return "";
+ }
+ return SIMPLE_DATE_FORMAT.get().format(date);
+ }
+
+ /**
+ * Creates log message string
+ *
+ * @param logValues log message values
+ *
+ * @return log message string
+ */
+ public static String createLogMessageString(final String[] logValues) {
+ final StringBuffer stringBuffer = new StringBuffer(512);
+ for (int i = 0; i < logValues.length; i++) {
+ final String logValue = logValues[i];
+ stringBuffer.append(logValue != null ? logValue : "");
+ if (i != logValues.length - 1) {
+ stringBuffer.append(LOG_MESSAGE_DELIMITER);
+ }
+ }
+ stringBuffer.append(CoreConstants.LINE_SEPARATOR);
+ return stringBuffer.toString();
+ }
+
+ /**
+ * Gets custom MDC value from Custom MDC Map for give key. Returns null if no value can be found
+ *
+ * @param key MDC Map key
+ * @param clazz expected value class type
+ * @param <T> class type
+ *
+ * @return value inside Custom MDC Map
+ */
+ private static <T> T getCustomMapValue(final String key, final Class<T> clazz) {
+ final Object value = CUSTOM_MDC_MAP.get(key);
+ if (value != null) {
+ return clazz.cast(value);
+ }
+ return null;
+ }
+
+
+ /**
+ * Get current Metric log spec from the custom MDC map and populates default values if not present
+ *
+ * @return Metric log spec
+ */
+ public static MetricLogSpec getMetricLogSpec() {
+ MetricLogSpecImpl metricLogSpec = getCustomMapValue(METRIC_LOG_SPEC_KEY, MetricLogSpecImpl.class);
+
+ if (metricLogSpec != null) {
+ if (metricLogSpec.getRequestIdLogInfo() == null || metricLogSpec.getRequestId() == null) {
+ metricLogSpec = metricLogSpec.withRequestIdLogInfo(createNewRequestIdLogInfo());
+ }
+ if (metricLogSpec.getServiceLogInfo() == null) {
+ metricLogSpec = metricLogSpec.withServiceLogInfo(EELFLoggerDefaults.DEFAULT_SERVICE_LOG_INFO);
+ }
+ if (metricLogSpec.getRequestTimingLogInfo() == null || metricLogSpec.getBeginTimestamp() == null ||
+ metricLogSpec.getEndTimestamp() == null) {
+ metricLogSpec =
+ metricLogSpec.withRequestTimingLogInfo(EELFLoggerDefaults.DEFAULT_REQUEST_TIMING_LOG_INFO);
+ }
+ if (metricLogSpec.getResponseLogInfo() == null) {
+ metricLogSpec = metricLogSpec.withResponseLogInfo(EELFLoggerDefaults.DEFAULT_RESPONSE_LOG_INFO);
+ }
+ final Date beginTimestamp = metricLogSpec.getBeginTimestamp();
+ final Date endTimestamp = metricLogSpec.getEndTimestamp();
+ final Long elapsedTime = metricLogSpec.getElapsedTime();
+ if (endTimestamp != null && beginTimestamp != null && elapsedTime == null) {
+ final RequestTimingLogInfoImpl requestTimingLogInfo =
+ new RequestTimingLogInfoImpl(beginTimestamp, endTimestamp,
+ endTimestamp.getTime() - beginTimestamp.getTime());
+ metricLogSpec = metricLogSpec.withRequestTimingLogInfo(requestTimingLogInfo);
+ }
+ if (metricLogSpec.getTargetServiceLogInfo() == null) {
+ metricLogSpec =
+ metricLogSpec.withTargetServiceLogInfo(EELFLoggerDefaults.DEFAULT_TARGET_SERVICE_LOG_INFO);
+ }
+ } else {
+ throw new IllegalArgumentException("Metric Log Spec must not be null");
+ }
+
+ return metricLogSpec;
+ }
+
+ /**
+ * Get current Debug log spec from the custom MDC map and populates default values if not present
+ *
+ * @return Debug log spec
+ */
+ public static DebugLogSpec getDebugLogSpec() {
+ final DebugLogSpecImpl debugLogSpec = getCustomMapValue(DEBUG_LOG_SPEC_KEY, DebugLogSpecImpl.class);
+ if (debugLogSpec == null || debugLogSpec.getRequestIdLogInfo() == null || debugLogSpec.getRequestId() == null) {
+ return new DebugLogSpecImpl(createNewRequestIdLogInfo());
+ }
+ return debugLogSpec;
+ }
+
+ /**
+ * Get current Error log spec from the custom MDC map and populates default values if not present
+ *
+ * @return Error log spec
+ */
+ public static ErrorLogSpec getErrorLogSpec() {
+ ErrorLogSpecImpl errorLogSpec = getCustomMapValue(ERROR_LOG_SPEC_KEY, ErrorLogSpecImpl.class);
+ if (errorLogSpec != null) {
+
+ if (errorLogSpec.getRequestIdLogInfo() == null || errorLogSpec.getRequestId() == null) {
+ errorLogSpec = errorLogSpec.withRequestIdLogInfo(createNewRequestIdLogInfo());
+ }
+ if (errorLogSpec.getServiceLogInfo() == null) {
+ errorLogSpec = errorLogSpec.withServiceLogInfo(EELFLoggerDefaults.DEFAULT_SERVICE_LOG_INFO);
+ }
+ if (errorLogSpec.getTargetServiceLogInfo() == null) {
+ errorLogSpec =
+ errorLogSpec.withTargetServiceLogInfo(EELFLoggerDefaults.DEFAULT_TARGET_SERVICE_LOG_INFO);
+ }
+ if (errorLogSpec.getErrorLogInfo() == null) {
+ errorLogSpec = errorLogSpec.withErrorLogInfo(EELFLoggerDefaults.DEFAULT_ERROR_LOG_INFO);
+ }
+
+ } else {
+ throw new IllegalArgumentException("Error Log Spec cannot be null");
+ }
+ return errorLogSpec;
+ }
+
+
+ /**
+ * Get current Audit log spec from the custom MDC map and populates default values if not present
+ *
+ * @return Audit log spec
+ */
+ public static AuditLogSpec getAuditLogSpec() {
+ AuditLogSpecImpl auditLogSpec = getCustomMapValue(AUDIT_LOG_SPEC_KEY, AuditLogSpecImpl.class);
+ if (auditLogSpec != null) {
+ if (auditLogSpec.getServiceLogInfo() == null) {
+ auditLogSpec = auditLogSpec.withServiceLogInfo(EELFLoggerDefaults.DEFAULT_SERVICE_LOG_INFO);
+ }
+ if (auditLogSpec.getRequestIdLogInfo() == null || auditLogSpec.getRequestId() == null) {
+ auditLogSpec = auditLogSpec.withRequestIdLogInfo(createNewRequestIdLogInfo());
+ }
+ if (auditLogSpec.getResponseLogInfo() == null) {
+ auditLogSpec = auditLogSpec.withResponseLogInfo(EELFLoggerDefaults.DEFAULT_RESPONSE_LOG_INFO);
+ }
+
+ if (auditLogSpec.getRequestTimingLogInfo() == null || auditLogSpec.getBeginTimestamp() == null ||
+ auditLogSpec.getEndTimestamp() == null) {
+ auditLogSpec =
+ auditLogSpec.withRequestTimingLogInfo(EELFLoggerDefaults.DEFAULT_REQUEST_TIMING_LOG_INFO);
+ }
+ final Date beginTimestamp = auditLogSpec.getBeginTimestamp();
+ final Date endTimestamp = auditLogSpec.getEndTimestamp();
+ final Long elapsedTime = auditLogSpec.getElapsedTime();
+ if (endTimestamp != null && beginTimestamp != null && elapsedTime == null) {
+ final RequestTimingLogInfoImpl requestTimingLogInfo =
+ new RequestTimingLogInfoImpl(beginTimestamp, endTimestamp,
+ endTimestamp.getTime() - beginTimestamp.getTime());
+ auditLogSpec = auditLogSpec.withRequestTimingLogInfo(requestTimingLogInfo);
+ }
+
+ } else {
+ throw new IllegalArgumentException("Audit Log Spec cannot be null");
+ }
+
+ return auditLogSpec;
+ }
+
+
+ private static RequestIdLogInfo createNewRequestIdLogInfo() {
+ return new RequestIdLogInfoImpl(UUID.randomUUID().toString());
+ }
+
+ /**
+ * Return Log Level Category from MDC Map
+ *
+ * @return log level category
+ */
+ public static Class<?> getLoggerClass() {
+ final Class<?> loggerClass = getCustomMapValue(LOGGER_CLASS_KEY, Class.class);
+ // logger class must always be non null
+ if (loggerClass != null) {
+ return loggerClass;
+ }
+ return LogUtils.class.getClass();
+ }
+
+
+ /**
+ * Return Log Level Category from MDC Map
+ *
+ * @return log level category
+ */
+ public static LogLevelCategory getLogLevelCategory() {
+ final LogLevelCategory logLevelCategory = getCustomMapValue(LOG_LEVEL_CATEGORY_KEY, LogLevelCategory.class);
+ if (logLevelCategory != null) {
+ return logLevelCategory;
+ }
+ return LogLevelCategory.ERROR;
+ }
+
+ /**
+ * Creates Default Optional Log spec
+ *
+ * @param loggerClass logger class name
+ * @param logLevelCategory Log leve category
+ *
+ * @return default optional log spec
+ */
+ private static OptionalLogSpecImpl createDefaultOptionalLogSpec(final Class<?> loggerClass,
+ final LogLevelCategory logLevelCategory) {
+ return new OptionalLogSpecImpl(createDefaultMessageLogInfo(logLevelCategory),
+ createDefaultCodeLogInfo(loggerClass), EELFLoggerDefaults.DEFAULT_CUSTOM_FIELDS_LOG_INFO,
+ EELFLoggerDefaults.DEFAULT_MISC_LOG_INFO);
+ }
+
+
+ /**
+ * Creates Default Code Log Info
+ *
+ * @param loggerClass logger class name
+ *
+ * @return default code log info
+ */
+ private static CodeLogInfoImpl createDefaultCodeLogInfo(final Class<?> loggerClass) {
+ // thread id can be extracted from the framework
+ return new CodeLogInfoImpl(null, loggerClass != null ? loggerClass.getName() : "");
+ }
+
+
+ /**
+ * Creates Default Message Log Info
+ *
+ * @param logLevelCategory Log leve category
+ *
+ * @return default message log info
+ */
+ private static MessageLogInfoImpl createDefaultMessageLogInfo(final LogLevelCategory logLevelCategory) {
+ return new MessageLogInfoImpl(new Date(),
+ getStatusCode(logLevelCategory),
+ getNagiosAlertLevel(logLevelCategory));
+ }
+
+
+ /**
+ * Creates Default App Log Spec
+ *
+ * @return default APP log Spec
+ */
+ public static AppLogInfoImpl createDefaultAppLogInfo() {
+ final String serviceInstanceId =
+ resolveProperty(null, AppLogInfo.Defaults.DEFAULT_SERVICE_INSTANCE_ID,
+ "SERVICE_NAME", "ServiceInstanceId", "SERVICE_INSTANCE_ID");
+ final String instanceUUID =
+ resolveProperty(null, AppLogInfo.Defaults.DEFAULT_INSTANCE_UUID,
+ "InstanceUUID", "INSTANCE_UUID");
+ final String virtualServerName =
+ resolveProperty(null, AppLogInfo.Defaults.DEFAULT_VIRTUAL_SERVER_NAME,
+ "VirtualServerName", "VIRTUAL_SERVER_NAME");
+ final String serverIPAddress = getHostIPAddress() != null ?
+ getHostIPAddress() : AppLogInfo.Defaults.DEFAULT_SERVER_IP_ADDRESS;
+ final String serverFQDN = getHostName() != null ? getHostName() : AppLogInfo.Defaults.DEFAULT_SERVER_FQDN;
+ return new AppLogInfoImpl(serviceInstanceId, instanceUUID, virtualServerName, serverIPAddress, serverFQDN);
+ }
+
+
+ /**
+ * Returns status code based on log level category
+ *
+ * @param logLevelCategory log level category
+ *
+ * @return request status code as string based on log level category
+ */
+ private static RequestStatusCode getStatusCode(final LogLevelCategory logLevelCategory) {
+ if (logLevelCategory == LogLevelCategory.DEBUG || logLevelCategory == LogLevelCategory.INFO ||
+ logLevelCategory == LogLevelCategory.WARN) {
+ return RequestStatusCode.COMPLETE;
+ } else {
+ return RequestStatusCode.ERROR;
+ }
+ }
+
+ /**
+ * Returns nagios Alert level based on log level category
+ *
+ * @param logLevelCategory log level category
+ *
+ * @return nagios alert level
+ */
+ private static NagiosAlertLevel getNagiosAlertLevel(final LogLevelCategory logLevelCategory) {
+ switch (logLevelCategory) {
+ case DEBUG:
+ return NagiosAlertLevel.OK;
+ case INFO:
+ return NagiosAlertLevel.OK;
+ case WARN:
+ return NagiosAlertLevel.WARNING;
+ case ERROR:
+ return NagiosAlertLevel.CRITICAL;
+ case FATAL:
+ return NagiosAlertLevel.CRITICAL;
+ default:
+ return NagiosAlertLevel.UNKNOWN;
+ }
+ }
+
+ /**
+ * Resolves property value if not present
+ *
+ * @param userPassedValue user passed property value
+ * @param defaultValue default value if no value is found after resolving the property
+ * @param propertyNames property names
+ *
+ * @return resolved property value
+ */
+ private static String resolveProperty(
+ final String userPassedValue, final String defaultValue, final String... propertyNames) {
+ // if user passed is present return that value
+ if (userPassedValue != null) {
+ return userPassedValue;
+ }
+ // resolve it using composite resolver
+ final String resolveProperty = resolveProperty(Arrays.asList(propertyNames));
+ return resolveProperty != null ? resolveProperty : defaultValue;
+ }
+
+ /**
+ * Resolves property values in different places
+ *
+ * @param propertyNames property Names
+ *
+ * @return property Value
+ */
+ private static String resolveProperty(final List<String> propertyNames) {
+ return COMPOSITE_PROPERTY_RESOLVER.resolve(propertyNames);
+ }
+
+
+ /**
+ * Determine host IP Address
+ *
+ * @return host ip address
+ */
+ private static String getHostIPAddress() {
+ final InetAddress inetAddress = getInetAddress();
+ if (inetAddress != null) {
+ return inetAddress.getHostAddress();
+ }
+ return null;
+ }
+
+ /**
+ * Determines fully qualified host name
+ *
+ * @return fully qualified host name
+ */
+ private static String getHostName() {
+ final InetAddress inetAddress = getInetAddress();
+ if (inetAddress != null) {
+ return inetAddress.getCanonicalHostName();
+ }
+ return null;
+ }
+
+ /**
+ * Fetches Inet Address
+ *
+ * @return Inet Address
+ */
+ private static InetAddress getInetAddress() {
+ try {
+ return InetAddress.getLocalHost();
+ } catch (UnknownHostException e) {
+ return null;
+ }
+ }
+
+
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/resources/META-INF/services/org.onap.dcae.utils.eelf.logger.api.log.EELFLogger b/eelf-logger/eelf-logger-logback-impl/src/main/resources/META-INF/services/org.onap.dcae.utils.eelf.logger.api.log.EELFLogger
new file mode 100644
index 0000000..d7d5c71
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/resources/META-INF/services/org.onap.dcae.utils.eelf.logger.api.log.EELFLogger
@@ -0,0 +1,20 @@
+#
+# ================================================================================
+# Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+# ================================================================================
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+# ============LICENSE_END=========================================================
+#
+#
+
+org.onap.dcae.utils.eelf.logger.logback.log.EELFLoggerImpl
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-async-appenders.xml b/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-async-appenders.xml
new file mode 100644
index 0000000..e2e93e4
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-async-appenders.xml
@@ -0,0 +1,55 @@
+<!--
+ ~ ================================================================================
+ ~ Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ ~ ================================================================================
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License.
+ ~ ============LICENSE_END=========================================================
+ ~
+ -->
+
+<included>
+
+ <!--
+ ASYNC APPENDERS CAN BE USED TO INCREASE THE PERFORMANCE OF ECOMP LOGGING, HOWEVER, ASYNC LOGGERS
+ CAN DROP MESSAGES IF QUEUE SIZE IF FULL AND DURING SHUT DOWN TIME.
+
+ SO INCREASED PERFORMANCE AT THE COST OF LESS RELIABLE LOGGING
+ -->
+
+ <appender name="asyncAuditLogAppender" class="ch.qos.logback.classic.AsyncAppender">
+ <queueSize>${queueSize}</queueSize>
+ <maxFlushTime>${maxFlushTime}</maxFlushTime>
+ <appender-ref ref="auditLogAppender"/>
+ </appender>
+
+ <appender name="asyncMetricLogAppender" class="ch.qos.logback.classic.AsyncAppender">
+ <queueSize>${queueSize}</queueSize>
+ <maxFlushTime>${maxFlushTime}</maxFlushTime>
+ <appender-ref ref="metricLogAppender"/>
+ </appender>
+
+ <appender name="asyncErrorLogAppender" class="ch.qos.logback.classic.AsyncAppender">
+ <queueSize>${queueSize}</queueSize>
+ <maxFlushTime>${maxFlushTime}</maxFlushTime>
+ <appender-ref ref="errorLogAppender"/>
+ </appender>
+
+ <appender name="asyncDebugLogAppender" class="ch.qos.logback.classic.AsyncAppender">
+ <queueSize>${queueSize}</queueSize>
+ <maxFlushTime>${maxFlushTime}</maxFlushTime>
+ <appender-ref ref="debugLogAppender"/>
+ </appender>
+
+</included>
+
+
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-defaults.xml b/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-defaults.xml
new file mode 100644
index 0000000..f9bb078
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-defaults.xml
@@ -0,0 +1,51 @@
+<!--
+ ~ ================================================================================
+ ~ Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ ~ ================================================================================
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License.
+ ~ ============LICENSE_END=========================================================
+ ~
+ -->
+
+<included>
+
+ <!-- LOG DIRECTORIES -->
+ <property scope="context" name="logDir" value="logs"/>
+ <property scope="context" name="debugDir" value="debug-logs"/>
+
+ <!-- SETUP LOG DIRECTORIES -->
+ <property scope="context" name="logDirectory" value="${logDir}/${componentName}"/>
+ <property scope="context" name="debugLogDirectory" value="${debugDir}/${componentName}"/>
+
+ <!--
+ MODIFY LOG DIR ON WINDOWS OS SO THAT TEST LOGS ARE UNDER TARGET DIR CAN BE CLEANED AFTER TESTS AUTOMATICALLY
+ -->
+ <property scope="context" name="modifyLogPathInWindows" value="true" />
+ <property scope="context" name="appendDirectory" value="target" />
+
+ <!-- LOG FILE NAMES -->
+ <property scope="context" name="metricLogName" value="metrics"/>
+ <property scope="context" name="auditLogName" value="audit"/>
+ <property scope="context" name="errorLogName" value="error"/>
+ <property scope="context" name="debugLogName" value="debug"/>
+
+ <!-- ROLLING FILE APPENDER DEFAULT SETTINGS -->
+ <property scope="context" name="minFileIndex" value="1"/>
+ <property scope="context" name="maxFileIndex" value="10"/>
+ <property scope="context" name="maxFileSize" value="2500KB"/>
+
+ <!-- ASYNC APPENDER DEFAULT SETTINGS -->
+ <property scope="context" name="queueSize" value="1024"/>
+ <property scope="context" name="maxFlushTime" value="5000"/>
+
+</included>
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-logback.xml b/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-logback.xml
new file mode 100644
index 0000000..7e08eb2
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-logback.xml
@@ -0,0 +1,45 @@
+<!--
+ ~ ================================================================================
+ ~ Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ ~ ================================================================================
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License.
+ ~ ============LICENSE_END=========================================================
+ ~
+ -->
+
+<included>
+
+ <include resource="eelf-defaults.xml"/>
+
+ <!-- CUSTOM STARTUP LISTENER REQUIRED TO SETUP DEFAULT APP LOG INFO DURING STARTUP TIME-->
+ <contextListener class="org.onap.dcae.utils.eelf.logger.logback.listener.LogbackStartupListener"/>
+
+ <!-- ADD REQUIRED APPENDERS -->
+ <include resource="eelf-required-appenders.xml"/>
+
+ <!-- ADD OPTIONAL APPENDERS: NOT ADDED BY DEFAULT -->
+ <!--<include resource="eelf-optional-appenders.xml"/>-->
+
+
+ <root level="DEBUG">
+ <!-- required appenders -->
+ <appender-ref ref="auditLogAppender"/>
+ <appender-ref ref="metricLogAppender"/>
+ <appender-ref ref="errorLogAppender"/>
+
+ <!-- optional appenders: not added by default -->
+ <!--<appender-ref ref="debugLogAppender"/>-->
+ <!--<appender-ref ref="STDOUT"/>-->
+ </root>
+
+</included>
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-optional-appenders.xml b/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-optional-appenders.xml
new file mode 100644
index 0000000..fb7ec7f
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-optional-appenders.xml
@@ -0,0 +1,68 @@
+<!--
+ ~ ================================================================================
+ ~ Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ ~ ================================================================================
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License.
+ ~ ============LICENSE_END=========================================================
+ ~
+ -->
+
+<included>
+
+ <!--
+ ============================= DEBUG LOG APPENDER ================================
+ -->
+ <appender name="debugLogAppender" class="ch.qos.logback.core.rolling.RollingFileAppender">
+
+ <filter class="org.onap.dcae.utils.eelf.logger.logback.filter.MarkerFilter">
+ <markers>DEBUG_LOG</markers>
+ <onMatch>ACCEPT</onMatch>
+ <onMismatch>DENY</onMismatch>
+ </filter>
+
+ <file>${debugLogDirectory}/${debugLogName}.log</file>
+
+ <rollingPolicy class="ch.qos.logback.core.rolling.FixedWindowRollingPolicy">
+ <fileNamePattern>${logDirectory}/${debugLogName}.%i.log.zip</fileNamePattern>
+ <minIndex>${minFileIndex}</minIndex>
+ <maxIndex>${maxFileIndex}</maxIndex>
+ </rollingPolicy>
+
+ <triggeringPolicy class="ch.qos.logback.core.rolling.SizeBasedTriggeringPolicy">
+ <maxFileSize>${maxFileSize}</maxFileSize>
+ </triggeringPolicy>
+
+ <encoder class="ch.qos.logback.core.encoder.LayoutWrappingEncoder">
+ <layout class="org.onap.dcae.utils.eelf.logger.logback.layout.DebugLogLayout"/>
+ </encoder>
+
+ </appender>
+
+
+ <!--
+ ============================= CONSOLE APPENDER ================================
+ -->
+ <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
+
+ <filter class="org.onap.dcae.utils.eelf.logger.logback.filter.MarkerFilter">
+ <markers>METRIC_LOG,AUDIT_LOG,ERROR_LOG,DEBUG_LOG</markers>
+ <onMatch>ACCEPT</onMatch>
+ <onMismatch>DENY</onMismatch>
+ </filter>
+
+ <encoder class="ch.qos.logback.core.encoder.LayoutWrappingEncoder">
+ <layout class="org.onap.dcae.utils.eelf.logger.logback.layout.ConsoleLayout"/>
+ </encoder>
+ </appender>
+
+</included>
diff --git a/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-required-appenders.xml b/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-required-appenders.xml
new file mode 100644
index 0000000..72f1a5d
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/main/resources/eelf-required-appenders.xml
@@ -0,0 +1,112 @@
+<!--
+ ~ ================================================================================
+ ~ Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ ~ ================================================================================
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License.
+ ~ ============LICENSE_END=========================================================
+ ~
+ -->
+
+<included>
+
+ <!--
+ ============================= AUDIT LOG APPENDER ================================
+ -->
+ <appender name="auditLogAppender" class="ch.qos.logback.core.rolling.RollingFileAppender">
+
+ <filter class="org.onap.dcae.utils.eelf.logger.logback.filter.MarkerFilter">
+ <markers>AUDIT_LOG</markers>
+ <onMatch>ACCEPT</onMatch>
+ <onMismatch>DENY</onMismatch>
+ </filter>
+
+ <file>${logDirectory}/${auditLogName}.log</file>
+
+ <rollingPolicy class="ch.qos.logback.core.rolling.FixedWindowRollingPolicy">
+ <fileNamePattern>${logDirectory}/${auditLogName}.%i.log.zip</fileNamePattern>
+ <minIndex>${minFileIndex}</minIndex>
+ <maxIndex>${maxFileIndex}</maxIndex>
+ </rollingPolicy>
+
+ <triggeringPolicy class="ch.qos.logback.core.rolling.SizeBasedTriggeringPolicy">
+ <maxFileSize>${maxFileSize}</maxFileSize>
+ </triggeringPolicy>
+
+ <encoder class="ch.qos.logback.core.encoder.LayoutWrappingEncoder">
+ <layout class="org.onap.dcae.utils.eelf.logger.logback.layout.AuditLogLayout"/>
+ </encoder>
+
+ </appender>
+
+
+ <!--
+ ============================= METRIC LOG APPENDER ================================
+ -->
+ <appender name="metricLogAppender" class="ch.qos.logback.core.rolling.RollingFileAppender">
+
+ <filter class="org.onap.dcae.utils.eelf.logger.logback.filter.MarkerFilter">
+ <markers>METRIC_LOG</markers>
+ <onMatch>ACCEPT</onMatch>
+ <onMismatch>DENY</onMismatch>
+ </filter>
+
+ <file>${logDirectory}/${metricLogName}.log</file>
+
+ <rollingPolicy class="ch.qos.logback.core.rolling.FixedWindowRollingPolicy">
+ <fileNamePattern>${logDirectory}/${metricLogName}.%i.log.zip</fileNamePattern>
+ <minIndex>${minFileIndex}</minIndex>
+ <maxIndex>${maxFileIndex}</maxIndex>
+ </rollingPolicy>
+
+ <triggeringPolicy class="ch.qos.logback.core.rolling.SizeBasedTriggeringPolicy">
+ <maxFileSize>${maxFileSize}</maxFileSize>
+ </triggeringPolicy>
+
+ <encoder class="ch.qos.logback.core.encoder.LayoutWrappingEncoder">
+ <layout class="org.onap.dcae.utils.eelf.logger.logback.layout.MetricLogLayout"/>
+ </encoder>
+
+ </appender>
+
+
+ <!--
+ ============================= ERROR LOG APPENDER ================================
+ -->
+ <appender name="errorLogAppender" class="ch.qos.logback.core.rolling.RollingFileAppender">
+
+ <filter class="org.onap.dcae.utils.eelf.logger.logback.filter.MarkerFilter">
+ <markers>ERROR_LOG</markers>
+ <onMatch>ACCEPT</onMatch>
+ <onMismatch>DENY</onMismatch>
+ </filter>
+
+ <file>${logDirectory}/${errorLogName}.log</file>
+
+ <rollingPolicy class="ch.qos.logback.core.rolling.FixedWindowRollingPolicy">
+ <fileNamePattern>${logDirectory}/${errorLogName}.%i.log.zip</fileNamePattern>
+ <minIndex>${minFileIndex}</minIndex>
+ <maxIndex>${maxFileIndex}</maxIndex>
+ </rollingPolicy>
+
+ <triggeringPolicy class="ch.qos.logback.core.rolling.SizeBasedTriggeringPolicy">
+ <maxFileSize>${maxFileSize}</maxFileSize>
+ </triggeringPolicy>
+
+ <encoder class="ch.qos.logback.core.encoder.LayoutWrappingEncoder">
+ <layout class="org.onap.dcae.utils.eelf.logger.logback.layout.ErrorLogLayout"/>
+ </encoder>
+
+ </appender>
+
+
+</included>
diff --git a/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/BaseLogbackUnitTest.java b/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/BaseLogbackUnitTest.java
new file mode 100644
index 0000000..fda4355
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/BaseLogbackUnitTest.java
@@ -0,0 +1,157 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback;
+
+
+import org.onap.dcae.utils.eelf.logger.api.info.CodeLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.CustomFieldsLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.ErrorLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.MessageLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.MiscLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.NagiosAlertLevel;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestIdLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestStatusCode;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestTimingLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.ResponseLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.ServiceLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.TargetServiceLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.spec.AuditLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.DebugLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.ErrorLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.MetricLogSpec;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+import org.onap.dcae.utils.eelf.logger.model.info.CodeLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.CustomFieldsLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.ErrorLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.MessageLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.MiscLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.RequestIdLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.RequestTimingLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.ResponseLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.ServiceLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.info.TargetServiceLogInfoImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.AuditLogSpecImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.DebugLogSpecImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.ErrorLogSpecImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.MetricLogSpecImpl;
+import org.onap.dcae.utils.eelf.logger.model.spec.OptionalLogSpecImpl;
+
+import java.util.Date;
+
+/**
+ * Base Logback Unit Test.
+ *
+ * @author Rajiv Singla
+ */
+public abstract class BaseLogbackUnitTest {
+
+ protected static final String TEST_SERVICE_INSTANCE_ID = "testServiceInstanceID";
+ protected static final String TEST_INSTANCE_UUID = "";
+
+ static {
+ System.setProperty("ServiceInstanceId", TEST_SERVICE_INSTANCE_ID);
+ System.setProperty("InstanceUUID", TEST_INSTANCE_UUID);
+ }
+
+ protected static final String TEST_REQUEST_ID = "403cdad8-4de7-450d-b441-561001decdd6";
+ protected static final String TEST_SERVICE_NAME = "testServiceName";
+ protected static final String TEST_PARTNER_NAME = "testPartnerName";
+ protected static final String TEST_CLIENT_IP_ADDRESS = "";
+
+ protected static final Date START_DATE = new Date();
+ protected static final Date END_DATE = new Date(new Date().getTime() + 30_000);
+ protected static final Long ELAPSED_TIME = END_DATE.getTime() - START_DATE.getTime();
+
+ protected static final Integer RESPONSE_CODE = 200;
+ protected static final String RESPONSE_DESCRIPTION = "TEST RESPONSE DESCRIPTION";
+
+ protected static final String TEST_TARGET_ENTITY = "testTargetEntity";
+ protected static final String TEST_TARGET_SERVICE_NAME = "testTargetServiceName";
+ protected static final String TEST_TARGET_VIRTUAL_ENTITY = "testTargetVirtualEntity";
+
+
+ protected static final String TEST_THREAD_ID = "testThreadId";
+ protected static final String TEST_CLASS_NAME = "testClassName";
+
+ protected static final String TEST_CUSTOM_FIELD1 = "testCustomField1";
+ protected static final String TEST_CUSTOM_FIELD2 = "testCustomField2";
+ protected static final String TEST_CUSTOM_FIELD3 = "testCustomField3";
+ protected static final String TEST_CUSTOM_FIELD4 = "testCustomField4";
+
+ protected static final String TEST_PROCESS_KEY = "testProcessId";
+
+ protected static final Integer TEST_ERROR_CODE = 500;
+ protected static final String TEST_ERROR_CODE_DESCRIPTION = "TEST ERROR CODE DESCRIPTION";
+
+
+ protected static RequestIdLogInfo getTestRequestIdLogInfo() {
+ return new RequestIdLogInfoImpl(TEST_REQUEST_ID);
+ }
+
+ protected static ServiceLogInfo getTestServiceLogInfo() {
+ return new ServiceLogInfoImpl(TEST_SERVICE_NAME, TEST_PARTNER_NAME, TEST_CLIENT_IP_ADDRESS);
+ }
+
+ protected static RequestTimingLogInfo getTestRequestTimingInfo() {
+ return new RequestTimingLogInfoImpl(START_DATE, END_DATE, ELAPSED_TIME);
+ }
+
+ protected static ResponseLogInfo getTestResponseLogInfo() {
+ return new ResponseLogInfoImpl(RESPONSE_CODE, RESPONSE_DESCRIPTION);
+ }
+
+ protected static AuditLogSpec getTestAuditLogSpec() {
+ return new AuditLogSpecImpl(getTestRequestIdLogInfo(), getTestServiceLogInfo(),
+ getTestRequestTimingInfo(), getTestResponseLogInfo());
+ }
+
+ protected static DebugLogSpec getTestDebugLogSpec() {
+ return new DebugLogSpecImpl(getTestRequestIdLogInfo());
+ }
+
+ protected static TargetServiceLogInfo getTestTargetServiceLogInfo() {
+ return new TargetServiceLogInfoImpl(TEST_TARGET_ENTITY, TEST_TARGET_SERVICE_NAME, TEST_TARGET_VIRTUAL_ENTITY);
+ }
+
+ protected static MetricLogSpec getTestMetricLogSpec() {
+ return new MetricLogSpecImpl(getTestRequestIdLogInfo(), getTestServiceLogInfo(),
+ getTestRequestTimingInfo(), getTestResponseLogInfo(), getTestTargetServiceLogInfo());
+ }
+
+ protected static ErrorLogInfo getTestErrorLogInfo() {
+ return new ErrorLogInfoImpl(TEST_ERROR_CODE, TEST_ERROR_CODE_DESCRIPTION);
+ }
+
+ protected static ErrorLogSpec getTestErrorLogSpec() {
+ return new ErrorLogSpecImpl(getTestRequestIdLogInfo(), getTestServiceLogInfo(), getTestTargetServiceLogInfo()
+ , getTestErrorLogInfo());
+ }
+
+ protected static OptionalLogSpec getTestOptionalLogSpec() {
+ final MessageLogInfo messageLogInfo = new MessageLogInfoImpl(new Date(), RequestStatusCode.COMPLETE,
+ NagiosAlertLevel.OK);
+ final CodeLogInfo codeLogInfo = new CodeLogInfoImpl(TEST_THREAD_ID, TEST_CLASS_NAME);
+ final CustomFieldsLogInfo customFieldsLogInfo = new CustomFieldsLogInfoImpl(TEST_CUSTOM_FIELD1,
+ TEST_CUSTOM_FIELD2, TEST_CUSTOM_FIELD3, TEST_CUSTOM_FIELD4);
+ final MiscLogInfo miscLogInfo = new MiscLogInfoImpl(TEST_PROCESS_KEY, "");
+ return new OptionalLogSpecImpl(messageLogInfo, codeLogInfo, customFieldsLogInfo, miscLogInfo);
+ }
+
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/AuditLogImplTest.java b/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/AuditLogImplTest.java
new file mode 100644
index 0000000..02b377a
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/AuditLogImplTest.java
@@ -0,0 +1,66 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.log;
+
+import org.junit.Test;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLogFactory;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLogger;
+import org.onap.dcae.utils.eelf.logger.api.spec.AuditLogSpec;
+import org.onap.dcae.utils.eelf.logger.logback.BaseLogbackUnitTest;
+import org.onap.dcae.utils.eelf.logger.logback.EELFLoggerDefaults;
+import org.onap.dcae.utils.eelf.logger.model.spec.AuditLogSpecImpl;
+
+/**
+ * Tests for Audit log implementations.
+ *
+ * @author Rajiv Singla
+ */
+public class AuditLogImplTest extends BaseLogbackUnitTest {
+
+ private static final EELFLogger LOG = EELFLogFactory.getLogger(AuditLogImplTest.class);
+
+ @Test
+ public void auditLoggerTest() throws Exception {
+
+ LOG.auditLog().info("Test Audit info message: {}",
+ getTestAuditLogSpec(), getTestOptionalLogSpec(), "infoArg");
+
+ final AuditLogSpec emptyAuditLog = new AuditLogSpecImpl(null, null,
+ null, null);
+
+ LOG.auditLog().info("Test Empty Audit info message.", emptyAuditLog,
+ EELFLoggerDefaults.DEFAULT_OPTIONAL_LOG_SPEC);
+
+ }
+
+
+ @Test
+ public void auditLoggerTestWithWarnLogLevel() throws Exception {
+ LOG.auditLog().warn("Test Audit warn message: {}",
+ getTestAuditLogSpec(), getTestOptionalLogSpec(), "warnArg");
+ }
+
+ @Test
+ public void auditLoggerTestWithErrorLogLevel() throws Exception {
+ LOG.auditLog().error("Test Audit error message: {}",
+ getTestAuditLogSpec(), getTestOptionalLogSpec(), "errorArg");
+
+ }
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/DebugLogImplTest.java b/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/DebugLogImplTest.java
new file mode 100644
index 0000000..76d41f9
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/DebugLogImplTest.java
@@ -0,0 +1,53 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.log;
+
+import org.junit.Test;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLogFactory;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLogger;
+import org.onap.dcae.utils.eelf.logger.api.spec.DebugLogSpec;
+import org.onap.dcae.utils.eelf.logger.logback.BaseLogbackUnitTest;
+import org.onap.dcae.utils.eelf.logger.logback.EELFLoggerDefaults;
+import org.onap.dcae.utils.eelf.logger.model.spec.DebugLogSpecImpl;
+
+
+/**
+ * Test for Debug log implementation.
+ *
+ * @author Rajiv Singla
+ */
+public class DebugLogImplTest extends BaseLogbackUnitTest {
+
+ private static final EELFLogger LOG = EELFLogFactory.getLogger(DebugLogImplTest.class);
+
+ @Test
+ public void debugLoggerTest() throws Exception {
+
+ LOG.debugLog().debug("Test DebugLog debug message: {}",
+ getTestDebugLogSpec(), getTestOptionalLogSpec(), "debugArg");
+
+ final DebugLogSpec emptyDebugLog = new DebugLogSpecImpl(null);
+
+ LOG.debugLog().debug("Test Empty DebugLog debug message.", emptyDebugLog,
+ EELFLoggerDefaults.DEFAULT_OPTIONAL_LOG_SPEC);
+
+ }
+
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/ErrorLogImplTest.java b/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/ErrorLogImplTest.java
new file mode 100644
index 0000000..0b96be5
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/ErrorLogImplTest.java
@@ -0,0 +1,61 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.log;
+
+import org.junit.Test;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLogFactory;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLogger;
+import org.onap.dcae.utils.eelf.logger.api.spec.ErrorLogSpec;
+import org.onap.dcae.utils.eelf.logger.logback.BaseLogbackUnitTest;
+import org.onap.dcae.utils.eelf.logger.logback.EELFLoggerDefaults;
+import org.onap.dcae.utils.eelf.logger.model.spec.ErrorLogSpecImpl;
+
+
+/**
+ * Tests for Error Log implementation.
+ *
+ * @author Rajiv Singla
+ */
+public class ErrorLogImplTest extends BaseLogbackUnitTest {
+
+ private static final EELFLogger LOG = EELFLogFactory.getLogger(ErrorLogImplTest.class);
+
+ @Test
+ public void errorLoggerTest() throws Exception {
+ LOG.errorLog().error("Test ErrorLog error message: {}",
+ getTestErrorLogSpec(), getTestOptionalLogSpec(), "errorArg");
+
+ final ErrorLogSpec emptyErrorLog = new ErrorLogSpecImpl(null, null,
+ null, null);
+
+ LOG.errorLog().error("Test Empty ErrorLog error message", emptyErrorLog,
+ EELFLoggerDefaults.DEFAULT_OPTIONAL_LOG_SPEC);
+
+ }
+
+ @Test
+ public void errorLoggerTestWithWarnLogLevel() throws Exception {
+ LOG.errorLog().warn("Test errorLog warn message: {}", getTestErrorLogSpec(), getTestOptionalLogSpec(),
+ "warnArg");
+
+ }
+
+
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/MetricLogImplTest.java b/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/MetricLogImplTest.java
new file mode 100644
index 0000000..8df1e9c
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/test/java/org/onap/dcae/utils/eelf/logger/logback/log/MetricLogImplTest.java
@@ -0,0 +1,67 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.logback.log;
+
+import org.junit.Test;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLogFactory;
+import org.onap.dcae.utils.eelf.logger.api.log.EELFLogger;
+import org.onap.dcae.utils.eelf.logger.api.spec.MetricLogSpec;
+import org.onap.dcae.utils.eelf.logger.logback.BaseLogbackUnitTest;
+import org.onap.dcae.utils.eelf.logger.logback.EELFLoggerDefaults;
+import org.onap.dcae.utils.eelf.logger.model.spec.MetricLogSpecImpl;
+
+
+/**
+ * Tests for Metric Log implementation.
+ *
+ * @author Rajiv Singla
+ */
+public class MetricLogImplTest extends BaseLogbackUnitTest {
+
+ private static final EELFLogger LOG = EELFLogFactory.getLogger(MetricLogImplTest.class);
+
+ @Test
+ public void metricLoggerTest() throws Exception {
+
+ LOG.metricLog().info("test Metric info message: {}", getTestMetricLogSpec(), getTestOptionalLogSpec(),
+ "infoArg");
+
+ final MetricLogSpec emptyMetricLog = new MetricLogSpecImpl(null, null, null, null, null);
+
+ LOG.metricLog().info("Test Empty Metric info message", emptyMetricLog,
+ EELFLoggerDefaults.DEFAULT_OPTIONAL_LOG_SPEC);
+ }
+
+ @Test
+ public void metricLoggerTestWithWarnLogLevel() throws Exception {
+ LOG.metricLog().warn("test Metric warn message: {}", getTestMetricLogSpec(), getTestOptionalLogSpec(),
+ "warnArg");
+
+ }
+
+ @Test
+ public void metricLoggerTestWithErrorLogLevel() throws Exception {
+ LOG.metricLog().warn("test Metric error message: {}", getTestMetricLogSpec(), getTestOptionalLogSpec(),
+ "errorArg");
+
+
+ }
+
+}
diff --git a/eelf-logger/eelf-logger-logback-impl/src/test/resources/logback.xml b/eelf-logger/eelf-logger-logback-impl/src/test/resources/logback.xml
new file mode 100644
index 0000000..b1cffd6
--- /dev/null
+++ b/eelf-logger/eelf-logger-logback-impl/src/test/resources/logback.xml
@@ -0,0 +1,41 @@
+<!--
+ ~ ================================================================================
+ ~ Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ ~ ================================================================================
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License.
+ ~ ============LICENSE_END=========================================================
+ ~
+ -->
+<configuration>
+
+ <!-- SET EELF COMPONENT NAME -->
+ <property scope="context" name="componentName" value="test-eelf-logger"/>
+ <contextName>${componentName}</contextName>
+
+ <include resource="eelf-logback.xml"/>
+
+ <include resource="eelf-optional-appenders.xml"/>
+
+ <root level="DEBUG">
+ <!-- required appenders -->
+ <appender-ref ref="auditLogAppender"/>
+ <appender-ref ref="metricLogAppender"/>
+ <appender-ref ref="errorLogAppender"/>
+
+ <!-- optional appenders -->
+ <appender-ref ref="debugLogAppender"/>
+ <appender-ref ref="STDOUT"/>
+ </root>
+
+
+</configuration>
diff --git a/eelf-logger/eelf-logger-model/pom.xml b/eelf-logger/eelf-logger-model/pom.xml
new file mode 100644
index 0000000..86f269a
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/pom.xml
@@ -0,0 +1,77 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ ~ ================================================================================
+ ~ Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ ~ ================================================================================
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License.
+ ~ ============LICENSE_END=========================================================
+ ~
+ -->
+
+<project xmlns="http://maven.apache.org/POM/4.0.0"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+
+ <modelVersion>4.0.0</modelVersion>
+
+ <parent>
+ <groupId>org.onap.dcaegen2.utils</groupId>
+ <artifactId>eelf-logger</artifactId>
+ <version>1.0.0-SNAPSHOT</version>
+ </parent>
+
+ <artifactId>eelf-logger-model</artifactId>
+ <packaging>jar</packaging>
+
+
+ <!-- EELF LOGGER MODELS CONTAINS IMMUTABLE MODEL OBJECTS FOR VARIOUS EELF LOGGER INTERFACES -->
+ <name>dcaegen2-utils-eelf-logger-model</name>
+ <description>Contains immutable model objects for various EELF Logger interfaces</description>
+
+ <properties>
+ <main.basedir>${project.parent.basedir}</main.basedir>
+ <!-- SONAR SETTINGS : EXCLUDE TEST COVERAGE AS MODEL ONLY CONTAINS POJOs AND NO BUSINESS LOGIC-->
+ <sonar.coverage.exclusions>**/model/**</sonar.coverage.exclusions>
+ </properties>
+
+ <!-- NOTE: THIS MODULE MUST NOT HAVE ANY DEPENDENCY BESIDES ECOMP LOGGER API IN COMPILE SCOPE -->
+ <dependencies>
+
+ <!-- ECOMP LOGGER API -->
+ <dependency>
+ <groupId>${project.groupId}</groupId>
+ <artifactId>eelf-logger-api</artifactId>
+ <version>${project.version}</version>
+ </dependency>
+
+ <!-- LOMBOK IS USED FOR CODE GENERATION IN PROVIDED SCOPE (NOT IN COMPILE SCOPE) -->
+ <dependency>
+ <groupId>org.projectlombok</groupId>
+ <artifactId>lombok</artifactId>
+ </dependency>
+
+ </dependencies>
+
+ <build>
+ <sourceDirectory>${project.build.directory}/generated-sources/delombok</sourceDirectory>
+ <plugins>
+ <plugin>
+ <groupId>org.projectlombok</groupId>
+ <artifactId>lombok-maven-plugin</artifactId>
+ </plugin>
+ </plugins>
+ </build>
+
+
+
+</project>
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/AppLogInfoImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/AppLogInfoImpl.java
new file mode 100644
index 0000000..689915c
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/AppLogInfoImpl.java
@@ -0,0 +1,53 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.info;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.AppLogInfo;
+
+/**
+ * Concrete model implementation for {@link AppLogInfo}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class AppLogInfoImpl implements AppLogInfo {
+
+ private static final long serialVersionUID = 1L;
+
+ private String serviceInstanceID;
+
+ private String instanceUUID;
+
+ private String virtualServerName;
+
+ private String serverIPAddress;
+
+ private String serverFQDN;
+
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/CodeLogInfoImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/CodeLogInfoImpl.java
new file mode 100644
index 0000000..7f5eb2f
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/CodeLogInfoImpl.java
@@ -0,0 +1,48 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.info;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.CodeLogInfo;
+
+/**
+ * Concrete model implementation for {@link CodeLogInfo}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class CodeLogInfoImpl implements CodeLogInfo {
+
+ private static final long serialVersionUID = 1L;
+
+ private String threadId;
+
+ private String className;
+
+
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/CustomFieldsLogInfoImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/CustomFieldsLogInfoImpl.java
new file mode 100644
index 0000000..151900d
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/CustomFieldsLogInfoImpl.java
@@ -0,0 +1,51 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.info;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.CustomFieldsLogInfo;
+
+/**
+ * Concrete model implementation for {@link CustomFieldsLogInfo}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class CustomFieldsLogInfoImpl implements CustomFieldsLogInfo {
+
+ private static final long serialVersionUID = 1L;
+
+ private String customField1;
+
+ private String customField2;
+
+ private String customField3;
+
+ private String customField4;
+
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/ErrorLogInfoImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/ErrorLogInfoImpl.java
new file mode 100644
index 0000000..18c2e95
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/ErrorLogInfoImpl.java
@@ -0,0 +1,47 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.info;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.ErrorLogInfo;
+
+/**
+ * Concrete model implementation for {@link ErrorLogInfo}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class ErrorLogInfoImpl implements ErrorLogInfo {
+
+ private static final long serialVersionUID = 1L;
+
+ private Integer errorCode;
+
+ private String errorDescription;
+
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/MessageLogInfoImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/MessageLogInfoImpl.java
new file mode 100644
index 0000000..65e722a
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/MessageLogInfoImpl.java
@@ -0,0 +1,54 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.info;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.MessageLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.NagiosAlertLevel;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestStatusCode;
+
+
+import java.util.Date;
+
+/**
+ * Concrete model implementation for {@link MessageLogInfo}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class MessageLogInfoImpl implements MessageLogInfo {
+
+ private static final long serialVersionUID = 1L;
+
+ private Date creationTimestamp;
+
+ private RequestStatusCode statusCode;
+
+ private NagiosAlertLevel alertSeverity;
+
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/MiscLogInfoImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/MiscLogInfoImpl.java
new file mode 100644
index 0000000..f7e648b
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/MiscLogInfoImpl.java
@@ -0,0 +1,47 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.info;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.MiscLogInfo;
+
+/**
+ * Concrete model implementation for {@link MiscLogInfo}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class MiscLogInfoImpl implements MiscLogInfo {
+
+ private static final long serialVersionUID = 1L;
+
+ private String processId;
+
+ private String unused;
+
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/RequestIdLogInfoImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/RequestIdLogInfoImpl.java
new file mode 100644
index 0000000..af939c4
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/RequestIdLogInfoImpl.java
@@ -0,0 +1,45 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.info;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestIdLogInfo;
+
+/**
+ * Concrete model implementation for {@link RequestIdLogInfo}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class RequestIdLogInfoImpl implements RequestIdLogInfo {
+
+ private static final long serialVersionUID = 1L;
+
+ private String requestId;
+
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/RequestTimingLogInfoImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/RequestTimingLogInfoImpl.java
new file mode 100644
index 0000000..19d860b
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/RequestTimingLogInfoImpl.java
@@ -0,0 +1,51 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.info;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestTimingLogInfo;
+
+import java.util.Date;
+
+/**
+ * Concrete model implementation for {@link RequestTimingLogInfo}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class RequestTimingLogInfoImpl implements RequestTimingLogInfo {
+
+ private static final long serialVersionUID = 1L;
+
+ private Date beginTimestamp;
+
+ private Date endTimestamp;
+
+ private Long elapsedTime;
+
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/ResponseLogInfoImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/ResponseLogInfoImpl.java
new file mode 100644
index 0000000..1f0bfbf
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/ResponseLogInfoImpl.java
@@ -0,0 +1,47 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.info;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.ResponseLogInfo;
+
+/**
+ * Concrete model implementation for {@link ResponseLogInfo}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class ResponseLogInfoImpl implements ResponseLogInfo {
+
+ private static final long serialVersionUID = 1L;
+
+ private Integer responseCode;
+
+ private String responseDescription;
+
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/ServiceLogInfoImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/ServiceLogInfoImpl.java
new file mode 100644
index 0000000..68d1f41
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/ServiceLogInfoImpl.java
@@ -0,0 +1,49 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.info;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.ServiceLogInfo;
+
+/**
+ * Concrete model implementation for {@link ServiceLogInfo}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class ServiceLogInfoImpl implements ServiceLogInfo {
+
+ private static final long serialVersionUID = 1L;
+
+ private String serviceName;
+
+ private String partnerName;
+
+ private String clientIPAddress;
+
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/TargetServiceLogInfoImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/TargetServiceLogInfoImpl.java
new file mode 100644
index 0000000..4a41e73
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/TargetServiceLogInfoImpl.java
@@ -0,0 +1,48 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.info;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.TargetServiceLogInfo;
+
+/**
+ * Concrete model implementation for {@link TargetServiceLogInfo}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class TargetServiceLogInfoImpl implements TargetServiceLogInfo {
+
+ private static final long serialVersionUID = 1L;
+
+ private String targetEntity;
+
+ private String targetServiceName;
+
+ private String targetVirtualEntity;
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/package-info.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/package-info.java
new file mode 100644
index 0000000..ce0966e
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/info/package-info.java
@@ -0,0 +1,23 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+/**
+ * Contains immutable implementations for EELF Logging Information interfaces
+ */
+package org.onap.dcae.utils.eelf.logger.model.info;
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/AppLogSpecImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/AppLogSpecImpl.java
new file mode 100644
index 0000000..d1e40ad
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/AppLogSpecImpl.java
@@ -0,0 +1,47 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.spec;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Delegate;
+import org.onap.dcae.utils.eelf.logger.api.info.AppLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.spec.AppLogSpec;
+
+
+/**
+ * Concrete model implementation for {@link AppLogSpec}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+public class AppLogSpecImpl implements AppLogSpec {
+
+ private static final long serialVersionUID = 1L;
+
+ @Delegate(types = AppLogSpec.class)
+ private AppLogInfo appLogInfo;
+
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/AuditLogSpecImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/AuditLogSpecImpl.java
new file mode 100644
index 0000000..c217595
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/AuditLogSpecImpl.java
@@ -0,0 +1,61 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.spec;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Delegate;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestIdLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestTimingLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.ResponseLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.ServiceLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.spec.AuditLogSpec;
+
+
+/**
+ * Concrete model implementation for {@link AuditLogSpec}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class AuditLogSpecImpl implements AuditLogSpec {
+
+ private static final long serialVersionUID = 1L;
+
+ @Delegate(types = RequestIdLogInfo.class)
+ private RequestIdLogInfo requestIdLogInfo;
+
+ @Delegate(types = ServiceLogInfo.class)
+ private ServiceLogInfo serviceLogInfo;
+
+ @Delegate(types = RequestTimingLogInfo.class)
+ private RequestTimingLogInfo requestTimingLogInfo;
+
+ @Delegate(types = ResponseLogInfo.class)
+ private ResponseLogInfo responseLogInfo;
+
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/DebugLogSpecImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/DebugLogSpecImpl.java
new file mode 100644
index 0000000..53a1070
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/DebugLogSpecImpl.java
@@ -0,0 +1,48 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.spec;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Delegate;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestIdLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.spec.DebugLogSpec;
+
+
+/**
+ * Concrete model implementation for {@link DebugLogSpec}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class DebugLogSpecImpl implements DebugLogSpec {
+
+ private static final long serialVersionUID = 1L;
+
+ @Delegate(types = RequestIdLogInfo.class)
+ private RequestIdLogInfo requestIdLogInfo;
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/ErrorLogSpecImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/ErrorLogSpecImpl.java
new file mode 100644
index 0000000..6e73fcf
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/ErrorLogSpecImpl.java
@@ -0,0 +1,61 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.spec;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Delegate;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.ErrorLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestIdLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.ServiceLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.TargetServiceLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.spec.ErrorLogSpec;
+
+
+/**
+ * Concrete model implementation for {@link ErrorLogSpec}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class ErrorLogSpecImpl implements ErrorLogSpec {
+
+ private static final long serialVersionUID = 1L;
+
+ @Delegate(types = RequestIdLogInfo.class)
+ private RequestIdLogInfo requestIdLogInfo;
+
+ @Delegate(types = ServiceLogInfo.class)
+ private ServiceLogInfo serviceLogInfo;
+
+ @Delegate(types = TargetServiceLogInfo.class)
+ private TargetServiceLogInfo targetServiceLogInfo;
+
+ @Delegate(types = ErrorLogInfo.class)
+ private ErrorLogInfo errorLogInfo;
+
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/MetricLogSpecImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/MetricLogSpecImpl.java
new file mode 100644
index 0000000..d910bc2
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/MetricLogSpecImpl.java
@@ -0,0 +1,64 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.spec;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Delegate;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestIdLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.RequestTimingLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.ResponseLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.ServiceLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.TargetServiceLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.spec.MetricLogSpec;
+
+
+/**
+ * Concrete model implementation for {@link MetricLogSpec}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class MetricLogSpecImpl implements MetricLogSpec {
+
+ private static final long serialVersionUID = 1L;
+
+ @Delegate(types = RequestIdLogInfo.class)
+ private RequestIdLogInfo requestIdLogInfo;
+
+ @Delegate(types = ServiceLogInfo.class)
+ private ServiceLogInfo serviceLogInfo;
+
+ @Delegate(types = RequestTimingLogInfo.class)
+ private RequestTimingLogInfo requestTimingLogInfo;
+
+ @Delegate(types = ResponseLogInfo.class)
+ private ResponseLogInfo responseLogInfo;
+
+ @Delegate(types = TargetServiceLogInfo.class)
+ private TargetServiceLogInfo targetServiceLogInfo;
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/OptionalLogSpecImpl.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/OptionalLogSpecImpl.java
new file mode 100644
index 0000000..755b4bf
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/OptionalLogSpecImpl.java
@@ -0,0 +1,60 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+package org.onap.dcae.utils.eelf.logger.model.spec;
+
+import lombok.AllArgsConstructor;
+import lombok.EqualsAndHashCode;
+import lombok.Getter;
+import lombok.ToString;
+import lombok.experimental.Delegate;
+import lombok.experimental.Wither;
+import org.onap.dcae.utils.eelf.logger.api.info.CodeLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.CustomFieldsLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.MessageLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.info.MiscLogInfo;
+import org.onap.dcae.utils.eelf.logger.api.spec.OptionalLogSpec;
+
+
+/**
+ * Concrete model implementation for {@link OptionalLogSpec}
+ *
+ * @author Rajiv Singla
+ */
+@Getter
+@AllArgsConstructor
+@EqualsAndHashCode
+@ToString
+@Wither
+public class OptionalLogSpecImpl implements OptionalLogSpec {
+
+ private static final long serialVersionUID = 1L;
+
+ @Delegate(types = MessageLogInfo.class)
+ private MessageLogInfo messageLogInfo;
+
+ @Delegate(types = CodeLogInfo.class)
+ private CodeLogInfo codeLogInfo;
+
+ @Delegate(types = CustomFieldsLogInfo.class)
+ private CustomFieldsLogInfo customFieldsLogInfo;
+
+ @Delegate(types = MiscLogInfo.class)
+ private MiscLogInfo miscLogInfo;
+}
diff --git a/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/package-info.java b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/package-info.java
new file mode 100644
index 0000000..73aec41
--- /dev/null
+++ b/eelf-logger/eelf-logger-model/src/main/java/org/onap/dcae/utils/eelf/logger/model/spec/package-info.java
@@ -0,0 +1,23 @@
+/*
+ * ================================================================================
+ * Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+
+/**
+ * Contains immutable implementations for EELF Logging specification interfaces
+ */
+package org.onap.dcae.utils.eelf.logger.model.spec;
diff --git a/eelf-logger/findbugs-exclude.xml b/eelf-logger/findbugs-exclude.xml
new file mode 100644
index 0000000..9eac36d
--- /dev/null
+++ b/eelf-logger/findbugs-exclude.xml
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="UTF-8"?>
+
+<!--
+ ~ ================================================================================
+ ~ Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ ~ ================================================================================
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License.
+ ~ ============LICENSE_END=========================================================
+ ~
+ -->
+
+<FindBugsFilter>
+
+ <Match>
+ <!-- MODEL OBJECTS ARE USING LOMBOK ANNOTATIONS SO SOME FINDBUGS ARE IGNORED-->
+ <Package name="~.*model.*"/>
+ <Bug pattern="ES_COMPARING_PARAMETER_STRING_WITH_EQ, RC_REF_COMPARISON, EI_EXPOSE_REP, EI_EXPOSE_REP2"/>
+ </Match>
+
+</FindBugsFilter>
diff --git a/eelf-logger/pmd-exclude.properties b/eelf-logger/pmd-exclude.properties
new file mode 100644
index 0000000..d325b88
--- /dev/null
+++ b/eelf-logger/pmd-exclude.properties
@@ -0,0 +1,22 @@
+#
+# ================================================================================
+# Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+# ================================================================================
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+# ============LICENSE_END=========================================================
+#
+#
+
+# List fully qualified names of classes that can be excluded for PMD (PROGRAMMING-MISTAKE-DETECTOR)
+
+# IGNORE TOO MANY STATIC IMPORTS
diff --git a/eelf-logger/pom.xml b/eelf-logger/pom.xml
new file mode 100644
index 0000000..acb5fda
--- /dev/null
+++ b/eelf-logger/pom.xml
@@ -0,0 +1,476 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ ~ ================================================================================
+ ~ Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+ ~ ================================================================================
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License.
+ ~ ============LICENSE_END=========================================================
+ ~
+ -->
+<project xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xmlns="http://maven.apache.org/POM/4.0.0"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+
+ <modelVersion>4.0.0</modelVersion>
+ <modules>
+ <module>eelf-logger-api</module>
+ <module>eelf-logger-model</module>
+ <module>eelf-logger-logback-impl</module>
+ </modules>
+
+ <parent>
+ <artifactId>utils</artifactId>
+ <groupId>org.onap.dcaegen2.utils</groupId>
+ <version>1.2.0-SNAPSHOT</version>
+ </parent>
+
+
+ <artifactId>eelf-logger</artifactId>
+ <name>dcaegen2-utils-eelf-logger</name>
+ <version>1.0.0-SNAPSHOT</version>
+ <packaging>pom</packaging>
+ <url>http://maven.apache.org</url>
+
+
+ <properties>
+
+ <!-- PROJECT SETTINGS-->
+ <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
+ <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
+ <main.basedir>${project.basedir}</main.basedir>
+
+ <!--TEST SETTINGS -->
+ <surefire.redirectTestOutputToFile>true</surefire.redirectTestOutputToFile>
+
+ <!-- PROJECT DEPENDENCIES -->
+ <slf4j.version>1.7.5</slf4j.version>
+ <logback.version>1.2.3</logback.version>
+ <lombok.version>1.16.10</lombok.version>
+
+
+ <!--TESTING DEPENDENCIES -->
+ <junit.version>4.12</junit.version>
+ <mockito.version>2.2.11</mockito.version>
+ <assertj-core.version>2.6.0</assertj-core.version>
+
+
+ <!-- PLUGINS VERSIONS -->
+ <compiler.plugin.version>3.3</compiler.plugin.version>
+ <surefire.plugin.version>2.19.1</surefire.plugin.version>
+ <failsafe.plugin.version>2.19.1</failsafe.plugin.version>
+ <findbugs.plugin.version>3.0.2</findbugs.plugin.version>
+
+ <pmd.plugin.version>3.5</pmd.plugin.version>
+ <javadoc.plugin.version>2.10.4</javadoc.plugin.version>
+ <source.plugin.version>2.4</source.plugin.version>
+ <jar.plugin.version>2.4</jar.plugin.version>
+ <deploy.plugin.version>2.8</deploy.plugin.version>
+ <lombok.plugin.version>1.16.10.0</lombok.plugin.version>
+ <maven.site.plugin>3.5.1</maven.site.plugin>
+
+ <!--PLUGIN SETTINGS -->
+ <compiler.source.version>1.7</compiler.source.version>
+ <compiler.target.version>1.7</compiler.target.version>
+ <unit.test.pattern>**/*Test.java</unit.test.pattern>
+ <skip.unit.tests>false</skip.unit.tests>
+ <integration.test.pattern>**/*IT.java</integration.test.pattern>
+ <skip.integration.tests>true</skip.integration.tests>
+ <pmd.violation.buildfail>true</pmd.violation.buildfail>
+ <findbugs.failOnError>true</findbugs.failOnError>
+
+ </properties>
+
+
+ <dependencyManagement>
+
+ <dependencies>
+
+ <!-- LOGGING -->
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-api</artifactId>
+ <version>${slf4j.version}</version>
+ </dependency>
+
+ <dependency>
+ <groupId>ch.qos.logback</groupId>
+ <artifactId>logback-classic</artifactId>
+ <version>${logback.version}</version>
+ </dependency>
+
+ <!-- CODE GENERATION -->
+ <dependency>
+ <groupId>org.projectlombok</groupId>
+ <artifactId>lombok</artifactId>
+ <version>${lombok.version}</version>
+ <scope>provided</scope>
+ </dependency>
+
+
+ <!-- TEST DEPENDENCIES -->
+ <dependency>
+ <groupId>junit</groupId>
+ <artifactId>junit</artifactId>
+ <version>${junit.version}</version>
+ <scope>test</scope>
+ </dependency>
+
+ <dependency>
+ <groupId>org.mockito</groupId>
+ <artifactId>mockito-core</artifactId>
+ <version>${mockito.version}</version>
+ <scope>test</scope>
+ </dependency>
+
+ <dependency>
+ <groupId>org.assertj</groupId>
+ <artifactId>assertj-core</artifactId>
+ <version>${assertj-core.version}</version>
+ <scope>test</scope>
+ </dependency>
+
+ </dependencies>
+
+ </dependencyManagement>
+
+
+ <!-- COMMON DEPENDENCIES FOR ALL SUB-PROJECTS -->
+ <dependencies>
+ <!-- TEST DEPENDENCIES -->
+ <dependency>
+ <groupId>junit</groupId>
+ <artifactId>junit</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.mockito</groupId>
+ <artifactId>mockito-core</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.assertj</groupId>
+ <artifactId>assertj-core</artifactId>
+ </dependency>
+ </dependencies>
+
+
+ <build>
+
+ <pluginManagement>
+
+ <plugins>
+ <!-- COMPILER PLUGIN -->
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-compiler-plugin</artifactId>
+ <version>${compiler.plugin.version}</version>
+ <configuration>
+ <source>${compiler.target.version}</source>
+ <target>${compiler.source.version}</target>
+ </configuration>
+ </plugin>
+
+ <!-- MAVEN SOURCE PLUGIN -->
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-source-plugin</artifactId>
+ <version>${source.plugin.version}</version>
+ <configuration>
+ <excludeResources>true</excludeResources>
+ </configuration>
+ <executions>
+ <execution>
+ <id>attach-sources</id>
+ <phase>verify</phase>
+ <goals>
+ <goal>jar-no-fork</goal>
+ </goals>
+ </execution>
+ </executions>
+ </plugin>
+
+
+ <!-- MAVEN JAVADOC PLUGIN -->
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-javadoc-plugin</artifactId>
+ <version>${javadoc.plugin.version}</version>
+ <configuration>
+ <!-- minimize console output messages -->
+ <quiet>true</quiet>
+ <verbose>false</verbose>
+ <useStandardDocletOptions>false</useStandardDocletOptions>
+ </configuration>
+ <executions>
+ <execution>
+ <id>aggregate</id>
+ <phase>site</phase>
+ <goals>
+ <goal>aggregate</goal>
+ </goals>
+ </execution>
+ <execution>
+ <id>attach-javadoc</id>
+ <goals>
+ <goal>jar</goal>
+ </goals>
+ </execution>
+ </executions>
+ </plugin>
+
+
+ <!-- SUREFIRE TEST PLUGIN -->
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-surefire-plugin</artifactId>
+ <version>${surefire.plugin.version}</version>
+ <configuration>
+ <skipTests>${skip.unit.tests}</skipTests>
+ <argLine>-Xmx2048m -Djava.awt.headless=true -XX:+UseConcMarkSweepGC
+ -XX:OnOutOfMemoryError="kill -9 %p" -XX:+HeapDumpOnOutOfMemoryError
+ </argLine>
+ <redirectTestOutputToFile>${surefire.redirectTestOutputToFile}</redirectTestOutputToFile>
+ <parallel>methods</parallel>
+ <threadCount>8</threadCount>
+ <forkCount>8</forkCount>
+ <reuseForks>true</reuseForks>
+ <reportFormat>xml</reportFormat>
+ <trimStackTrace>false</trimStackTrace>
+ <systemPropertyVariables>
+ <java.io.tmpdir>${project.build.directory}</java.io.tmpdir>
+ <logback.configurationFile>
+ ${basedir}/src/test/resources/logback-test.xml
+ </logback.configurationFile>
+ </systemPropertyVariables>
+ <includes>
+ <include>${unit.test.pattern}</include>
+ </includes>
+ <excludes>
+ <exclude>${integration.test.pattern}</exclude>
+ </excludes>
+ <!-- Sets the VM argument line used when unit tests are run. -->
+ <argLine>${surefireArgLine}</argLine>
+ </configuration>
+ <dependencies>
+ <dependency>
+ <groupId>org.apache.maven.surefire</groupId>
+ <artifactId>surefire-junit47</artifactId>
+ <version>${surefire.plugin.version}</version>
+ </dependency>
+ </dependencies>
+ </plugin>
+
+ <!-- FAIL SAFE PLUGIN FOR INTEGRATION TEST -->
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-failsafe-plugin</artifactId>
+ <version>${failsafe.plugin.version}</version>
+ <executions>
+ <execution>
+ <id>integration-tests</id>
+ <goals>
+ <goal>integration-test</goal>
+ <goal>verify</goal>
+ </goals>
+ <configuration>
+ <skipTests>${skip.integration.tests}</skipTests>
+ <!-- Sets the VM argument line used when integration tests are run. -->
+ <!--suppress MavenModelInspection -->
+ <argLine>${failsafeArgLine}</argLine>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+
+
+ <!-- FIND BUGS (STATIC CODE ANALYSIS) PLUGIN -->
+ <plugin>
+ <groupId>org.codehaus.mojo</groupId>
+ <artifactId>findbugs-maven-plugin</artifactId>
+ <version>${findbugs.plugin.version}</version>
+ <configuration>
+ <effort>Max</effort>
+ <threshold>Low</threshold>
+ <xmlOutput>true</xmlOutput>
+ <!-- BUILD FAIL ON FINDBUGS ERRORS -->
+ <failOnError>${findbugs.failOnError}</failOnError>
+ <excludeFilterFile>${main.basedir}/findbugs-exclude.xml</excludeFilterFile>
+ <outputDirectory>${project.reporting.outputDirectory}/findbugs</outputDirectory>
+ <findbugsXmlOutputDirectory>${project.reporting.outputDirectory}/findbugs
+ </findbugsXmlOutputDirectory>
+ </configuration>
+ <executions>
+ <execution>
+ <id>analyze-compile</id>
+ <phase>compile</phase>
+ <goals>
+ <goal>check</goal>
+ </goals>
+ </execution>
+ </executions>
+ </plugin>
+
+ <!-- PMD PLUGIN SETUP -->
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-pmd-plugin</artifactId>
+ <version>${pmd.plugin.version}</version>
+ <configuration>
+ <sourceEncoding>${project.build.sourceEncoding}</sourceEncoding>
+ <targetJdk>${compiler.target.version}</targetJdk>
+ <linkXRef>false</linkXRef>
+ <!-- BUILD FAIL ON PMD VIOLATION -->
+ <failOnViolation>${pmd.violation.buildfail}</failOnViolation>
+ <targetDirectory>${project.reporting.outputDirectory}/pmd</targetDirectory>
+ <minimumTokens>200</minimumTokens>
+ </configuration>
+ <executions>
+ <execution>
+ <id>pmd-check</id>
+ <goals>
+ <goal>check</goal>
+ </goals>
+ <configuration>
+ <printFailingErrors>true</printFailingErrors>
+ <excludeFromFailureFile>${main.basedir}/pmd-exclude.properties</excludeFromFailureFile>
+ </configuration>
+ </execution>
+ <execution>
+ <id>cpd-check</id>
+ <goals>
+ <goal>cpd-check</goal>
+ </goals>
+ <configuration>
+ <printFailingErrors>true</printFailingErrors>
+ <excludeFromFailureFile>${main.basedir}/cpd-exclude.properties</excludeFromFailureFile>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+
+
+
+
+ <!-- LOMBOK PLUGIN -->
+ <plugin>
+ <groupId>org.projectlombok</groupId>
+ <artifactId>lombok-maven-plugin</artifactId>
+ <version>${lombok.plugin.version}</version>
+ <executions>
+ <execution>
+ <id>delombok</id>
+ <phase>generate-sources</phase>
+ <goals>
+ <goal>delombok</goal>
+ </goals>
+ <configuration>
+ <addOutputDirectory>false</addOutputDirectory>
+ <sourceDirectory>src/main/java</sourceDirectory>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+
+ <!-- JAR PLUGIN -->
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-jar-plugin</artifactId>
+ <version>${jar.plugin.version}</version>
+ <configuration>
+ <archive>
+ <manifest>
+ <addDefaultImplementationEntries>true</addDefaultImplementationEntries>
+ </manifest>
+ <manifestEntries>
+ <Implementation-Build-Version>${project.version}</Implementation-Build-Version>
+ </manifestEntries>
+ </archive>
+ </configuration>
+ </plugin>
+
+ <!-- DEPLOY PLUGIN -->
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-deploy-plugin</artifactId>
+ <version>${deploy.plugin.version}</version>
+ <configuration>
+ <deployAtEnd>true</deployAtEnd>
+ </configuration>
+ </plugin>
+
+ </plugins>
+
+ </pluginManagement>
+
+ <plugins>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-compiler-plugin</artifactId>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-jar-plugin</artifactId>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-surefire-plugin</artifactId>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-failsafe-plugin</artifactId>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-deploy-plugin</artifactId>
+ </plugin>
+
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-source-plugin</artifactId>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-javadoc-plugin</artifactId>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-pmd-plugin</artifactId>
+ </plugin>
+
+ <plugin>
+ <groupId>org.codehaus.mojo</groupId>
+ <artifactId>findbugs-maven-plugin</artifactId>
+ </plugin>
+ </plugins>
+
+ </build>
+
+ <profiles>
+ <profile>
+ <id>disable-java8-doclint</id>
+ <activation>
+ <jdk>[1.8,)</jdk>
+ </activation>
+ <properties>
+ <additionalparam>-Xdoclint:none</additionalparam>
+ </properties>
+ </profile>
+ </profiles>
+
+</project>
diff --git a/eelf-logger/version.properties b/eelf-logger/version.properties
new file mode 100644
index 0000000..907cdc4
--- /dev/null
+++ b/eelf-logger/version.properties
@@ -0,0 +1,25 @@
+#
+# ================================================================================
+# Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+# ================================================================================
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+# ============LICENSE_END=========================================================
+#
+#
+
+major=1
+minor=0
+patch=0
+base_version=${major}.${minor}.${patch}
+release_version=${base_version}
+snapshot_version=${base_version}-SNAPSHOT
diff --git a/mvn-phase-script.sh b/mvn-phase-script.sh
index 5fa716a..7d432af 100755
--- a/mvn-phase-script.sh
+++ b/mvn-phase-script.sh
@@ -33,17 +33,10 @@ if [ -z "${MVN_NEXUSPROXY}" ]; then
echo "MVN_NEXUSPROXY environment variable not set. Cannot proceed"
exit 1
fi
-if [ -z "$SETTINGS_FILE" ]; then
- echo "SETTINGS_FILE environment variable not set. Cannot proceed"
- exit 2
-fi
+export SETTINGS_FILE=${SETTINGS_FILE:-$HOME/.m2/settings.xml}
set +e
-if ! wget -O ${PROJECT_ROOT}/mvn-phase-lib.sh \
- "$MVN_RAWREPO_BASEURL_DOWNLOAD"/org.onap.dcaegen2.utils/releases/scripts/mvn-phase-lib.sh; then
- cp "${PROJECT_ROOT}"/scripts/mvn-phase-lib.sh "${PROJECT_ROOT}/mvn-phase-lib.sh"
-fi
-source "${PROJECT_ROOT}"/mvn-phase-lib.sh
+source "${PROJECT_ROOT}"/scripts/mvn-phase-lib.sh
# This is the base for where "deploy" will upload
@@ -86,9 +79,12 @@ test)
echo "==> test phase script"
case $MVN_PROJECT_MODULEID in
*)
- set +e
- run_tox_test
- set -e
+ if [ -f tox.ini ]
+ then
+ set -e
+ run_tox_test
+ set +e
+ fi
;;
esac
;;
diff --git a/onap-dcae-cbs-docker-client/.coveragerc b/onap-dcae-cbs-docker-client/.coveragerc
index 38c506c..c60c1ee 100644
--- a/onap-dcae-cbs-docker-client/.coveragerc
+++ b/onap-dcae-cbs-docker-client/.coveragerc
@@ -21,8 +21,3 @@ exclude_lines =
# Don't complain if non-runnable code isn't run:
if 0:
if __name__ == .__main__.:
-
-[xml]
-output = coverage-reports/coverage-configbinding.xml
-
-
diff --git a/onap-dcae-cbs-docker-client/.gitignore b/onap-dcae-cbs-docker-client/.gitignore
index c86ccf6..4f07413 100644
--- a/onap-dcae-cbs-docker-client/.gitignore
+++ b/onap-dcae-cbs-docker-client/.gitignore
@@ -1,3 +1,4 @@
+.pytest_cache/
xunit-results.xml
.DS_Store
# Byte-compiled / optimized / DLL files
diff --git a/onap-dcae-cbs-docker-client/Changelog.md b/onap-dcae-cbs-docker-client/Changelog.md
index 5027203..1269750 100644
--- a/onap-dcae-cbs-docker-client/Changelog.md
+++ b/onap-dcae-cbs-docker-client/Changelog.md
@@ -1,9 +1,23 @@
# Change Log
All notable changes to this project will be documented in this file.
-The format is based on [Keep a Changelog](http://keepachangelog.com/)
+The format is based on [Keep a Changelog](http://keepachangelog.com/)
and this project adheres to [Semantic Versioning](http://semver.org/).
+## [1.0.2]
+* Refactor some code, PEP8 compliance
+* Add flake8 to tox
+
+## [1.0.1]
+* [Sadly, Missing]
+
+## [1.0.0]
+* Depend on the CBS 2.0.0 API
+* Add new endpoint for getting all
+
+## [0.0.5]
+* Dont pin requests version
+
## [0.0.3]
* Changelog started
* Unit test suite created
diff --git a/onap-dcae-cbs-docker-client/README.md b/onap-dcae-cbs-docker-client/README.md
index 1e622a7..81a8ef0 100644
--- a/onap-dcae-cbs-docker-client/README.md
+++ b/onap-dcae-cbs-docker-client/README.md
@@ -1,11 +1,11 @@
# Python CBS Docker Client
-Used for DCAE Dockerized microservices written in Python. Pulls your configuration from the config_binding_service. Expects that CONSUL_HOST and HOSTNAME are set as env variables, which is true in DCAE.
+Used for DCAE Dockerized microservices written in Python. Pulls your configuration from the config_binding_service. Expects that CONSUL_HOST and HOSTNAME are set as env variables, which is true in DCAE.
# Client Usage
## Development outside of Docker
-To test your raw code without Docker, you will need to set the env variables CONSUL_HOST and HOSTNAME (name of your key to pull from) that are set in DCAEs Docker enviornment.
+To test your raw code without Docker, you will need to set the env variables CONSUL_HOST and HOSTNAME (name of your key to pull from) that are set in DCAEs Docker enviornment.
1. `CONSUL_HOST` is the hostname only of the Consul instance you are talking to
2. HOSTNAME is the name of your component in Consul
@@ -13,6 +13,7 @@ To test your raw code without Docker, you will need to set the env variables CON
```
>>> from onap_dcae_cbs_docker_client import client
>>> client.get_config()
+>>> client.get_all()
```
# Installation
@@ -24,6 +25,6 @@ pip install onap-dcae-cbs-docker-client
# Testing
```
-tox -c tox-local.ini
+tox
```
diff --git a/onap-dcae-cbs-docker-client/onap_dcae_cbs_docker_client/__init__.py b/onap-dcae-cbs-docker-client/onap_dcae_cbs_docker_client/__init__.py
index 9e81f65..e9d0246 100644
--- a/onap-dcae-cbs-docker-client/onap_dcae_cbs_docker_client/__init__.py
+++ b/onap-dcae-cbs-docker-client/onap_dcae_cbs_docker_client/__init__.py
@@ -1,6 +1,5 @@
-# org.onap.dcae
# ================================================================================
-# Copyright (c) 2017 AT&T Intellectual Property. All rights reserved.
+# Copyright (c) 2017-2018 AT&T Intellectual Property. All rights reserved.
# ================================================================================
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -16,4 +15,3 @@
# ============LICENSE_END=========================================================
#
# ECOMP is a trademark and service mark of AT&T Intellectual Property.
-
diff --git a/onap-dcae-cbs-docker-client/onap_dcae_cbs_docker_client/client.py b/onap-dcae-cbs-docker-client/onap_dcae_cbs_docker_client/client.py
index ce9ac74..adcec85 100644
--- a/onap-dcae-cbs-docker-client/onap_dcae_cbs_docker_client/client.py
+++ b/onap-dcae-cbs-docker-client/onap_dcae_cbs_docker_client/client.py
@@ -1,6 +1,5 @@
-# org.onap.dcae
# ================================================================================
-# Copyright (c) 2017 AT&T Intellectual Property. All rights reserved.
+# Copyright (c) 2017-2018 AT&T Intellectual Property. All rights reserved.
# ================================================================================
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -18,39 +17,50 @@
# ECOMP is a trademark and service mark of AT&T Intellectual Property.
import json
-import requests
import os
import logging
+import requests
+
+LOGGER = logging.getLogger().getChild(__name__)
+
+
+class ENVsMissing(Exception):
+ """
+ Exception to represent critical ENVs are missing
+ """
+ pass
+
+
+#########
+# HELPERS
-root = logging.getLogger()
-logger = root.getChild(__name__)
def _get_uri_from_consul(consul_url, name):
"""
Call consul's catalog
- TODO: currently assumes there is only one service with this HOSTNAME
+ TODO: currently assumes there is only one service with this hostname
"""
url = "{0}/v1/catalog/service/{1}".format(consul_url, name)
- logger.debug("Trying to lookup service: {0}".format(url))
+ LOGGER.debug("Trying to lookup service: {0}".format(url))
res = requests.get(url)
- try:
- res.raise_for_status()
- services = res.json()
- return "http://{0}:{1}".format(services[0]["ServiceAddress"], services[0]["ServicePort"])
- except Exception as e:
- logger.error("Exception occured when querying Consul: either could not hit {0} or no service registered. Error code: {1}, Error Text: {2}".format(url, res.status_code, res.text))
- return None
+ res.raise_for_status()
+ services = res.json()
+ return "http://{0}:{1}".format(services[0]["ServiceAddress"], services[0]["ServicePort"])
+
def _get_envs():
"""
- Returns HOSTNAME, CONSUL_HOST, CONFIG_BINDING_SERVICE or crashes for caller to deal with
+ Returns hostname, consul_host.
+ If the necessary ENVs are not found, this is fatal, and raises an exception.
"""
- HOSTNAME = os.environ["HOSTNAME"]
- CONSUL_HOST = os.environ["CONSUL_HOST"]
- return HOSTNAME, CONSUL_HOST
+ if "HOSTNAME" not in os.environ or "CONSUL_HOST" not in os.environ:
+ raise ENVsMissing("HOSTNAME or CONSUL_HOST missing")
+ hostname = os.environ["HOSTNAME"]
+ consul_host = os.environ["CONSUL_HOST"]
+ return hostname, consul_host
-#Public
-def get_config():
+
+def _get_path(path):
"""
This call does not raise an exception if Consul or the CBS cannot complete the request.
It logs an error and returns {} if the config is not bindable.
@@ -62,24 +72,39 @@ def get_config():
config = {}
- HOSTNAME, CONSUL_HOST = _get_envs()
+ hostname, consul_host = _get_envs()
- #not sure how I as the component developer is supposed to know consul port
- consul_url = "http://{0}:8500".format(CONSUL_HOST)
+ # not sure how I as the component developer is supposed to know consul port
+ consul_url = "http://{0}:8500".format(consul_host)
- #get the CBS URL. Would not need the following hoorahrah if we had DNS.
- cbs_url = _get_uri_from_consul(consul_url, "config_binding_service")
- if cbs_url is None:
- logger.error("Cannot bind config at this time, cbs is unreachable")
- else:
- #get my config
- my_config_endpoint = "{0}/service_component/{1}".format(cbs_url, HOSTNAME)
+ try:
+ # get my config
+ cbs_url = _get_uri_from_consul(consul_url, "config_binding_service")
+ my_config_endpoint = "{0}/{1}/{2}".format(cbs_url, path, hostname)
res = requests.get(my_config_endpoint)
- try:
- res.raise_for_status()
- config = res.json()
- logger.info("get_config returned the following configuration: {0}".format(json.dumps(config)))
- except:
- logger.error("in get_config, the config binding service endpoint {0} blew up on me. Error code: {1}, Error text: {2}".format(my_config_endpoint, res.status_code, res.text))
+
+ res.raise_for_status()
+ config = res.json()
+ LOGGER.info("get_config returned the following configuration: {0}".format(
+ json.dumps(config)))
+ except requests.exceptions.HTTPError as exc:
+ LOGGER.error("in get_config, the config binding service endpoint %s was not reachable. Error code: %d, Error text: %s", my_config_endpoint, res.status_code, res.text)
+ except Exception as exc:
+ LOGGER.exception(exc)
return config
+
+#########
+# Public
+def get_all():
+ """
+ Hit the CBS service_component_all endpoint
+ """
+ return _get_path("service_component_all")
+
+
+def get_config():
+ """
+ Hit the CBS service_component endpoint
+ """
+ return _get_path("service_component")
diff --git a/onap-dcae-cbs-docker-client/pom.xml b/onap-dcae-cbs-docker-client/pom.xml
index d334aae..d006a29 100644
--- a/onap-dcae-cbs-docker-client/pom.xml
+++ b/onap-dcae-cbs-docker-client/pom.xml
@@ -34,19 +34,13 @@ ECOMP is a trademark and service mark of AT&T Intellectual Property.
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<!-- Sonar -->
- <sonar.skip>false</sonar.skip>
<sonar.sources>.</sonar.sources>
<sonar.junit.reportsPath>xunit-results.xml</sonar.junit.reportsPath>
- <!--
- <sonar.python.coverage.reportPath>coverage.xml</sonar.python.coverage.reportPath>
- see https://docs.sonarqube.org/display/PLUG/Python+Coverage+Results+Import
- Ant pattern describing the path to coverage reports, relative to projects root. Leave unset to use the default ("coverage-reports/coverage-*.xml").
- -->
+ <sonar.python.coverage.reportPath>coverage.xml</sonar.python.coverage.reportPath>
<sonar.language>py</sonar.language>
<sonar.pluginName>Python</sonar.pluginName>
<sonar.inclusions>**/*.py</sonar.inclusions>
- <sonar.exclusions>tests/*</sonar.exclusions>
- <sonar.host.url>http://135.205.228.63:9000</sonar.host.url>
+ <sonar.exclusions>tests/*,setup.py</sonar.exclusions>
</properties>
<build>
<finalName>${project.artifactId}-${project.version}</finalName>
diff --git a/onap-dcae-cbs-docker-client/requirements.txt b/onap-dcae-cbs-docker-client/requirements.txt
deleted file mode 100644
index 856c82c..0000000
--- a/onap-dcae-cbs-docker-client/requirements.txt
+++ /dev/null
@@ -1 +0,0 @@
-requests==2.18.3
diff --git a/onap-dcae-cbs-docker-client/setup.py b/onap-dcae-cbs-docker-client/setup.py
index 9f23048..b4fdf0e 100644
--- a/onap-dcae-cbs-docker-client/setup.py
+++ b/onap-dcae-cbs-docker-client/setup.py
@@ -1,6 +1,5 @@
-# org.onap.dcae
# ================================================================================
-# Copyright (c) 2017 AT&T Intellectual Property. All rights reserved.
+# Copyright (c) 2017-2018 AT&T Intellectual Property. All rights reserved.
# ================================================================================
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -17,23 +16,19 @@
#
# ECOMP is a trademark and service mark of AT&T Intellectual Property.
-import os
from setuptools import setup, find_packages
-from pip.req import parse_requirements
-from pip.download import PipSession
-
-install_reqs = parse_requirements("requirements.txt", session=PipSession())
-reqs = [str(ir.req) for ir in install_reqs]
setup(
- name = "onap_dcae_cbs_docker_client",
- description = "very lightweight client for a DCAE dockerized component to get it's config from the CBS",
- version = "0.0.3",
+ name="onap_dcae_cbs_docker_client",
+ description="very lightweight client for a DCAE dockerized component to get it's config from the CBS",
+ version="1.0.2",
packages=find_packages(),
- author = "Tommy Carpenter",
- author_email = "tommy@research.att.com",
+ author="Tommy Carpenter",
+ author_email="tommy@research.att.com",
license='Apache 2',
- keywords = "",
- url = "",
- install_requires=reqs
+ keywords="",
+ url="",
+ install_requires=[
+ "requests>= 2.0.0, < 3.0.0"
+ ]
)
diff --git a/onap-dcae-cbs-docker-client/tests/test_client.py b/onap-dcae-cbs-docker-client/tests/test_client.py
index 6c9062b..dd6ab10 100644
--- a/onap-dcae-cbs-docker-client/tests/test_client.py
+++ b/onap-dcae-cbs-docker-client/tests/test_client.py
@@ -1,36 +1,63 @@
-from onap_dcae_cbs_docker_client.client import get_config
-import requests
+# ================================================================================
+# Copyright (c) 2017-2018 AT&T Intellectual Property. All rights reserved.
+# ================================================================================
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+# ============LICENSE_END=========================================================
+#
+# ECOMP is a trademark and service mark of AT&T Intellectual Property.
+from onap_dcae_cbs_docker_client.client import get_config, get_all
+
class FakeResponse:
def __init__(self, status_code, thejson):
self.status_code = status_code
self.thejson = thejson
+
def raise_for_status(self):
pass
+
def json(self):
return self.thejson
-def test_client(monkeypatch):
- def monkeyed_requests_get(url):
- #mock all the get calls for existent and non-existent
- if url == "http://consuldotcom:8500/v1/catalog/service/config_binding_service":
- return FakeResponse(
- status_code = 200,
- thejson = [
- {"ServiceAddress" : "666.666.666.666",
- "ServicePort" : 8888
- }]
- )
- elif url == "http://666.666.666.666:8888/service_component/mybestfrienddotcom":
- return FakeResponse(
- status_code = 200,
- thejson = {"key_to_your_heart" : 666})
+def monkeyed_requests_get(url):
+ # mock all the get calls for existent and non-existent
+ if url == "http://consuldotcom:8500/v1/catalog/service/config_binding_service":
+ return FakeResponse(status_code=200,
+ thejson=[{"ServiceAddress": "666.666.666.666",
+ "ServicePort": 8888}])
+ elif url == "http://666.666.666.666:8888/service_component_all/mybestfrienddotcom":
+ return FakeResponse(status_code=200,
+ thejson={"config": {"key_to_your_heart": 666},
+ "dti": {"some amazing": "dti stuff"},
+ "policies": {"event": {"foo": "bar"},
+ "items": [{"foo2": "bar2"}]},
+ "otherkey": {"foo3": "bar3"}})
-
- monkeypatch.setattr('requests.get', monkeyed_requests_get)
- assert(get_config() == {"key_to_your_heart" : 666})
+ elif url == "http://666.666.666.666:8888/service_component/mybestfrienddotcom":
+ return FakeResponse(status_code=200,
+ thejson={"key_to_your_heart": 666})
+def test_config(monkeypatch):
+ monkeypatch.setattr('requests.get', monkeyed_requests_get)
+ assert(get_config() == {"key_to_your_heart": 666})
+def test_all(monkeypatch):
+ monkeypatch.setattr('requests.get', monkeyed_requests_get)
+ assert(get_all() == {"config": {"key_to_your_heart": 666},
+ "dti": {"some amazing": "dti stuff"},
+ "policies": {"event": {"foo": "bar"},
+ "items": [{"foo2": "bar2"}]},
+ "otherkey": {"foo3": "bar3"}})
diff --git a/onap-dcae-cbs-docker-client/tox-local.ini b/onap-dcae-cbs-docker-client/tox-local.ini
index a5991a9..8e48932 100644
--- a/onap-dcae-cbs-docker-client/tox-local.ini
+++ b/onap-dcae-cbs-docker-client/tox-local.ini
@@ -1,15 +1,21 @@
[tox]
-envlist = py27,py36
+envlist = py27,py36,flake8
[testenv]
deps=
- -rrequirements.txt
pytest
coverage
pytest-cov
-setenv =
+setenv =
CONSUL_HOST = consuldotcom
HOSTNAME = mybestfrienddotcom
commands=pytest --cov {envsitepackagesdir}/onap_dcae_cbs_docker_client --cov-report html
+[testenv:flake8]
+basepython = python3.6
+skip_install = true
+deps = flake8
+commands = flake8 setup.py onap_dcae_cbs_docker_client tests
+[flake8]
+ignore = E501
diff --git a/onap-dcae-cbs-docker-client/tox.ini b/onap-dcae-cbs-docker-client/tox.ini
index 9e57fc0..6bbe73f 100644
--- a/onap-dcae-cbs-docker-client/tox.ini
+++ b/onap-dcae-cbs-docker-client/tox.ini
@@ -1,15 +1,26 @@
# content of: tox.ini , put in same dir as setup.py
[tox]
-envlist = py27,py35
+envlist = py27,py36,flake8
[testenv]
deps=
- -rrequirements.txt
pytest
coverage
pytest-cov
setenv =
CONSUL_HOST = consuldotcom
HOSTNAME = mybestfrienddotcom
+ PYTHONPATH={toxinidir}
-commands=pytest --junitxml xunit-results.xml --cov {envsitepackagesdir}/onap_dcae_cbs_docker_client --cov-report=xml
+commands=
+ pytest --junitxml xunit-results.xml --cov onap_dcae_cbs_docker_client --cov-report xml
+ coverage xml
+
+[testenv:flake8]
+basepython = python3.6
+skip_install = true
+deps = flake8
+commands = flake8 setup.py onap_dcae_cbs_docker_client tests
+
+[flake8]
+ignore = E501
diff --git a/onap-dcae-dcaepolicy-lib/.coveragerc b/onap-dcae-dcaepolicy-lib/.coveragerc
index 26ed8ac..43c7005 100644
--- a/onap-dcae-dcaepolicy-lib/.coveragerc
+++ b/onap-dcae-dcaepolicy-lib/.coveragerc
@@ -23,7 +23,3 @@ exclude_lines =
if __name__ == .__main__.:
ignore_errors = True
-
-[xml]
-output = coverage-reports/coverage-onap_dcae_dcaepolicy_lib.xml
-
diff --git a/onap-dcae-dcaepolicy-lib/LICENSE.txt b/onap-dcae-dcaepolicy-lib/LICENSE.txt
index 45ec201..0b6ac42 100644
--- a/onap-dcae-dcaepolicy-lib/LICENSE.txt
+++ b/onap-dcae-dcaepolicy-lib/LICENSE.txt
@@ -1,7 +1,5 @@
============LICENSE_START=======================================================
-org.onap.dcae
-================================================================================
-Copyright (c) 2017 AT&T Intellectual Property. All rights reserved.
+Copyright (c) 2017-2018 AT&T Intellectual Property. All rights reserved.
================================================================================
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
diff --git a/onap-dcae-dcaepolicy-lib/README.md b/onap-dcae-dcaepolicy-lib/README.md
index ff37256..b46f0b1 100644
--- a/onap-dcae-dcaepolicy-lib/README.md
+++ b/onap-dcae-dcaepolicy-lib/README.md
@@ -1,4 +1,5 @@
# onap-dcae-dcaepolicy-lib - policy in dcae controller
+
- python-package to be used in cloudify plugins to maintain the policies lifecycle
## upload the python package to pypi server
@@ -8,23 +9,26 @@ python setup.py sdist upload
```
---
-# usage in plugins
-**requirements.txt**
+## usage in plugins
+
+### **requirements.txt**
+
```python
onap-dcae-dcaepolicy-lib==1.0.0
```
-**tasks.py**
-- import
+### **tasks.py**
+
+import
```python
from onap_dcae_dcaepolicy_lib import Policies
```
-# examples of **@operation** with **@Policies.<>** decorator
+### examples of **@operation** with **@Policies.<>** decorator
-## Usage
+### Usage:
import the dcaepolicy-node-type.yaml into your blueprint to use the dcae.nodes.type node
@@ -46,9 +50,12 @@ node_templates:
Then the dcaepolicyplugin will bring the latest policy to the dcae.nodes.policy node during the install workflow of cloudify.
-------
-## cloudify.interfaces.lifecycle.**configure**
+---
+
+### cloudify.interfaces.lifecycle.**configure**
+
- gather policy data into runtime_properties of policy consumer node
+
```yaml
cloudify.interfaces.lifecycle:
configure:
@@ -64,23 +71,15 @@ APPLICATION_CONFIG = "application_config"
SERVICE_COMPONENT_NAME = "service_component_name"
@operation
-@Policies.gather_policies_to_node
+@Policies.gather_policies_to_node()
def node_configure(**kwargs):
- """decorate with @Policies.gather_policies_to_node on policy consumer node to
+ """decorate with @Policies.gather_policies_to_node() on policy consumer node to
prepopulate runtime_properties[POLICIES]
"""
- app_config = None
- if APPLICATION_CONFIG in ctx.node.properties:
- # dockerized blueprint puts the app config into property application_config
- app_config = ctx.node.properties.get(APPLICATION_CONFIG)
- else:
- # CDAP components expect that in property app_config
- app_config = ctx.node.properties.get("app_config")
-
- app_config = Policies.shallow_merge_policies_into(app_config)
+ app_config = ctx.node.properties.get(APPLICATION_CONFIG)
+
ctx.instance.runtime_properties[APPLICATION_CONFIG] = app_config
- ctx.logger.info("example: applied policy_configs to property app_config: {0}" \
- .format(json.dumps(app_config)))
+ ctx.logger.info("app_config: {0}".format(json.dumps(app_config)))
if SERVICE_COMPONENT_NAME in ctx.instance.runtime_properties:
ctx.logger.info("saving app_config({0}) to consul under key={1}" \
@@ -88,16 +87,6 @@ def node_configure(**kwargs):
ctx.instance.runtime_properties[SERVICE_COMPONENT_NAME]))
DiscoveryClient.put_kv(ctx.instance.runtime_properties[SERVICE_COMPONENT_NAME], app_config)
- # alternative 1 - use the list of policy configs from policies in runtime_properties
- policy_configs = Policies.get_policy_configs()
- if policy_configs:
- ctx.logger.warn("TBD: apply policy_configs: {0}".format(json.dumps(policy_configs)))
-
- # alternative 2 - use the policies dict by policy_id from runtime_properties
- if POLICIES in ctx.instance.runtime_properties:
- policies = ctx.instance.runtime_properties[POLICIES]
- ctx.logger.warn("TBD: apply policies: {0}".format(json.dumps(policies)))
-
ctx.logger.info("deploying the demo component: {0}...".format(ctx.node.id))
demo_app = DemoApp(ctx.node.id)
demo_app.start()
@@ -105,8 +94,10 @@ def node_configure(**kwargs):
demo_app.get_logs()
```
-------
-## execute-operation **policy-update**
+---
+
+### execute-operation **policy-update**
+
```yaml
dcae.interfaces.policy:
policy_update:
@@ -114,6 +105,7 @@ dcae.interfaces.policy:
```
execute-operation **policy-update** that gets a list of changed policy-configs
+
```python
from .discovery import DiscoveryClient
@@ -123,25 +115,13 @@ APPLICATION_CONFIG = "application_config"
SERVICE_COMPONENT_NAME = "service_component_name"
@operation
-@Policies.update_policies_on_node(configs_only=True)
-def policy_update(updated_policies, **kwargs):
+@Policies.update_policies_on_node()
+def policy_update(updated_policies, removed_policies=None, policies=None, **kwargs):
"""decorate with @Policies.update_policies_on_node() to update runtime_properties[POLICIES]
:updated_policies: contains the list of changed policy-configs when configs_only=True (default).
Use configs_only=False to bring the full policy objects in :updated_policies:.
"""
- app_config = DiscoveryClient.get_value(ctx.instance.runtime_properties[SERVICE_COMPONENT_NAME])
-
- # This is how to merge the policies into app_config object
- app_config = Policies.shallow_merge_policies_into(app_config)
-
- ctx.logger.info("merged updated_policies {0} into app_config {1}"
- .format(json.dumps(updated_policies), json.dumps(app_config)))
-
- ctx.instance.runtime_properties[APPLICATION_CONFIG] = app_config
-
- DiscoveryClient.put_kv(ctx.instance.runtime_properties[SERVICE_COMPONENT_NAME], app_config)
-
# example how to notify the dockerized component about the policy change
notify_app_through_script = True
if notify_app_through_script:
@@ -149,24 +129,29 @@ def policy_update(updated_policies, **kwargs):
.format(json.dumps(updated_policies), json.dumps(app_config)))
demo_app = DemoApp(ctx.node.id)
demo_app.notify_app_through_script(
- POLICY_MESSAGE_TYPE,
+ "policies",
updated_policies=updated_policies,
- application_config=app_config
+ removed_policies=removed_policies,
+ policies=policies
)
```
example of the **changed\_policies** with **configs_only=True**
+
- list of config objects (preparsed from json string)
+
- manual mess produced by mock_policy_updater
+
```json
[{
- "policy_updated_from_ver": "2",
- "policy_updated_to_ver": "3",
- "updated_policy_id": "DCAE_alex.Config_db_client_policy_id_value",
- "policy_hello": "world!",
- "policy_updated_ts": "2017-08-17T21:49:39.279187Z"
+ "policy_updated_from_ver": "2",
+ "policy_updated_to_ver": "3",
+ "updated_policy_id": "DCAE_alex.Config_db_client_policy_id_value",
+ "policy_hello": "world!",
+ "policy_updated_ts": "2017-08-17T21:49:39.279187Z"
}]
```
+
---
example of **policies** in runtime_properties **before policy-update**
diff --git a/onap-dcae-dcaepolicy-lib/onap_dcae_dcaepolicy_lib/__init__.py b/onap-dcae-dcaepolicy-lib/onap_dcae_dcaepolicy_lib/__init__.py
index b3658b1..f8a2498 100644
--- a/onap-dcae-dcaepolicy-lib/onap_dcae_dcaepolicy_lib/__init__.py
+++ b/onap-dcae-dcaepolicy-lib/onap_dcae_dcaepolicy_lib/__init__.py
@@ -1,8 +1,5 @@
-"""expose the Policies class on the package level"""
-
-# org.onap.dcae
# ================================================================================
-# Copyright (c) 2017 AT&T Intellectual Property. All rights reserved.
+# Copyright (c) 2017-2018 AT&T Intellectual Property. All rights reserved.
# ================================================================================
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -19,4 +16,6 @@
#
# ECOMP is a trademark and service mark of AT&T Intellectual Property.
-from .dcae_policy import Policies, POLICIES, POLICY_MESSAGE_TYPE
+"""expose the Policies class on the package level"""
+
+from .dcae_policy import Policies
diff --git a/onap-dcae-dcaepolicy-lib/onap_dcae_dcaepolicy_lib/dcae_policy.py b/onap-dcae-dcaepolicy-lib/onap_dcae_dcaepolicy_lib/dcae_policy.py
index 6a277f3..65c2614 100644
--- a/onap-dcae-dcaepolicy-lib/onap_dcae_dcaepolicy_lib/dcae_policy.py
+++ b/onap-dcae-dcaepolicy-lib/onap_dcae_dcaepolicy_lib/dcae_policy.py
@@ -1,8 +1,5 @@
-"""dcae_policy contains decorators for the policy lifecycle in cloudify"""
-
-# org.onap.dcae
# ================================================================================
-# Copyright (c) 2017 AT&T Intellectual Property. All rights reserved.
+# Copyright (c) 2017-2018 AT&T Intellectual Property. All rights reserved.
# ================================================================================
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -19,124 +16,293 @@
#
# ECOMP is a trademark and service mark of AT&T Intellectual Property.
+"""dcae_policy contains decorators for the policy lifecycle in cloudify"""
+
import json
-import copy
+import traceback
+from copy import deepcopy
from functools import wraps
from cloudify import ctx
from cloudify.context import NODE_INSTANCE
from cloudify.exceptions import NonRecoverableError
+from .policies_output import PoliciesOutput
+
POLICIES = 'policies'
+POLICY_FILTERS = 'policy_filters'
+POLICIES_FILTERED = 'policies_filtered'
POLICY_ID = 'policy_id'
POLICY_BODY = 'policy_body'
POLICY_VERSION = "policyVersion"
POLICY_CONFIG = 'config'
+
+POLICY_FILTER = 'policy_filter'
+POLICY_FILTER_ID = 'policy_filter_id'
+
+POLICY_PERSISTENT = 'policy_persistent'
DCAE_POLICY_TYPE = 'dcae.nodes.policy'
-POLICY_MESSAGE_TYPE = 'policy'
+DCAE_POLICIES_TYPE = 'dcae.nodes.policies'
+
+ACTION_GATHERED = "gathered"
+ACTION_UPDATED = "updated"
+
+CONFIG_ATTRIBUTES = "configAttributes"
class Policies(object):
"""static class for policy operations"""
+ _updated_policies = {}
+ _removed_policies = {}
@staticmethod
- def gather_policies_to_node(func):
- """decorate with @Policies.gather_policies_to_node to
- gather the policies from dcae.nodes.policy nodes this node depends on.
+ def _init():
+ """init static members"""
+ Policies._updated_policies = {}
+ Policies._removed_policies = {}
- Places the policies into runtime_properties["policies"].
+ @staticmethod
+ def _set_policies(policies):
+ """store the :policies: in :runtime_properties[POLICIES]:"""
+ if not policies:
+ if POLICIES in ctx.instance.runtime_properties:
+ del ctx.instance.runtime_properties[POLICIES]
+ return
- Call Policies.shallow_merge_policies_into(config) to merge the policies into config.
- """
- def _merge_policy_with_node(target):
- """get all properties of the policy node and add the actual policy"""
- policy = dict(target.node.properties)
- if POLICY_BODY in target.instance.runtime_properties:
- policy[POLICY_BODY] = target.instance.runtime_properties[POLICY_BODY]
- return policy
+ ctx.instance.runtime_properties[POLICIES] = policies
- if not func:
+ @staticmethod
+ def _add_policy(policy_id, policy, policy_persistent, policies):
+ """only add the latest version of policy to policies"""
+ prev_policy = policies.get(policy_id)
+ prev_policy_persistent = (prev_policy or {}).get(POLICY_PERSISTENT)
+
+ if not prev_policy \
+ or (policy_persistent and not prev_policy_persistent) \
+ or (policy_persistent == prev_policy_persistent and policy.get(POLICY_BODY)):
+ policy = deepcopy(policy)
+ policy[POLICY_PERSISTENT] = policy_persistent
+ policies[policy_id] = policy
+
+ @staticmethod
+ def _gather_policy(target, policies):
+ """adds the policy from dcae.nodes.policy node to policies"""
+ if DCAE_POLICY_TYPE not in target.node.type_hierarchy:
return
+ policy_id = target.node.properties.get(POLICY_ID)
+ if not policy_id:
+ return True
+ policy = deepcopy(dict(target.node.properties))
+ policy_body = target.instance.runtime_properties.get(POLICY_BODY)
+ if policy_body:
+ policy[POLICY_BODY] = policy_body
- @wraps(func)
- def wrapper(*args, **kwargs):
- """gather and save the policies from dcae.nodes.policy nodes this node related to"""
+ Policies._add_policy(policy_id, policy, True, policies)
+ return True
+
+ @staticmethod
+ def _fix_policy_filter(policy_filter):
+ if CONFIG_ATTRIBUTES in policy_filter:
+ config_attributes = policy_filter.get(CONFIG_ATTRIBUTES)
+ if isinstance(config_attributes, dict):
+ return
try:
- if ctx.type == NODE_INSTANCE:
- policies = dict([(rel.target.node.properties[POLICY_ID], \
- _merge_policy_with_node(rel.target)) \
- for rel in ctx.instance.relationships \
- if DCAE_POLICY_TYPE in rel.target.node.type_hierarchy \
- and POLICY_ID in rel.target.node.properties \
- and rel.target.node.properties[POLICY_ID] \
- ])
- if policies:
- ctx.instance.runtime_properties[POLICIES] = policies
- except Exception as ex:
- error = "Failed to set the policies {0}".format(str(ex))
- ctx.logger.error(error)
- raise NonRecoverableError(error)
-
- return func(*args, **kwargs)
- return wrapper
+ config_attributes = json.loads(config_attributes)
+ if config_attributes and isinstance(config_attributes, dict):
+ policy_filter[CONFIG_ATTRIBUTES] = config_attributes
+ return
+ except (ValueError, TypeError):
+ pass
+ if config_attributes:
+ ctx.logger.warn("unexpected %s: %s", CONFIG_ATTRIBUTES, config_attributes)
+ del policy_filter[CONFIG_ATTRIBUTES]
@staticmethod
- def _update_policies_on_ctx(updated_policies):
- """update policies in runtime_properties and return changed_policies"""
- if POLICIES not in ctx.instance.runtime_properties:
+ def _gather_policies(target, policies, policy_filters):
+ """adds the policies and policy-filter from dcae.nodes.policies node to policies"""
+ if DCAE_POLICIES_TYPE not in target.node.type_hierarchy:
return
- if not updated_policies:
- ctx.logger.error("update_policies_on_ctx - no updated_policies provided in arguments")
+
+ property_policy_filter = target.node.properties.get(POLICY_FILTER)
+ if property_policy_filter:
+ policy_filter = deepcopy(dict(
+ (k, v) for (k, v) in dict(property_policy_filter).iteritems()
+ if v or isinstance(v, (int, float))
+ ))
+ Policies._fix_policy_filter(policy_filter)
+
+ if policy_filter:
+ policy_filters[target.instance.id] = {
+ POLICY_FILTER_ID : target.instance.id,
+ POLICY_FILTER : policy_filter
+ }
+
+ filtered_policies = target.instance.runtime_properties.get(POLICIES_FILTERED)
+ if not filtered_policies or not isinstance(filtered_policies, dict):
+ return True
+ for (policy_id, policy) in filtered_policies.iteritems():
+ Policies._add_policy(policy_id, policy, False, policies)
+ return True
+
+ @staticmethod
+ def _get_policy_bodies_dict(policies):
+ """returns a dict of policy_id -> policy_body if policy_body exists"""
+ if not policies:
+ return {}
+
+ return dict((policy_id, policy.get(POLICY_BODY))
+ for policy_id, policy in policies.iteritems() if policy.get(POLICY_BODY)
+ )
+
+ @staticmethod
+ def gather_policies_to_node():
+ """
+ decorate with @Policies.gather_policies_to_node() to
+ gather the policies from dcae.nodes.policy nodes this node depends on.
+
+ Places the policies into runtime_properties["policies"].
+
+ Stores <scn>:policies data in consul-kv
+ """
+ def gather_policies_decorator(func):
+ """the decorator"""
+ if not func:
+ return
+
+ @wraps(func)
+ def wrapper(*args, **kwargs):
+ """gather and save the policies from dcae.nodes.policy nodes this node related to"""
+ if ctx.type != NODE_INSTANCE:
+ raise NonRecoverableError("can only invoke gather_policies_to_node on node")
+
+ policies_outputted = False
+ policy_bodies = []
+ try:
+ policies = {}
+ policy_filters = {}
+ for rel in ctx.instance.relationships:
+ _ = Policies._gather_policy(rel.target, policies) \
+ or Policies._gather_policies(rel.target, policies, policy_filters)
+
+ Policies._set_policies(policies)
+ if policy_filters:
+ ctx.instance.runtime_properties[POLICY_FILTERS] = policy_filters
+
+ policy_bodies = Policies._get_policy_bodies_dict(policies)
+ if policy_bodies:
+ policies_outputted = PoliciesOutput.store_policies(ACTION_GATHERED, policy_bodies)
+ except Exception as ex:
+ error = "Failed to set the policies {0}".format(str(ex))
+ ctx.logger.error("{0}: {1}".format(error, traceback.format_exc()))
+ raise NonRecoverableError(error)
+
+ func_result = func(*args, **kwargs)
+
+ if not policies_outputted and policy_bodies:
+ PoliciesOutput.store_policies(ACTION_GATHERED, policy_bodies)
+
+ return func_result
+ return wrapper
+ return gather_policies_decorator
+
+ @staticmethod
+ def _update_policies(updated_policies, added_policies, removed_policies):
+ """
+ filter and update policies in runtime_properties
+ and return the ordered filtered list of changed_policies
+ """
+ Policies._init()
+
+ if not updated_policies and not removed_policies and not added_policies:
+ ctx.logger.error("update_policies_on_ctx - no updated, added, or removed policies received")
return
- policies = ctx.instance.runtime_properties[POLICIES]
- ctx.logger.info("update_policies_on_ctx: {0}".format(json.dumps(updated_policies)))
- changed_policies = []
- ignored_policies = []
- unexpected_policies = []
- same_policies = []
+ updated_policies = updated_policies or []
+ added_policies = added_policies or {}
+ removed_policies = removed_policies or []
+
+ ctx.logger.info("updated_policies: {0}, added_policies: {1}, removed_policies: {2}"
+ .format(json.dumps(updated_policies),
+ json.dumps(added_policies),
+ json.dumps(removed_policies)))
+
+ policies = ctx.instance.runtime_properties.get(POLICIES, {})
+ policy_filters = ctx.instance.runtime_properties.get(POLICY_FILTERS, {})
+
+ for policy_id in removed_policies:
+ removed_policy = policies.get(policy_id)
+ if removed_policy and POLICY_BODY in removed_policy:
+ Policies._removed_policies[policy_id] = deepcopy(removed_policy)
+ if removed_policy.get(POLICY_PERSISTENT):
+ del policies[policy_id][POLICY_BODY]
+ else:
+ del policies[policy_id]
+
+ new_policies = dict((policy_id, policy)
+ for policy_filter_id in policy_filters
+ for (policy_id, policy) in added_policies.get(policy_filter_id, {})
+ .get(POLICIES, {}).iteritems())
+
+ ctx.logger.info("new_policies: {0}".format(json.dumps(new_policies)))
+
+ for (policy_id, policy) in new_policies.iteritems():
+ deployed_policy = policies.get(policy_id)
+ if not deployed_policy:
+ policies[policy_id] = policy
+ Policies._updated_policies[policy_id] = policy
+ continue
+ updated_policies.append(policy)
+
+ skipped = {"ignored": [], "unexpected": [], "same": [], "duplicate": []}
for policy in updated_policies:
- if POLICY_ID not in policy or policy[POLICY_ID] not in policies:
- ignored_policies.append(policy)
+ policy_id = policy.get(POLICY_ID)
+ if not policy_id or policy_id not in policies:
+ skipped["ignored"].append(policy)
+ continue
+
+ if policy_id in Policies._updated_policies:
+ skipped["duplicate"].append(policy)
+ continue
+
+ updated_policy_body = policy.get(POLICY_BODY, {})
+ updated_policy_version = updated_policy_body.get(POLICY_VERSION)
+ if not updated_policy_version or POLICY_CONFIG not in updated_policy_body:
+ skipped["unexpected"].append(policy)
continue
- if POLICY_BODY not in policy or POLICY_VERSION not in policy[POLICY_BODY] \
- or not policy[POLICY_BODY][POLICY_VERSION]:
- unexpected_policies.append(policy)
+
+ deployed_policy = policies.get(policy_id)
+ deployed_policy_version = deployed_policy.get(POLICY_BODY, {}).get(POLICY_VERSION)
+ if updated_policy_version == deployed_policy_version:
+ skipped["same"].append(policy)
continue
- deployed_policy = policies[policy[POLICY_ID]].get(POLICY_BODY, {})
- new_policy_body = policy[POLICY_BODY]
- if not deployed_policy or POLICY_VERSION not in deployed_policy \
- or not deployed_policy[POLICY_VERSION] \
- or deployed_policy[POLICY_VERSION] != new_policy_body[POLICY_VERSION]:
- policies[policy[POLICY_ID]][POLICY_BODY] = new_policy_body
- changed_policies.append(dict(policies[policy[POLICY_ID]]))
- else:
- same_policies.append(policy)
-
- if same_policies:
- ctx.logger.info("same policies: {0}".format(json.dumps(same_policies)))
- if ignored_policies:
- ctx.logger.info("ignored policies: {0}".format(json.dumps(ignored_policies)))
- if unexpected_policies:
- ctx.logger.warn("unexpected policies: {0}".format(json.dumps(unexpected_policies)))
-
- if changed_policies:
- ctx.instance.runtime_properties[POLICIES] = policies
- return changed_policies
+ policies[policy_id][POLICY_BODY] = updated_policy_body
+ Policies._updated_policies[policy_id] = policy
+
+ if skipped["same"] or skipped["ignored"] or skipped["unexpected"] or skipped["duplicate"]:
+ ctx.logger.info("skipped updates on policies: {0}".format(json.dumps(skipped)))
+
+ if Policies._updated_policies or Policies._removed_policies:
+ Policies._set_policies(policies)
+ policy_bodies = Policies._get_policy_bodies_dict(policies)
+ PoliciesOutput.store_policies(ACTION_UPDATED, policy_bodies)
@staticmethod
- def update_policies_on_node(configs_only=True):
- """decorate each policy_update operation with @Policies.update_policies_on_node to
+ def update_policies_on_node():
+ """
+ decorate each policy_update operation with @Policies.update_policies_on_node() to
filter out the updated_policies to only what applies to the current node instance,
update runtime_properties["policies"]
- :configs_only: - set to True if expect to see only the config in updated_policies
- instead of the whole policy object (False)
+ updates <scn>:policies data in consul-kv
Passes through the filtered list of updated_policies that apply to the current node instance
- :updated_policies: contains the list of changed policy-configs when configs_only=True.
+ :updated_policies: contains the list of changed policy_bodies
+
+ :removed_policies: contains the list of removed policy_bodies
+
+ :policies: contains the list of current policy_bodies
"""
def update_policies_decorator(func):
"""actual decorator"""
@@ -144,56 +310,64 @@ class Policies(object):
return
@wraps(func)
- def wrapper(updated_policies, **kwargs):
- """update matching policies on context"""
+ def wrapper(updated_policies=None, added_policies=None, removed_policies=None, **kwargs):
+ """update matching policies on the node"""
if ctx.type != NODE_INSTANCE:
- return
+ raise NonRecoverableError("can only invoke update_policies_on_node on node")
+
+ try:
+ Policies._update_policies(updated_policies, added_policies, removed_policies)
+
+ updated_policies = Policies.get_policy_bodies(
+ selected_policies=Policies._updated_policies
+ )
- updated_policies = Policies._update_policies_on_ctx(updated_policies)
- if updated_policies:
- if configs_only:
- updated_policies = [policy[POLICY_BODY][POLICY_CONFIG] \
- for policy in updated_policies \
- if POLICY_BODY in policy \
- and POLICY_CONFIG in policy[POLICY_BODY] \
- ]
- return func(updated_policies, **kwargs)
+ removed_policies = Policies.get_policy_bodies(
+ selected_policies=Policies._removed_policies
+ )
+
+ except Exception as ex:
+ error = "Failed to update the policies {0}".format(str(ex))
+ ctx.logger.error("{0}: {1}".format(error, traceback.format_exc()))
+ raise NonRecoverableError(error)
+
+ if updated_policies or removed_policies:
+ return func(updated_policies,
+ removed_policies=removed_policies,
+ policies=Policies.get_policy_bodies(),
+ **kwargs)
return wrapper
return update_policies_decorator
-
@staticmethod
- def get_policy_configs():
- """returns the list of policy configs from the runtime policies"""
- if ctx.type != NODE_INSTANCE \
- or POLICIES not in ctx.instance.runtime_properties:
- return
- policies = ctx.instance.runtime_properties[POLICIES]
- if not policies:
+ def cleanup_policies_on_node(func):
+ """
+ decorate each delete operation with @Policies.cleanup_policies_on_node to
+ remove <scn>:policies data in consul-kv
+ """
+ if not func:
return
- policy_configs = [policies[policy_id][POLICY_BODY][POLICY_CONFIG] \
- for policy_id in policies \
- if POLICY_BODY in policies[policy_id] \
- and POLICY_CONFIG in policies[policy_id][POLICY_BODY] \
- ]
- return policy_configs
- @staticmethod
- def shallow_merge_policies_into(config):
- """shallow merge the policy configs (dict) into config that is expected to be a dict"""
- if config is None:
- config = {}
- policy_configs = Policies.get_policy_configs()
- if not policy_configs or not isinstance(config, dict):
- return config
-
- for policy_config in copy.deepcopy(policy_configs):
- if not isinstance(policy_config, dict):
- continue
+ @wraps(func)
+ def wrapper(**kwargs):
+ """remove policies in consul-kv"""
+ if ctx.type == NODE_INSTANCE:
+ try:
+ PoliciesOutput.delete_policies()
+ except Exception as ex:
+ error = "Failed to cleanup policies in consul-kv {0}".format(str(ex))
+ ctx.logger.error("{0}: {1}".format(error, traceback.format_exc()))
- config.update(policy_config)
- for cfg_item in policy_config:
- if policy_config[cfg_item] is None:
- config.pop(cfg_item, None)
+ return func(**kwargs)
+ return wrapper
+
+ @staticmethod
+ def get_policy_bodies(selected_policies=None):
+ """returns the list of policy_body objects if policy_body exists"""
+ if isinstance(selected_policies, dict):
+ return deepcopy([policy.get(POLICY_BODY)
+ for policy in selected_policies.values() if policy.get(POLICY_BODY)])
- return config
+ policies = ctx.instance.runtime_properties.get(POLICIES, {})
+ return deepcopy([policy.get(POLICY_BODY)
+ for policy in policies.values() if policy.get(POLICY_BODY)])
diff --git a/onap-dcae-dcaepolicy-lib/onap_dcae_dcaepolicy_lib/policies_output.py b/onap-dcae-dcaepolicy-lib/onap_dcae_dcaepolicy_lib/policies_output.py
new file mode 100644
index 0000000..d8125c0
--- /dev/null
+++ b/onap-dcae-dcaepolicy-lib/onap_dcae_dcaepolicy_lib/policies_output.py
@@ -0,0 +1,148 @@
+# ================================================================================
+# Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+# ================================================================================
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+# ============LICENSE_END=========================================================
+#
+# ECOMP is a trademark and service mark of AT&T Intellectual Property.
+
+"""client to talk to consul on standard port 8500"""
+
+import base64
+import json
+import urllib
+import uuid
+from datetime import datetime
+
+import requests
+from cloudify import ctx
+
+
+class PoliciesOutput(object):
+ """static class for store-delete policies in consul kv"""
+ # it is safe to assume that consul agent is at consul:8500
+ # define consul alis in /etc/hosts on cloudify manager vm
+ # $ cat /etc/hosts
+ # 127.0.0.1 localhost localhost.localdomain localhost4 localhost4.localdomain4 consul
+ CONSUL_TRANSACTION_URL = "http://consul:8500/v1/txn"
+
+ POLICIES_EVENT = 'policies_event'
+
+ POLICIES_FOLDER_MASK = "{0}:policies/{1}"
+ MAX_OPS_PER_TXN = 64
+
+ OPERATION_SET = "set"
+ OPERATION_DELETE = "delete"
+ OPERATION_DELETE_FOLDER = "delete-tree"
+ SERVICE_COMPONENT_NAME = "service_component_name"
+
+
+ @staticmethod
+ def _gen_txn_operation(verb, service_component_name, key=None, value=None):
+ """returns the properly formatted operation to be used inside transaction"""
+ key = PoliciesOutput.POLICIES_FOLDER_MASK.format(
+ service_component_name, urllib.quote(key or "")
+ )
+ if value:
+ return {"KV": {"Verb": verb, "Key": key, "Value": base64.b64encode(value)}}
+ return {"KV": {"Verb": verb, "Key": key}}
+
+
+ @staticmethod
+ def _run_transaction(operation_name, txn):
+ """run a single transaction of several operations at consul /txn"""
+ if not txn:
+ return None
+
+ response = None
+ try:
+ response = requests.put(PoliciesOutput.CONSUL_TRANSACTION_URL, json=txn)
+ except requests.exceptions.RequestException as ex:
+ ctx.logger.error(
+ "RequestException - failed to {0} at {1}: {2} on txn={3}"
+ .format(operation_name, PoliciesOutput.CONSUL_TRANSACTION_URL,
+ str(ex), json.dumps(txn)))
+ return None
+
+ if response.status_code != requests.codes.ok:
+ ctx.logger.error(
+ "failed {0} for {1} {2}: text={3} txn={4}"
+ .format(response.status_code, operation_name,
+ PoliciesOutput.CONSUL_TRANSACTION_URL, response.text, json.dumps(txn)))
+ return None
+ ctx.logger.info(
+ "response {0} for {1} {2}: text={3} txn={4}"
+ .format(response.status_code, operation_name,
+ PoliciesOutput.CONSUL_TRANSACTION_URL, response.text, json.dumps(txn)))
+ return True
+
+
+ @staticmethod
+ def store_policies(action, policy_bodies):
+ """put the policy_bodies for service_component_name into consul-kv"""
+ service_component_name = ctx.instance.runtime_properties.get(
+ PoliciesOutput.SERVICE_COMPONENT_NAME
+ )
+ if not service_component_name:
+ ctx.logger.warn("failed to find service_component_name to store_policies in consul-kv")
+ return False
+
+ event = {
+ "action": action,
+ "timestamp": (datetime.utcnow().isoformat()[:-3] + 'Z'),
+ "update_id": str(uuid.uuid4()),
+ "policies_count": len(policy_bodies)
+ }
+ ctx.instance.runtime_properties[PoliciesOutput.POLICIES_EVENT] = event
+
+ store_policies = [
+ PoliciesOutput._gen_txn_operation(PoliciesOutput.OPERATION_SET, service_component_name,
+ "items/" + policy_id, json.dumps(policy_body))
+ for policy_id, policy_body in policy_bodies.iteritems()
+ ]
+ txn = [
+ PoliciesOutput._gen_txn_operation(
+ PoliciesOutput.OPERATION_DELETE_FOLDER, service_component_name),
+ PoliciesOutput._gen_txn_operation(
+ PoliciesOutput.OPERATION_SET, service_component_name, "event", json.dumps(event))
+ ]
+ idx_step = PoliciesOutput.MAX_OPS_PER_TXN - len(txn)
+ for idx in xrange(0, len(store_policies), idx_step):
+ txn += store_policies[idx : idx + idx_step]
+ if not PoliciesOutput._run_transaction("store_policies", txn):
+ return False
+ txn = []
+
+ PoliciesOutput._run_transaction("store_policies", txn)
+ return True
+
+
+ @staticmethod
+ def delete_policies():
+ """delete policies for service_component_name in consul-kv"""
+ if PoliciesOutput.POLICIES_EVENT not in ctx.instance.runtime_properties:
+ return
+
+ service_component_name = ctx.instance.runtime_properties.get(
+ PoliciesOutput.SERVICE_COMPONENT_NAME
+ )
+ if not service_component_name:
+ ctx.logger.warn("failed to find service_component_name to delete_policies in consul-kv")
+ return
+
+ delete_policies = [
+ PoliciesOutput._gen_txn_operation(
+ PoliciesOutput.OPERATION_DELETE_FOLDER, service_component_name
+ )
+ ]
+ PoliciesOutput._run_transaction("delete_policies", delete_policies)
diff --git a/onap-dcae-dcaepolicy-lib/pom.xml b/onap-dcae-dcaepolicy-lib/pom.xml
index d4a7a74..b7ae319 100644
--- a/onap-dcae-dcaepolicy-lib/pom.xml
+++ b/onap-dcae-dcaepolicy-lib/pom.xml
@@ -1,7 +1,7 @@
<?xml version="1.0"?>
<!--
================================================================================
-Copyright (c) 2017 AT&T Intellectual Property. All rights reserved.
+Copyright (c) 2017-2018 AT&T Intellectual Property. All rights reserved.
================================================================================
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -28,7 +28,7 @@ ECOMP is a trademark and service mark of AT&T Intellectual Property.
<groupId>org.onap.dcaegen2.utils</groupId>
<artifactId>onap-dcae-dcaepolicy-lib</artifactId>
<name>dcaegen2-utils-onap-dcae-dcaepolicy-lib</name>
- <version>1.1.0-SNAPSHOT</version>
+ <version>2.4.0-SNAPSHOT</version>
<url>http://maven.apache.org</url>
<properties>
@@ -38,9 +38,12 @@ ECOMP is a trademark and service mark of AT&T Intellectual Property.
<!-- sonar.host.url>http://localhost:9000</sonar.host.url -->
<!-- below are language dependent -->
<!-- for Python -->
+ <sonar.junit.reportsPath>xunit-results.xml</sonar.junit.reportsPath>
+ <sonar.python.coverage.reportPath>coverage.xml</sonar.python.coverage.reportPath>
<sonar.language>py</sonar.language>
<sonar.pluginName>Python</sonar.pluginName>
<sonar.inclusions>**/*.py</sonar.inclusions>
+ <sonar.exclusions>tests/*,setup.py</sonar.exclusions>
<!-- for JavaScaript -->
<!--
<sonar.language>js</sonar.language>
diff --git a/onap-dcae-dcaepolicy-lib/setup.py b/onap-dcae-dcaepolicy-lib/setup.py
index 7a4e71a..a2ff93f 100644
--- a/onap-dcae-dcaepolicy-lib/setup.py
+++ b/onap-dcae-dcaepolicy-lib/setup.py
@@ -1,8 +1,5 @@
-"""setup.py is used for package build and distribution"""
-
-# org.onap.dcae
# ================================================================================
-# Copyright (c) 2017 AT&T Intellectual Property. All rights reserved.
+# Copyright (c) 2017-2018 AT&T Intellectual Property. All rights reserved.
# ================================================================================
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -19,12 +16,14 @@
#
# ECOMP is a trademark and service mark of AT&T Intellectual Property.
+"""setup.py is used for package build and distribution"""
+
from setuptools import setup, find_packages
setup(
name='onap-dcae-dcaepolicy-lib',
description='lib of policy decorators to be used by cloudify plugins of dcae controller',
- version="1.0.0",
+ version="2.4.0",
author='Alex Shatov',
author_email="alexs@att.com",
license='Apache 2',
@@ -33,7 +32,6 @@ setup(
],
keywords='onap policy dcae controller cloudify plugin',
classifiers=[
- 'Development Status :: 4 - Beta',
'Intended Audience :: Telecommunications Industry',
'Programming Language :: Python :: 2.7'
]
diff --git a/onap-dcae-dcaepolicy-lib/tests/__init__.py b/onap-dcae-dcaepolicy-lib/tests/__init__.py
new file mode 100644
index 0000000..6c84c78
--- /dev/null
+++ b/onap-dcae-dcaepolicy-lib/tests/__init__.py
@@ -0,0 +1,19 @@
+# ================================================================================
+# Copyright (c) 2018 AT&T Intellectual Property. All rights reserved.
+# ================================================================================
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+# ============LICENSE_END=========================================================
+#
+# ECOMP is a trademark and service mark of AT&T Intellectual Property.
+
+"""unit test the onap-dcae-dcaepolicy-lib"""
diff --git a/onap-dcae-dcaepolicy-lib/tests/log_ctx.py b/onap-dcae-dcaepolicy-lib/tests/log_ctx.py
index 9f5464d..0d82687 100644
--- a/onap-dcae-dcaepolicy-lib/tests/log_ctx.py
+++ b/onap-dcae-dcaepolicy-lib/tests/log_ctx.py
@@ -1,8 +1,5 @@
-""":@CtxLogger.log_ctx: decorator for logging the cloudify ctx before and after operation"""
-
-# org.onap.dcae
# ================================================================================
-# Copyright (c) 2017 AT&T Intellectual Property. All rights reserved.
+# Copyright (c) 2017-2018 AT&T Intellectual Property. All rights reserved.
# ================================================================================
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -19,7 +16,10 @@
#
# ECOMP is a trademark and service mark of AT&T Intellectual Property.
+""":@CtxLogger.log_ctx: decorator for logging the cloudify ctx before and after operation"""
+
import json
+import traceback
from functools import wraps
from cloudify import ctx
@@ -102,7 +102,8 @@ class CtxLogger(object):
ctx.logger.info("{0} context: {1}".format(\
func_name, json.dumps(CtxLogger.get_ctx_info())))
except Exception as ex:
- ctx.logger.error("Failed to log the node context: {0}".format(str(ex)))
+ ctx.logger.error("Failed to log the node context: {0}: {1}" \
+ .format(str(ex), traceback.format_exc()))
@staticmethod
def log_ctx(pre_log=True, after_log=False, exe_task=None):
@@ -119,8 +120,8 @@ class CtxLogger(object):
if ctx.type == NODE_INSTANCE and exe_task:
ctx.instance.runtime_properties[exe_task] = func.__name__
except Exception as ex:
- ctx.logger.error("Failed to set exe_task {0}: {1}".format(\
- exe_task, str(ex)))
+ ctx.logger.error("Failed to set exe_task {0}: {1}: {2}" \
+ .format(exe_task, str(ex), traceback.format_exc()))
if pre_log:
CtxLogger.log_ctx_info('before ' + func.__name__)
diff --git a/onap-dcae-dcaepolicy-lib/tests/mock_cloudify_ctx.py b/onap-dcae-dcaepolicy-lib/tests/mock_cloudify_ctx.py
index 0c130c0..50aa46e 100644
--- a/onap-dcae-dcaepolicy-lib/tests/mock_cloudify_ctx.py
+++ b/onap-dcae-dcaepolicy-lib/tests/mock_cloudify_ctx.py
@@ -1,8 +1,5 @@
-
# ============LICENSE_START=======================================================
-# org.onap.dcae
-# ================================================================================
-# Copyright (c) 2017 AT&T Intellectual Property. All rights reserved.
+# Copyright (c) 2017-2018 AT&T Intellectual Property. All rights reserved.
# ================================================================================
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -19,6 +16,8 @@
#
# ECOMP is a trademark and service mark of AT&T Intellectual Property.
+"""mock of cloudify context with relationships and type_hierrarchy"""
+
from cloudify.mocks import MockCloudifyContext, MockNodeInstanceContext, MockNodeContext
TARGET_NODE_ID = "target_node_id"
diff --git a/onap-dcae-dcaepolicy-lib/tests/test_dcae_policy.py b/onap-dcae-dcaepolicy-lib/tests/test_dcae_policy.py
index 29b192c..4b3e39c 100644
--- a/onap-dcae-dcaepolicy-lib/tests/test_dcae_policy.py
+++ b/onap-dcae-dcaepolicy-lib/tests/test_dcae_policy.py
@@ -1,7 +1,5 @@
# ============LICENSE_START=======================================================
-# org.onap.dcae
-# ================================================================================
-# Copyright (c) 2017 AT&T Intellectual Property. All rights reserved.
+# Copyright (c) 2017-2018 AT&T Intellectual Property. All rights reserved.
# ================================================================================
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -18,31 +16,43 @@
#
# ECOMP is a trademark and service mark of AT&T Intellectual Property.
+"""tests of decorators around the cloudify operations to handle policy actions"""
+
+import copy
import json
import logging
from datetime import datetime, timedelta
+from functools import wraps
import pytest
-
+import requests
from cloudify import ctx
-from cloudify.state import current_ctx
from cloudify.exceptions import NonRecoverableError
+from cloudify.state import current_ctx
-from mock_cloudify_ctx import MockCloudifyContextFull, TARGET_NODE_ID, TARGET_NODE_NAME
-from log_ctx import CtxLogger
-
-from onap_dcae_dcaepolicy_lib import Policies, POLICIES
+from onap_dcae_dcaepolicy_lib import dcae_policy
+from onap_dcae_dcaepolicy_lib.dcae_policy import Policies
+from onap_dcae_dcaepolicy_lib.policies_output import PoliciesOutput
+from tests.log_ctx import CtxLogger
+from tests.mock_cloudify_ctx import (TARGET_NODE_ID, TARGET_NODE_NAME,
+ MockCloudifyContextFull)
-DCAE_POLICY_TYPE = 'dcae.nodes.policy'
POLICY_ID = 'policy_id'
POLICY_VERSION = "policyVersion"
POLICY_NAME = "policyName"
POLICY_BODY = 'policy_body'
POLICY_CONFIG = 'config'
+CONFIG_NAME = "ConfigName"
+
MONKEYED_POLICY_ID = 'monkeyed.Config_peach'
MONKEYED_POLICY_ID_2 = 'monkeyed.Config_peach_2'
+MONKEYED_POLICY_ID_M = 'monkeyed.Config_multi'
+MONKEYED_POLICY_ID_M_2 = 'monkeyed.Config_multi_2'
+MONKEYED_POLICY_ID_M_3 = 'monkeyed.Config_multi_3'
+MONKEYED_POLICY_ID_B = 'monkeyed.Config_both'
APPLICATION_CONFIG = "application_config"
-LOG_FILE = 'test_onap_dcae_dcaepolicy_lib.log'
+LOG_FILE = 'logs/test_onap_dcae_dcaepolicy_lib.log'
+LOREM_IPSUM = """Lorem ipsum dolor sit amet consectetur ametist""".split()
RUN_TS = datetime.utcnow()
@@ -66,20 +76,28 @@ class MonkeyedLogHandler(object):
class MonkeyedPolicyBody(object):
"""policy body that policy-engine returns"""
@staticmethod
- def create_policy_body(policy_id, policy_version=1):
+ def create_policy_body(policy_id, policy_version=1, priority=None, **kwargs):
"""returns a fake policy-body"""
prev_ver = policy_version - 1
timestamp = RUN_TS + timedelta(hours=prev_ver)
- prev_ver = str(prev_ver)
this_ver = str(policy_version)
config = {
- "policy_updated_from_ver": prev_ver,
+ "policy_updated_from_ver": str(prev_ver),
"policy_updated_to_ver": this_ver,
- "policy_hello": "world!",
+ "policy_hello": LOREM_IPSUM[prev_ver % len(LOREM_IPSUM)],
"policy_updated_ts": timestamp.isoformat()[:-3] + 'Z',
"updated_policy_id": policy_id
}
+ config.update(copy.deepcopy(kwargs) or {})
+
+ matching_conditions = {
+ "ONAPName": "DCAE",
+ CONFIG_NAME: "alex_config_name"
+ }
+ if priority is not None:
+ matching_conditions["priority"] = priority
+
return {
"policyConfigMessage": "Config Retrieved! ",
"policyConfigStatus": "CONFIG_RETRIEVED",
@@ -87,23 +105,29 @@ class MonkeyedPolicyBody(object):
POLICY_NAME: "{0}.{1}.xml".format(policy_id, this_ver),
POLICY_VERSION: this_ver,
POLICY_CONFIG: config,
- "matchingConditions": {
- "ECOMPName": "DCAE",
- "ConfigName": "alex_config_name"
- },
+ "matchingConditions": matching_conditions,
"responseAttributes": {},
"property": None
}
@staticmethod
- def create_policy(policy_id, policy_version=1):
+ def create_policy_bare(policy_id, policy_version=1, priority=None, **kwargs):
"""returns the whole policy object for policy_id and policy_version"""
return {
- POLICY_ID : policy_id,
- POLICY_BODY : MonkeyedPolicyBody.create_policy_body(policy_id, policy_version)
+ POLICY_ID: policy_id,
+ POLICY_BODY: MonkeyedPolicyBody.create_policy_body(
+ policy_id, policy_version, priority, **kwargs)
}
@staticmethod
+ def create_policy(policy_id, policy_version=1, policy_persistent=True, priority=None, **kwargs):
+ """returns the whole policy object for policy_id and policy_version"""
+ policy = MonkeyedPolicyBody.create_policy_bare(
+ policy_id, policy_version, priority, **kwargs)
+ policy[dcae_policy.POLICY_PERSISTENT] = bool(policy_persistent)
+ return policy
+
+ @staticmethod
def is_the_same_dict(policy_body_1, policy_body_2):
"""check whether both policy_body objects are the same"""
if not isinstance(policy_body_1, dict) or not isinstance(policy_body_2, dict):
@@ -111,23 +135,25 @@ class MonkeyedPolicyBody(object):
for key in policy_body_1.keys():
if key not in policy_body_2:
return False
- if isinstance(policy_body_1[key], dict):
- return MonkeyedPolicyBody.is_the_same_dict(
- policy_body_1[key], policy_body_2[key])
- if (policy_body_1[key] is None and policy_body_2[key] is not None) \
- or (policy_body_1[key] is not None and policy_body_2[key] is None) \
- or (policy_body_1[key] != policy_body_2[key]):
+
+ val_1 = policy_body_1[key]
+ val_2 = policy_body_2[key]
+ if isinstance(val_1, dict) \
+ and not MonkeyedPolicyBody.is_the_same_dict(val_1, val_2):
+ return False
+ if (val_1 is None and val_2 is not None) \
+ or (val_1 is not None and val_2 is None) \
+ or (val_1 != val_2):
return False
return True
-
class MonkeyedNode(object):
"""node in cloudify"""
BLUEPRINT_ID = 'test_dcae_policy_bp_id'
DEPLOYMENT_ID = 'test_dcae_policy_dpl_id'
EXECUTION_ID = 'test_dcae_policy_exe_id'
- def __init__(self, node_id, node_name, node_type, properties,
+ def __init__(self, node_id, node_name, node_type, properties=None,
relationships=None, runtime_properties=None):
self.node_id = node_id
self.node_name = node_name
@@ -142,121 +168,1119 @@ class MonkeyedNode(object):
relationships=relationships,
runtime_properties=runtime_properties
)
- MonkeyedLogHandler.add_handler_to(self.ctx.logger)
+
+class MonkeyedResponse(object):
+ """Monkey response"""
+ def __init__(self, full_path, headers=None, resp_json=None):
+ self.full_path = full_path
+ self.status_code = 200
+ self.headers = headers or {}
+ self.resp_json = resp_json
+ self.text = json.dumps(resp_json or {})
+
+ def json(self):
+ """returns json of response"""
+ return self.resp_json
+
+ def raise_for_status(self):
+ """always happy"""
+ pass
+
+def get_app_config():
+ """just get the config"""
+ config = copy.deepcopy(dict(ctx.instance.runtime_properties.get(APPLICATION_CONFIG, {})))
+ if not config:
+ config = copy.deepcopy(dict(ctx.node.properties.get(APPLICATION_CONFIG, {})))
+ return config
+
+def operation_node_configure(**kwargs):
+ """do the node-configure operation"""
+ ctx.logger.info("operation_node_configure kwargs: {0}".format(kwargs))
+
+ app_config = get_app_config()
+ ctx.instance.runtime_properties[APPLICATION_CONFIG] = app_config
+ ctx.instance.runtime_properties[PoliciesOutput.SERVICE_COMPONENT_NAME] = "unit_test_scn"
+ ctx.logger.info("property app_config: {0}".format(json.dumps(app_config)))
@CtxLogger.log_ctx(pre_log=True, after_log=True, exe_task='exe_task')
-@Policies.gather_policies_to_node
+@Policies.gather_policies_to_node()
def node_configure(**kwargs):
"""decorate with @Policies.gather_policies_to_node on policy consumer node to
bring all policies to runtime_properties["policies"]
"""
- ctx.logger.info("node_configure kwargs: {0}".format(kwargs))
+ operation_node_configure(**kwargs)
- app_config = None
- if APPLICATION_CONFIG in ctx.node.properties:
- # dockerized blueprint puts the app config into property application_config
- app_config = ctx.node.properties.get(APPLICATION_CONFIG)
+@CtxLogger.log_ctx(pre_log=True, after_log=True, exe_task='execute_operation')
+@Policies.update_policies_on_node()
+def policy_update(updated_policies, removed_policies=None, **kwargs):
+ """decorate with @Policies.update_policies_on_node() to update runtime_properties["policies"]
- app_config = Policies.shallow_merge_policies_into(app_config)
- ctx.instance.runtime_properties[APPLICATION_CONFIG] = app_config
- ctx.logger.info("example: applied policy_configs to property app_config: {0}" \
- .format(json.dumps(app_config)))
+ :updated_policies: contains the list of changed policy-configs when configs_only=True (default).
+ """
+ # This is how to merge the policies into default app_config object
+ # (runtime_properties[APPLICATION_CONFIG] = application_config)
+ app_config = get_app_config()
+ ctx.logger.info("app_config {0}".format(json.dumps(app_config)))
- policy_configs = Policies.get_policy_configs()
- if policy_configs:
- ctx.logger.warn("TBD: apply policy_configs: {0}".format(json.dumps(policy_configs)))
+ ctx.instance.runtime_properties[APPLICATION_CONFIG] = app_config
@CtxLogger.log_ctx(pre_log=True, after_log=True, exe_task='execute_operation')
-@Policies.update_policies_on_node(configs_only=True)
-def policy_update(updated_policies, **kwargs):
+@Policies.update_policies_on_node()
+def policy_update_not_only_config(updated_policies, removed_policies=None, **kwargs):
"""decorate with @Policies.update_policies_on_node() to update runtime_properties["policies"]
:updated_policies: contains the list of changed policy-configs when configs_only=True (default).
- Use configs_only=False to bring the full policy objects in :updated_policies:.
-
- Use :Policies.shallow_merge_policies_into(): to merge the updated_policies into app_config
"""
- app_config = ctx.instance.runtime_properties[APPLICATION_CONFIG]
+ # This is how to merge the policies into default app_config object
+ # (runtime_properties[APPLICATION_CONFIG] = application_config)
+ app_config = get_app_config()
+ ctx.logger.info("app_config {0}".format(json.dumps(app_config)))
+
+ ctx.instance.runtime_properties[APPLICATION_CONFIG] = app_config
- # This is how to merge the policies into app_config object
- app_config = Policies.shallow_merge_policies_into(app_config)
+@CtxLogger.log_ctx(pre_log=True, after_log=True, exe_task='execute_operation')
+@Policies.update_policies_on_node()
+def policy_update_many_calcs(updated_policies, removed_policies=None, policies=None, **kwargs):
+ """decorate with @Policies.update_policies_on_node() to update runtime_properties["policies"]
- ctx.logger.info("merged updated_policies {0} into app_config {1}"
- .format(json.dumps(updated_policies), json.dumps(app_config)))
+ :updated_policies: contains the list of changed policy-configs when configs_only=True (default).
+ """
+ app_config = get_app_config()
+ ctx.logger.info("app_config {0}".format(json.dumps(app_config)))
ctx.instance.runtime_properties[APPLICATION_CONFIG] = app_config
+@CtxLogger.log_ctx(pre_log=True, after_log=True, exe_task='exe_task')
+@Policies.cleanup_policies_on_node
+def node_delete(**kwargs):
+ """delete <service_component_name> records in consul-kv"""
+ operation_node_configure(**kwargs)
+
+
+class CurrentCtx(object):
+ """cloudify context"""
+ _node_ms = None
+
+ @staticmethod
+ def set_current_ctx(include_bad=True, include_good=True):
+ """set up the nodes for cloudify"""
+ Policies._init()
+
+ def add_target_to_relationships(relationships, node):
+ """adds the node as the target of relationships"""
+ relationships.append({TARGET_NODE_ID: node.node_id, TARGET_NODE_NAME: node.node_name})
+
+ relationships = []
+ if include_good:
+ node_policy = MonkeyedNode(
+ 'dcae_policy_node_id',
+ 'dcae_policy_node_name',
+ dcae_policy.DCAE_POLICY_TYPE,
+ {POLICY_ID: MONKEYED_POLICY_ID},
+ None,
+ {POLICY_BODY: MonkeyedPolicyBody.create_policy_body(
+ MONKEYED_POLICY_ID, priority="1")}
+ )
+ add_target_to_relationships(relationships, node_policy)
+
+ if include_bad:
+ bad_policy_2 = MonkeyedNode(
+ 'bad_policy_2_node_id',
+ 'bad_policy_2_node_name',
+ dcae_policy.DCAE_POLICY_TYPE,
+ {POLICY_ID: MONKEYED_POLICY_ID_2},
+ None,
+ None
+ )
+ add_target_to_relationships(relationships, bad_policy_2)
+
+ if include_good:
+ node_policy_2 = MonkeyedNode(
+ 'dcae_policy_node_id_2',
+ 'dcae_policy_node_name_2',
+ dcae_policy.DCAE_POLICY_TYPE,
+ {POLICY_ID: MONKEYED_POLICY_ID_2},
+ None,
+ {POLICY_BODY: MonkeyedPolicyBody.create_policy_body(
+ MONKEYED_POLICY_ID_2, 4, priority="2")}
+ )
+ add_target_to_relationships(relationships, node_policy_2)
+
+ if include_bad:
+ bad_policy_3 = MonkeyedNode(
+ 'bad_policy_3_node_id',
+ 'bad_policy_3_node_name',
+ dcae_policy.DCAE_POLICY_TYPE,
+ {POLICY_ID: MONKEYED_POLICY_ID_2},
+ None,
+ None
+ )
+ add_target_to_relationships(relationships, bad_policy_3)
+
+ bad_policy_4 = MonkeyedNode(
+ 'bad_policy_4_node_id',
+ 'bad_policy_4_node_name',
+ dcae_policy.DCAE_POLICY_TYPE,
+ None,
+ None,
+ None
+ )
+ add_target_to_relationships(relationships, bad_policy_4)
+
+ weird_policy_5 = MonkeyedNode(
+ 'weird_policy_5_node_id',
+ 'weird_policy_5_node_name',
+ dcae_policy.DCAE_POLICY_TYPE,
+ None,
+ None,
+ {POLICY_BODY: MonkeyedPolicyBody.create_policy_body(
+ MONKEYED_POLICY_ID, 3, priority="2")}
+ )
+ add_target_to_relationships(relationships, weird_policy_5)
+
+ if include_good:
+ node_policies = MonkeyedNode(
+ 'dcae_policies_node_id',
+ 'dcae_policies_node_name',
+ dcae_policy.DCAE_POLICIES_TYPE,
+ {dcae_policy.POLICY_FILTER: {
+ POLICY_NAME: MONKEYED_POLICY_ID_M + ".*",
+ dcae_policy.CONFIG_ATTRIBUTES: json.dumps({
+ CONFIG_NAME: "alex_config_name"
+ })
+ }},
+ None,
+ {dcae_policy.POLICIES_FILTERED: {
+ MONKEYED_POLICY_ID_M:
+ MonkeyedPolicyBody.create_policy_bare(MONKEYED_POLICY_ID_M, 3)}}
+ )
+ add_target_to_relationships(relationships, node_policies)
+
+ node_policies_2 = MonkeyedNode(
+ 'dcae_policies_2_node_id',
+ 'dcae_policies_2_node_name',
+ dcae_policy.DCAE_POLICIES_TYPE,
+ {dcae_policy.POLICY_FILTER: {POLICY_NAME: MONKEYED_POLICY_ID_M + ".*"}},
+ None,
+ {dcae_policy.POLICIES_FILTERED: {
+ MONKEYED_POLICY_ID_M:
+ MonkeyedPolicyBody.create_policy_bare(MONKEYED_POLICY_ID_M, 2)}}
+ )
+ add_target_to_relationships(relationships, node_policies_2)
+
+ policies_empty = MonkeyedNode(
+ 'dcae_policies_empty_node_id',
+ 'dcae_policies_empty_node_name',
+ dcae_policy.DCAE_POLICIES_TYPE,
+ {dcae_policy.POLICY_FILTER: {"empty": None}},
+ None,
+ None
+ )
+ add_target_to_relationships(relationships, policies_empty)
+
+ policies_empty_2 = MonkeyedNode(
+ 'dcae_policies_empty_2_node_id',
+ 'dcae_policies_empty_2_node_name',
+ dcae_policy.DCAE_POLICIES_TYPE,
+ None,
+ None,
+ None
+ )
+ add_target_to_relationships(relationships, policies_empty_2)
+
+ non_policies = MonkeyedNode(
+ 'non_policies_node_id',
+ 'non_policies_node_name',
+ "non.policy.type"
+ )
+ add_target_to_relationships(relationships, non_policies)
+
+ if include_good:
+ node_policies_b = MonkeyedNode(
+ 'dcae_policies_b_node_id',
+ 'dcae_policies_b_node_name',
+ dcae_policy.DCAE_POLICIES_TYPE,
+ {dcae_policy.POLICY_FILTER: {POLICY_NAME: MONKEYED_POLICY_ID_M + ".*"}},
+ None,
+ {dcae_policy.POLICIES_FILTERED: {
+ MONKEYED_POLICY_ID_B:
+ MonkeyedPolicyBody.create_policy_bare(MONKEYED_POLICY_ID_B, 1)}}
+ )
+ add_target_to_relationships(relationships, node_policies_b)
+
+ node_policies_b_2 = MonkeyedNode(
+ 'dcae_policies_b_2_node_id',
+ 'dcae_policies_b_2_node_name',
+ dcae_policy.DCAE_POLICIES_TYPE,
+ {dcae_policy.POLICY_FILTER: {POLICY_NAME: MONKEYED_POLICY_ID_M + ".*"}},
+ None,
+ {dcae_policy.POLICIES_FILTERED: {
+ MONKEYED_POLICY_ID_B:
+ MonkeyedPolicyBody.create_policy_bare(MONKEYED_POLICY_ID_B, 2)}}
+ )
+ add_target_to_relationships(relationships, node_policies_b_2)
+
+ if include_good:
+ node_policy_b = MonkeyedNode(
+ 'dcae_policy_b_node_id',
+ 'dcae_policy_b_node_name',
+ dcae_policy.DCAE_POLICY_TYPE,
+ {POLICY_ID: MONKEYED_POLICY_ID_B},
+ None,
+ {POLICY_BODY: MonkeyedPolicyBody.create_policy_body(
+ MONKEYED_POLICY_ID_B, 4, priority="1.5")}
+ )
+ add_target_to_relationships(relationships, node_policy_b)
+
+ node_policies_b_5 = MonkeyedNode(
+ 'dcae_policies_b_5_node_id',
+ 'dcae_policies_b_5_node_name',
+ dcae_policy.DCAE_POLICIES_TYPE,
+ {dcae_policy.POLICY_FILTER: {POLICY_NAME: MONKEYED_POLICY_ID_M + ".*"}},
+ None,
+ {dcae_policy.POLICIES_FILTERED: {
+ MONKEYED_POLICY_ID_B:
+ MonkeyedPolicyBody.create_policy_bare(MONKEYED_POLICY_ID_B, 5)}}
+ )
+ add_target_to_relationships(relationships, node_policies_b_5)
+
+
+ CurrentCtx._node_ms = MonkeyedNode(
+ 'test_ms_id', 'test_ms_name', "ms.nodes.type",
+ {APPLICATION_CONFIG: MonkeyedPolicyBody.create_policy_body(
+ "no_policy", db_port="123", weather="snow")[POLICY_CONFIG]
+ },
+ relationships
+ )
+ current_ctx.set(CurrentCtx._node_ms.ctx)
+ MonkeyedLogHandler.add_handler_to(CurrentCtx._node_ms.ctx.logger)
+
+ @staticmethod
+ def reset():
+ """reset context"""
+ current_ctx.set(CurrentCtx._node_ms.ctx)
+
+
+def monkeyed_consul_boom(full_path, json):
+ """boom on monkeypatch for the put to consul"""
+ raise requests.ConnectionError("monkey-boom")
+
+
+@pytest.fixture()
+def fix_consul_boom(monkeypatch):
+ """monkeyed discovery request.put"""
+ PoliciesOutput._lazy_inited = False
+ monkeypatch.setattr('requests.put', monkeyed_consul_boom)
+ yield fix_consul_boom
+ PoliciesOutput._lazy_inited = False
+
+
+def monkeyed_consul_put(full_path, json):
+ """monkeypatch for the put to consul"""
+ return MonkeyedResponse(full_path)
+
+
+@pytest.fixture()
+def fix_consul(monkeypatch):
+ """monkeyed discovery request.put"""
+ PoliciesOutput._lazy_inited = False
+ monkeypatch.setattr('requests.put', monkeyed_consul_put)
+ yield fix_consul
+ PoliciesOutput._lazy_inited = False
+
+
+def cfy_ctx(include_bad=True, include_good=True):
+ """test and safely clean up"""
+ def cfy_ctx_decorator(func):
+ """test and safely clean up"""
+ if not func:
+ return
+
+ @wraps(func)
+ def ctx_wrapper(*args, **kwargs):
+ """test"""
+ try:
+ CurrentCtx.set_current_ctx(include_bad, include_good)
+
+ func(*args, **kwargs)
+
+ finally:
+ ctx.logger.info("MockCloudifyContextFull.clear")
+ MockCloudifyContextFull.clear()
+ current_ctx.clear()
+
+ return ctx_wrapper
+ return cfy_ctx_decorator
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True)
+def test_gather_policies_to_node():
+ """test gather_policies_to_node"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True)
def test_policies_to_node():
- """test gather_policies_to_node and policy_update"""
-
- node_policy = MonkeyedNode(
- 'test_dcae_policy_node_id',
- 'test_dcae_policy_node_name',
- DCAE_POLICY_TYPE,
- {POLICY_ID: MONKEYED_POLICY_ID},
- None,
- {POLICY_BODY : MonkeyedPolicyBody.create_policy_body(MONKEYED_POLICY_ID)}
- )
- node_policy_2 = MonkeyedNode(
- 'test_dcae_policy_node_id_2',
- 'test_dcae_policy_node_name_2',
- DCAE_POLICY_TYPE,
- {POLICY_ID: MONKEYED_POLICY_ID_2},
- None,
- {POLICY_BODY : MonkeyedPolicyBody.create_policy_body(MONKEYED_POLICY_ID_2)}
- )
- node_ms = MonkeyedNode('test_ms_id', 'test_ms_name', "ms.nodes.type", None, \
- [{TARGET_NODE_ID: node_policy.node_id, TARGET_NODE_NAME: node_policy.node_name},
- {TARGET_NODE_ID: node_policy_2.node_id, TARGET_NODE_NAME: node_policy_2.node_name}
- ])
-
- try:
- current_ctx.set(node_ms.ctx)
+ """test gather_policies_to_node"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+ assert MONKEYED_POLICY_ID in policies
+ expected_1 = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID, priority="1")
+ policy = policies[MONKEYED_POLICY_ID]
+ ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID, json.dumps(expected_1)))
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_1)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_1, policy)
+
+ assert MONKEYED_POLICY_ID_B in policies
+ expected_b = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_B, 4, priority="1.5")
+ policy = policies[MONKEYED_POLICY_ID_B]
+ ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID_B, json.dumps(expected_b)))
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_B, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_b)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_b, policy)
+
+ assert MONKEYED_POLICY_ID_2 in policies
+ expected_2 = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_2, 4, priority="2")
+ policy = policies[MONKEYED_POLICY_ID_2]
+ ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID_2, json.dumps(expected_2)))
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_2, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_2)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_2, policy)
+
+ assert MONKEYED_POLICY_ID_M in policies
+ expected_m = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_M, 2, False)
+ policy = policies[MONKEYED_POLICY_ID_M]
+ ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID_M, json.dumps(expected_m)))
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_M, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_m)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_m, policy)
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True)
+def test_update_policies():
+ """test policy_update"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+ updated_policy = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_2, 2, priority="aa20")
+ added_policy = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_M_2, 2,
+ False, priority="1")
+ ctx.logger.info("policy_update: [{0}]".format(json.dumps(updated_policy)))
+
+ ctx.logger.info("policy[{0}]: not yet in policies".format(MONKEYED_POLICY_ID_M_2))
+ assert MONKEYED_POLICY_ID_M_2 not in policies
+
+ policy_filter_ids = runtime_properties.get(dcae_policy.POLICY_FILTERS, {}).keys() or ["--"]
+
+ policy_update(updated_policies=[updated_policy],
+ added_policies={
+ policy_filter_ids[0]: {
+ dcae_policy.POLICIES: {MONKEYED_POLICY_ID_M_2: added_policy}}
+ },
+ removed_policies=[MONKEYED_POLICY_ID_M])
+
+ ctx.logger.info("policy[{0}]: removed".format(MONKEYED_POLICY_ID_M))
+ assert MONKEYED_POLICY_ID_M not in policies
+
+ assert MONKEYED_POLICY_ID_M_2 in policies
+ policy = policies[MONKEYED_POLICY_ID_M_2]
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_M_2, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, added_policy)
+ assert MonkeyedPolicyBody.is_the_same_dict(added_policy, policy)
+
+ assert MONKEYED_POLICY_ID_2 in policies
+ policy = policies[MONKEYED_POLICY_ID_2]
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_2, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, updated_policy)
+ assert MonkeyedPolicyBody.is_the_same_dict(updated_policy, policy)
+
+ assert MONKEYED_POLICY_ID in policies
+ policy = policies[MONKEYED_POLICY_ID]
+ expected_1 = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID, priority="1")
+ ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID, json.dumps(expected_1)))
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_1)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_1, policy)
+
+ assert MONKEYED_POLICY_ID_B in policies
+ policy = policies[MONKEYED_POLICY_ID_B]
+ expected_b = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_B, 4, priority="1.5")
+ ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID_B, json.dumps(expected_1)))
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_B, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_b)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_b, policy)
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True)
+def test_update_not_only_config():
+ """test policy_update"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+ updated_policy = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_2, 2, priority="aa20")
+ added_policy = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_M_2, 2,
+ False, priority="1")
+ ctx.logger.info("policy_update: [{0}]".format(json.dumps(updated_policy)))
+
+ ctx.logger.info("policy[{0}]: not yet in policies".format(MONKEYED_POLICY_ID_M_2))
+ assert MONKEYED_POLICY_ID_M_2 not in policies
+
+ policy_filter_ids = runtime_properties.get(dcae_policy.POLICY_FILTERS, {}).keys() or ["--"]
+
+ policy_update_not_only_config(updated_policies=[updated_policy],
+ added_policies={
+ policy_filter_ids[0]: {
+ dcae_policy.POLICIES: {MONKEYED_POLICY_ID_M_2: added_policy}}
+ },
+ removed_policies=[MONKEYED_POLICY_ID_M])
+
+ ctx.logger.info("policy[{0}]: removed".format(MONKEYED_POLICY_ID_M))
+ assert MONKEYED_POLICY_ID_M not in policies
+
+ assert MONKEYED_POLICY_ID_M_2 in policies
+ policy = policies[MONKEYED_POLICY_ID_M_2]
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_M_2, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, added_policy)
+ assert MonkeyedPolicyBody.is_the_same_dict(added_policy, policy)
+
+ assert MONKEYED_POLICY_ID_2 in policies
+ policy = policies[MONKEYED_POLICY_ID_2]
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_2, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, updated_policy)
+ assert MonkeyedPolicyBody.is_the_same_dict(updated_policy, policy)
+
+ assert MONKEYED_POLICY_ID in policies
+ policy = policies[MONKEYED_POLICY_ID]
+ expected_1 = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID, priority="1")
+ ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID, json.dumps(expected_1)))
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_1)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_1, policy)
+
+ assert MONKEYED_POLICY_ID_B in policies
+ policy = policies[MONKEYED_POLICY_ID_B]
+ expected_b = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_B, 4, priority="1.5")
+ ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID_B, json.dumps(expected_1)))
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_B, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_b)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_b, policy)
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True)
+def test_update_policies_not():
+ """test policy_update - ignore all policies with junk params"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ assert APPLICATION_CONFIG in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ app_config = runtime_properties[APPLICATION_CONFIG]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+ ctx.logger.info("app_config: {0}".format(json.dumps(app_config)))
+
+ expected_policies = copy.deepcopy(policies)
+ expected_app_config = copy.deepcopy(app_config)
+
+ existing_policy = MonkeyedPolicyBody.create_policy_bare(MONKEYED_POLICY_ID, priority="1")
+ damaged_policy = MonkeyedPolicyBody.create_policy_bare(MONKEYED_POLICY_ID_2)
+ del damaged_policy[POLICY_BODY][POLICY_CONFIG]
+ updated_policy = MonkeyedPolicyBody.create_policy_bare(MONKEYED_POLICY_ID_M_3, 3)
+ added_policy = MonkeyedPolicyBody.create_policy_bare(MONKEYED_POLICY_ID_M_2, 4)
+ junk_policy_filter_id = "<<<junk_removed_policy_id>>>"
+ unexpected_removed_policy_id = "<<<junk_removed_policy_id>>>"
+ ctx.logger.info("policy_update: [{0}]".format(json.dumps(updated_policy)))
+
+ assert MONKEYED_POLICY_ID in policies
+ assert MONKEYED_POLICY_ID_2 in policies
+ assert MONKEYED_POLICY_ID_M_2 not in policies
+ assert MONKEYED_POLICY_ID_M_3 not in policies
+ assert unexpected_removed_policy_id not in policies
+ assert junk_policy_filter_id not in runtime_properties.get(dcae_policy.POLICY_FILTERS, {})
+
+ policy_filter_ids = runtime_properties.get(dcae_policy.POLICY_FILTERS, {}).keys() or ["--"]
+
+ policy_update(updated_policies=[existing_policy, damaged_policy, updated_policy],
+ added_policies={
+ junk_policy_filter_id: {
+ dcae_policy.POLICIES: {MONKEYED_POLICY_ID_M_2: added_policy}},
+ policy_filter_ids[0]: {
+ dcae_policy.POLICIES: {MONKEYED_POLICY_ID_2: damaged_policy}}
+ },
+ removed_policies=[unexpected_removed_policy_id])
+
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ ctx.logger.info("policies not changed: {0}".format(json.dumps(policies)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policies, expected_policies)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_policies, policies)
+
+ ctx.logger.info("app_config not changed: {0}".format(json.dumps(app_config)))
+ assert MonkeyedPolicyBody.is_the_same_dict(app_config, expected_app_config)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_app_config, app_config)
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True)
+def test_update_many_calcs():
+ """test policy_update"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+ updated_policy = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_2, 2, priority="aa20")
+ added_policy = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_M_2, 2,
+ False, priority="1")
+ ctx.logger.info("policy_update: [{0}]".format(json.dumps(updated_policy)))
+ ctx.logger.info("policy[{0}]: not yet in policies".format(MONKEYED_POLICY_ID_M_2))
+ assert MONKEYED_POLICY_ID_M_2 not in policies
+
+ policy_filter_ids = runtime_properties.get(dcae_policy.POLICY_FILTERS, {}).keys() or ["--"]
+
+ policy_update_many_calcs(updated_policies=[updated_policy],
+ added_policies={
+ policy_filter_ids[0]: {
+ dcae_policy.POLICIES: {MONKEYED_POLICY_ID_M_2: added_policy}}
+ },
+ removed_policies=[MONKEYED_POLICY_ID_M])
+
+ ctx.logger.info("policy[{0}]: removed".format(MONKEYED_POLICY_ID_M))
+ assert MONKEYED_POLICY_ID_M not in policies
+
+ assert MONKEYED_POLICY_ID_M_2 in policies
+ policy = policies[MONKEYED_POLICY_ID_M_2]
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_M_2, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, added_policy)
+ assert MonkeyedPolicyBody.is_the_same_dict(added_policy, policy)
+
+ assert MONKEYED_POLICY_ID_2 in policies
+ policy = policies[MONKEYED_POLICY_ID_2]
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_2, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, updated_policy)
+ assert MonkeyedPolicyBody.is_the_same_dict(updated_policy, policy)
+
+ assert MONKEYED_POLICY_ID in policies
+ policy = policies[MONKEYED_POLICY_ID]
+ expected_1 = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID, priority="1")
+ ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID, json.dumps(expected_1)))
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_1)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_1, policy)
+
+ assert MONKEYED_POLICY_ID_B in policies
+ policy = policies[MONKEYED_POLICY_ID_B]
+ expected_b = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_B, 4, priority="1.5")
+ ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID_B, json.dumps(expected_1)))
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_B, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_b)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_b, policy)
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True)
+def test_remove_all_policies():
+ """test policy_update - remove all policies"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+ remove_policy_ids = policies.keys()
+
+ policy_update(updated_policies=None, added_policies=None, removed_policies=remove_policy_ids)
+
+ ctx.logger.info("removed: {0}".format(remove_policy_ids))
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+ assert dcae_policy.POLICIES in runtime_properties
+ assert Policies.get_policy_bodies() == []
+
+ assert APPLICATION_CONFIG in runtime_properties
+ assert APPLICATION_CONFIG in ctx.node.properties
+ app_config = runtime_properties[APPLICATION_CONFIG]
+ expected_config = dict(ctx.node.properties[APPLICATION_CONFIG])
+ ctx.logger.info("expected = default application_config: {0}".format(json.dumps(app_config)))
+ assert MonkeyedPolicyBody.is_the_same_dict(app_config, expected_config)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_config, app_config)
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True)
+def test_remove_all_policies_twice():
+ """test policy_update - remove all policies twice"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+ remove_policy_ids = policies.keys()
+
+ policy_update(updated_policies=None, added_policies=None, removed_policies=remove_policy_ids)
+ policy_update(updated_policies=None, added_policies=None, removed_policies=remove_policy_ids)
+
+ ctx.logger.info("removed: {0}".format(remove_policy_ids))
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+ assert dcae_policy.POLICIES in runtime_properties
+ assert Policies.get_policy_bodies() == []
+
+ assert APPLICATION_CONFIG in runtime_properties
+ assert APPLICATION_CONFIG in ctx.node.properties
+ app_config = runtime_properties[APPLICATION_CONFIG]
+ expected_config = dict(ctx.node.properties[APPLICATION_CONFIG])
+ ctx.logger.info("expected = default application_config: {0}".format(json.dumps(app_config)))
+ assert MonkeyedPolicyBody.is_the_same_dict(app_config, expected_config)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_config, app_config)
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True)
+def test_remove_then_update():
+ """test policy_update"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+ remove_policy_ids = policies.keys()
+ policy_update(updated_policies=None, added_policies=None, removed_policies=remove_policy_ids)
+
+ updated_policy = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_2, 2, priority="aa20")
+ added_policy = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_M_2, 2,
+ False, priority="1")
+ ctx.logger.info("policy_update: [{0}]".format(json.dumps(updated_policy)))
+
+ ctx.logger.info("policy[{0}]: not yet in policies".format(MONKEYED_POLICY_ID_M_2))
+ assert MONKEYED_POLICY_ID_M_2 not in policies
+
+ policy_filter_ids = runtime_properties.get(dcae_policy.POLICY_FILTERS, {}).keys() or ["--"]
+
+ policy_update(updated_policies=[updated_policy],
+ added_policies={
+ policy_filter_ids[0]: {
+ dcae_policy.POLICIES: {MONKEYED_POLICY_ID_M_2: added_policy}}
+ },
+ removed_policies=[MONKEYED_POLICY_ID_M])
+
+ ctx.logger.info("policy[{0}]: removed".format(MONKEYED_POLICY_ID_M))
+ assert MONKEYED_POLICY_ID_M not in policies
+
+ assert MONKEYED_POLICY_ID_M_2 in policies
+ policy = policies[MONKEYED_POLICY_ID_M_2]
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_M_2, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, added_policy)
+ assert MonkeyedPolicyBody.is_the_same_dict(added_policy, policy)
+
+ assert MONKEYED_POLICY_ID_2 in policies
+ policy = policies[MONKEYED_POLICY_ID_2]
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_2, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, updated_policy)
+ assert MonkeyedPolicyBody.is_the_same_dict(updated_policy, policy)
+
+ assert MONKEYED_POLICY_ID in policies
+ assert MONKEYED_POLICY_ID_B in policies
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True)
+def test_remove_update_many_calcs():
+ """test policy_update"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+ remove_policy_ids = policies.keys()
+ policy_update_many_calcs(updated_policies=None,
+ added_policies=None,
+ removed_policies=remove_policy_ids)
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+ updated_policy = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_2, 2, priority="aa20")
+ added_policy = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_M_2, 2,
+ False, priority="1")
+ ctx.logger.info("policy_update: [{0}]".format(json.dumps(updated_policy)))
+
+ ctx.logger.info("policy[{0}]: not yet in policies".format(MONKEYED_POLICY_ID_M_2))
+ assert MONKEYED_POLICY_ID_M_2 not in policies
+
+ policy_filter_ids = runtime_properties.get(dcae_policy.POLICY_FILTERS, {}).keys() or ["--"]
+
+ policy_update_many_calcs(updated_policies=[updated_policy],
+ added_policies={
+ policy_filter_ids[0]: {
+ dcae_policy.POLICIES: {MONKEYED_POLICY_ID_M_2: added_policy}}
+ },
+ removed_policies=[MONKEYED_POLICY_ID_M])
+
+ ctx.logger.info("policy[{0}]: removed".format(MONKEYED_POLICY_ID_M))
+ assert MONKEYED_POLICY_ID_M not in policies
+
+ assert MONKEYED_POLICY_ID_M_2 in policies
+ policy = policies[MONKEYED_POLICY_ID_M_2]
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_M_2, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, added_policy)
+ assert MonkeyedPolicyBody.is_the_same_dict(added_policy, policy)
+
+ assert MONKEYED_POLICY_ID_2 in policies
+ policy = policies[MONKEYED_POLICY_ID_2]
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_2, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, updated_policy)
+ assert MonkeyedPolicyBody.is_the_same_dict(updated_policy, policy)
+
+ assert MONKEYED_POLICY_ID in policies
+ assert MONKEYED_POLICY_ID_B in policies
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True)
+def test_bad_update_many_calcs():
+ """test policy_update"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+ damaged_policy = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_2, 2, priority="aa20")
+ damaged_policy[POLICY_BODY][POLICY_CONFIG] = ["damaged config"]
+
+ added_policy = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_M_2, 2,
+ False, priority="1")
+ added_policy[POLICY_BODY][POLICY_CONFIG] = {"unexpected":"foo", "none": None}
+
+ ctx.logger.info("policy_update: [{0}]".format(json.dumps(damaged_policy)))
+
+ ctx.logger.info("policy[{0}]: not yet in policies".format(MONKEYED_POLICY_ID_M_2))
+ assert MONKEYED_POLICY_ID_M_2 not in policies
+
+ policy_filter_ids = runtime_properties.get(dcae_policy.POLICY_FILTERS, {}).keys() or ["--"]
+
+ policy_update_many_calcs(updated_policies=[damaged_policy],
+ added_policies={
+ policy_filter_ids[0]: {
+ dcae_policy.POLICIES: {MONKEYED_POLICY_ID_M_2: added_policy}}
+ },
+ removed_policies=[MONKEYED_POLICY_ID_M])
+
+ ctx.logger.info("policy[{0}]: removed".format(MONKEYED_POLICY_ID_M))
+ assert MONKEYED_POLICY_ID_M not in policies
+
+ assert MONKEYED_POLICY_ID_M_2 in policies
+ policy = policies[MONKEYED_POLICY_ID_M_2]
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_M_2, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, added_policy)
+ assert MonkeyedPolicyBody.is_the_same_dict(added_policy, policy)
+
+ assert MONKEYED_POLICY_ID_2 in policies
+ policy = policies[MONKEYED_POLICY_ID_2]
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_2, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, damaged_policy)
+ assert MonkeyedPolicyBody.is_the_same_dict(damaged_policy, policy)
+
+ assert MONKEYED_POLICY_ID in policies
+ policy = policies[MONKEYED_POLICY_ID]
+ expected_1 = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID, priority="1")
+ ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID, json.dumps(expected_1)))
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_1)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_1, policy)
+
+ assert MONKEYED_POLICY_ID_B in policies
+ policy = policies[MONKEYED_POLICY_ID_B]
+ expected_b = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_B, 4, priority="1.5")
+ ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID_B, json.dumps(expected_1)))
+ ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_B, json.dumps(policy)))
+ assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_b)
+ assert MonkeyedPolicyBody.is_the_same_dict(expected_b, policy)
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True, include_good=False)
+def test_bad_policies():
+ """test bad policy nodes"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True, include_good=False)
+def test_wrong_ctx_node_configure():
+ """test wrong ctx"""
+ current_ctx.set(ctx.instance.relationships[0])
+ ctx_type = ctx.type
+
+ with pytest.raises(NonRecoverableError) as excinfo:
+ node_configure()
+
+ CurrentCtx.reset()
+ ctx.logger.info("{0} not a node boom: {1}".format(ctx_type, str(excinfo.value)))
+ assert ctx_type == 'cloudify.relationships.depends_on'
+ assert str(excinfo.value) == "can only invoke gather_policies_to_node on node"
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True, include_good=False)
+def test_wrong_ctx_policy_update():
+ """test wrong ctx"""
+ no_policies = Policies.get_policy_bodies()
+ current_ctx.set(ctx.instance.relationships[0])
+ ctx_type = ctx.type
+
+ with pytest.raises(NonRecoverableError) as excinfo:
+ policy_update(updated_policies=None, added_policies=None, removed_policies=None)
+
+ CurrentCtx.reset()
+ ctx.logger.info("{0} not a node boom: {1}".format(ctx_type, str(excinfo.value)))
+ assert ctx_type == 'cloudify.relationships.depends_on'
+ assert no_policies == []
+ assert str(excinfo.value) == "can only invoke update_policies_on_node on node"
+
+def test_defenses_on_decorators():
+ """test defenses of code mainly for code coverage"""
+ should_be_none = Policies.gather_policies_to_node()(None)
+ assert should_be_none is None
+
+ should_be_none = Policies.update_policies_on_node()(None)
+ assert should_be_none is None
+
+def monkeyed_set_policies_boom(policies):
+ """monkeypatch for exception"""
+ raise Exception("Policies._set_policies boom: {0}".format(json.dumps(policies or {})))
+
+@pytest.fixture()
+def fix_boom_gather(monkeypatch):
+ """monkeyed boom"""
+ monkeypatch.setattr('onap_dcae_dcaepolicy_lib.dcae_policy.Policies._set_policies',
+ monkeyed_set_policies_boom)
+ return fix_boom_gather # provide the fixture value
+
+@cfy_ctx(include_bad=True, include_good=False)
+@pytest.mark.usefixtures("fix_boom_gather")
+def test_exception_on_gather():
+ """test exception on gather"""
+ with pytest.raises(NonRecoverableError) as excinfo:
node_configure()
- runtime_properties = ctx.instance.runtime_properties
- ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
-
- assert POLICIES in runtime_properties
- policies = runtime_properties[POLICIES]
- ctx.logger.info("policies: {0}".format(json.dumps(policies)))
-
- assert MONKEYED_POLICY_ID in policies
- expected_1 = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID)
- policy = policies[MONKEYED_POLICY_ID]
- ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID, json.dumps(expected_1)))
- ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID, json.dumps(policy)))
- assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_1)
- assert MonkeyedPolicyBody.is_the_same_dict(expected_1, policy)
-
- assert MONKEYED_POLICY_ID_2 in policies
- expected_2 = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_2)
- policy = policies[MONKEYED_POLICY_ID_2]
- ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID_2, json.dumps(expected_2)))
- ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_2, json.dumps(policy)))
- assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_2)
- assert MonkeyedPolicyBody.is_the_same_dict(expected_2, policy)
-
- updated_policy = MonkeyedPolicyBody.create_policy(MONKEYED_POLICY_ID_2, 2)
- ctx.logger.info("policy_update: [{0}]".format(json.dumps(updated_policy)))
-
- policy_update([updated_policy])
-
- assert MONKEYED_POLICY_ID_2 in policies
- policy = policies[MONKEYED_POLICY_ID_2]
- ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID_2, json.dumps(policy)))
- assert MonkeyedPolicyBody.is_the_same_dict(policy, updated_policy)
- assert MonkeyedPolicyBody.is_the_same_dict(updated_policy, policy)
-
- assert MONKEYED_POLICY_ID in policies
- policy = policies[MONKEYED_POLICY_ID]
- ctx.logger.info("expected[{0}]: {1}".format(MONKEYED_POLICY_ID, json.dumps(expected_1)))
- ctx.logger.info("policy[{0}]: {1}".format(MONKEYED_POLICY_ID, json.dumps(policy)))
- assert MonkeyedPolicyBody.is_the_same_dict(policy, expected_1)
- assert MonkeyedPolicyBody.is_the_same_dict(expected_1, policy)
-
- finally:
- MockCloudifyContextFull.clear()
- current_ctx.clear()
+ ctx.logger.info("monkeyed_set_policies_boom: {0}".format(str(excinfo.value)))
+ assert str(excinfo.value).startswith("Failed to set the policies ")
+
+def monkeyed_update_policies_boom(policies):
+ """monkeypatch for exception"""
+ raise Exception("Policies._update_policies boom")
+
+@pytest.fixture()
+def fix_boom_update_policies(monkeypatch):
+ """monkeyed boom"""
+ monkeypatch.setattr('onap_dcae_dcaepolicy_lib.dcae_policy.Policies._update_policies',
+ monkeyed_update_policies_boom)
+ return fix_boom_update_policies # provide the fixture value
+
+@cfy_ctx(include_bad=True, include_good=False)
+@pytest.mark.usefixtures("fix_boom_update_policies")
+def test_exception_on_update():
+ """test exception on update_policies"""
+ with pytest.raises(NonRecoverableError) as excinfo:
+ policy_update(updated_policies=None, added_policies=None, removed_policies=None)
+
+ ctx.logger.info("monkeyed_update_policies_boom: {0}".format(str(excinfo.value)))
+ assert str(excinfo.value).startswith("Failed to update the policies ")
+
+@cfy_ctx(include_bad=True, include_good=False)
+def test_defenses_on_policy_update():
+ """test defenses on policy_update"""
+ policy_update(updated_policies=None, added_policies=None, removed_policies=None)
+ ctx.logger.info("policy_update() ok")
+
+@cfy_ctx(include_bad=True, include_good=False)
+def test_defenses_on_set_policies():
+ """test defenses of code mainly for code coverage"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+ Policies._set_policies({})
+
+ assert dcae_policy.POLICIES not in runtime_properties
+
+ Policies._set_policies({})
+
+ assert dcae_policy.POLICIES not in runtime_properties
+
+@pytest.mark.usefixtures("fix_consul")
+@cfy_ctx(include_bad=True)
+def test_delete_node():
+ """test delete"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+ node_delete()
+
+
+@pytest.mark.usefixtures("fix_consul_boom")
+@cfy_ctx(include_bad=True)
+def test_delete_node_no_consul():
+ """test delete without consul"""
+ node_configure()
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES in runtime_properties
+ policies = runtime_properties[dcae_policy.POLICIES]
+ ctx.logger.info("policies: {0}".format(json.dumps(policies)))
+
+ node_delete()
+
+
+@pytest.mark.usefixtures("fix_consul_boom")
+@cfy_ctx(include_bad=True)
+def test_delete_node_no_policies():
+ """test delete without consul and setup"""
+
+ ctx.instance.runtime_properties[PoliciesOutput.POLICIES_EVENT] = {}
+ ctx.instance.runtime_properties[PoliciesOutput.SERVICE_COMPONENT_NAME] = "delete_node_empty"
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES not in runtime_properties
+
+ node_delete()
+
+
+@pytest.mark.usefixtures("fix_consul_boom")
+@cfy_ctx(include_bad=True)
+def test_delete_node_empty():
+ """test delete without consul and setup"""
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES not in runtime_properties
+
+ node_delete()
+
+@pytest.mark.usefixtures("fix_consul_boom")
+@cfy_ctx(include_bad=True)
+def test_delete_node_lost_scn():
+ """test delete without consul and setup"""
+ ctx.instance.runtime_properties[PoliciesOutput.POLICIES_EVENT] = {}
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES not in runtime_properties
+
+ node_delete()
+
+
+@pytest.mark.usefixtures("fix_consul_boom")
+@cfy_ctx(include_bad=True)
+def test_delete_node_empty_config():
+ """test delete without consul and setup"""
+
+ ctx.instance.runtime_properties[PoliciesOutput.POLICIES_EVENT] = {}
+ ctx.instance.runtime_properties[PoliciesOutput.SERVICE_COMPONENT_NAME] = "delete_node_empty"
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES not in runtime_properties
+
+ node_delete()
+
+@pytest.mark.usefixtures("fix_consul_boom")
+@cfy_ctx(include_bad=True)
+def test_delete_ms_no_consul_addr():
+ """test delete without consul and setup"""
+
+ ctx.instance.runtime_properties[PoliciesOutput.POLICIES_EVENT] = {}
+ ctx.instance.runtime_properties[PoliciesOutput.SERVICE_COMPONENT_NAME] = "delete_node_empty"
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES not in runtime_properties
+
+ node_delete()
+
+
+@pytest.mark.usefixtures("fix_consul_boom")
+@cfy_ctx(include_bad=True)
+def test_delete_bad_config():
+ """test delete without consul and setup"""
+
+ ctx.instance.runtime_properties[PoliciesOutput.POLICIES_EVENT] = {}
+ ctx.instance.runtime_properties[PoliciesOutput.SERVICE_COMPONENT_NAME] = "delete_node_empty"
+
+ runtime_properties = ctx.instance.runtime_properties
+ ctx.logger.info("runtime_properties: {0}".format(json.dumps(runtime_properties)))
+
+ assert dcae_policy.POLICIES not in runtime_properties
+
+ node_delete()
+
diff --git a/onap-dcae-dcaepolicy-lib/tox-local.ini b/onap-dcae-dcaepolicy-lib/tox-local.ini
index ed9879a..41d5708 100644
--- a/onap-dcae-dcaepolicy-lib/tox-local.ini
+++ b/onap-dcae-dcaepolicy-lib/tox-local.ini
@@ -1,3 +1,4 @@
+# tox -c tox-local.ini | tee -a logs/test_onap_dcae_dcaepolicy_lib.log 2>&1
[tox]
envlist = py27
@@ -12,5 +13,3 @@ setenv =
PYTHONPATH={toxinidir}
# recreate = True
commands=pytest -v --cov onap_dcae_dcaepolicy_lib --cov-report html
-
-
diff --git a/onap-dcae-dcaepolicy-lib/tox.ini b/onap-dcae-dcaepolicy-lib/tox.ini
index 78af290..9bace46 100644
--- a/onap-dcae-dcaepolicy-lib/tox.ini
+++ b/onap-dcae-dcaepolicy-lib/tox.ini
@@ -11,4 +11,11 @@ deps=
pytest-cov
setenv =
PYTHONPATH={toxinidir}
-commands=pytest --junitxml xunit-reports/xunit-result-onap_dcae_dcaepolicy_lib.xml --cov onap_dcae_dcaepolicy_lib --cov-report=xml
+whitelist_externals=
+ rm
+ mkdir
+commands=
+ rm -rf {toxinidir}/logs
+ mkdir {toxinidir}/logs
+ pytest --junitxml xunit-results.xml --cov onap_dcae_dcaepolicy_lib --cov-report xml
+ coverage xml
diff --git a/pom.xml b/pom.xml
index c03e65a..e611b20 100644
--- a/pom.xml
+++ b/pom.xml
@@ -38,28 +38,16 @@ ECOMP is a trademark and service mark of AT&T Intellectual Property.
<module>onap-dcae-dcaepolicy-lib</module>
<module>python-discovery-client</module>
<module>python-dockering</module>
+ <module>dcaeapplib</module>
+ <module>eelf-logger</module>
</modules>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
- <sonar.skip>true</sonar.skip>
- <sonar.sources>*/</sonar.sources>
- <sonar.junit.reportsPath>**/xunit-results.xml</sonar.junit.reportsPath>
- <sonar.python.coverage.reportPath>**/coverage.xml</sonar.python.coverage.reportPath>
<!-- customize the SONARQUBE URL -->
<sonar.host.url>http://localhost:9000</sonar.host.url>
- <sonar.exclusions>tests/*</sonar.exclusions>
- <!-- below are language dependent -->
- <!-- for Python -->
- <sonar.language>py</sonar.language>
- <sonar.pluginName>Python</sonar.pluginName>
- <sonar.inclusions>**/*.py</sonar.inclusions>
- <!-- for JavaScaript -->
- <!--
- <sonar.language>js</sonar.language>
- <sonar.pluginName>JS</sonar.pluginName>
- <sonar.inclusions>**/*.js</sonar.inclusions>
- -->
+ <!-- taken care of in the children -->
+ <sonar.exclusions>**/*.py</sonar.exclusions>
</properties>
<build>
<finalName>${project.artifactId}-${project.version}</finalName>
diff --git a/python-discovery-client/pom.xml b/python-discovery-client/pom.xml
index b420626..0854b5a 100644
--- a/python-discovery-client/pom.xml
+++ b/python-discovery-client/pom.xml
@@ -40,7 +40,7 @@ ECOMP is a trademark and service mark of AT&T Intellectual Property.
<sonar.language>py</sonar.language>
<sonar.pluginName>Python</sonar.pluginName>
<sonar.inclusions>**/*.py</sonar.inclusions>
- <sonar.exclusions>tests/*</sonar.exclusions>
+ <sonar.exclusions>tests/*,setup.py</sonar.exclusions>
</properties>
<build>
<finalName>${project.artifactId}-${project.version}</finalName>
diff --git a/python-discovery-client/setup.py b/python-discovery-client/setup.py
index 8648808..5a044ee 100644
--- a/python-discovery-client/setup.py
+++ b/python-discovery-client/setup.py
@@ -18,8 +18,6 @@
# ECOMP is a trademark and service mark of AT&T Intellectual Property.
from setuptools import setup, find_packages
-from pip.req import parse_requirements
-from pip.download import PipSession
setup(
name = "onap-dcae-discovery-client",
diff --git a/python-discovery-client/tox.ini b/python-discovery-client/tox.ini
index 5b492c9..d8386d8 100644
--- a/python-discovery-client/tox.ini
+++ b/python-discovery-client/tox.ini
@@ -7,4 +7,8 @@ deps=
pytest
coverage
pytest-cov
-commands=pytest --junitxml xunit-results.xml --cov {envsitepackagesdir}/discovery_client --cov-report=xml
+setenv=
+ PYTHONPATH={toxinidir}
+commands=
+ pytest --junitxml xunit-results.xml --cov discovery_client --cov-report=xml
+ coverage xml
diff --git a/python-dockering/pom.xml b/python-dockering/pom.xml
index aa24d9c..7dd0de5 100644
--- a/python-dockering/pom.xml
+++ b/python-dockering/pom.xml
@@ -40,7 +40,7 @@ ECOMP is a trademark and service mark of AT&T Intellectual Property.
<sonar.language>py</sonar.language>
<sonar.pluginName>Python</sonar.pluginName>
<sonar.inclusions>**/*.py</sonar.inclusions>
- <sonar.exclusions>tests/*</sonar.exclusions>
+ <sonar.exclusions>tests/*,setup.py</sonar.exclusions>
</properties>
<build>
<finalName>${project.artifactId}-${project.version}</finalName>
diff --git a/python-dockering/tox.ini b/python-dockering/tox.ini
index 280cf78..71de279 100644
--- a/python-dockering/tox.ini
+++ b/python-dockering/tox.ini
@@ -7,4 +7,8 @@ deps=
pytest
coverage
pytest-cov
-commands=pytest --junitxml xunit-results.xml --cov {envsitepackagesdir}/dockering --cov-report=xml
+setenv=
+ PYTHONPATH={toxinidir}
+commands=
+ pytest --junitxml xunit-results.xml --cov dockering --cov-report xml
+ coverage xml
diff --git a/scripts/mvn-phase-lib.sh b/scripts/mvn-phase-lib.sh
index 6cef83e..2bf82bd 100644
--- a/scripts/mvn-phase-lib.sh
+++ b/scripts/mvn-phase-lib.sh
@@ -1,7 +1,7 @@
#!/bin/bash
# ================================================================================
-# Copyright (c) 2017 AT&T Intellectual Property. All rights reserved.
+# Copyright (c) 2017-2018 AT&T Intellectual Property. All rights reserved.
# ================================================================================
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -15,8 +15,6 @@
# See the License for the specific language governing permissions and
# limitations under the License.
# ============LICENSE_END=========================================================
-#
-# ECOMP is a trademark and service mark of AT&T Intellectual Property.
#MVN_PROJECT_MODULEID="$1"
@@ -52,16 +50,18 @@ if [ -z "$WORKSPACE" ]; then
WORKSPACE=$(pwd)
fi
-if [ -z "$SETTINGS_FILE" ]; then
- echo "SETTINGS_FILE environment variable not set. Cannot proceed"
- exit
-fi
+export SETTINGS_FILE=${SETTINGS_FILE:-$HOME/.m2/settings.xml}
+RELEASE_TAG=${MVN_RELEASE_TAG:-R3}
+if [ "$RELEASE_TAG" == "R1" ]; then
+ unset RELEASE_TAG
+fi
# mvn phase in life cycle
MVN_PHASE="$2"
+echo "MVN_RELEASE_TAG is [$MVN_RELEASE_TAG]"
echo "MVN_PROJECT_MODULEID is [$MVN_PROJECT_MODULEID]"
echo "MVN_PHASE is [$MVN_PHASE]"
echo "MVN_PROJECT_GROUPID is [$MVN_PROJECT_GROUPID]"
@@ -76,7 +76,6 @@ echo "MVN_RAWREPO_SERVERID is [$MVN_RAWREPO_SERVERID]"
echo "MVN_DOCKERREGISTRY_SNAPSHOT is [$MVN_DOCKERREGISTRY_SNAPSHOT]"
echo "MVN_DOCKERREGISTRY_PUBLIC is [$MVN_DOCKERREGISTRY_PUBLIC]"
echo "MVN_DOCKERREGISTRY_RELEASE is [$MVN_DOCKERREGISTRY_RELEASE]"
-
echo "MVN_PYPISERVER_SERVERID [$MVN_PYPISERVER_SERVERID]"
echo "MVN_PYPISERVER_BASEURL is [$MVN_PYPISERVER_BASEURL]"
@@ -108,19 +107,30 @@ expand_templates()
export ONAPTEMPLATE_RAWREPOURL_org_onap_ccsdk_platform_plugins_snapshots="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.ccsdk.platform.plugins"
export ONAPTEMPLATE_RAWREPOURL_org_onap_ccsdk_platform_blueprints_releases="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.ccsdk.platform.blueprints"
export ONAPTEMPLATE_RAWREPOURL_org_onap_ccsdk_platform_blueprints_snapshots="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.ccsdk.platform.blueprints"
-
- export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_releases="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2/releases"
- export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_snapshots="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2/snapshots"
- export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_platform_plugins_releases="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2.platform.plugins/releases"
- export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_platform_plugins_snapshots="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2.platform.plugins/snapshots"
- export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_platform_blueprints_releases="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2.platform.blueprints/releases"
- export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_platform_blueprints_snapshots="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2.platform.blueprints/snapshots"
+
+
+ if [ -z "$RELEASE_TAG" ]; then
+ export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_releases="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2/releases"
+ export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_snapshots="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2/snapshots"
+ export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_platform_plugins_releases="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2.platform.plugins/releases"
+ export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_platform_plugins_snapshots="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2.platform.plugins/snapshots"
+ export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_platform_blueprints_releases="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2.platform.blueprints/releases"
+ export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_platform_blueprints_snapshots="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2.platform.blueprints/snapshots"
+ else
+ export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_releases="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2/$RELEASE_TAG"
+ export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_snapshots="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2/$RELEASE_TAG"
+ export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_platform_plugins_releases="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2.platform.plugins/$RELEASE_TAG"
+ export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_platform_plugins_snapshots="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2.platform.plugins/$RELEASE_TAG"
+ export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_platform_blueprints_releases="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2.platform.blueprints/$RELEASE_TAG"
+ export ONAPTEMPLATE_RAWREPOURL_org_onap_dcaegen2_platform_blueprints_snapshots="$MVN_RAWREPO_BASEURL_DOWNLOAD/org.onap.dcaegen2.platform.blueprints/$RELEASE_TAG"
+ fi
+
export ONAPTEMPLATE_PYPIURL_org_onap_dcaegen2="${MVN_PYPISERVER_BASEURL}"
# docker registry templates are for poll, so use PUBLIC registry
- export ONAPTEMPLATE_DOCKERREGURL_org_onap_dcaegen2_releases="$MVN_DOCKERREGISTRY_PUBLIC"
- export ONAPTEMPLATE_DOCKERREGURL_org_onap_dcaegen2_snapshots="${MVN_DOCKERREGISTRY_PUBLIC}/snapshots"
+ export ONAPTEMPLATE_DOCKERREGURL_org_onap_dcaegen2_releases="${MVN_DOCKERREGISTRY_PUBLIC}"
+ export ONAPTEMPLATE_DOCKERREGURL_org_onap_dcaegen2_snapshots="${MVN_DOCKERREGISTRY_PUBLIC}"
# Mvn repo
export ONAPTEMPLATE_MVN_org_onap_dcaegen2_analytics_tca_snapshots="${MVN_NEXUSPROXY}/service/local/repositories/snapshots/content/org/onap/dcaegen2/analytics/tca"
@@ -171,7 +181,7 @@ expand_templates()
echo "====> Resolving the following template from environment variables "
echo "$TEMPLATES"
for KEY in $TEMPLATES; do
- VALUE1=$(eval 'echo "$"'"$KEY"'"' | sed 1q)
+ VALUE1=$(eval 'echo "$'"$KEY"'"' | sed 1q)
VALUE2=$(eval 'echo "$'"$KEY"'"' | sed -e 's/\//\\\//g' -e 's/$/\\/' -e '$s/\\$//')
echo "======> Resolving template $KEY to value $VALUE1 for file $F2"
@@ -191,12 +201,12 @@ test_templates()
find . -name '*-template' | sed -e 's/-template$//' |
while read file
do
- egrep '^ - .?https?://' < $file
+ egrep '^ - .?https?://' < "$file"
done | awk '{print $2}' | sed -e 's/"//g' | sort -u |
while read url
do
- curl -L -w '%{http_code}' -s -o /dev/null "$url" > $TMP
- case $(< $TMP) in
+ curl -L -w '%{http_code}' -s -o /dev/null "$url" > "$TMP"
+ case $(< "$TMP") in
2* ) ;;
* ) echo ">>>>>>>>>>>>>>>> $url not found <<<<<<<<<<<<<<<<" ;;
esac
@@ -207,14 +217,14 @@ test_templates()
find . -name '*-template' | sed -e 's/-template$//' |
while read blueprint
do
- check-blueprint-vs-input -b $blueprint -i check-blueprint-vs-input/lib/sample-inputs.yaml || true
+ check-blueprint-vs-input -b "$blueprint" -i check-blueprint-vs-input/lib/sample-inputs.yaml || true
done
}
run_tox_test()
{
- set -x
+ set -e -x
CURDIR=$(pwd)
TOXINIS=$(find . -name "tox.ini")
for TOXINI in "${TOXINIS[@]}"; do
@@ -223,8 +233,9 @@ run_tox_test()
rm -rf ./venv-tox ./.tox
virtualenv ./venv-tox
source ./venv-tox/bin/activate
- pip install --upgrade pip
- pip install --upgrade tox argparse
+ pip install pip==9.0.3
+ pip install --upgrade argparse
+ pip install tox==2.9.1
pip freeze
tox
deactivate
@@ -250,17 +261,40 @@ build_wagons()
echo "In $PLUGIN_DIR, build plugin $PLUGIN_NAME, version $PLUGIN_VERSION"
- wagon create --format tar.gz "${PLUGIN_DIR}"
+ wagon create -r "${PLUGIN_DIR}/requirements.txt" --format tar.gz "${PLUGIN_DIR}"
PKG_FILE_NAMES=( "${PLUGIN_NAME}-${PLUGIN_VERSION}"*.wgn )
echo Built package: "${PKG_FILE_NAMES[@]}"
- cd $CURDIR
+ cd "$CURDIR"
done
deactivate
rm -rf venv-pkg
}
+build_archives_for_wagons()
+{
+ rm -rf ./*.tgz ./*.zip venv-pkg
+
+ SETUPFILES=$(find "$(pwd)" -name "setup.py")
+ CURDIR=$(pwd)
+ for SETUPFILE in $SETUPFILES; do
+ PLUGIN_FULL_DIR=$(dirname "$SETUPFILE")
+ PLUGIN_BASE_DIR=$(basename "$PLUGIN_FULL_DIR")
+ PLUGIN_NAME=$(grep 'name' "$SETUPFILE" | cut -f2 -d'=' | sed 's/[^0-9a-zA-Z\.]*//g')
+ PLUGIN_VERSION=$(grep 'version' "$SETUPFILE" | cut -f2 -d'=' | sed 's/[^0-9\.]*//g')
+
+ cd "${PLUGIN_FULL_DIR}"/..
+ echo "In $(pwd), build plugin zip $PLUGIN_NAME, version $PLUGIN_VERSION"
+
+ zip -r "${PLUGIN_NAME}-${PLUGIN_VERSION}.zip" "./${PLUGIN_BASE_DIR}"
+ tar -czvf "${PLUGIN_NAME}-${PLUGIN_VERSION}.tgz" "./${PLUGIN_BASE_DIR}"
+
+ echo "Built archives for package ${PLUGIN_NAME}-${PLUGIN_VERSION} at $(pwd)"
+ cd "$CURDIR"
+ done
+}
+
upload_raw_file()
{
@@ -280,6 +314,10 @@ upload_raw_file()
OUTPUT_FILE_TYPE='text/x-shellscript'
elif [ "$EXT" == 'gz' ]; then
OUTPUT_FILE_TYPE='application/gzip'
+ elif [ "$EXT" == 'tgz' ]; then
+ OUTPUT_FILE_TYPE='application/gzip'
+ elif [ "$EXT" == 'zip' ]; then
+ OUTPUT_FILE_TYPE='application/zip'
elif [ "$EXT" == 'wgn' ]; then
OUTPUT_FILE_TYPE='application/gzip'
else
@@ -294,17 +332,13 @@ upload_raw_file()
else
PROJECT_NAME=${FQDN}
fi
- if [ "$MVN_DEPLOYMENT_TYPE" == 'SNAPSHOT' ]; then
- SEND_TO="${REPO}/${PROJECT_NAME}/snapshots"
- elif [ "$MVN_DEPLOYMENT_TYPE" == 'STAGING' ]; then
- SEND_TO="${REPO}/${PROJECT_NAME}/releases"
+
+ if [ -z "$RELEASE_TAG" ]; then
+ SEND_TO="${REPO}/${PROJECT_NAME}"
else
- echo "Unreconfnized deployment type, quit"
- exit
+ SEND_TO="${REPO}/${PROJECT_NAME}/${RELEASE_TAG}"
fi
- #if [ ! -z "$MVN_PROJECT_MODULEID" ]; then
- # SEND_TO="$SEND_TO/$MVN_PROJECT_MODULEID"
- #fi
+
if [ ! -z "$2" ]; then
SEND_TO="$SEND_TO/$2"
fi
@@ -314,7 +348,36 @@ upload_raw_file()
curl -vkn --netrc-file "${NETRC}" --upload-file "${OUTPUT_FILE}" -X PUT -H "Content-Type: $OUTPUT_FILE_TYPE" "${SEND_TO}/${OUTPUT_FILE}"
}
+upload_wagon_archives()
+{
+ SETUPFILES=$(find "$(pwd)" -name "setup.py")
+ CURDIR=$(pwd)
+ for SETUPFILE in $SETUPFILES; do
+ PLUGIN_FULL_DIR=$(dirname "$SETUPFILE")
+ PLUGIN_BASE_DIR=$(basename "$PLUGIN_FULL_DIR")
+ PLUGIN_NAME=$(grep 'name' "$SETUPFILE" | cut -f2 -d'=' | sed 's/[^0-9a-zA-Z\.]*//g')
+ PLUGIN_VERSION=$(grep 'version' "$SETUPFILE" | cut -f2 -d'=' | sed 's/[^0-9\.]*//g')
+
+ cd "${PLUGIN_FULL_DIR}"/..
+ echo "In $(pwd), upload zip archive for $PLUGIN_NAME, version $PLUGIN_VERSION"
+ ARCHIVE_FILE_NAME="${PLUGIN_NAME}-${PLUGIN_VERSION}.zip"
+ if [ -z "$ARCHIVE_FILE_NAME" ]; then
+ echo "!!! No zip archive file found ${ARCHIVE_FILE_NAME}"
+ exit -1
+ fi
+ upload_raw_file "${ARCHIVE_FILE_NAME}" "${PLUGIN_NAME}/${PLUGIN_VERSION}"
+ echo "In $(pwd), upload tgz archive for $PLUGIN_NAME, version $PLUGIN_VERSION"
+ ARCHIVE_FILE_NAME="${PLUGIN_NAME}-${PLUGIN_VERSION}.tgz"
+ if [ -z "$ARCHIVE_FILE_NAME" ]; then
+ echo "!!! No tgz archive file found ${ARCHIVE_FILE_NAME}"
+ exit -1
+ fi
+ upload_raw_file "${ARCHIVE_FILE_NAME}" "${PLUGIN_NAME}/${PLUGIN_VERSION}"
+
+ cd "${CURDIR}"
+ done
+}
upload_wagons_and_type_yamls()
{
@@ -341,19 +404,18 @@ upload_wagons_and_type_yamls()
cp -f "$TYPEFILE_NAME" "$NEWFILENAME"
fi
- TYPEFILE_PACKAGE_VERSION=$(grep -R 'package_version' $TYPEFILE_NAME |cut -f2 -d ':' |sed -r 's/\s+//g')
- WAGONFILE_NAME=$(ls -1 $PLUGIN_NAME-$TYPEFILE_PACKAGE_VERSION-*.wgn)
+ TYPEFILE_PACKAGE_VERSION=$(grep -R 'package_version' "$TYPEFILE_NAME" |cut -f2 -d ':' |sed -r 's/\s+//g')
+ WAGONFILE_NAME=$(ls -1 "${PLUGIN_NAME}"-"${TYPEFILE_PACKAGE_VERSION}"-*.wgn)
if [ -z "$WAGONFILE_NAME" ]; then
echo "!!! No wagonfile found with matching package name and version as required in typefile: "
echo " $TYPEFILE_NAME plugin $PLUGIN_NAME package version ${TYPEFILE_PACKAGE_VERSION}"
exit -1
fi
- upload_raw_file "$NEWFILENAME" type_files/${PLUGIN_NAME}/${PLUGIN_VERSION_MAJOR}
- upload_raw_file "$NEWFILENAME" type_files/${PLUGIN_NAME}/${PLUGIN_VERSION_MAJOR_MINOR}
- upload_raw_file "${WAGONFILE_NAME}" "plugins/${PLUGIN_NAME}"
+ upload_raw_file "${NEWFILENAME}" "${PLUGIN_NAME}/${PLUGIN_VERSION}"
+ upload_raw_file "${WAGONFILE_NAME}" "${PLUGIN_NAME}/${PLUGIN_VERSION}"
- rm -r $WAGONFILE_NAME
+ rm -r "$WAGONFILE_NAME"
if [ "$TYPEFILE_NAME" != "$NEWFILENAME" ]; then
rm -f "$NEWFILENAME"
fi
@@ -367,6 +429,13 @@ upload_files_of_extension()
upload_raw_file "$F" "$2"
done
}
+upload_files_of_extension_recursively()
+{
+ FILES=$(find . -name "*.$1")
+ for F in $FILES ; do
+ upload_raw_file "$F" "$2"
+ done
+}
generate_pypirc_then_publish()
@@ -398,9 +467,22 @@ EOL
+# following the https://wiki.onap.org/display/DW/Independent+Versioning+and+Release+Process
+#IndependentVersioningandReleaseProcess-StandardizedDockerTagging
build_and_push_docker()
{
- IMAGENAME="onap/${FQDN}.${MVN_PROJECT_MODULEID}"
+ # Old tagging
+ #IMAGENAME="onap/${FQDN}.${MVN_PROJECT_MODULEID}"
+ # new tagging
+ ENDID=$(echo $FQDN | rev | cut -f1 -d '.' |rev)
+ if [ "$ENDID" == "${MVN_PROJECT_MODULEID}" ]; then
+ #IMAGENAME="onap/${FQDN/org.onap./}"
+ IMAGENAME="onap/${FQDN}"
+ else
+ #IMAGENAME="onap/${FQDN/org.onap./}.${MVN_PROJECT_MODULEID}"
+ IMAGENAME="onap/${FQDN}.${MVN_PROJECT_MODULEID}"
+ fi
+
IMAGENAME=$(echo "$IMAGENAME" | sed -e 's/_*$//g' -e 's/\.*$//g')
IMAGENAME=$(echo "$IMAGENAME" | tr '[:upper:]' '[:lower:]')
@@ -408,16 +490,16 @@ build_and_push_docker()
VERSION="${MVN_PROJECT_VERSION//[^0-9.]/}"
VERSION2=$(echo "$VERSION" | cut -f1-2 -d'.')
- LFQI="${IMAGENAME}:${VERSION}-${TIMESTAMP}"
+ LFQI="${IMAGENAME}:${VERSION}-${TIMESTAMP}"Z
# build a docker image
docker build --rm -f ./Dockerfile -t "${LFQI}" ./
+ # all local builds push to SNAPSHOT repo
REPO=""
if [ $MVN_DEPLOYMENT_TYPE == "SNAPSHOT" ]; then
- REPO=$MVN_DOCKERREGISTRY_SNASHOT
+ REPO=$MVN_DOCKERREGISTRY_SNAPSHOT
elif [ $MVN_DEPLOYMENT_TYPE == "STAGING" ]; then
- # there seems to be no staging docker registry? set to use SNAPSHOT also
- REPO=$MVN_DOCKERREGISTRY_RELEASE
+ REPO=$MVN_DOCKERREGISTRY_SNAPSHOT
else
echo "Fail to determine DEPLOYMENT_TYPE"
REPO=$MVN_DOCKERREGISTRY_SNAPSHOT
@@ -437,19 +519,14 @@ build_and_push_docker()
echo docker login "$REPO" -u "$USER" -p "$PASS_PROVIDED"
docker login "$REPO" -u "$USER" -p "$PASS"
- if [ $MVN_DEPLOYMENT_TYPE == "SNAPSHOT" ]; then
- REPO="$REPO/snapshots"
- elif [ $MVN_DEPLOYMENT_TYPE == "STAGING" ]; then
- # there seems to be no staging docker registry? set to use SNAPSHOT also
- #REPO=$MVN_DOCKERREGISTRY_RELEASE
- REPO="$REPO"
- else
- echo "Fail to determine DEPLOYMENT_TYPE"
- REPO="$REPO/unknown"
- fi
-
- OLDTAG="${LFQI}"
- PUSHTAGS="${REPO}/${IMAGENAME}:${VERSION2}-${TIMESTAMP} ${REPO}/${IMAGENAME}:${VERSION2} ${REPO}/${IMAGENAME}:${VERSION2}-latest"
+ # local tag is imagename:version-timestamp
+ OLDTAG="${LFQI}"
+ # three tags are pushed:
+ # {imagename}:{semver}-SNAPSHOT-{timestamp}Z this is what CIMAN-132 asks
+ # {imagename}:{semver} latest of current version, for testing
+ # {imagename}:latest latest of all, used mainly by csit
+ # LFQI="${IMAGENAME}:${VERSION}-${TIMESTAMP}"Z
+ PUSHTAGS="${REPO}/${IMAGENAME}:${VERSION}-SNAPSHOT-${TIMESTAMP}Z ${REPO}/${IMAGENAME}:${VERSION} ${REPO}/${IMAGENAME}:latest"
for NEWTAG in ${PUSHTAGS}
do
echo "tagging ${OLDTAG} to ${NEWTAG}"
@@ -459,8 +536,4 @@ build_and_push_docker()
OLDTAG="${NEWTAG}"
done
fi
-
}
-
-
-
diff --git a/scripts/pom.xml b/scripts/pom.xml
index 12e71fb..4ff29df 100644
--- a/scripts/pom.xml
+++ b/scripts/pom.xml
@@ -45,7 +45,7 @@ ECOMP is a trademark and service mark of AT&T Intellectual Property.
<sonar.language>py</sonar.language>
<sonar.pluginName>Python</sonar.pluginName>
<sonar.inclusions>**/*.py</sonar.inclusions>
- <sonar.exclusions>tests/*</sonar.exclusions>
+ <sonar.exclusions>tests/*,setup.py</sonar.exclusions>
<sonar.host.url>http://135.205.228.63:9000</sonar.host.url>
</properties>
<build>