xradio 0.0.26__py3-none-any.whl → 0.0.28__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -101,7 +101,7 @@ def _add_vel_attrs(xds: xr.Dataset, helpers: dict) -> xr.Dataset:
101
101
  vel_coord = xds.coords["velocity"]
102
102
  meta = {"units": "m/s"}
103
103
  if helpers["has_freq"]:
104
- meta["doppler_type"] = helpers["doppler"]
104
+ meta["doppler_type"] = helpers.get("doppler", "RADIO")
105
105
  else:
106
106
  meta["doppler_type"] = _doppler_types[0]
107
107
  meta["type"] = "doppler"
@@ -570,8 +570,8 @@ def _get_freq_values(helpers: dict) -> list:
570
570
  crval=helpers["crval"][freq_idx],
571
571
  crpix=helpers["crpix"][freq_idx],
572
572
  cdelt=helpers["cdelt"][freq_idx],
573
- cunit=helpers["cunit"][freq_idx],
574
573
  )
574
+ cunit = helpers["cunit"][freq_idx]
575
575
  helpers["frequency"] = vals * u.Unit(cunit)
576
576
  return vals
577
577
  elif "VOPT" in ctype:
@@ -606,9 +606,9 @@ def _get_velocity_values(helpers: dict) -> list:
606
606
  return helpers["velocity"].to(u.m / u.s).value
607
607
  elif "frequency" in helpers:
608
608
  v = _compute_velocity_values(
609
- restfreq=helpers["reestfreq"],
609
+ restfreq=helpers["restfreq"],
610
610
  freq_values=helpers["frequency"].to("Hz").value,
611
- doppler=helpers["doppler"],
611
+ doppler=helpers.get("doppler", "RADIO"),
612
612
  )
613
613
  helpers["velocity"] = v * (u.m / u.s)
614
614
  return v
@@ -796,7 +796,12 @@ def _get_transpose_list(helpers: dict) -> tuple:
796
796
  transpose_list[4] = i
797
797
  not_covered.remove("m")
798
798
  not_covered.remove("v")
799
- elif b.startswith("frequency") or b.startswith("vopt") or b.startswith("vrad"):
799
+ elif (
800
+ b.startswith("frequency")
801
+ or b.startswith("freq")
802
+ or b.startswith("vopt")
803
+ or b.startswith("vrad")
804
+ ):
800
805
  transpose_list[2] = i
801
806
  not_covered.remove("f")
802
807
  elif b.startswith("stok"):
@@ -110,53 +110,56 @@ def write_binary_blob_to_disk(arr, file_path, compressor):
110
110
  - None
111
111
  """
112
112
  import graphviper.utils.logger as logger
113
+
113
114
  # Encode the NumPy array using the codec
114
- logger.debug('1. Before compressor ' + file_path)
115
+ logger.debug("1. Before compressor " + file_path)
115
116
  compressed_arr = compressor.encode(np.ascontiguousarray(arr))
116
117
 
117
- logger.debug('2. Before makedir')
118
+ logger.debug("2. Before makedir")
118
119
  # Ensure the directory exists before saving the file
119
120
  os.makedirs(os.path.dirname(file_path), exist_ok=True)
120
121
 
121
122
  arr_len = len(compressed_arr)
122
- logger.debug('3. Before write the len is: ' + str(arr_len))
123
- #Save the compressed array to disk
123
+ logger.debug("3. Before write the len is: " + str(arr_len))
124
+ # Save the compressed array to disk
124
125
  # with open(file_path, "wb") as file:
125
126
  # file.write(compressed_arr)
126
-
127
- logger.debug('4. Using new writer: ' + str(arr_len))
127
+
128
+ logger.debug("4. Using new writer: " + str(arr_len))
128
129
  write_to_lustre_chunked(file_path, compressed_arr)
129
-
130
+
130
131
  # /.lustre/aoc/sciops/pford/CHILES/cube_image/uid___A002_Xee7674_X2844_Cube_3.img.zarr/SKY/0.0.110.0.0
131
132
  # 348192501 bytes
132
133
  # 332.0622453689575 M
133
-
134
+
134
135
  # from io import BufferedWriter
135
136
  # # Calculate buffer size based on compressed_arr size (adjust multiplier)
136
137
  # buffer_size = min(len(compressed_arr), 1024 * 1024 * 4) # Max 4 MB buffer
137
138
  # with BufferedWriter(open(file_path, "wb"), buffer_size) as f:
138
139
  # f.write(compressed_arr)
139
- # f.flush() # Ensure data gets written to disk
140
-
141
-
142
- logger.debug('4. Write completed')
140
+ # f.flush() # Ensure data gets written to disk
141
+
142
+ logger.debug("4. Write completed")
143
143
 
144
144
  # print(f"Compressed array saved to {file_path}")
145
145
 
146
146
 
147
- def write_to_lustre_chunked(file_path, compressed_arr, chunk_size=1024 * 1024 * 128): # 128 MiB chunks
148
- """
149
- Writes compressed data to a Lustre file path with chunking.
147
+ def write_to_lustre_chunked(
148
+ file_path, compressed_arr, chunk_size=1024 * 1024 * 128
149
+ ): # 128 MiB chunks
150
+ """
151
+ Writes compressed data to a Lustre file path with chunking.
152
+
153
+ Args:
154
+ file_path: Path to the file for writing.
155
+ compressed_arr: Compressed data array to write.
156
+ chunk_size: Size of each data chunk in bytes (default: 128 MiB).
157
+ """
158
+ with open(file_path, "wb") as f:
159
+ for i in range(0, len(compressed_arr), chunk_size):
160
+ chunk = compressed_arr[i : i + chunk_size]
161
+ f.write(chunk)
150
162
 
