2019-10-20 18:02:52 +02:00
|
|
|
import * as types from "../../../modules/types";
|
2019-11-01 09:29:57 +01:00
|
|
|
import { Repository, File, Action, Link } from "@scm-manager/ui-types";
|
2019-10-20 18:02:52 +02:00
|
|
|
import { apiClient } from "@scm-manager/ui-components";
|
|
|
|
|
import { isPending } from "../../../modules/pending";
|
|
|
|
|
import { getFailure } from "../../../modules/failure";
|
2018-09-27 16:32:37 +02:00
|
|
|
|
2019-10-20 18:02:52 +02:00
|
|
|
export const FETCH_SOURCES = "scm/repos/FETCH_SOURCES";
|
2018-09-27 16:32:37 +02:00
|
|
|
export const FETCH_SOURCES_PENDING = `${FETCH_SOURCES}_${types.PENDING_SUFFIX}`;
|
|
|
|
|
export const FETCH_SOURCES_SUCCESS = `${FETCH_SOURCES}_${types.SUCCESS_SUFFIX}`;
|
|
|
|
|
export const FETCH_SOURCES_FAILURE = `${FETCH_SOURCES}_${types.FAILURE_SUFFIX}`;
|
|
|
|
|
|
2019-12-17 12:42:31 +01:00
|
|
|
export function fetchSources(repository: Repository, revision: string, path: string, initialLoad = true) {
|
2019-12-17 10:25:53 +01:00
|
|
|
return function(dispatch: any, getState: () => any) {
|
|
|
|
|
const state = getState();
|
2019-12-17 12:42:05 +01:00
|
|
|
if (
|
|
|
|
|
isFetchSourcesPending(state, repository, revision, path) ||
|
|
|
|
|
isUpdateSourcePending(state, repository, revision, path)
|
|
|
|
|
) {
|
2019-12-17 10:25:53 +01:00
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (initialLoad) {
|
2019-12-11 15:49:33 +01:00
|
|
|
dispatch(fetchSourcesPending(repository, revision, path));
|
2019-12-17 10:25:53 +01:00
|
|
|
} else {
|
2019-12-17 12:36:58 +01:00
|
|
|
dispatch(updateSourcesPending(repository, revision, path, getSources(state, repository, revision, path)));
|
2019-12-11 15:49:33 +01:00
|
|
|
}
|
2018-09-27 16:32:37 +02:00
|
|
|
return apiClient
|
2018-09-28 11:31:38 +02:00
|
|
|
.get(createUrl(repository, revision, path))
|
2018-09-27 16:32:37 +02:00
|
|
|
.then(response => response.json())
|
2019-12-11 15:49:33 +01:00
|
|
|
.then((sources: File) => {
|
2019-11-01 13:52:53 +01:00
|
|
|
dispatch(fetchSourcesSuccess(repository, revision, path, sources));
|
2018-09-27 16:32:37 +02:00
|
|
|
})
|
|
|
|
|
.catch(err => {
|
2019-11-01 13:52:53 +01:00
|
|
|
dispatch(fetchSourcesFailure(repository, revision, path, err));
|
2018-09-27 16:32:37 +02:00
|
|
|
});
|
|
|
|
|
};
|
|
|
|
|
}
|
|
|
|
|
|
2018-09-28 11:31:38 +02:00
|
|
|
function createUrl(repository: Repository, revision: string, path: string) {
|
2019-11-01 09:29:57 +01:00
|
|
|
const base = (repository._links.sources as Link).href;
|
2018-09-28 11:31:38 +02:00
|
|
|
if (!revision && !path) {
|
|
|
|
|
return base;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// TODO handle trailing slash
|
2019-10-20 18:02:52 +02:00
|
|
|
const pathDefined = path ? path : "";
|
2018-10-23 13:03:15 +02:00
|
|
|
return `${base}${encodeURIComponent(revision)}/${pathDefined}`;
|
2018-09-28 11:31:38 +02:00
|
|
|
}
|
|
|
|
|
|
2019-10-21 10:57:56 +02:00
|
|
|
export function fetchSourcesPending(repository: Repository, revision: string, path: string): Action {
|
2018-09-27 16:32:37 +02:00
|
|
|
return {
|
|
|
|
|
type: FETCH_SOURCES_PENDING,
|
2019-10-20 18:02:52 +02:00
|
|
|
itemId: createItemId(repository, revision, path)
|
2018-09-27 16:32:37 +02:00
|
|
|
};
|
|
|
|
|
}
|
|
|
|
|
|
2019-12-17 12:42:05 +01:00
|
|
|
export function updateSourcesPending(
|
|
|
|
|
repository: Repository,
|
|
|
|
|
revision: string,
|
|
|
|
|
path: string,
|
|
|
|
|
currentSources: any
|
|
|
|
|
): Action {
|
2019-12-17 10:25:53 +01:00
|
|
|
return {
|
|
|
|
|
type: "UPDATE_PENDING",
|
2019-12-17 12:42:05 +01:00
|
|
|
payload: { updatePending: true, sources: currentSources },
|
2019-12-17 10:25:53 +01:00
|
|
|
itemId: createItemId(repository, revision, path)
|
|
|
|
|
};
|
|
|
|
|
}
|
|
|
|
|
|
2019-10-21 10:57:56 +02:00
|
|
|
export function fetchSourcesSuccess(repository: Repository, revision: string, path: string, sources: File) {
|
2018-09-27 16:32:37 +02:00
|
|
|
return {
|
|
|
|
|
type: FETCH_SOURCES_SUCCESS,
|
2019-12-17 10:25:53 +01:00
|
|
|
payload: { updatePending: false, sources },
|
2019-10-20 18:02:52 +02:00
|
|
|
itemId: createItemId(repository, revision, path)
|
2018-09-27 16:32:37 +02:00
|
|
|
};
|
|
|
|
|
}
|
|
|
|
|
|
2019-10-21 10:57:56 +02:00
|
|
|
export function fetchSourcesFailure(repository: Repository, revision: string, path: string, error: Error): Action {
|
2018-09-27 16:32:37 +02:00
|
|
|
return {
|
|
|
|
|
type: FETCH_SOURCES_FAILURE,
|
|
|
|
|
payload: error,
|
2019-10-20 18:02:52 +02:00
|
|
|
itemId: createItemId(repository, revision, path)
|
2018-09-27 16:32:37 +02:00
|
|
|
};
|
|
|
|
|
}
|
|
|
|
|
|
2018-09-28 11:31:38 +02:00
|
|
|
function createItemId(repository: Repository, revision: string, path: string) {
|
2019-10-20 18:02:52 +02:00
|
|
|
const revPart = revision ? revision : "_";
|
|
|
|
|
const pathPart = path ? path : "";
|
2019-11-01 09:29:57 +01:00
|
|
|
return `${repository.namespace}/${repository.name}/${decodeURIComponent(revPart)}/${pathPart}`;
|
2018-09-27 16:32:37 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// reducer
|
|
|
|
|
|
|
|
|
|
export default function reducer(
|
|
|
|
|
state: any = {},
|
2019-10-19 16:38:07 +02:00
|
|
|
action: Action = {
|
2019-10-20 18:02:52 +02:00
|
|
|
type: "UNKNOWN"
|
|
|
|
|
}
|
2018-09-27 16:32:37 +02:00
|
|
|
): any {
|
2019-12-17 12:36:58 +01:00
|
|
|
if (action.itemId && (action.type === FETCH_SOURCES_SUCCESS || action.type === "UPDATE_PENDING")) {
|
2018-09-27 16:32:37 +02:00
|
|
|
return {
|
2018-12-21 13:39:24 +01:00
|
|
|
...state,
|
2019-10-20 18:02:52 +02:00
|
|
|
[action.itemId]: action.payload
|
2018-09-27 16:32:37 +02:00
|
|
|
};
|
|
|
|
|
}
|
|
|
|
|
return state;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// selectors
|
|
|
|
|
|
2019-10-21 10:57:56 +02:00
|
|
|
export function isDirectory(state: any, repository: Repository, revision: string, path: string): boolean {
|
2018-10-25 11:27:31 +02:00
|
|
|
const currentFile = getSources(state, repository, revision, path);
|
|
|
|
|
if (currentFile && !currentFile.directory) {
|
|
|
|
|
return false;
|
|
|
|
|
} else {
|
|
|
|
|
return true; //also return true if no currentFile is found since it is the "default" path
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2018-09-27 16:32:37 +02:00
|
|
|
export function getSources(
|
|
|
|
|
state: any,
|
2018-09-28 11:31:38 +02:00
|
|
|
repository: Repository,
|
|
|
|
|
revision: string,
|
2019-10-20 18:02:52 +02:00
|
|
|
path: string
|
2019-10-19 16:38:07 +02:00
|
|
|
): File | null | undefined {
|
2018-09-27 16:32:37 +02:00
|
|
|
if (state.sources) {
|
2019-12-17 10:25:53 +01:00
|
|
|
return state.sources[createItemId(repository, revision, path)]?.sources;
|
2018-09-27 16:32:37 +02:00
|
|
|
}
|
|
|
|
|
return null;
|
|
|
|
|
}
|
|
|
|
|
|
2019-10-21 10:57:56 +02:00
|
|
|
export function isFetchSourcesPending(state: any, repository: Repository, revision: string, path: string): boolean {
|
2019-12-17 10:25:53 +01:00
|
|
|
return state && isPending(state, FETCH_SOURCES, createItemId(repository, revision, path));
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
function isUpdateSourcePending(state: any, repository: Repository, revision: string, path: string): boolean {
|
|
|
|
|
return state?.sources[createItemId(repository, revision, path)]?.updatePending;
|
2018-09-27 16:32:37 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
export function getFetchSourcesFailure(
|
|
|
|
|
state: any,
|
2018-09-28 11:31:38 +02:00
|
|
|
repository: Repository,
|
|
|
|
|
revision: string,
|
2019-10-20 18:02:52 +02:00
|
|
|
path: string
|
2019-10-19 16:38:07 +02:00
|
|
|
): Error | null | undefined {
|
2019-10-21 10:57:56 +02:00
|
|
|
return getFailure(state, FETCH_SOURCES, createItemId(repository, revision, path));
|
2018-09-27 16:32:37 +02:00
|
|
|
}
|