This is an automated email from the ASF dual-hosted git repository.

yasithdev pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/airavata.git


The following commit(s) were added to refs/heads/master by this push:
     new 6111274658 feat(storage-service): expose file modified-time and 
content-type in metadata
6111274658 is described below

commit 61112746588fd0319e229f3495aa63bbcf26c26f
Author: Yasith Jayawardana <[email protected]>
AuthorDate: Tue Jun 9 01:57:52 2026 -0400

    feat(storage-service): expose file modified-time and content-type in 
metadata
    
    The gRPC storage listing (list_dir/get_file_metadata) left modified_time 
and content_type unset even though FileMetadataResponse declares them. Populate 
both: FileMetadata gains modifiedTime + contentType; SSHJStorageAdaptor sets 
modifiedTime from SFTP stat mtime and guesses content_type from the filename; 
toFileMetadataResponse copies them through. created_time is not available over 
SFTP and stays unset.
---
 .../airavata/compute/util/SSHJStorageAdaptor.java    |  6 +++++-
 .../org/apache/airavata/interfaces/FileMetadata.java | 20 ++++++++++++++++++++
 .../storage/grpc/UserStorageGrpcService.java         |  2 ++
 3 files changed, 27 insertions(+), 1 deletion(-)

diff --git 
a/airavata-api/compute-service/src/main/java/org/apache/airavata/compute/util/SSHJStorageAdaptor.java
 
b/airavata-api/compute-service/src/main/java/org/apache/airavata/compute/util/SSHJStorageAdaptor.java
index cbd5d63b81..1582e915e7 100644
--- 
a/airavata-api/compute-service/src/main/java/org/apache/airavata/compute/util/SSHJStorageAdaptor.java
+++ 
b/airavata-api/compute-service/src/main/java/org/apache/airavata/compute/util/SSHJStorageAdaptor.java
@@ -148,9 +148,13 @@ public class SSHJStorageAdaptor implements 
StorageResourceAdaptor {
         try (SFTPClient sftp = openSftp()) {
             FileAttributes attrs = sftp.stat(remoteFile);
             FileMetadata meta = new FileMetadata();
-            meta.setName(remoteFile.substring(remoteFile.lastIndexOf('/') + 
1));
+            String name = remoteFile.substring(remoteFile.lastIndexOf('/') + 
1);
+            meta.setName(name);
             meta.setSize(attrs.getSize());
             meta.setDirectory(attrs.getType() == FileMode.Type.DIRECTORY);
+            // SFTP mtime is seconds since the epoch; expose it as epoch 
millis.
+            meta.setModifiedTime(attrs.getMtime() * 1000L);
+            
meta.setContentType(java.net.URLConnection.guessContentTypeFromName(name));
             return meta;
         } catch (Exception e) {
             throw new AgentException("Failed to get file metadata: " + 
remoteFile, e);
diff --git 
a/airavata-api/src/main/java/org/apache/airavata/interfaces/FileMetadata.java 
b/airavata-api/src/main/java/org/apache/airavata/interfaces/FileMetadata.java
index c5768a62cf..a26fb31614 100644
--- 
a/airavata-api/src/main/java/org/apache/airavata/interfaces/FileMetadata.java
+++ 
b/airavata-api/src/main/java/org/apache/airavata/interfaces/FileMetadata.java
@@ -25,6 +25,8 @@ public class FileMetadata {
     private long size;
     private int permissions = 420;
     private boolean isDirectory;
+    private long modifiedTime;
+    private String contentType;
 
     public String getName() {
         return name;
@@ -57,4 +59,22 @@ public class FileMetadata {
     public void setDirectory(boolean isDirectory) {
         this.isDirectory = isDirectory;
     }
+
+    /** Last-modified time in epoch milliseconds, or 0 if unknown. */
+    public long getModifiedTime() {
+        return modifiedTime;
+    }
+
+    public void setModifiedTime(long modifiedTime) {
+        this.modifiedTime = modifiedTime;
+    }
+
+    /** MIME content type guessed from the file name, or null if unknown. */
+    public String getContentType() {
+        return contentType;
+    }
+
+    public void setContentType(String contentType) {
+        this.contentType = contentType;
+    }
 }
diff --git 
a/airavata-api/storage-service/src/main/java/org/apache/airavata/storage/grpc/UserStorageGrpcService.java
 
b/airavata-api/storage-service/src/main/java/org/apache/airavata/storage/grpc/UserStorageGrpcService.java
index 3b963b8d23..79d121e9c0 100644
--- 
a/airavata-api/storage-service/src/main/java/org/apache/airavata/storage/grpc/UserStorageGrpcService.java
+++ 
b/airavata-api/storage-service/src/main/java/org/apache/airavata/storage/grpc/UserStorageGrpcService.java
@@ -422,6 +422,8 @@ public class UserStorageGrpcService extends 
UserStorageServiceGrpc.UserStorageSe
                 .setPath(path)
                 .setSize(meta.getSize())
                 .setIsDirectory(meta.isDirectory())
+                .setModifiedTime(meta.getModifiedTime())
+                .setContentType(meta.getContentType() != null ? 
meta.getContentType() : "")
                 .build();
     }
 }

Reply via email to