151
- Args:
152
- file_path: Path to the file for writing.
153
- compressed_arr: Compressed data array to write.
154
- chunk_size: Size of each data chunk in bytes (default: 128 MiB).
155
- """
156
- with open(file_path, "wb") as f:
157
- for i in range(0, len(compressed_arr), chunk_size):
158
- chunk = compressed_arr[i:i + chunk_size]
159
- f.write(chunk)
160
163
 
161
164
  def read_binary_blob_from_disk(file_path, compressor, dtype=np.float64):
162
165
  """
@@ -33,7 +33,10 @@ def _convert_beam_to_rad(beam: dict) -> dict:
33
33
  """
34
34
  mybeam = {}
35
35
  for k in beam:
36
- q = u.quantity.Quantity(f"{beam[k]['value']}{beam[k]['unit']}")
36
+ try:
37
+ q = u.quantity.Quantity(f"{beam[k]['value']}{beam[k]['unit']}")
38
+ except:
39
+ q = u.quantity.Quantity(f"{beam[k]['value']}{beam[k]['units']}")
37
40
  q = q.to("rad")
38
41
  j = "pa" if k == "positionangle" else k
39
42
  mybeam[j] = {"type": "quantity", "value": q.value, "units": "rad"}
@@ -43,10 +43,11 @@ class processing_set(dict):
43
43
  "start_frequency": [],
44
44
  "end_frequency": [],
45
45
  "shape": [],
46
- "field_coords": []
46
+ "field_coords": [],
47
47
  }
48
48
  from astropy.coordinates import SkyCoord
49
49
  import astropy.units as u
50
+
50
51
  for key, value in self.items():
51
52
  summary_data["name"].append(key)
52
53
  summary_data["ddi"].append(value.attrs["ddi"])
@@ -69,11 +70,23 @@ class processing_set(dict):
69
70
  summary_data["start_frequency"].append(value["frequency"].values[0])
70
71
  summary_data["end_frequency"].append(value["frequency"].values[-1])
71
72
 
72
- ra_dec_rad = value[data_name].attrs["field_info"]['phase_direction']['data']
73
- frame = value[data_name].attrs["field_info"]['phase_direction']['attrs']['frame'].lower()
74
- coord = SkyCoord(ra=ra_dec_rad[0]*u.rad, dec=ra_dec_rad[1]*u.rad, frame=frame)
73
+ ra_dec_rad = value[data_name].attrs["field_info"]["phase_direction"]["data"]
74
+ frame = (
75
+ value[data_name]
76
+ .attrs["field_info"]["phase_direction"]["attrs"]["frame"]
77
+ .lower()
78
+ )
79
+ coord = SkyCoord(
80
+ ra=ra_dec_rad[0] * u.rad, dec=ra_dec_rad[1] * u.rad, frame=frame
81
+ )
75
82
 
76
- summary_data["field_coords"].append([frame, coord.ra.to_string(unit=u.hour), coord.dec.to_string(unit=u.deg)])
83
+ summary_data["field_coords"].append(
84
+ [
85
+ frame,
86
+ coord.ra.to_string(unit=u.hour),
87
+ coord.dec.to_string(unit=u.deg),
88
+ ]
89
+ )
77
90
  summary_df = pd.DataFrame(summary_data)
78
91
  return summary_df
79
92
 
@@ -619,10 +619,61 @@ def read_col_conversion(
619
619
  Function to perform delayed reads from table columns when converting
620
620
  (no need for didxs)
621
621
  """
