dssg / dssg/triage

FileNotFoundError in SingleModelAnalyzer.crosstabs_pos_vs_neg due to incorrect S3Store temp path

Open
#986 1 comment 0 reactions 0 assignees View on GitHub
Dominant language
Jupyter Notebook
Stars
201
Forks
62
PR merge metrics
No merged PRs in 30d

Description

Hello everyone,

I'm really sorry for the delay.

I'm experiencing some issues with the crosstabs_pos_vs_neg method from the SingleModelAnalyzer module (the exact same error occurs when I use the run_crosstabs_from_matrix method).

### **Steps to reproduce**

I'm running it as follows:

```python
from triage.component.postmodeling.base import SingleModelAnalyzer
from sqlalchemy import create_engine

project_path = "s3://egobiernoytp-conjusticia-zacatecas/triage_output_post_reinicio/"
rank_column = "rank_abs_no_ties"
rank_threshold = 100
thresholds = {rank_column : rank_threshold }
model_id = 4687

db_conn = create_engine("postgresql+psycopg2://")

model_analyzer = SingleModelAnalyzer(model_id, db_conn)

model_analyzer.crosstabs_pos_vs_neg(project_path, thresholds)
```

### **Error message**

The error message is:

```
2025-09-26 18:01:49 - INFO file in S3
2025-09-26 18:01:49 - INFO Found credentials in shared credentials file: ~/.aws/credentials
---------------------------------------------------------------------------
FileNotFoundError Traceback (most recent call last)
Cell In[5], line 1
----> 1 model_analyzer.crosstabs_pos_vs_neg(project_path, thresholds)

File ~/vir_env/issue_of_crosstabs/lib/python3.10/site-packages/triage/component/postmodeling/base.py:441, in SingleModelAnalyzer.crosstabs_pos_vs_neg(self, project_path, thresholds, matrix_uuid, push_to_db, table_name, return_df, replace, predictions_table)
437 matrix_storage_engine = project_storage.matrix_storage_engine()
439 matrix_store = matrix_storage_engine.get_store(matrix_uuid=matrix_uuid)
--> 441 matrix = matrix_store.design_matrix
443 labels = matrix_store.labels
444 features = matrix.columns

File ~/vir_env/issue_of_crosstabs/lib/python3.10/site-packages/triage/component/catwalk/storage.py:430, in MatrixStore.design_matrix(self)
427 @property
428 def design_matrix(self):
429 """The matrix without the label vector, only the index and features"""
--> 430 return self.matrix_label_tuple[0]

File ~/vir_env/issue_of_crosstabs/lib/python3.10/site-packages/triage/component/catwalk/storage.py:418, in MatrixStore.matrix_label_tuple(self)
416 if self._matrix_label_tuple:
417 return self._matrix_label_tuple
--> 418 design_matrix, labels = self._preprocess_and_split_matrix(self._load())
419 if self.should_cache:
420 self._matrix_label_tuple = design_matrix, labels

File ~/vir_env/issue_of_crosstabs/lib/python3.10/site-packages/triage/component/catwalk/storage.py:652, in CSVMatrixStore._load(self)
650 start = time.time()
651 logger.debug(f"load matrix with polars {filename_}")
--> 652 df_pl = pl.read_csv(filename_, infer_schema_length=0).with_columns(pl.all().exclude(
653 ['entity_id', 'as_of_date']).cast(pl.Float32, strict=False))
654 end = time.time()
656 logger.debug(f"time for loading matrix as polar df (sec): {(end-start)/60}")

File ~/vir_env/issue_of_crosstabs/lib/python3.10/site-packages/polars/io/csv/functions.py:354, in read_csv(source, has_header, columns, new_columns, separator, comment_char, quote_char, skip_rows, dtypes, null_values, missing_utf8_is_empty_string, ignore_errors, try_parse_dates, n_threads, infer_schema_length, batch_size, n_rows, encoding, low_memory, rechunk, use_pyarrow, storage_options, skip_rows_after_header, row_count_name, row_count_offset, sample_size, eol_char)
346 dtypes = {
347 new_to_current.get(column_name, column_name): column_dtype
348 for column_name, column_dtype in dtypes.items()
349 }
351 with _prepare_file_arg(
352 source, encoding=encoding, use_pyarrow=False, **storage_options
353 ) as data:
--> 354 df = pl.DataFrame._read_csv(
355 data,
356 has_header=has_header,
357 columns=columns if columns else projection,
358 separator=separator,
359 comment_char=comment_char,
360 quote_char=quote_char,
361 skip_rows=skip_rows,
362 dtypes=dtypes,
363 null_values=null_values,
364 missing_utf8_is_empty_string=missing_utf8_is_empty_string,
365 ignore_errors=ignore_errors,
366 try_parse_dates=try_parse_dates,
367 n_threads=n_threads,
368 infer_schema_length=infer_schema_length,
369 batch_size=batch_size,
370 n_rows=n_rows,
371 encoding=encoding if encoding == "utf8-lossy" else "utf8",
372 low_memory=low_memory,
373 rechunk=rechunk,
374 skip_rows_after_header=skip_rows_after_header,
375 row_count_name=row_count_name,
376 row_count_offset=row_count_offset,
377 sample_size=sample_size,
378 eol_char=eol_char,
379 )
381 if new_columns:
382 return _update_columns(df, new_columns)

File ~/vir_env/issue_of_crosstabs/lib/python3.10/site-packages/polars/dataframe/frame.py:784, in DataFrame._read_csv(cls, source, has_header, columns, separator, comment_char, quote_char, skip_rows, dtypes, null_values, missing_utf8_is_empty_string, ignore_errors, try_parse_dates, n_threads, infer_schema_length, batch_size, n_rows, encoding, low_memory, rechunk, skip_rows_after_header, row_count_name, row_count_offset, sample_size, eol_char)
777 raise ValueError(
778 "cannot use glob patterns and integer based projection as `columns`"
779 " argument; Use columns: List[str]"
780 )
782 projection, columns = handle_projection_columns(columns)
--> 784 self._df = PyDataFrame.read_csv(
785 source,
786 infer_schema_length,
787 batch_size,
788 has_header,
789 ignore_errors,
790 n_rows,
791 skip_rows,
792 projection,
793 separator,
794 rechunk,
795 columns,
796 encoding,
797 n_threads,
798 path,
799 dtype_list,
800 dtype_slice,
801 low_memory,
802 comment_char,
803 quote_char,
804 processed_null_values,
805 missing_utf8_is_empty_string,
806 try_parse_dates,
807 skip_rows_after_header,
808 _prepare_row_count_args(row_count_name, row_count_offset),
809 sample_size=sample_size,
810 eol_char=eol_char,
811 )
812 return self

FileNotFoundError: No such file or directory: /tmp/edgarhr/51589255b01ec8757dd039221c2573ad.csv.gz
```

