Skip to content

Commit 7ca78d2

Browse files
author
Khaled Basbous
committed
feat(Nuvlabox): Bulk update support (#935)
fix(Job): Set created-by attribute as user at the origin of the creation of the job fix(Job): Allow user to cancel created bulk jobs fix(Job): Move job utils and create new utils namespace and refactor to reuse code fix(Common utils): Enhance cannot do action because of state error message
1 parent c52e86f commit 7ca78d2

16 files changed

Lines changed: 301 additions & 299 deletions

File tree

code/src/com/sixsq/nuvla/server/resources/common/std_crud.clj

Lines changed: 12 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
(ns com.sixsq.nuvla.server.resources.common.std-crud
22
"Standard CRUD functions for resources."
33
(:require
4-
[clojure.data.json :as json]
54
[clojure.stacktrace :as st]
65
[clojure.string :as str]
76
[clojure.tools.logging :as log]
@@ -13,6 +12,7 @@
1312
[com.sixsq.nuvla.server.resources.common.crud :as crud]
1413
[com.sixsq.nuvla.server.resources.common.state-machine :as sm]
1514
[com.sixsq.nuvla.server.resources.common.utils :as u]
15+
[com.sixsq.nuvla.server.resources.job.utils :as job-utils]
1616
[com.sixsq.nuvla.server.resources.spec.acl-collection :as acl-collection]
1717
[com.sixsq.nuvla.server.util.response :as r]))
1818

@@ -177,41 +177,22 @@
177177
result (db/bulk-delete resource-name options)]
178178
(r/json-response result))))
179179

180-
(defn create-bulk-job
181-
[action-name target-resource authn-info acl payload]
182-
(let [json-payload (-> payload
183-
(assoc :authn-info authn-info)
184-
(json/write-str))
185-
create-request {:params {:resource-name "job"}
186-
:body {:action action-name
187-
:target-resource {:href target-resource}
188-
:payload json-payload
189-
:acl acl}
190-
:nuvla/authn auth/internal-identity}
191-
{{job-id :resource-id
192-
job-status :status} :body} (crud/add create-request)]
193-
(when (not= job-status 201)
194-
(throw (r/ex-response
195-
(str "unable to create async job for " action-name)
196-
500 target-resource)))
197-
(r/map-response (str "starting " action-name " with async " job-id)
198-
202 target-resource job-id)))
199-
200180
(defn bulk-action-fn
201181
[resource-name collection-acl _collection-uri]
202182
(validate-collection-acl collection-acl)
203183
(fn [{:keys [params body] :as request}]
204184
(throw-bulk-header-missing request)
205185
(throw-bulk-require-cimi-filter request)
206186
(a/throw-cannot-bulk-action collection-acl request)
207-
(let [authn-info (auth/current-authentication request)
208-
acl {:owners ["group/nuvla-admin"]
209-
:view-acl [(auth/current-active-claim request)]}
210-
action-name (-> params
211-
:action
212-
(str/replace #"-" "_")
213-
(str "_" resource-name))]
214-
(create-bulk-job action-name resource-name authn-info acl body))))
187+
(let [active-claim (auth/current-active-claim request)
188+
acl {:owners ["group/nuvla-admin"]
189+
:view-acl [active-claim]
190+
:manage [active-claim]}
191+
action-name (-> params
192+
:action
193+
(str/replace #"-" "_")
194+
(str "_" resource-name))]
195+
(job-utils/create-bulk-job action-name resource-name request acl body))))
215196

216197
(defn add-metric-fn
217198
[resource-name collection-acl _resource-uri & {:keys [validate-fn options]}]
@@ -228,8 +209,8 @@
228209
(throw-bulk-header-missing request)
229210
(a/throw-cannot-add collection-acl request)
230211
(a/throw-cannot-bulk-action collection-acl request)
231-
(let [options (select-keys request [:nuvla/authn :body])
232-
response (db/bulk-insert-metrics resource-name body options)]
212+
(let [options (select-keys request [:nuvla/authn :body])
213+
response (db/bulk-insert-metrics resource-name body options)]
233214
(r/json-response response))))
234215

