Repository: kestra-io/kestra (java)

Issue:
io.kestra.plugin.git.Push
### Explain the bug

When running git.Push task with property namespaceFiles enabled and no namespace files exist in the namespace an error is triggered.
In the given example, the branch did not exist. Another run with namespaceFiles: commented out, resulted in a successful run.

Configuration snippet:
```
- id: backup
  type: io.kestra.plugin.git.Push
  namespaceFiles:
    enabled: true
  flows:
    enabled: true
    childNamespaces: true
    gitDirectory: _flows
```

 Stack trace:
```
Branch $BRANCH_NAME does not exist, creating it
Start cloning from 'https://gitlab/'
/$NAMESPACE/_files/ (File not found)
java.io.FileNotFoundException: /$NAMESPACE/_files/ (File not found)
	at io.kestra.storage.minio.MinioStorage.reThrowMinioStorageException(MinioStorage.java:395)
	at io.kestra.storage.minio.MinioStorage.getFileAttributes(MinioStorage.java:154)
	at io.kestra.storage.minio.MinioStorage.getAttributes(MinioStorage.java:138)
	at io.kestra.storage.minio.$MinioStorage$Definition$Intercepted.$$access$$getAttributes(Unknown Source)
	at io.kestra.storage.minio.$MinioStorage$Definition$Exec.dispatch(Unknown Source)
	at io.micronaut.context.AbstractExecutableMethodsDefinition$DispatchedExecutableMethod.invoke(AbstractExecutableMethodsDefinition.java:371)
	at io.micronaut.aop.chain.MethodInterceptorChain.proceed(MethodInterceptorChain.java:128)
	at io.micronaut.aop.internal.intercepted.SynchronousInterceptedMethod.interceptResult(SynchronousInterceptedMethod.java:55)
	at io.micronaut.retry.intercept.OverrideRetryInterceptor.retrySync(OverrideRetryInterceptor.java:93)
	at io.micronaut.retry.intercept.OverrideRetryInterceptor.intercept(OverrideRetryInterceptor.java:68)
	at io.micronaut.aop.chain.MethodInterceptorChain.proceed(MethodInterceptorChain.java:137)
	at io.kestra.storage.minio.$MinioStorage$Definition$Intercepted.getAttributes(Unknown Source)
	at io.kestra.storage.minio.MinioStorage.list(MinioStorage.java:74)
	at io.kestra.storage.minio.$MinioStorage$Definition$Intercepted.$$access$$list(Unknown Source)
	at io.kestra.storage.minio.$MinioStorage$Definition$Exec.dispatch(Unknown Source)
	at io.micronaut.context.AbstractExecutableMethodsDefinition$DispatchedExecutableMethod.invoke(AbstractExecutableMethodsDefinition.java:371)
	at io.micronaut.aop.chain.MethodInterceptorChain.proceed(MethodInterceptorChain.java:128)
	at io.micronaut.aop.internal.intercepted.SynchronousInterceptedMethod.interceptResult(SynchronousInterceptedMethod.java:55)
	at io.micronaut.retry.intercept.OverrideRetryInterceptor.retrySync(OverrideRetryInterceptor.java:93)
	at io.micronaut.retry.intercept.OverrideRetryInterceptor.intercept(OverrideRetryInterceptor.java:68)
	at io.micronaut.aop.chain.MethodInterceptorChain.proceed(MethodInterceptorChain.java:137)
	at io.kestra.storage.minio.$MinioStorage$Definition$Intercepted.list(Unknown Source)
	at io.kestra.core.runners.NamespaceFilesService.recursiveList(NamespaceFilesService.java:80)
	at io.kestra.core.runners.NamespaceFilesService.inject(NamespaceFilesService.java:36)
	at io.kestra.plugin.git.Push.run(Push.java:237)
	at io.kestra.plugin.git.Push.run(Push.java:38)
	at io.kestra.core.runners.Worker$WorkerThread.run(Worker.java:729)
```


### Environment Information

- Kestra Version: 0.14.4
- Operating System and Java Version (if not using Kestra Docker image):
Docker image

Pull request:
fix(core): don't crash upon injecting Namespace Files if the root folder doesn't exist
closes #2965 

Patch:
diff --git a/core/src/main/java/io/kestra/core/runners/NamespaceFilesService.java b/core/src/main/java/io/kestra/core/runners/NamespaceFilesService.java
index 7986bf075..59ed96103 100644
--- a/core/src/main/java/io/kestra/core/runners/NamespaceFilesService.java
+++ b/core/src/main/java/io/kestra/core/runners/NamespaceFilesService.java
@@ -9,6 +9,7 @@ import jakarta.inject.Inject;
 import jakarta.inject.Singleton;
 import lombok.extern.slf4j.Slf4j;
 
+import java.io.FileNotFoundException;
 import java.io.IOException;
 import java.io.InputStream;
 import java.net.URI;
@@ -78,7 +79,13 @@ public class NamespaceFilesService {
         URI uri = uri(namespace, path);
 
         List<URI> result = new ArrayList<>();
-        List<FileAttributes> list = storageInterface.list(tenantId, uri);
+        List<FileAttributes> list;
+        try {
+            list = storageInterface.list(tenantId, uri);
+        } catch (FileNotFoundException e) {
+            // prevent crashing upon trying to inject namespace files while the root namespace files folder doesn't exist
+            return result;
+        }
 
         for (var file: list) {
             URI current = URI.create((path != null ? path.getPath() : "") +  "/" + file.getFileName());


Test patch:
diff --git a/core/src/test/java/io/kestra/core/runners/NamespaceFilesServiceTest.java b/core/src/test/java/io/kestra/core/runners/NamespaceFilesServiceTest.java
index 232e63aca..d08815994 100644
--- a/core/src/test/java/io/kestra/core/runners/NamespaceFilesServiceTest.java
+++ b/core/src/test/java/io/kestra/core/runners/NamespaceFilesServiceTest.java
@@ -168,6 +168,22 @@ class NamespaceFilesServiceTest {
         assertThat(content, is("2"));
     }
 
+    @Test
+    public void nsFilesRootFolderDoesntExist() throws Exception {
+        RunContext runContext = runContextFactory.of();
+        List<URI> injected = namespaceFilesService.inject(
+            runContextFactory.of(),
+            "tenant1",
+            "io.kestra." + IdUtils.create(),
+            runContext.tempDir(),
+            NamespaceFiles
+                .builder()
+                .enabled(true)
+                .build()
+        );
+        assertThat(injected.size(), is(0));
+    }
+
     private void put(@Nullable String tenantId, String namespace, String path, String content) throws IOException {
         storageInterface.put(
             tenantId,