### **Observed behavior**

I'm running this from an S2 machine using my user account (edgarhr). It is an Ubuntu 22.04.5 machine, and I have tried Triage versions 5.5.1 and 5.5.3.

It seems that `CatWalkStorage` is saving the matrix from S3 locally in an incorrect temporary path. When it tries to access the file, it cannot find it. I suspect this because when I run the crosstabs_pos_vs_neg method, the file `/tmp/edgarhr/51589255b01ec8757dd039221c2573ad.csv.gz` does not exist; instead, there is a file named `"edgarhr"` in the tmp directory.

### **Workaround**

To get the crosstabs_pos_vs_neg method to run, I modified the `download` function of the S3Store class (CatWalkStorage component) as follows:

Aquí va tu código modificado del download

The main difference is that I join what you call `dirpath` with the name of the S3 file and I call it `filepath_`. This is the path I use for downloading.

When I removed the `/tmp/edgarhr `**`file`** and ran the crosstabs_pos_vs_neg method again with this modification in CatWalkStorage, it worked correctly.

### **Environment**

- OS: Ubuntu 22.04.5
- Python: 3.10.12
- Triage versions: 5.5.1 and 5.5.3
- Running on: S2 machine

Contributor guide

Open the contributing guide

Research direction

Start in triage/component/catwalk/storage.py, following S3Store.download and the CSVMatrixStore._load stack trace. Reproduce with SingleModelAnalyzer.crosstabs_pos_vs_neg against the S3 project path and inspect how the temporary download path is constructed. Done means the downloaded matrix is saved where the loader expects it and the crosstabs operation no longer raises FileNotFoundError.

Written by the indexing model from the issue text.

Assessment

Tech stack
aws, python
Domain
backend, cloud
Issue type
Bug
Difficulty
3/5
Estimated time
1-2 days
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
35/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.