aaa2a0a83f49c2bce0975d2cf1aea879941ce257
[policy/drools-applications.git] /
1 /*-
2  * ============LICENSE_START=======================================================
3  * guard
4  * ================================================================================
5  * Copyright (C) 2018 AT&T Intellectual Property. All rights reserved.
6  * ================================================================================
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  * 
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  * 
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  * ============LICENSE_END=========================================================
19  */
20
21 package org.onap.policy.guard;
22
23 import java.util.HashSet;
24 import java.util.Set;
25 import java.util.UUID;
26 import java.util.function.Supplier;
27 import org.drools.core.WorkingMemory;
28 import org.slf4j.Logger;
29 import org.slf4j.LoggerFactory;
30 import com.att.research.xacml.api.DataTypeException;
31 import com.att.research.xacml.std.annotations.RequestParser;
32
33 public class CallGuardTaskEmbedded implements Runnable {
34
35     private static final Logger logger = LoggerFactory.getLogger(CallGuardTaskEmbedded.class);
36
37     /**
38      * Actor/recipe pairs whose guard requests need a VF Module count. Each element is of
39      * the form "<actor>:<recipe>".
40      */
41     private static final Set<String> NEEDS_VF_COUNT = new HashSet<>();
42
43     /**
44      * Actor/recipe pairs whose guard requests need the VF Module count to be incremented
45      * (i.e., because a module is being added). Each element is of the form
46      * "<actor>:<recipe>".
47      */
48     private static final Set<String> INCR_VF_COUNT = new HashSet<>();
49
50     static {
51         INCR_VF_COUNT.add("SO:VF Module Create");
52         NEEDS_VF_COUNT.addAll(INCR_VF_COUNT);
53     }
54
55     private WorkingMemory workingMemory;
56     private String clname;
57     private String actor;
58     private String recipe;
59     private String target;
60     private String requestId;
61     private Integer vfCount;
62
63     /**
64      * Populated once the response has been determined, which may happen during the
65      * constructor or later, during {@link #run()}.
66      */
67     private PolicyGuardResponse guardResponse;
68
69     /**
70      * Guard url is grabbed from PolicyEngine.manager properties
71      */
72     public CallGuardTaskEmbedded(WorkingMemory wm, String cl, String act, String rec, String tar, String reqId, Supplier<Integer> vfcnt) {
73         workingMemory = wm;
74         clname = cl;
75         actor = act;
76         recipe = rec;
77         requestId = reqId;
78         target = tar;
79
80         vfCount = null;
81
82         String key = act + ":" + rec;
83
84         if (NEEDS_VF_COUNT.contains(key)) {
85             // this actor/recipe needs the count - get it
86             if ((vfCount = vfcnt.get()) == null) {
87                 /*
88                  * The count is missing - create an artificial Deny, which will be
89                  * inserted into working memory when "run()" is called.
90                  */
91                 guardResponse = new PolicyGuardResponse(Util.DENY, UUID.fromString(requestId), recipe);
92                 logger.error("CallEmbeddedGuardTask.run missing VF Module count; requestId={}", requestId);
93                 return;
94             }
95
96             if (INCR_VF_COUNT.contains(key)) {
97                 // this actor/recipe needs the count to be incremented
98                 ++vfCount;
99             }
100         }
101     }
102
103     @Override
104     public void run() {
105         if (guardResponse != null) {
106             // already have a response - just insert it
107             workingMemory.insert(guardResponse);
108             return;
109         }
110         
111         final long startTime = System.nanoTime();
112         com.att.research.xacml.api.Request request = null;
113
114         PolicyGuardXacmlRequestAttributes xacmlReq =
115                         new PolicyGuardXacmlRequestAttributes(clname, actor, recipe, target, requestId, vfCount);
116
117         try {
118             request = RequestParser.parseRequest(xacmlReq);
119         } catch (IllegalArgumentException | IllegalAccessException | DataTypeException e) {
120             logger.error("CallEmbeddedGuardTask.run threw: {}", e);
121         }
122
123
124         logger.debug("\n********** XACML REQUEST START ********");
125         logger.debug("{}", request);
126         logger.debug("********** XACML REQUEST END ********\n");
127
128         String guardDecision = null;
129
130         //
131         // Make guard request
132         //
133         guardDecision = new PolicyGuardXacmlHelperEmbedded().callPdp(xacmlReq);
134
135         logger.debug("\n********** XACML RESPONSE START ********");
136         logger.debug("{}", guardDecision);
137         logger.debug("********** XACML RESPONSE END ********\n");
138
139         //
140         // Check if the restful call was unsuccessful or property doesn't exist
141         //
142         if (guardDecision == null) {
143             logger.error("********** XACML FAILED TO CONNECT ********");
144             guardDecision = Util.INDETERMINATE;
145         }
146
147         guardResponse = new PolicyGuardResponse(guardDecision, UUID.fromString(this.requestId), this.recipe);
148
149
150         //
151         // Create an artificial Guard response in case we didn't get a clear Permit or Deny
152         //
153         if (guardResponse.getResult().equals("Indeterminate")) {
154             guardResponse.setOperation(recipe);
155             guardResponse.setRequestID(UUID.fromString(requestId));
156         }
157
158         long estimatedTime = System.nanoTime() - startTime;
159         logger.debug("\n\n============ Guard inserted with decision {} !!! =========== time took: {} mili sec \n\n",
160                 guardResponse.getResult(), (double) estimatedTime / 1000 / 1000);
161         workingMemory.insert(guardResponse);
162
163     }
164
165 }