Skip to content
Snippets Groups Projects
WorkflowVersionView.vue 3.97 KiB
<script setup lang="ts">
import { onMounted, reactive, watch } from "vue";
import { WorkflowVersionService } from "@/client/workflow";
import type { WorkflowVersionFull } from "@/client/workflow";
import axios from "axios";
import MarkdownRenderer from "@/components/MarkdownRenderer.vue";
import ParameterSchemaFormComponent from "@/components/parameter-schema/ParameterSchemaFormComponent.vue";

const props = defineProps<{
  versionId: string;
  workflowId: string;
  activeTab: string;
}>();

const versionState = reactive<{
  loading: boolean;
  fileLoading: boolean;
  version: undefined | WorkflowVersionFull;
  descriptionMarkdown: string;
  changelogMarkdown: string;
  errorLoading: boolean;
  parameterSchema: Record<string, never>;
}>({
  loading: true,
  fileLoading: true,
  version: undefined,
  errorLoading: false,
  descriptionMarkdown: "",
  changelogMarkdown: "",
  parameterSchema: {},
});

watch(
  () => props.versionId,
  (newVersionId, oldVersionId) => {
    if (newVersionId !== oldVersionId) {
      // If bucket is changed, update the objects
      updateVersion(newVersionId, props.workflowId);
    }
  }
);

function updateVersion(versionId: string, workflowId: string) {
  versionState.loading = true;
  versionState.fileLoading = true;
  WorkflowVersionService.workflowVersionGetWorkflowVersion(
    versionId,
    workflowId
  )
    .then((version) => {
      versionState.version = version;
      downloadVersionFiles(version);
    })
    .catch(() => {
      versionState.version = undefined;
    })
    .finally(() => {
      versionState.loading = false;
    });
}

function downloadVersionFiles(version: WorkflowVersionFull) {
  versionState.fileLoading = true;
  const descriptionPromise = axios.get(version.readme_url).then((response) => {
    versionState.descriptionMarkdown = response.data;
  });
  const changelogPromise = axios.get(version.changelog_url).then((response) => {
    versionState.changelogMarkdown = response.data;
  });
  const parameterPromise = axios
    .get(version.parameter_schema_url)
    .then((response) => {
      versionState.parameterSchema = response.data;
    });
  Promise.all([descriptionPromise, changelogPromise, parameterPromise]).finally(
    () => {
      versionState.fileLoading = false;
    }
  );
}

onMounted(() => {
  updateVersion(props.versionId, props.workflowId);
});
</script>

<template>
  <ul class="nav justify-content-evenly nav-tabs bg-dark fs-5 mb-3">
    <li class="nav-item">
      <router-link
        class="nav-link"
        aria-current="page"
        :to="{ query: { tab: 'description' } }"
        :class="{ active: props.activeTab === 'description' }"
        >Description
      </router-link>
    </li>
    <li class="nav-item">
      <router-link
        class="nav-link"
        :to="{ query: { tab: 'parameters' } }"
        :class="{ active: props.activeTab === 'parameters' }"
        >Parameters
      </router-link>
    </li>
    <li class="nav-item">
      <router-link
        class="nav-link"
        :to="{ query: { tab: 'changes' } }"
        :class="{ active: props.activeTab === 'changes' }"
        >Releases
      </router-link>
    </li>
  </ul>
  <div v-if="versionState.fileLoading">
    <p class="placeholder-glow mt-2 mb-4">
      <span class="placeholder col-7 fs-1"></span>
    </p>
    <p
      v-for="n in 8"
      :key="n"
      class="placeholder-glow row ms-1"
      :class="'my-' + Math.floor(Math.random() * 6)"
    >
      <span
        class="placeholder"
        :class="'col-' + Math.floor(Math.random() * 9 + 2)"
      ></span>
    </p>
  </div>
  <div v-else class="px-2">
    <p v-if="props.activeTab === 'description'">
      <markdown-renderer :markdown="versionState.descriptionMarkdown" />
    </p>
    <parameter-schema-form-component
      v-else-if="props.activeTab === 'parameters'"
      :schema="versionState.parameterSchema"
    />
    <p v-else-if="props.activeTab === 'changes'">
      <markdown-renderer :markdown="versionState.changelogMarkdown" />
    </p>
  </div>
</template>

<style scoped></style>