• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

gripmock / grpctestify-rust / 24287400320

11 Apr 2026 05:09PM UTC coverage: 75.314% (+1.2%) from 74.127%
24287400320

Pull #32

github

web-flow
Merge 772555062 into 65f4b1f6e
Pull Request #32: multi requests

1718 of 2382 new or added lines in 17 files covered. (72.12%)

85 existing lines in 6 files now uncovered.

15776 of 20947 relevant lines covered (75.31%)

2047.09 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

98.53
/src/plugins/empty.rs
1
use anyhow::Result;
2
use serde_json::Value;
3

4
use crate::assert::engine::AssertionResult;
5
use crate::plugins::{
6
    Plugin, PluginContext, PluginPurity, PluginResult, PluginReturnKind, PluginSignature,
7
};
8

9
pub struct EmptyPlugin;
10

11
impl Plugin for EmptyPlugin {
12
    fn name(&self) -> &str {
320✔
13
        "empty"
320✔
14
    }
320✔
15

16
    fn description(&self) -> &str {
4✔
17
        "Checks whether a value is empty (null, empty string, empty array, empty object)"
4✔
18
    }
4✔
19

20
    fn signature(&self) -> PluginSignature {
66✔
21
        PluginSignature {
66✔
22
            return_kind: PluginReturnKind::Boolean,
66✔
23
            purity: PluginPurity::Pure,
66✔
24
            deterministic: true,
66✔
25
            idempotent: true,
66✔
26
            safe_for_rewrite: true,
66✔
27
            arg_names: &["value"],
66✔
28
        }
66✔
29
    }
66✔
30

31
    fn execute(&self, args: &[Value], _context: &PluginContext) -> Result<PluginResult> {
12✔
32
        if args.len() != 1 {
12✔
33
            return Ok(PluginResult::Assertion(AssertionResult::Error(
2✔
34
                "empty: expects exactly 1 argument".to_string(),
2✔
35
            )));
2✔
36
        }
10✔
37

38
        let is_empty = match &args[0] {
10✔
39
            Value::Null => true,
1✔
40
            Value::String(s) => s.is_empty(),
2✔
41
            Value::Array(values) => values.is_empty(),
3✔
42
            Value::Object(map) => map.is_empty(),
2✔
43
            _ => false,
2✔
44
        };
45

46
        Ok(PluginResult::Value(Value::Bool(is_empty)))
10✔
47
    }
12✔
48
}
49

50
#[cfg(test)]
51
mod tests {
52
    use super::*;
53

54
    fn create_context() -> PluginContext<'static> {
11✔
55
        PluginContext::new(&Value::Null)
11✔
56
    }
11✔
57

58
    #[test]
59
    fn test_empty_plugin_name() {
1✔
60
        let plugin = EmptyPlugin;
1✔
61
        assert_eq!(plugin.name(), "empty");
1✔
62
    }
1✔
63

64
    #[test]
65
    fn test_empty_plugin_empty_string() {
1✔
66
        let plugin = EmptyPlugin;
1✔
67
        let context = create_context();
1✔
68
        let result = plugin
1✔
69
            .execute(&[Value::String(String::new())], &context)
1✔
70
            .unwrap();
1✔
71
        assert!(matches!(result, PluginResult::Value(Value::Bool(true))));
1✔
72
    }
1✔
73

74
    #[test]
75
    fn test_empty_plugin_non_empty_string() {
1✔
76
        let plugin = EmptyPlugin;
1✔
77
        let context = create_context();
1✔
78
        let result = plugin
1✔
79
            .execute(&[Value::String("hello".to_string())], &context)
1✔
80
            .unwrap();
1✔
81
        assert!(matches!(result, PluginResult::Value(Value::Bool(false))));
1✔
82
    }
1✔
83

84
    #[test]
85
    fn test_empty_plugin_empty_array() {
1✔
86
        let plugin = EmptyPlugin;
1✔
87
        let context = create_context();
1✔
88
        let result = plugin.execute(&[Value::Array(vec![])], &context).unwrap();
1✔
89
        assert!(matches!(result, PluginResult::Value(Value::Bool(true))));
1✔
90
    }
1✔
91

92
    #[test]
93
    fn test_empty_plugin_null() {
1✔
94
        let plugin = EmptyPlugin;
1✔
95
        let context = create_context();
1✔
96
        let result = plugin.execute(&[Value::Null], &context).unwrap();
1✔
97
        assert!(matches!(result, PluginResult::Value(Value::Bool(true))));
1✔
98
    }