235216
(defn generic-bulk-operation-fn

code/src/com/sixsq/nuvla/server/resources/common/utils.clj

Lines changed: 5 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -371,22 +371,19 @@
371371
[state resource]
372372
(= (:state resource) state))
373373

374-
(def is-not-in-state? (complement is-state?))
375-
376-
377-
(defn throw-can-not-do
374+
(defn throw-cannot-do
378375
[{:keys [id] :as resource} pred error-msg]
379376
(if (pred resource)
380377
resource
381378
(throw (r/ex-response error-msg 409 id))))
382379

383-
(defn throw-can-not-do-action
380+
(defn throw-cannot-do-action
384381
[{:keys [id] :as resource} pred action]
385-
(throw-can-not-do resource pred (format "operation '%s' not allowed on %s" action id)))
382+
(throw-cannot-do resource pred (format "operation '%s' not allowed on %s" action id)))
386383

387-
(defn throw-can-not-do-action-invalid-state
384+
(defn throw-cannot-do-action-invalid-state
388385
[{:keys [id state] :as resource} pred action]
389-
(throw-can-not-do resource pred (format "invalid state (%s) for %s on %s" state action id)))
386+
(throw-cannot-do resource pred (format "Action %s cannot be called on %s in state %s!" action id state)))
390387

391388
(defn filter-eq-vals
392389
[attribute vals]

code/src/com/sixsq/nuvla/server/resources/credential.clj

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ passwords) or other services (e.g. TLS credentials for Docker). Creating new
1010
[com.sixsq.nuvla.server.resources.common.crud :as crud]
1111
[com.sixsq.nuvla.server.resources.common.std-crud :as std-crud]
1212
[com.sixsq.nuvla.server.resources.common.utils :as u]
13-
[com.sixsq.nuvla.server.resources.job :as job]
13+
[com.sixsq.nuvla.server.resources.job.utils :as job-utils]
1414
[com.sixsq.nuvla.server.resources.resource-metadata :as md]
1515
[com.sixsq.nuvla.server.resources.spec.credential :as credential]
1616
[com.sixsq.nuvla.server.util.log :as logu]
@@ -138,10 +138,11 @@ passwords) or other services (e.g. TLS credentials for Docker). Creating new
138138
(if-let [active-claim (auth/current-active-claim request)]
139139
(let [job-type "credential_check"
140140
{{job-id :resource-id
141-
job-status :status} :body} (job/create-job id job-type
142-
{:owners ["group/nuvla-admin"]
143-
:view-acl [active-claim]}
144-
:priority 50)
141+
job-status :status} :body} (job-utils/create-job id job-type
142+
{:owners ["group/nuvla-admin"]
143+
:view-acl [active-claim]}
144+
(auth/current-user-id request)
145+
:priority 50)
145146
job-msg (str "starting " id " with async " job-id)]
146147
(when (not= job-status 201)
147148
(throw (r/ex-response (format "unable to create async job to %s" job-type) 500 id)))

