From 4dddc8c1e52f61d42d4fa61d508fe29c77bffac8 Mon Sep 17 00:00:00 2001 From: Robert Butora <robert.butora@inaf.it> Date: Thu, 25 Apr 2024 16:28:14 +0200 Subject: [PATCH] implements PIXELS param (cfitsio extSyntax [1:10,1:50,1:1000:10]) has precedense over POS,BAND,POL,TIME --- .../servlet/src/main/java/cutout/Cutout.java | 8 +- .../src/main/java/cutout/CutoutImpl.java | 166 ++++++++++-------- .../src/main/java/webapi/ServletCutout.java | 25 +-- 3 files changed, 109 insertions(+), 90 deletions(-) diff --git a/data-access/servlet/src/main/java/cutout/Cutout.java b/data-access/servlet/src/main/java/cutout/Cutout.java index 33d5080..37a210d 100644 --- a/data-access/servlet/src/main/java/cutout/Cutout.java +++ b/data-access/servlet/src/main/java/cutout/Cutout.java @@ -14,11 +14,13 @@ import vo.parameter.*; public interface Cutout { - public void doStream(String relPathname, int hdunum, Pos pos, Band band, Time time, Pol pol, - OutputStream outputStream) throws IOException, InterruptedException; + public void doStream(String relPathname, int hdunum, + Pos pos, Band band, Time time, Pol pol, String pixels, + OutputStream outputStream) throws IOException, InterruptedException; - public CutResult doFile(String relPathname, int hdunum, Pos pos, Band band, Time time, Pol pol, + public CutResult doFile(String relPathname, int hdunum, + Pos pos, Band band, Time time, Pol pol, String pixels, boolean countNullValues, FitsCard[] extraCards) throws IOException, InterruptedException; diff --git a/data-access/servlet/src/main/java/cutout/CutoutImpl.java b/data-access/servlet/src/main/java/cutout/CutoutImpl.java index d5ff731..9fc4275 100644 --- a/data-access/servlet/src/main/java/cutout/CutoutImpl.java +++ b/data-access/servlet/src/main/java/cutout/CutoutImpl.java @@ -94,11 +94,20 @@ class CutoutImpl implements Cutout return region; } - public void doStream(String relPathname, int hdunum, Pos pos, Band band, Time time, Pol pol, + public void doStream(String relPathname, int hdunum, + Pos pos, Band band, Time time, Pol pol, String pixels, OutputStream outputStream) throws IOException, InterruptedException - { - Instant start = Instant.now(); + { + Instant start = Instant.now(); + + boolean has_overlap = false; + boolean pixels_valid = (pixels != null); + + String boundsString = ""; + String absPathname = settings.fitsPaths.surveys() + "/" + relPathname; + if( !pixels_valid ) + { ByteArrayOutputStream bos = new ByteArrayOutputStream(); if(bos == null) throw new AssertionError("byte output stream for bounds was not created, is null"); @@ -112,8 +121,6 @@ class CutoutImpl implements Cutout String coordString = jReq.toString(); LOGGER.info("coordString: " + coordString); - String absPathname = settings.fitsPaths.surveys() + "/" + relPathname; - /* calc bounds */ String[] cmdBounds = new String[4]; @@ -126,59 +133,63 @@ class CutoutImpl implements Cutout execBounds.doRun(bos, cmdBounds); LOGGER.info("execBounds exitValue: " + execBounds.exitValue); - bos.close(); - boolean has_result = (execBounds.exitValue == 0); - Instant boundsDone = Instant.now(); - LOGGER.info("EXECTIME boundsDone: " + Duration.between(start, boundsDone)); - if(has_result) { - String boundsString = new String(bos.toByteArray()); + boundsString = new String(bos.toByteArray()); + // remove end-of-line (was added by vlkb_ast.cpp: cout << ... << endl) String lineSeparator = System.lineSeparator(); boundsString = boundsString.replace(lineSeparator, ""); LOGGER.info("BOUNDS: " + boundsString); - if((boundsString != null) && boundsString.trim().isEmpty()) + has_overlap = !((boundsString != null) && boundsString.trim().isEmpty()); + + if( !has_overlap ) { throw new IllegalArgumentException( "region in file does not overlap with region defined by SODA parameters"); } - else - { - /* cutout -> outputStream */ + } + bos.close(); - String[] cmdCut = new String[6]; - cmdCut[0] = "/usr/local/bin/vlkb"; - cmdCut[1] = "imcopy"; - cmdCut[2] = absPathname; - cmdCut[3] = String.valueOf(hdunum-1); - cmdCut[4] = boundsString; - cmdCut[5] = settings.fitsPaths.cutouts(); + Instant boundsDone = Instant.now(); + LOGGER.info("EXECTIME boundsDone: " + Duration.between(start, boundsDone)); + } - if(outputStream == null) - LOGGER.info("supplied outputStream for cut-file is null"); + if(has_overlap || pixels_valid) + { + /* cutout -> outputStream */ - ExecCmd execCut = new ExecCmd(); - execCut.doRun(outputStream, cmdCut); + String[] cmdCut = new String[6]; + cmdCut[0] = "/usr/local/bin/vlkb"; + cmdCut[1] = "imcopy"; + cmdCut[2] = absPathname; + cmdCut[3] = String.valueOf(hdunum-1); + cmdCut[4] = pixels_valid ? pixels : boundsString; + cmdCut[5] = settings.fitsPaths.cutouts(); - Instant cutDone = Instant.now(); - LOGGER.info("EXECTIME cutDone: " + Duration.between(start, cutDone)); - } - } - else - { - throw new IllegalArgumentException( - "overlap computation could not be completed with the given arguments"); - } + if(outputStream == null) + LOGGER.info("supplied outputStream for cut-file is null"); + + ExecCmd execCut = new ExecCmd(); + execCut.doRun(outputStream, cmdCut); + + Instant cutDone = Instant.now(); + LOGGER.info("EXECTIME cutDone: " + Duration.between(start, cutDone)); + } + else + { + throw new IllegalArgumentException( + "overlap computation could not be completed with the given arguments"); } + } private NullValueCount doCountNullValues(String absPathname, int hdunum) - throws IOException, InterruptedException + throws IOException, InterruptedException { ByteArrayOutputStream bos = new ByteArrayOutputStream(); if(bos == null) @@ -226,61 +237,64 @@ class CutoutImpl implements Cutout public CutResult doFile(String relPathname, int hdunum, - Pos pos, Band band, Time time, Pol pol, + Pos pos, Band band, Time time, Pol pol, String pixels, boolean countNullValues, FitsCard[] extraCards) - throws IOException, InterruptedException - { - LOGGER.info("trace: " + pos.toString() ); + throws IOException, InterruptedException + { + LOGGER.info("trace: " + pos.toString() ); - CutResult cutResult = new CutResult(); + CutResult cutResult = new CutResult(); - if(settings.amqpConn.isHostnameEmpty()) - { - LOGGER.info("Using doStream() to local file"); + if(settings.amqpConn.isHostnameEmpty()) + { + LOGGER.info("Using doStream() to local file"); - String absSubimgPathname = settings.fitsPaths.cutouts() - + "/" + generateSubimgPathname(relPathname, hdunum); + String absSubimgPathname = settings.fitsPaths.cutouts() + + "/" + generateSubimgPathname(relPathname, hdunum); - LOGGER.info("Uses local filename : " + absSubimgPathname); + LOGGER.info("Uses local filename : " + absSubimgPathname); - OutputStream fileOutputStream = new FileOutputStream( new File(absSubimgPathname) ); + OutputStream fileOutputStream = new FileOutputStream( new File(absSubimgPathname) ); - doStream(relPathname, hdunum, pos, band, time, pol, fileOutputStream); + doStream(relPathname, hdunum, pos, band, time, pol, pixels, fileOutputStream); - // engine returns absPathname see common/cutout.cpp::do_cutout_file() - cutResult.filename = absSubimgPathname; - cutResult.filesize = Files.size(Paths.get(absSubimgPathname)); + // engine returns absPathname see common/cutout.cpp::do_cutout_file() + cutResult.filename = absSubimgPathname; + cutResult.filesize = Files.size(Paths.get(absSubimgPathname)); - if(countNullValues) - { - cutResult.nullValueCount = doCountNullValues(absSubimgPathname, 1); - } + if(countNullValues) + { + cutResult.nullValueCount = doCountNullValues(absSubimgPathname, 1); + } - if(extraCards == null || (extraCards.length < 1)) - { - LOGGER.info("Adding extraCards to cut-file not implemented when using 'vlkb' exec (implemented in engine vlkbd/AMQP)"); + if(extraCards == null || (extraCards.length < 1)) + { + LOGGER.info("Adding extraCards to cut-file not implemented when using 'vlkb' exec (implemented in engine vlkbd/AMQP)"); + } } - } - else - { - LOGGER.info("Using AMQP"); + else + { + LOGGER.info("Using AMQP"); - JsonEncoder jReq = new JsonEncoder(); - jReq.add(relPathname, hdunum); - jReq.add(pos); - jReq.add(band); - jReq.add(time); - jReq.add(pol); - jReq.add(countNullValues); - jReq.add(extraCards); + JsonEncoder jReq = new JsonEncoder(); + jReq.add(relPathname, hdunum); + jReq.add(pos); + jReq.add(band); + jReq.add(time); + jReq.add(pol); - String outJson = doRpc( jReq.toString() ); + // jReq.add(pixels), FIXME implement to supoort PIXLES in vlkb-legacy by AMQP - cutResult = JsonDecoder.responseFromCutoutJson( outJson ); - } + jReq.add(countNullValues); + jReq.add(extraCards); - return cutResult; - } + String outJson = doRpc( jReq.toString() ); + + cutResult = JsonDecoder.responseFromCutoutJson( outJson ); + } + + return cutResult; + } diff --git a/data-access/servlet/src/main/java/webapi/ServletCutout.java b/data-access/servlet/src/main/java/webapi/ServletCutout.java index be98798..344716d 100644 --- a/data-access/servlet/src/main/java/webapi/ServletCutout.java +++ b/data-access/servlet/src/main/java/webapi/ServletCutout.java @@ -88,6 +88,7 @@ public class ServletCutout extends javax.servlet.http.HttpServlet + "<PARAM name=\"BAND\" ucd=\"stat.interval\" unit=\"m\" datatype=\"double\" arraysize=\"2\" xtype=\"interval\" value=\"\"/>" + "<PARAM name=\"TIME\" ucd=\"time.interval;obs.exposure\" unit=\"d\" datatype=\"double\" arraysize=\"2\" xtype=\"interval\" value=\"\"/>" + "<PARAM name=\"POL\" ucd=\"meta.code;phys.polarization\" datatype=\"char\" arraysize=\"*\" value=\"\"/>" + + "<PARAM name=\"PIXELS\" ucd=\"instr.pixel;meta.dataset\" datatype=\"char\" arraysize=\"*\" value=\"\"/>" + "<PARAM name=\"RESPONSEFORMAT\" ucd=\"meta.code.mime\" datatype=\"char\" arraysize=\"*\" value=\"application/fits\"/>" + "<PARAM name=\"POSSYS\" ucd=\"pos.frame\" datatype=\"char\" arraysize=\"*\" value=\"\">" @@ -114,7 +115,7 @@ public class ServletCutout extends javax.servlet.http.HttpServlet } - protected void doCutoutStream(String id, Pos pos, Band band, Time time, Pol pol, + protected void doCutoutStream(String id, Pos pos, Band band, Time time, Pol pol, String pixels, OutputStream respOutputStream) throws IOException, InterruptedException { LOGGER.info("trace" + pos); @@ -122,12 +123,12 @@ public class ServletCutout extends javax.servlet.http.HttpServlet Resolver rsl = new ResolverFromId(); rsl.resolve(id); - cutout.doStream(rsl.relPathname(), rsl.hdunum(), pos, band, time, pol, respOutputStream); + cutout.doStream(rsl.relPathname(), rsl.hdunum(), pos, band, time, pol, pixels, respOutputStream); } - protected DataLink doCutoutFile(String id, Pos pos, Band band, Time time, Pol pol, + protected DataLink doCutoutFile(String id, Pos pos, Band band, Time time, Pol pol, String pixels, boolean countNullValues, String respFormat) throws IOException, InterruptedException { @@ -166,11 +167,11 @@ public class ServletCutout extends javax.servlet.http.HttpServlet final String DEFAULT_TIME_SYSTEM = "MJD_UTC"; // FIXME take from confif file - if(pos != null) pos.setSystem(DEFAULT_SKY_SYSTEM); - if(band != null) band.setSystem(DEFAULT_SPEC_SYSTEM); - if(time != null) time.setSystem(DEFAULT_TIME_SYSTEM); + //if(pos != null) pos.setSystem(DEFAULT_SKY_SYSTEM); + //if(band != null) band.setSystem(DEFAULT_SPEC_SYSTEM); + //if(time != null) time.setSystem(DEFAULT_TIME_SYSTEM); - CutResult cutResult = cutout.doFile(relPathname, hdunum, pos, band, time, pol, false, null); + CutResult cutResult = cutout.doFile(relPathname, hdunum, pos, band, time, pol, pixels, false, null); DataLink dlk = new DataLink(); @@ -292,22 +293,24 @@ public class ServletCutout extends javax.servlet.http.HttpServlet Band band = Band.parseBand(params, DEFAULT_SPEC_SYSTEM); Time time = Time.parseTime(params, DEFAULT_TIME_SYSTEM); Pol pol = Pol.parsePol(params); + String pixels = SingleStringParam.parseSingleStringParam(params, "PIXELS"); String respFormat = sodaReq_getResponseFormat(request, DEFAULT_RESPONSEFORMAT); LOGGER.info("responseFormat: " + respFormat); - if(respFormat.equals("application/fits")) + if(respFormat.startsWith("application/fits")) { response.setContentType(respFormat); - doCutoutStream(id, pos, band, time, pol, respOutputStream); + doCutoutStream(id, pos, band, time, pol, pixels, respOutputStream); } - else if(respFormat.equals("application/x-vlkb+xml")) + else if(respFormat.startsWith("application/x-vlkb+xml")) { boolean countNullValues = vlkbReq_getNullValues(request); response.setContentType(respFormat); - DataLink respDataLink = doCutoutFile(id, pos, band, time, pol, countNullValues, respFormat); + DataLink respDataLink = doCutoutFile(id, pos, band, time, pol, pixels, countNullValues, + respFormat); /* FIXME errors from engine not checked - cut-file might not have been created */ LOGGER.info("DataLink - id:" + respDataLink.id + " url: " + respDataLink.accessUrl ); -- GitLab