1✔
99

100
    #[test]
101
    fn test_empty_plugin_empty_object() {
1✔
102
        let plugin = EmptyPlugin;
1✔
103
        let context = create_context();
1✔
104
        let result = plugin
1✔
105
            .execute(&[Value::Object(serde_json::Map::new())], &context)
1✔
106
            .unwrap();
1✔
107
        assert!(matches!(result, PluginResult::Value(Value::Bool(true))));
1✔
108
    }
1✔
109

110
    #[test]
111
    fn test_empty_plugin_non_empty_object() {
1✔
112
        let plugin = EmptyPlugin;
1✔
113
        let context = create_context();
1✔
114
        let obj = serde_json::json!({"key": "value"});
1✔
115
        let result = plugin.execute(&[obj], &context).unwrap();
1✔
116
        assert!(matches!(result, PluginResult::Value(Value::Bool(false))));
1✔
117
    }
1✔
118

119
    #[test]
120
    fn test_empty_plugin_non_empty_array() {
1✔
121
        let plugin = EmptyPlugin;
1✔
122
        let context = create_context();
1✔
123
        let arr = Value::Array(vec![Value::Number(serde_json::Number::from(1))]);
1✔
124
        let result = plugin.execute(&[arr], &context).unwrap();
1✔
125
        assert!(matches!(result, PluginResult::Value(Value::Bool(false))));
1✔
126
    }
1✔
127

128
    #[test]
129
    fn test_empty_plugin_number_type() {
1✔
130
        let plugin = EmptyPlugin;
1✔
131
        let context = create_context();
1✔
132
        let result = plugin
1✔
133
            .execute(&[Value::Number(serde_json::Number::from(42))], &context)
1✔
134
            .unwrap();
1✔
135
        assert!(matches!(result, PluginResult::Value(Value::Bool(false))));
1✔
136
    }
1✔
137

138
    #[test]
139
    fn test_empty_plugin_bool_type() {
1✔
140
        let plugin = EmptyPlugin;
1✔
141
        let context = create_context();
1✔
142
        let result = plugin.execute(&[Value::Bool(true)], &context).unwrap();
1✔
143
        assert!(matches!(result, PluginResult::Value(Value::Bool(false))));
1✔
144
    }
1✔
145

146
    #[test]
147
    fn test_empty_plugin_no_args() {
1✔
148
        let plugin = EmptyPlugin;
1✔
149
        let context = create_context();
1✔
150
        let result = plugin.execute(&[], &context).unwrap();
1✔
151
        if let PluginResult::Assertion(AssertionResult::Error(msg)) = result {
1✔
152
            assert!(msg.contains("1 argument"));
1✔
153
        } else {
NEW
154
            panic!("Expected Error assertion result");
×
155
        }
156
    }
1✔
157

158
    #[test]
159
    fn test_empty_plugin_too_many_args() {
1✔
160
        let plugin = EmptyPlugin;
1✔
161
        let context = create_context();
1✔
162
        let result = plugin
1✔
163
            .execute(
1✔
164
                &[
1✔
165
                    Value::String("a".to_string()),
1✔
166
                    Value::String("b".to_string()),
1✔
167
                ],
1✔
168
                &context,
1✔
169
            )
170
            .unwrap();
1✔
171
        if let PluginResult::Assertion(AssertionResult::Error(msg)) = result {
1✔
172
            assert!(msg.contains("1 argument"));
1✔
173
        } else {
NEW
174
            panic!("Expected Error assertion result");
×
175
        }
176
    }
1✔
177

178
    #[test]
179
    fn test_empty_plugin_description() {
1✔
180
        let plugin = EmptyPlugin;
1✔
181
        assert!(plugin.description().contains("empty"));
1✔
182
    }
1✔
183

184
    #[test]
185
    fn test_empty_plugin_signature() {
1✔
186
        let plugin = EmptyPlugin;
1✔
187
        let sig = plugin.signature();
1✔
188
        assert_eq!(sig.arg_names, &["value"]);
1✔
189
        assert!(sig.safe_for_rewrite);
1✔
190
        assert!(sig.idempotent);
1✔
191
        assert!(sig.deterministic);
1✔
192
    }
1✔
193
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc