Skip to content

Commit 708046f

Browse files
authored
Merge branch 'main' into feat/crd-versioning-merged-crds
2 parents cb94a09 + d4936e6 commit 708046f

File tree

19 files changed

+313
-198
lines changed

19 files changed

+313
-198
lines changed

.github/workflows/pr_pre-commit.yaml

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,17 +7,38 @@ on:
77
env:
88
CARGO_TERM_COLOR: always
99
RUST_TOOLCHAIN_VERSION: "1.80.1"
10+
HADOLINT_VERSION: "v1.17.6"
1011

1112
jobs:
1213
pre-commit:
1314
runs-on: ubuntu-latest
1415
steps:
1516
- uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
17+
with:
18+
fetch-depth: 0
1619
- uses: actions/setup-python@82c7e631bb3cdc910f68e0081d67478d79c6982d # v5.1.0
1720
with:
1821
python-version: '3.12'
1922
- uses: dtolnay/rust-toolchain@master
2023
with:
2124
toolchain: ${{ env.RUST_TOOLCHAIN_VERSION }}
2225
components: rustfmt,clippy
26+
- name: Setup Hadolint
27+
shell: bash
28+
run: |
29+
set -euo pipefail
30+
31+
LOCATION_DIR="$HOME/.local/bin"
32+
LOCATION_BIN="$LOCATION_DIR/hadolint"
33+
34+
SYSTEM=$(uname -s)
35+
ARCH=$(uname -m)
36+
37+
mkdir -p "$LOCATION_DIR"
38+
curl -sL -o "${LOCATION_BIN}" "https://github.com/hadolint/hadolint/releases/download/${{ env.HADOLINT_VERSION }}/hadolint-$SYSTEM-$ARCH"
39+
chmod 700 "${LOCATION_BIN}"
40+
41+
echo "$LOCATION_DIR" >> "$GITHUB_PATH"
2342
- uses: pre-commit/action@2c7b3805fd2a0fd8c1884dcaebf91fc102a13ecd # v3.0.1
43+
with:
44+
extra_args: "--from-ref ${{ github.event.pull_request.base.sha }} --to-ref ${{ github.event.pull_request.head.sha }}"

.github/workflows/reviewdog.yaml

Lines changed: 0 additions & 51 deletions
This file was deleted.

.pre-commit-config.yaml

Lines changed: 18 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,10 @@
11
---
2-
# See https://pre-commit.com for more information
3-
# See https://pre-commit.com/hooks.html for more hooks
2+
default_language_version:
3+
node: system
4+
45
repos:
56
- repo: https://github.com/pre-commit/pre-commit-hooks
6-
rev: v4.2.0
7+
rev: 2c9f875913ee60ca25ce70243dc24d5b6415598c # 4.6.0
78
hooks:
89
- id: trailing-whitespace
910
- id: end-of-file-fixer
@@ -12,28 +13,38 @@ repos:
1213
- id: detect-private-key
1314

1415
- repo: https://github.com/doublify/pre-commit-rust
15-
rev: v1.0
16+
rev: eeee35a89e69d5772bdee97db1a6a898467b686e # 1.0
1617
hooks:
1718
- id: fmt
1819
args: ["--all", "--", "--check"]
1920
- id: clippy
2021
args: ["--all-targets", "--", "-D", "warnings"]
2122
- repo: https://github.com/adrienverge/yamllint
22-
rev: v1.26.3
23+
rev: 81e9f98ffd059efe8aa9c1b1a42e5cce61b640c6 # 1.35.1
2324
hooks:
2425
- id: yamllint
2526

2627
- repo: https://github.com/igorshubovych/markdownlint-cli
27-
rev: v0.31.1
28+
rev: f295829140d25717bc79368d3f966fc1f67a824f # 0.41.0
2829
hooks:
2930
- id: markdownlint
3031

3132
- repo: https://github.com/koalaman/shellcheck-precommit
32-
rev: v0.10.0
33+
rev: 2491238703a5d3415bb2b7ff11388bf775372f29 # 0.10.0
3334
hooks:
3435
- id: shellcheck
3536
args: ["--severity=info"]
3637

