aboutsummaryrefslogtreecommitdiff
path: root/src/lib/core
diff options
context:
space:
mode:
authorJoseph Hunkeler <jhunkeler@users.noreply.github.com>2026-07-07 12:08:23 -0400
committerGitHub <noreply@github.com>2026-07-07 12:08:23 -0400
commitddb7178e8a22ad8ba30f2cf65205814eafbb2bf8 (patch)
tree7e9a6ced76ac3086b865c1cb7e7d4c106c0d4dc1 /src/lib/core
parent6171233840094edfe3b60be546b15664fe5fa3ea (diff)
parent1ed03ee259024f09a7fca378e6e483d93eb118e5 (diff)
downloadstasis-1.9.0.tar.gz
Merge pull request #152 from jhunkeler/force-repeatable1.9.0
Implement --force-repeatable option
Diffstat (limited to 'src/lib/core')
-rw-r--r--src/lib/core/include/core.h1
-rw-r--r--src/lib/core/include/utils.h11
-rw-r--r--src/lib/core/utils.c58
3 files changed, 66 insertions, 4 deletions
diff --git a/src/lib/core/include/core.h b/src/lib/core/include/core.h
index ed523be..e3e54c9 100644
--- a/src/lib/core/include/core.h
+++ b/src/lib/core/include/core.h
@@ -57,6 +57,7 @@ struct STASIS_GLOBAL {
int task_timeout; ///!< Time in seconds before task is terminated
char *wheel_builder; ///!< Backend to build wheels (build, cibuildwheel, manylinux)
char *wheel_builder_manylinux_image; ///!< Image to use for a Manylinux build
+ bool force_repeatable; ///!< Reduces surface area of random changes between builds
struct {
char *tox_posargs;
char *conda_reactivate;
diff --git a/src/lib/core/include/utils.h b/src/lib/core/include/utils.h
index e75995a..f9937b5 100644
--- a/src/lib/core/include/utils.h
+++ b/src/lib/core/include/utils.h
@@ -180,6 +180,15 @@ char *git_describe(const char *path);
char *git_rev_parse(const char *path, char *args);
/**
+ * Check if a file in a git repository is flagged with 'assumed-unchanged'.
+ *
+ * @param filename path to file
+ * @return -1 on error, 0 if
+ */
+
+int is_git_assumed_unchanged(char *filename);
+
+/**
* Helper function to initialize simple STASIS internal path strings
*
* ```c
@@ -473,7 +482,7 @@ int in_ascii_range(char c, char lower, char upper);
#define GIT_HASH_LEN 40
int is_git_sha(char const *hash);
-int check_python_package_dependencies(const char *srcdir);
+int check_python_package_dependencies(const char *srcdir, struct StrList **out_files, struct StrList **out_matches);
void seconds_to_human_readable(int v, char *result, size_t maxlen);
diff --git a/src/lib/core/utils.c b/src/lib/core/utils.c
index 462604d..eee8bec 100644
--- a/src/lib/core/utils.c
+++ b/src/lib/core/utils.c
@@ -1078,7 +1078,7 @@ static int read_vcs_records(const size_t line, char **data) {
// no match, continue
return 1;
}
-int check_python_package_dependencies(const char *srcdir) {
+int check_python_package_dependencies(const char *srcdir, struct StrList **out_files, struct StrList **out_matches) {
const char *configs[] = {
"pyproject.toml",
"setup.cfg",
@@ -1103,12 +1103,23 @@ int check_python_package_dependencies(const char *srcdir) {
}
const size_t count = strlist_count(data);
if (count) {
- printf("\nERROR: VCS requirement(s) detected in %s:\n", configfile);
+ if (out_files) {
+ strlist_append(out_files, (char *) configs[i]);
+ }
for (size_t j = 0; j < count; j++) {
char *record = strlist_item(data, j);
lstrip(record);
strip(record);
- printf("[%zu] %s\n", j, record);
+ char *match = substring_between(record, "\"\"");
+ if (!match) {
+ SYSERROR("unable to allocate bytes for matched sub-string");
+ guard_strlist_free(&data);
+ return -1;
+ }
+ if (out_matches) {
+ strlist_append(out_matches, match);
+ }
+ guard_free(match);
}
guard_strlist_free(&data);
return 1;
@@ -1306,3 +1317,44 @@ int is_file_compressed(const char *filename) {
return 0;
}
+/**
+ * Check if a file in a git repository is flagged as 'assumed-unchanged'.
+ *
+ * @param filename path to file
+ * @return -1 on error, 0 if
+ */
+int is_git_assumed_unchanged(char *filename) {
+ char *cmd = NULL;
+ if (asprintf(&cmd, "git ls-files -v -- '%s'", filename) < 0) {
+ SYSERROR("unable to allocate memory for file path");
+ return -1;
+ }
+ int status = 0;
+ char *output = shell_output(cmd, &status);
+ if (!output) {
+ SYSERROR("unable to allocate memory for git ls-files output");
+ guard_free(cmd);
+ return -1;
+ }
+ if (status) {
+ SYSERROR("git ls-files command failed to run");
+ guard_free(cmd);
+ guard_free(output);
+ return -1;
+ }
+ guard_free(cmd);
+
+ char *token = NULL;
+ char *data = output;
+ while ((token = strsep(&data, LINE_SEP)) != NULL) {
+ char *bname = path_basename(filename);
+ // "h" indicates assume-unchanged has been applied (see: man git-ls-files and option '-v')
+ if (strstr(token, bname) && startswith(token, "h")) {
+ guard_free(output);
+ return 1;
+ }
+ }
+
+ guard_free(output);
+ return 0;
+}