622
- data = tb_tool.getcol(col)
622
+
623
+ # Workaround for https://github.com/casacore/python-casacore/issues/130
624
+ # WARNING: Assumes tb_tool is a single measurement set not an MMS.
625
+ # WARNING: Assumes the num_frequencies * num_polarisations > 2**29. If false,
626
+ # https://github.com/casacore/python-casacore/issues/130 isn't mitigated.
627
+
628
+ # Use casacore to get the shape of a row for this column
629
+
630
+ #################################################################################
631
+
632
+ # Get the total number of rows in the base measurement set
633
+ nrows_total = tb_tool.nrows()
634
+
635
+ # getcolshapestring() only works on columns where a row element is an
636
+ # array (ie fails for TIME, etc)
637
+ # Assumes RuntimeError is because the column is a scalar
638
+ try:
639
+
640
+ shape_string = tb_tool.getcolshapestring(col)[0]
641
+ extra_dimensions = tuple(
642
+ [
643
+ int(idx)
644
+ for idx in shape_string.replace("[", "").replace("]", "").split(", ")
645
+ ]
646
+ )
647
+ full_shape = tuple(
648
+ [nrows_total]
649
+ + [
650
+ int(idx)
651
+ for idx in shape_string.replace("[", "").replace("]", "").split(", ")
652
+ ]
653
+ )
654
+ except RuntimeError:
655
+ extra_dimensions = ()
656
+ full_shape = (nrows_total,)
657
+
658
+ #################################################################################
659
+
660
+ # Get dtype of the column. Only read first row from disk
661
+ col_dtype = np.array(tb_tool.col(col)[0]).dtype
662
+
663
+ # Construct the numpy array to populate with data
664
+ data = np.empty(full_shape, dtype=col_dtype)
665
+
666
+ # Use built-in casacore table iterator to populate the data column by unique times.
667
+ start_row = 0
668
+ for ts in tb_tool.iter("TIME", sort=False):
669
+ num_rows = ts.nrows()
670
+ # Note don't use getcol() because it's less safe. See:
671
+ # https://github.com/casacore/python-casacore/issues/130#issuecomment-463202373
672
+ ts.getcolnp(col, data[start_row : start_row + num_rows])
673
+ start_row += num_rows
623
674
 
624
675
  # TODO
625
- # check np.full() with np.nan performance vs np.zeros or np.ones
626
- fulldata = np.full(cshape + data.shape[1:], np.nan, dtype=data.dtype)
676
+ # Can we return a view of `data` instead of copying?
677
+ fulldata = np.full(cshape + extra_dimensions, np.nan, dtype=col_dtype)
627
678
  fulldata[tidxs, bidxs] = data
628
679
  return fulldata