38+
- repo: https://github.com/rhysd/actionlint
39+
rev: 62dc61a45fc95efe8c800af7a557ab0b9165d63b # 1.7.1
40+
hooks:
41+
- id: actionlint
42+
43+
- repo: https://github.com/hadolint/hadolint
44+
rev: b3555ba9c2bfd9401e79f2f0da68dd1ae38e10c7 # 2.12.0
45+
hooks:
46+
- id: hadolint
47+
3748
- repo: local
3849
hooks:
3950
- id: .scripts/verify-crate-versions

crates/stackable-operator/CHANGELOG.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,9 +15,11 @@ All notable changes to this project will be documented in this file.
1515
### Fixed
1616

1717
- Fix the CRD description of `ClientAuthenticationDetails` to not contain internal Rust doc, but a public CRD description ([#846]).
18+
- `StackableAffinity` fields are no longer erroneously marked as required ([#855]).
1819

1920
[#846]: https://github.com/stackabletech/operator-rs/pull/846
2021
[#851]: https://github.com/stackabletech/operator-rs/pull/851
22+
[#855]: https://github.com/stackabletech/operator-rs/pull/855
2123

2224
## [0.74.0] - 2024-08-22
2325

crates/stackable-operator/src/commons/affinity.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -38,15 +38,15 @@ pub const TOPOLOGY_KEY_HOSTNAME: &str = "kubernetes.io/hostname";
3838
)]
3939
pub struct StackableAffinity {
4040
/// Same as the `spec.affinity.podAffinity` field on the Pod, see the [Kubernetes docs](https://kubernetes.io/docs/concepts/scheduling-eviction/assign-pod-node)
41-
#[fragment_attrs(schemars(schema_with = "raw_optional_object_schema"))]
41+
#[fragment_attrs(serde(default), schemars(schema_with = "raw_optional_object_schema"))]
4242
pub pod_affinity: Option<PodAffinity>,
4343

4444
/// Same as the `spec.affinity.podAntiAffinity` field on the Pod, see the [Kubernetes docs](https://kubernetes.io/docs/concepts/scheduling-eviction/assign-pod-node)
45-
#[fragment_attrs(schemars(schema_with = "raw_optional_object_schema"))]
45+
#[fragment_attrs(serde(default), schemars(schema_with = "raw_optional_object_schema"))]
4646
pub pod_anti_affinity: Option<PodAntiAffinity>,
4747

4848
/// Same as the `spec.affinity.nodeAffinity` field on the Pod, see the [Kubernetes docs](https://kubernetes.io/docs/concepts/scheduling-eviction/assign-pod-node)
49-
#[fragment_attrs(schemars(schema_with = "raw_optional_object_schema"))]
49+
#[fragment_attrs(serde(default), schemars(schema_with = "raw_optional_object_schema"))]
5050
pub node_affinity: Option<NodeAffinity>,
5151

5252
// This schema isn't big, so it can stay

crates/stackable-versioned-macros/src/attrs/common/item.rs

Lines changed: 38 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
use darling::{util::SpannedValue, Error, FromMeta};
22
use k8s_version::Version;
33
use proc_macro2::Span;
4-
use syn::{spanned::Spanned, Attribute, Ident, Path};
4+
use syn::{spanned::Spanned, Attribute, Ident, Path, Type};
55

66
use crate::{
77
attrs::common::ContainerAttributes,
@@ -55,14 +55,14 @@ where
5555
}
5656
}
5757

58-
for rename in &*self.common_attributes().renames {
58+
for change in &*self.common_attributes().changes {
5959
if !container_attrs
6060
.versions
6161
.iter()
62-
.any(|v| v.name == *rename.since)
62+
.any(|v| v.name == *change.since)
6363
{
6464
errors.push(
65-
Error::custom("variant action `renamed` uses version which was not declared via #[versioned(version)]")
65+
Error::custom("variant action `changed` uses version which was not declared via #[versioned(version)]")
6666
.with_span(item)
6767
);
6868
}
@@ -97,15 +97,20 @@ pub(crate) enum ItemType {
9797
Variant,
9898
}
9999

100+
// TODO (@Techassi): Shower thought: Track actions as a Vec of an ActionAttribute
101+
// enum and implement Ord on it. This would allow us to order the items by type
102+
// of action (added < changed < deprecated) as well as sort changed action to
103+
// each other by specified version (which already implements Ord)
104+
100105
/// These attributes are meant to be used in super structs, which add
101106
/// [`Field`](syn::Field) or [`Variant`](syn::Variant) specific attributes via
102107
/// darling's flatten feature. This struct only provides shared attributes.
103108
///
104109
/// ### Shared Item Rules
105110
///
106111
/// - An item can only ever be added once at most. An item not marked as 'added'
107-
/// is part of the container in every version until renamed or deprecated.
108-
/// - An item can be renamed many times. That's why renames are stored in a
112+
/// is part of the container in every version until changed or deprecated.
113+
/// - An item can be changed many times. That's why changes are stored in a
109114
/// [`Vec`].
110115
/// - An item can only be deprecated once. A field or variant not marked as
111116
/// 'deprecated' will be included up until the latest version.
@@ -115,10 +120,10 @@ pub(crate) struct ItemAttributes {
115120
/// only be present at most once.
116121
pub(crate) added: Option<AddedAttributes>,
117122

118-
/// This parses the `renamed` attribute on items (fields or variants). It
123+
/// This parses the `changed` attribute on items (fields or variants). It
119124
/// can be present 0..n times.
120-
#[darling(multiple, rename = "renamed")]
121-
pub(crate) renames: Vec<RenamedAttributes>,
125+
#[darling(multiple, rename = "changed")]
126+
pub(crate) changes: Vec<ChangedAttributes>,
122127

123128
/// This parses the `deprecated` attribute on items (fields or variants). It
124129
/// can only be present at most once.
@@ -138,20 +143,6 @@ impl ItemAttributes {
138143

139144
let mut errors = Error::accumulator();
140145

141-
// TODO (@Techassi): Make the field or variant 'note' optional, because
142-
// in the future, the macro will generate parts of the deprecation note
143-
// automatically. The user-provided note will then be appended to the
144-
// auto-generated one.
145-
146-
if let Some(deprecated) = &self.deprecated {
147-
if deprecated.note.is_empty() {
148-
errors.push(
149-
Error::custom("deprecation note must not be empty")
150-
.with_span(&deprecated.note.span()),
151-
);
152-
}
153-
}
154-
155146
// Semantic validation
156147
errors.handle(self.validate_action_combinations(item_ident, item_type));
157148
errors.handle(self.validate_action_order(item_ident, item_type));
@@ -175,34 +166,34 @@ impl ItemAttributes {
175166
/// cannot be marked as added in a particular version and then marked as
176167
/// deprecated immediately after. Fields and variants must be included for
177168
/// at least one version before being marked deprecated.
178-
/// - `added` and `renamed` using the same version: The same reasoning from
169+
/// - `added` and `changed` using the same version: The same reasoning from
179170
/// above applies here as well. Fields and variants must be included for
180-
/// at least one version before being renamed.
181-
/// - `renamed` and `deprecated` using the same version: Again, the same
171+
/// at least one version before being changed.
172+
/// - `changed` and `deprecated` using the same version: Again, the same
182173
/// rules from above apply here as well.
183174
fn validate_action_combinations(
184175
&self,
185176
item_ident: &Ident,
186177
item_type: &ItemType,
187178
) -> Result<(), Error> {
188-
match (&self.added, &self.renames, &self.deprecated) {
179+
match (&self.added, &self.changes, &self.deprecated) {
189180
(Some(added), _, Some(deprecated)) if *added.since == *deprecated.since => {
190181
Err(Error::custom(format!(
191182
"{item_type} cannot be marked as `added` and `deprecated` in the same version"
192183
))
193184
.with_span(item_ident))
194185
}
195-
(Some(added), renamed, _) if renamed.iter().any(|r| *r.since == *added.since) => {
186+
(Some(added), changed, _) if changed.iter().any(|r| *r.since == *added.since) => {
196187
Err(Error::custom(format!(
197-
"{item_type} cannot be marked as `added` and `renamed` in the same version"
188+
"{item_type} cannot be marked as `added` and `changed` in the same version"
198189
))
199190
.with_span(item_ident))
200191
}
201-
(_, renamed, Some(deprecated))
202-
if renamed.iter().any(|r| *r.since == *deprecated.since) =>
192+
(_, changed, Some(deprecated))
193+
if changed.iter().any(|r| *r.since == *deprecated.since) =>
203194
{
204195
Err(Error::custom(
205-
format!("{item_type} cannot be marked as `deprecated` and `renamed` in the same version"),
196+
format!("{item_type} cannot be marked as `deprecated` and `changed` in the same version"),
206197
)
207198
.with_span(item_ident))
208199
}
@@ -220,7 +211,7 @@ impl ItemAttributes {
220211
/// ensures that these versions are chronologically sound, that means,
221212
/// that the version of the deprecated action must be greater than the
222213
/// version of the added action.
223-
/// - All `renamed` actions must use a greater version than `added` but a
214+
/// - All `changed` actions must use a greater version than `added` but a
224215
/// lesser version than `deprecated`.
225216
fn validate_action_order(&self, item_ident: &Ident, item_type: &ItemType) -> Result<(), Error> {
226217
let added_version = self.added.as_ref().map(|a| *a.since);
@@ -238,14 +229,14 @@ impl ItemAttributes {
238229
}
239230
}
240231

241-
// Now, iterate over all renames and ensure that their versions are
232+
// Now, iterate over all changes and ensure that their versions are
242233
// between the added and deprecated version.
243-
if !self.renames.iter().all(|r| {
234+
if !self.changes.iter().all(|r| {
244235
added_version.map_or(true, |a| a < *r.since)
245236
&& deprecated_version.map_or(true, |d| d > *r.since)
246237
}) {
247238
return Err(Error::custom(
248-
"all renames must use versions higher than `added` and lower than `deprecated`",
239+
"all changes must use versions higher than `added` and lower than `deprecated`",
249240
)
250241
.with_span(item_ident));
251242
}
@@ -320,27 +311,32 @@ pub(crate) struct AddedAttributes {
320311

321312
fn default_default_fn() -> SpannedValue<Path> {
322313
SpannedValue::new(
323-
syn::parse_str("std::default::Default::default").expect("internal error: path must parse"),
314+
syn::parse_str("::std::default::Default::default")
315+
.expect("internal error: path must parse"),
324316
Span::call_site(),
325317
)
326318
}
327319

328-
/// For the renamed() action
320+
/// For the changed() action
329321
///
330322
/// Example usage:
331-
/// - `renamed(since = "...", from = "...")`
323+
/// - `changed(since = "...", from_name = "...")`
324+
/// - `changed(since = "...", from_name = "..." from_type="...")`
332325
#[derive(Clone, Debug, FromMeta)]
333-
pub(crate) struct RenamedAttributes {
326+
pub(crate) struct ChangedAttributes {
334327
pub(crate) since: SpannedValue<Version>,
335-
pub(crate) from: SpannedValue<String>,
328+
pub(crate) from_name: Option<SpannedValue<String>>,
329+
330+
pub(crate) from_type: Option<SpannedValue<Type>>,
336331
}
337332

338333
/// For the deprecated() action
339334
///
340335
/// Example usage:
336+
/// - `deprecated(since = "...")`
341337
/// - `deprecated(since = "...", note = "...")`
342338
#[derive(Clone, Debug, FromMeta)]
343339
pub(crate) struct DeprecatedAttributes {
344340
pub(crate) since: SpannedValue<Version>,
345-
pub(crate) note: SpannedValue<String>,
341+
pub(crate) note: Option<SpannedValue<String>>,
346342
}

crates/stackable-versioned-macros/src/attrs/field.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -50,8 +50,8 @@ impl FieldAttributes {
5050
.ident
5151
.as_ref()
5252
.expect("internal error: field must have an ident");
53-
self.common.validate(ident, &ItemType::Field, &self.attrs)?;
5453

54+
self.common.validate(ident, &ItemType::Field, &self.attrs)?;
5555
Ok(self)
5656
}
5757
}

0 commit comments

Comments
 (0)