function ssw_service_modify_query, ssw_service_jobid , qq_struct, waves=waves, max_frames=max_frames, testing=testing, hcr=hcr, $
   debug=debug, quiet=quiet,ingest_hcr=ingest_hcr, method=method, aia_scale=aia_scale, ok=ok, im_patch=im_patch, $
   submit=submit,  qsubmit=qsubmit,  query_struct=query_struct, qinfo=qinfo, $
   _extra=_extra, add_waves=add_waves, replace_waves=replace_waves
;+
;
;   Input Parameters:
;      ssw_service_jobid - SSW service jobid of form: ssw_service_yyyymmdd_hhmm_<pid> ; ex SSW cutout service
;                          Alternately, supply HEK/HCR or HER record (which include ssw_service_jobid (hcr.GOAL, etc)
;
;   Output Parameters:
;      qq_struct - optional output - structure version of returned/modified query ; via url_decode.pro: qq_struct=url_decode(retval/query-string)
;      
;   Output:
;      Function returns modified SSW cutout service query = original query + adjusted tags WAVES, etc.
;   
;
;   Keyword Parameters:
;      waves - comma separated list of new WAVES to add - 29-jun-2023 mod removes default; let User/calling App supply 
;      MAX_FRAMES - usual per SSW cutout Service;- set this to low number for test/sanity check
;      submit - (switch) - if set, submit the modified query ->  <Q>/requested/ 
;      qsubmit  String, Q Name to use for /SUBMIT; Override Submit-> Q/<requested> Default = where job found <Q>/finished - IMPLIES/
;      _extra - keyword/value pairs supplied in this call -> ssw_make_query via inheritance
;      (other) - all other query param/value inherit verbatim values in the oro;iginal query 
;      add_waves - (switch) if set, will ADD user 'waves' list to the input <query>.WAVES - implies REDO of existing per-wave cutouts
;      replace_waves - (switch) This is DEFAULT -  will REPLACE inputo;  <query>.WAVES with user input WAVES - implies no REDOS of existing WAVES
;      
;   History: 
;      15-jan-2023 (circa) - Samuel L. Freeland - initially for IRIS & SUVI but any SSW cutout
;                               Query is fair game - tweak/add existing Query
;      14-feb-2023 - add .QUERY_SOURCE if not present - add Original query to track/link
;      29-jun-2023 - removed heritage default WAVES HMI centric - let User/Calling-App supply WAVES as desired
;      10-dec-2023 - modified call to ssw_service_jobid2query to leverage new QINFO output parameter
;                    Added /SUBMIT keyword&function (finally..) - Q management help via ssw_jobid2query QINFO output
;      26-apr-2024 - defined /ADD_WAVES & /REPLACE_WAVES keywords and function
;       3-sep-2024 - add optional positional Output parameter <qq_struct> - just the structure version of This function's modified Query-string
;                    (was typing IDL> qstr=URL_DECODE(<qstring_output>) after majority of test calls so just include that output)...
;      21-feb-2025 - allow <ssw_service_jobid> to be a query_string (tbd if I rename the heritage variable name <ssw_service_jobid> to
;                    something more inclusive or just live with the slightly mis-leading name...) 
;                    Allows direct application to client-side <ssw_make_query> output.
;                    output without expectation of a QUERY_FILE/QFILE
;
;      25-apr-2025 - Add QSUBMIT to redirect new/modified query -> different <QSUBMIT>/<requested>/ If Exists & Valid-Q,  implies /SUBMIT 
;-
;
add_waves=keyword_set(add_waves)    ; new/returned query.WAVES
debug=keyword_set(debug)
ssw_nomore=get_logenv('ssw_nomore')   ; safe initial state of $ssw_nomore for later
set_logenv,'ssw_nomore','1'   ; inhibit more-like behavior - just print everything without waiting for [space] bar 
OK=0 ; 
; 
ssw_jobid=''  ; 
delvarx,query_struct   ; this is a one-way flow - assure query_struct is not defined on input; created below.
query_input=0          ; defalt is ssw JOBID input - will toggle to 1/true  if query string was input
case 1 of
   n_params() lt 1: begin
      box_message,"Need SSW service jobid (ssw_service_<date>_<pid> -OR- HEK-HCR/HER record; not supplied bailing w/o  action"
      return,-1  ; <<<< EARLY EXIT  
   endcase
   strpos(ssw_service_jobid,'=') gt 0 and strpos(ssw_service_jobid,'&') gt 0: begin       ; Query string supplied
      box_message,'ssw_service_jobid Query String >> ' + ssw_service_jobid
      query_struct=url_decode(ssw_service_jobid)   ; Query String -> Query Stucture named <query_struct>
      query_input=1
      ssw_query_file=ssw_service_jobid   ; ** since no query file, assigning query string 
;                                        ; ** both are valid values for ssw_make_query call below..
      if debug then stop,'Case query string input, not ssw-jobid ssw_service_jobid,query_struct'
   endcase
   required_tags(ssw_service_jobid,'sdo_ssw_jobid'):    ssw_jobid=ssw_service_jobid.sdo_ssw_jobid ; likely HEK-HCR record
   required_tags(ssw_service_jobid,'order_time,jobid'): ssw_jobid=ssw_service_jobid.jobid         ; likely cutout service QQ
   data_chk(ssw_service_jobid,/string): ssw_jobid=ssw_service_jobid[0]
   else:
end


if ~data_chk(query_struct,/struct) then begin         ; Block for input is ssw jobid;  
                                                      ; Skipped if input is QUERY_string, Not ssw_jobid 
if strpos(ssw_jobid,'ssw_service') eq -1 then begin
   box_message,'I do not believe  that your input a valid ssw_service jobid>>> ' + ssw_jobid[0] + ' ..returning no action
   return,'  ; <<< EARLY EXIT on no ssw_service jobid found'
endif

ssw_query_file=ssw_service_jobid2query(ssw_jobid[0],qinfo, found=found,query_struct=query_struct,valid_queues=valid_queues)

if ~found then begin
   box_message, 'Could not find original ssw service Query in any of the known Qs.'
   return,-1  ; <<< EARLY EXIT if cannot find original SSW cutout service query
endif

; ================ depracated block - Beta-Blocker - functionality replaced with 'gen' mod 2'ssw_make_query.pro'
; compile beta version of ssw_make_query (mods to support 'add_wave', and aia->suvi etc.
; recompile,'$SSW_ONTOLOGY/idl_mods/ssw_make_query2.pro'  
; recompile,'$SSW/site/idl/http/ssw_service_config/iris_hmi/ssw_make_query2' ; comment out since updated ssw_make_query released

; if n_elements(waves) eq '' then waves='blos,cont'  ; 1st use case: Add HMI blos&cont ->  HMI  IRIS L2 AIA ; removed 29-jun-23
; If user supplied WAVES, a little xtra bookeeping

; 
endif   ; End of SSW jobid-input (was skipped for verbatim Query String input.


; define/add  .QUERY_SOURCE if not already present
if ~required_tags(query_struct,'query_source') then $
   query_struct=add_tag(query_struct,([ssw_jobid[0],'ssw_make_query'])(0),'query_source')
orig_waves=gt_tagval(query_struct,/waves,missing='') ;Existing input <query>.WAVES
swaves=''
case 1 of
  n_elements(waves) gt 1:   swaves=arr2str(trim(waves),'_')
  data_chk(waves,/string):  swaves=str_replace(waves,',','_')
  else: waves=orig_waves
endcase

if add_waves and orig_waves ne '' and swaves[0] ne '' then begin  ; User wants <inquery>.WAVES -PLUS- input WAVES=<waves>
   all_waves=all_vals([str2arr(orig_waves,/nomult),str2arr(waves,/nomult)]) ; Uniq Subset <query>.WAVEs + WAVES
   all_waves=arr2str(all_waves) ; comma delimited wave list as expected by downline Apps
   if get_logenv('check_waves') then stop,'waves,orig_waves,all_waves'
endif else all_waves=waves
box_message,'Modified <query>.WAVES >> '+ all_waves[0]

blend_waves=([gt_tagval(query_struct,/blend_waves,missing=''),''])(swaves ne '')

ssw_modified_query=ssw_make_query(in_query=ssw_query_file,waves=all_waves, max_frames=max_frames,_extra=_extra, $
   query_source=query_struct.query_source + ': '+ ssw_jobid + '_ssmq_' + swaves +' _' + time2file(reltime(/now)))

OK=1
retval=ssw_modified_query
hcr=keyword_set(hcr) or keyword_set(ingest_hcr)
if hcr then begin ; xtra HCR query logic - the Why is a TBD, think its a KEYWORD_SET(0) ...but this works...
   hcroff='HCR=0' & hcron='HCR=1'
   chkhcr=where_pattern(retval,hcroff,offcnt)
   if offcnt gt 0 then retval=str_replace(retval,hcroff,hcron)
   if debug then stop,'hcroff/on,off cnt'
endif

submit=keyword_set(submit) or data_chk(qsubmit,/string)

if keyword_set(submit) then begin 
   box_message,'You have requested /SUBMIT.. let me check a couple things..'
   qparent= qinfo.qparent                  ; default Q for submit = Q/<requested> where Q=where found   
   if data_chk(qsubmit,/string) then begin
      box_message,'QSubmit supplied, verifying.. valid queue'  ; Check User supplied QSubmit vs. Valid_Queues
      ssq=where(strpos(valid_queues,qsubmit[0]) ne -1,vqcnt)
      if vqcnt eq 1 then qparent=valid_queues[ssq]             ; User QSubmit OK, so using that 
   endif
   new_jobid=qinfo.ssw_jobid_input + '_ssmq_' +swaves
   request_dir=concat_dir(qparent,'requested') 
   box_message,'ready to submit ' + new_jobid + ' to >>' + request_dir
   if debug then stop,'new_jobid,retval,request_dir'
   file_append,concat_dir(request_dir,new_jobid),retval,/NEW    ; ,/new - replace, dont append if file already exists
endif
   
if n_params() gt 1 then qq_struct=url_decode(retval) ; user wants structure version of returned query string
   
if debug then begin
   help,url_decode(retval),/str
   stop,'before return, retval'
endif
set_logenv,'ssw_nomore',ssw_nomore    ; restore starting environmental


return,retval ; return modified query
end