@@ -196,7 +196,9 @@ def read_main_table_chunks(
196
196
  # loop over time chunks
197
197
  for time_chunk in range(0, n_unique_times, n_time_chunks):
198
198
  time_start = unique_times[time_chunk] - tol
199
- time_end = unique_times[min(n_unique_times, time_chunk + n_time_chunks) - 1] + tol
199
+ time_end = (
200
+ unique_times[min(n_unique_times, time_chunk + n_time_chunks) - 1] + tol
201
+ )
200
202
 
201
203
  # chunk time length
202
204
  ctlen = min(n_unique_times, time_chunk + n_time_chunks) - time_chunk
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: xradio
3
- Version: 0.0.26
3
+ Version: 0.0.28
4
4
  Summary: Xarray Radio Astronomy Data IO
5
5
  Author-email: Jan-Willem Steeb <jsteeb@nrao.edu>
6
6
  License: BSD 3-Clause License
@@ -8,7 +8,7 @@ xradio/image/__init__.py,sha256=HAD0GfopIbhdxOYckyW6S9US_dSWmZrwIl3FHUzZwrE,435
8
8
  xradio/image/image.py,sha256=QoJ_BTLoMfeXJzU1yvtidBIhaMmjNA5_-6C3FWJRUeI,15635
9
9
  xradio/image/_util/__init__.py,sha256=M9lxD1Gc7kv0ucDEDbjLRuIEuESev-IG8j9EaCKUAkA,77
10
10
  xradio/image/_util/casacore.py,sha256=DmBTHUQ6870N5ARuFnYSfjZSLniJYgsjrsICUlCREYM,4234
11
- xradio/image/_util/common.py,sha256=hzVcnq4pYhxvkbMAIBzhWKdLN4nrqRGlmFwABxkww7A,8921
11
+ xradio/image/_util/common.py,sha256=vQs7Du9FSkb_D64Syt3IkiWkb_GmG9xhDPdgbpgP9Ok,9031
12
12
  xradio/image/_util/fits.py,sha256=gyGm06fuCKqVGK7uv-ObvQNfFawUDsIOa_nQyklM3Aw,329
13
13
  xradio/image/_util/image_factory.py,sha256=6tPzs20FTm2wEshHc1xqtTV7D0TbKxGLUKAVtvOc68I,10506
14
14
  xradio/image/_util/zarr.py,sha256=xTjg-KY-T4vuyua8pvuZZjCL-rI_wAsPjPUOYd5PZr4,1512
@@ -16,11 +16,11 @@ xradio/image/_util/_casacore/__init__.py,sha256=OlsiRE40o1jSbBI4khgQQzgfDYbAlOMK
16
16
  xradio/image/_util/_casacore/common.py,sha256=ky999eTCWta8w-uIs-7P7rPhZRLuh9yTuQXAxPvaPm4,1579
17
17
  xradio/image/_util/_casacore/xds_from_casacore.py,sha256=Rht4A32QLAQ7uizwKfOsZ3Z819shvlUbsZfAuTIVerU,42562
18
18
  xradio/image/_util/_casacore/xds_to_casacore.py,sha256=P6c-yoOjuVQkm07ApA7FFKfje4aPwV-MsRFKaRaPq9I,15338
19
- xradio/image/_util/_fits/xds_from_fits.py,sha256=rsV2OMK3g4U_GYKgj68cZXWIlXi0M0oU2M9FtAUeCk8,28339
19
+ xradio/image/_util/_fits/xds_from_fits.py,sha256=kpZ2gdbDQtoUD1DdQZymup5OVnB3e73D66LruLYESsw,28445
20
20
  xradio/image/_util/_zarr/common.py,sha256=apMX_bF4Hr3pFGjnDFpp36KgmhTYAPBZquNkjBHrsXk,307
21
21
  xradio/image/_util/_zarr/xds_from_zarr.py,sha256=hz6lHlpybfr_r8pn_uObDHOFmN5h75F11bkBv8KCuP0,3192
22
22
  xradio/image/_util/_zarr/xds_to_zarr.py,sha256=wogXbwX8n3Sl9PHoc3_Y_LBowQsQ-94HZQFZ5NcxUZA,1624
23
- xradio/image/_util/_zarr/zarr_low_level.py,sha256=5D8Vu8QZD8CpKSPMkxHhnKpdk3vhUStW3kQFHUQUQns,10984
23
+ xradio/image/_util/_zarr/zarr_low_level.py,sha256=JJ_NgYTAbfiOXkpqIv9nA3bvthaqTZtumVYsLse_qGU,11001
24
24
  xradio/schema/__init__.py,sha256=UpejQegOaCLrsbcR4MLudR0RxeE0sN3zxFXM8rzyJPo,444
25
25
  xradio/schema/bases.py,sha256=vcW47jZWpJ0mJdni7eFVY7zJoper2sy2VjX8LE3pUqc,150
26
26
  xradio/schema/check.py,sha256=3u79hRL3pGF6dvQE0LF21nGdAVnRXWwgnbMmStGBSSA,16310
@@ -28,7 +28,7 @@ xradio/schema/dataclass.py,sha256=vkc2cqLjGV5QN8j70GbBaNfslT_KLWmebsPGeBEuGcs,88
28
28
  xradio/schema/metamodel.py,sha256=RHrihyaetinu7_lGTTZ31Rlv-_Db_EgQCXzk56H004o,3476
29
29
  xradio/schema/typing.py,sha256=coF3LuKOlCUJGKTUUH81EcjePZ86koOYzm8qzsAw-HU,9983
30
30
  xradio/vis/__init__.py,sha256=AV2WG26NzFB1LEEtFaq1ULQKz9VnluEAjg0Qb5Ju7m8,358
31
- xradio/vis/_processing_set.py,sha256=zYCswmWjsRN_8M61IkbMo6zpI-4ABMWpKZkL8f20KGo,4187
31
+ xradio/vis/_processing_set.py,sha256=M56gIsF_3mKJjjbyU8E7jp0W8niojSrpqETdInOjwVQ,4398
32
32
  xradio/vis/convert_msv2_to_processing_set.py,sha256=7vTjqtWFEBOySnLVoadceKCA4VLgOig7eCs1dxrdYQA,3966
33
33
  xradio/vis/load_processing_set.py,sha256=ldgg0GqFwYuNc2fPkRlc_lW2Kt7naq2wFGloALl0J4Y,6753
34
34
  xradio/vis/model.py,sha256=uBjvvhYEY1p-3H3NStrt1ZKMQACLGLo93OiEBvDVId8,17083
@@ -51,8 +51,8 @@ xradio/vis/_vis_utils/_ms/partitions.py,sha256=vlBIaJgKKNkxE1okQxJ3NZTk9vnKHklB2
51
51
  xradio/vis/_vis_utils/_ms/subtables.py,sha256=hkSa3sXUaSRVEv2CNK65Svx5Uyp3opZHaHYnJucehyU,3728
52
52
  xradio/vis/_vis_utils/_ms/_tables/load.py,sha256=TXrEf7fKfsP0Wp7fB7DLWeOS_Z8A1OLKGWGNSoiYHOM,1665
53
53
  xradio/vis/_vis_utils/_ms/_tables/load_main_table.py,sha256=HyIfjaQXfFA30YRUzU2H_ugRnArQ1XOiVGKxC9PbiOo,13497
54
- xradio/vis/_vis_utils/_ms/_tables/read.py,sha256=lt3JOre-7WyzTprUuZIowi6aEcXc8R367oLZUB0vdhk,21781
55
- xradio/vis/_vis_utils/_ms/_tables/read_main_table.py,sha256=9XasWazrGSkQ6C4jSrItIGidaTUzh-bdSRYkYR5j0Dg,23958
54
+ xradio/vis/_vis_utils/_ms/_tables/read.py,sha256=qFhRAucl7M5FsKefRZcOLCoUAA8ua0805Gq8IiLPZ-4,23749
55
+ xradio/vis/_vis_utils/_ms/_tables/read_main_table.py,sha256=1Qj-1psYMJtV0hdjfaBZu-4pNIagllHcnANoI1rI6xU,23982
56
56
  xradio/vis/_vis_utils/_ms/_tables/read_subtables.py,sha256=_3AlxlLJwdu__a8sfG8a7-wz-yTo2S7JyVit17XaxKs,11741
57
57
  xradio/vis/_vis_utils/_ms/_tables/table_query.py,sha256=q8EGFf_zIwHcHnvFJOn8hPh8zFZQ3f7BGbXvL3bHad4,555
58
58
  xradio/vis/_vis_utils/_ms/_tables/write.py,sha256=Uuk4QGib_QOc8i6g7OYB9E6SxMUDPlXDYXlHqkzPX5Q,8475
@@ -64,8 +64,8 @@ xradio/vis/_vis_utils/_utils/xds_helper.py,sha256=UhtAZV5DyYzVVBkXzwDAOz6TICxotQ
64
64
  xradio/vis/_vis_utils/_zarr/encoding.py,sha256=GENIlThV6a9CUCL6gIGlu9c6NR3OFWNos6mpxZjMwDc,536
65
65
  xradio/vis/_vis_utils/_zarr/read.py,sha256=ikNGlOdHuZ_cgWpPAZ4iHzeLdU44I0iBLcqSEiM_hCk,7111
66
66
  xradio/vis/_vis_utils/_zarr/write.py,sha256=exvrqNVnVKk6LzbDPm_fm142YzX-7lHGqklXTQB9wh0,8864
67
- xradio-0.0.26.dist-info/LICENSE.txt,sha256=dvACd-5O67yjSZlnEKcWmu3DqwzBtbC922iPv0KOeAw,1516
68
- xradio-0.0.26.dist-info/METADATA,sha256=Z3bKRq6dhmg8EIvgddHYafA9TSFoWd1PDerkpkkf8Gw,4089
69
- xradio-0.0.26.dist-info/WHEEL,sha256=GJ7t_kWBFywbagK5eo9IoUwLW6oyOeTKmQ-9iHFVNxQ,92
70
- xradio-0.0.26.dist-info/top_level.txt,sha256=dQu27fGBZJ2Yk-gW5XeD-dZ76Xa4Xcvk60Vz-dwXp7k,7
71
- xradio-0.0.26.dist-info/RECORD,,
67
+ xradio-0.0.28.dist-info/LICENSE.txt,sha256=dvACd-5O67yjSZlnEKcWmu3DqwzBtbC922iPv0KOeAw,1516
68
+ xradio-0.0.28.dist-info/METADATA,sha256=rHayCyOKEbXPz7q0u5LrsKeJNXl21ylyvnmPL_OB73g,4089
69
+ xradio-0.0.28.dist-info/WHEEL,sha256=GJ7t_kWBFywbagK5eo9IoUwLW6oyOeTKmQ-9iHFVNxQ,92
70
+ xradio-0.0.28.dist-info/top_level.txt,sha256=dQu27fGBZJ2Yk-gW5XeD-dZ76Xa4Xcvk60Vz-dwXp7k,7
71
+ xradio-0.0.28.dist-info/RECORD,,