code/src/com/sixsq/nuvla/server/resources/deployment.clj

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -213,7 +213,7 @@ a container orchestration engine.
213213
deployment (-> (crud/retrieve-by-id-as-admin deployment-id)
214214
(a/throw-cannot-delete request)
215215
(cond-> (not force-delete)
216-
(u/throw-can-not-do-action-invalid-state
216+
(u/throw-cannot-do-action-invalid-state
217217
utils/can-delete? "delete")))]
218218
(ectx/add-to-context :acl (:acl deployment))
219219
(ectx/add-to-context :resource deployment)
@@ -286,7 +286,7 @@ a container orchestration engine.
286286
(try
287287
(let [id (str resource-type "/" uuid)
288288
deployment (-> (crud/retrieve-by-id-as-admin id)
289-
(u/throw-can-not-do-action-invalid-state utils/can-start? "start")
289+
(u/throw-cannot-do-action-invalid-state utils/can-start? "start")
290290
(utils/throw-when-payment-required request)
291291
(utils/throw-can-not-access-registries-creds request)
292292
(utils/throw-can-not-access-helm-repo-cred request)
@@ -316,7 +316,7 @@ a container orchestration engine.
316316
(try
317317
(let [deployment (-> (str resource-type "/" uuid)
318318
(crud/retrieve-by-id-as-admin)
319-
(u/throw-can-not-do-action-invalid-state utils/can-stop? "stop"))
319+
(u/throw-cannot-do-action-invalid-state utils/can-stop? "stop"))
320320
execution-mode (:execution-mode deployment)]
321321
(-> deployment
322322
(assoc :state "STOPPING")
@@ -334,7 +334,7 @@ a container orchestration engine.
334334
(-> (str resource-type "/" uuid)
335335
(crud/retrieve-by-id-as-admin)
336336
(a/throw-cannot-manage request)
337-
(u/throw-can-not-do-action-invalid-state utils/can-create-log? "create-log")
337+
(u/throw-cannot-do-action-invalid-state utils/can-create-log? "create-log")
338338
(utils/throw-when-payment-required request)
339339
(utils/create-log request))
340340
(catch Exception e
@@ -372,7 +372,7 @@ a container orchestration engine.
372372
(let [current (-> (str resource-type "/" uuid)
373373
(crud/retrieve-by-id-as-admin)
374374
(a/throw-cannot-manage request)
375-
(u/throw-can-not-do-action-invalid-state
375+
(u/throw-cannot-do-action-invalid-state
376376
utils/can-update? "update_deployment")
377377
(utils/throw-when-payment-required request)
378378
(utils/throw-can-not-access-registries-creds request)
@@ -394,7 +394,7 @@ a container orchestration engine.
394394
(try
395395
(-> (str resource-type "/" uuid)
396396
(crud/retrieve-by-id-as-admin)
397-
(u/throw-can-not-do-action utils/can-detach? "detach")
397+
(u/throw-cannot-do-action utils/can-detach? "detach")
398398
(dissoc :deployment-set :deployment-set-name)
399399
u/update-timestamps
400400
db/edit)

code/src/com/sixsq/nuvla/server/resources/deployment/utils.clj

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,8 @@
1414
[com.sixsq.nuvla.server.resources.configuration-nuvla :as config-nuvla]
1515
[com.sixsq.nuvla.server.resources.credential :as credential]
1616
[com.sixsq.nuvla.server.resources.credential-template-api-key :as cred-api-key]
17-
[com.sixsq.nuvla.server.resources.job :as job]
1817
[com.sixsq.nuvla.server.resources.job.interface :as job-interface]
18+
[com.sixsq.nuvla.server.resources.job.utils :as job-utils]
1919
[com.sixsq.nuvla.server.resources.module.utils :as module-utils]
2020
[com.sixsq.nuvla.server.resources.nuvlabox.utils :as nuvlabox-utils]
2121
[com.sixsq.nuvla.server.resources.resource-log :as resource-log]
@@ -113,13 +113,14 @@
113113
low-priority (get-in request [:body :low-priority] false)
114114
parent-job (get-in request [:body :parent-job])
115115
{{job-id :resource-id
116-
job-status :status} :body} (job/create-job
116+
job-status :status} :body} (job-utils/create-job
117117
id action
118118
(-> {:owners ["group/nuvla-admin"]}
119119
(a/acl-append :edit-data nuvlabox)
120120
(a/acl-append :manage nuvlabox)
121121
(a/acl-append :view-data active-claim)
122122
(a/acl-append :manage active-claim))
123+
(auth/current-user-id request)
123124
:parent-job parent-job
124125
:priority (if low-priority 999 50)
125126
:execution-mode execution-mode
@@ -225,11 +226,11 @@
225226
(map crud/retrieve-by-id-as-admin)))
226227
registries-infra (when full
227228
(map (comp crud/retrieve-by-id-as-admin :parent) registries-creds))
228-
module-content (some-> deployment :module :content)
229+
module-content (some-> deployment :module :content)
229230
helm-repo-cred (some-> module-content :helm-repo-cred
230231
crud/retrieve-by-id-as-admin)
231-
helm-repo-url (some-> module-content :helm-repo-url
232-
crud/retrieve-by-id-as-admin)]
232+
helm-repo-url (some-> module-content :helm-repo-url
233+
crud/retrieve-by-id-as-admin)]
233234
(job-interface/get-context->response
234235
deployment
235236
credential

code/src/com/sixsq/nuvla/server/resources/deployment_set.clj

Lines changed: 12 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -6,15 +6,13 @@ These resources represent a deployment set that regroups deployments.
66
[clojure.tools.logging :as log]
77
[com.sixsq.nuvla.auth.acl-resource :as a]
88
[com.sixsq.nuvla.auth.utils :as auth]
9-
[com.sixsq.nuvla.db.filter.parser :as parser]
109
[com.sixsq.nuvla.db.impl :as db]
1110
[com.sixsq.nuvla.server.resources.common.crud :as crud]
1211
[com.sixsq.nuvla.server.resources.common.state-machine :as sm]
1312
[com.sixsq.nuvla.server.resources.common.std-crud :as std-crud]
1413
[com.sixsq.nuvla.server.resources.common.utils :as u]
1514
[com.sixsq.nuvla.server.resources.deployment-set.operational-status :as os]
1615
[com.sixsq.nuvla.server.resources.deployment-set.utils :as utils]
17-
[com.sixsq.nuvla.server.resources.job :as job]
1816
[com.sixsq.nuvla.server.resources.job.interface :as job-interface]
1917
[com.sixsq.nuvla.server.resources.job.utils :as job-utils]
2018
[com.sixsq.nuvla.server.resources.module :as module]
@@ -192,19 +190,19 @@ These resources represent a deployment set that regroups deployments.
192190

193191
(defn action-bulk
194192
[{:keys [id] :as _resource} {{:keys [action]} :params :as request}]
195-
(let [authn-info (auth/current-authentication request)
196-
acl {:owners ["group/nuvla-admin"]
197-
:view-acl [(auth/current-active-claim request)]}]
198-
(std-crud/create-bulk-job
199-
(utils/bulk-action-job-name action) id authn-info acl {})))
193+
(let [acl {:owners ["group/nuvla-admin"]
194+
:view-acl [(auth/current-active-claim request)]}]
195+
(job-utils/create-bulk-job
196+
(utils/bulk-action-job-name action) id request acl {})))
200197

201198
(defn action-simple
202199
[{:keys [id] :as _resource} {{:keys [action]} :params :as request}]
203200
(let [job-action (utils/action-job-name action)
204201
{{job-id :resource-id
205-
job-status :status} :body} (job/create-job id (utils/action-job-name action)
206-
{:owners ["group/nuvla-admin"]
207-
:view-acl [(auth/current-active-claim request)]})
202+
job-status :status} :body} (job-utils/create-job id (utils/action-job-name action)
203+
{:owners ["group/nuvla-admin"]
204+
:view-acl [(auth/current-active-claim request)]}
205+
(auth/current-user-id request))
208206
job-msg (str action " on " id " with async " job-id)]
209207
(if (not= job-status 201)
210208
(throw (r/ex-response (format "unable to create async job to %s" job-action) 500 id))
@@ -352,18 +350,10 @@ These resources represent a deployment set that regroups deployments.
352350

353351
(defn cancel-latest-job
354352
[{:keys [id] :as _resource} _request]
355-
(let [filter-str (format "target-resource/href='%s' and (state='%s' or state='%s')" id
356-
job-utils/state-queued job-utils/state-running)
357-
[_ [{job-id :id}]]
358-
(crud/query-as-admin
359-
job/resource-type
360-
{:cimi-params {:filter (parser/parse-cimi-filter filter-str)
361-
:orderby [["created" :desc]]
362-
:last 1}})]
363-
(if job-id
364-
(do (crud/do-action-as-admin job-id job-utils/action-cancel)
365-
(r/map-response "operation cancelled" 200))
366-
(r/map-response "no running operation found that can be cancelled" 404))))
353+
(if-let [job-id (job-utils/existing-job-id-not-in-final-state id)]
354+
(do (crud/do-action-as-admin job-id job-utils/action-cancel)
355+
(r/map-response "operation cancelled" 200))
356+
(r/map-response "no running operation found that can be cancelled" 404)))
367357

368358
(defmethod crud/do-action [resource-type utils/action-cancel]
369359
[request]

code/src/com/sixsq/nuvla/server/resources/job.clj

Lines changed: 14 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ request.
2525
[com.sixsq.nuvla.server.util.metadata :as gen-md]))
2626

2727

28-
(def ^:const resource-type (u/ns->type *ns*))
28+
(def ^:const resource-type utils/resource-type)
2929

3030

3131
(def ^:const collection-type (u/ns->collection-type *ns*))
@@ -77,9 +77,10 @@ request.
7777
;; CRUD operations
7878
;;
7979

80-
(defn add-impl [{{:keys [priority execution-mode version]
81-
:or {priority 999 execution-mode "push"
82-
version latest-version} :as body} :body :as request}]
80+
(defn add-impl [{{:keys [priority execution-mode version created-by]
81+
:or {priority 999
82+
execution-mode "push"
83+
version latest-version} :as body} :body :as request}]
8384
(a/throw-cannot-add collection-acl request)
8485
(let [id (u/new-resource-id resource-type)
8586
zk-path (when (#{"push" "mixed"} execution-mode)
@@ -94,7 +95,7 @@ request.
9495
(assoc :execution-mode execution-mode)
9596
(assoc :version version)
9697
u/update-timestamps
97-
(u/set-created-by request)
98+
(cond-> (nil? created-by) (u/set-created-by request))
9899
utils/job-cond->addition
99100
(crud/add-acl request)
100101
(cond-> zk-path (assoc :tags [zk-path]))
@@ -173,13 +174,15 @@ request.
173174
(utils/can-timeout? resource request) (update :operations conj timeout-op)
174175
(utils/can-get-context? resource request) (update :operations conj get-context-op))))
175176

177+
(defn create-cancel-children-jobs-job
178+
[{:keys [acl] parent-job-id :id :as _parent-job} request]
179+
(utils/create-job parent-job-id "cancel_children_jobs" acl
180+
(auth/current-user-id request)
181+
:priority 10))
176182

177-
(declare create-cancel-children-jobs-job)
178-
179-
180-
(defn cancel-children-jobs-async [{action :action :as job}]
183+
(defn cancel-children-jobs-async [{action :action :as job} request]
181184
(when (str/starts-with? action "bulk")
182-
(create-cancel-children-jobs-job job)))
185+
(create-cancel-children-jobs-job job request)))
183186

184187

185188
(defmethod crud/do-action [resource-type utils/action-cancel]
@@ -195,7 +198,7 @@ request.
195198
(crud/validate)
196199
(db/edit {:refresh false}))
197200
job (:body response)]
198-
(cancel-children-jobs-async job)
201+
(cancel-children-jobs-async job (auth/current-active-claim request))
199202
(log/warn "Canceled job : " id)
200203
(interface/on-cancel job)
201204
response)
@@ -229,31 +232,3 @@ request.
229232
response)
230233
(catch Exception e
231234
(or (ex-data e) (throw e)))))
232-
233-
;;
234-
;; internal crud
235-
;;
236-
237-
(defn create-job
238-
[target-resource action acl & {:keys [priority affected-resources
239-
execution-mode payload
240-
parent-job]}]
241-
(let [job-map (cond-> {:action action
242-
:target-resource {:href target-resource}
243-
:acl acl}
244-
priority (assoc :priority priority)
245-
parent-job (assoc :parent-job parent-job)
246-
affected-resources (assoc :affected-resources affected-resources)
247-
execution-mode (assoc :execution-mode execution-mode)
248-
payload (assoc :payload payload))
249-
create-request {:params {:resource-name resource-type}
250-
:body job-map
251-
:nuvla/authn auth/internal-identity}]
252-
(crud/add create-request)))
253-
254-
255-
(defn create-cancel-children-jobs-job
256-
[{:keys [acl] parent-job-id :id :as _parent-job}]
257-
(create-job parent-job-id "cancel_children_jobs" acl
258-
:priority 10))
259-

0 commit comments

Comments
 (0)