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

mendersoftware / gui / 951400782

pending completion
951400782

Pull #3900

gitlab-ci

web-flow
chore: bump @testing-library/jest-dom from 5.16.5 to 5.17.0

Bumps [@testing-library/jest-dom](https://github.com/testing-library/jest-dom) from 5.16.5 to 5.17.0.
- [Release notes](https://github.com/testing-library/jest-dom/releases)
- [Changelog](https://github.com/testing-library/jest-dom/blob/main/CHANGELOG.md)
- [Commits](https://github.com/testing-library/jest-dom/compare/v5.16.5...v5.17.0)

---
updated-dependencies:
- dependency-name: "@testing-library/jest-dom"
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
Pull Request #3900: chore: bump @testing-library/jest-dom from 5.16.5 to 5.17.0

4446 of 6414 branches covered (69.32%)

8342 of 10084 relevant lines covered (82.73%)

186.0 hits per line

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

81.32
/src/js/components/releases/dialogs/artifactinformationform.js
1
// Copyright 2020 Northern.tech AS
2
//
3
//    Licensed under the Apache License, Version 2.0 (the "License");
4
//    you may not use this file except in compliance with the License.
5
//    You may obtain a copy of the License at
6
//
7
//        http://www.apache.org/licenses/LICENSE-2.0
8
//
9
//    Unless required by applicable law or agreed to in writing, software
10
//    distributed under the License is distributed on an "AS IS" BASIS,
11
//    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
//    See the License for the specific language governing permissions and
13
//    limitations under the License.
14
import React, { useEffect, useRef, useState } from 'react';
15
import { Link } from 'react-router-dom';
16

17
import { InfoOutlined as InfoIcon } from '@mui/icons-material';
18
import { FormControl, Input, InputLabel, TextField, Tooltip } from '@mui/material';
19

20
import { TIMEOUTS } from '../../../constants/appConstants';
21
import { onboardingSteps } from '../../../constants/onboardingConstants';
22
import { useDebounce } from '../../../utils/debouncehook';
23
import { getOnboardingComponentFor } from '../../../utils/onboardingmanager';
24
import useWindowSize from '../../../utils/resizehook';
25
import ChipSelect from '../../common/chipselect';
26
import { FileInformation } from './addartifact';
27

28
export const ReleaseTooltip = () => (
7✔
29
  <div style={{ fontSize: 12 }}>
1✔
30
    <p>
31
      If a Release with this name already exists, this new Artifact may be grouped into a Release with other Artifacts of the same name - so long as they are
32
      compatible with different device types
33
    </p>
34
    <Link to="/help/releases-artifacts" style={{ color: '#679ba5' }}>
35
      Learn more about releases
36
    </Link>
37
  </div>
38
);
39

40
const defaultVersion = '1.0.0';
7✔
41

42
export const VersionInformation = ({ creation = {}, onRemove, updateCreation }) => {
7!
43
  const { file, fileSystem: propFs, name, softwareName: propName, softwareVersion: version = '', type } = creation;
2!
44
  const [fileSystem, setFileSystem] = useState(propFs);
2✔
45
  const [softwareName, setSoftwareName] = useState(propName || name.replace('.', '-'));
2✔
46
  const [softwareVersion, setSoftwareVersion] = useState(version || defaultVersion);
2✔
47

48
  useEffect(() => {
2✔
49
    updateCreation({ finalStep: true });
1✔
50
  }, []);
51

52
  useEffect(() => {
2✔
53
    updateCreation({ fileSystem, softwareName, softwareVersion, isValid: fileSystem && softwareName && softwareVersion });
1✔
54
  }, [fileSystem, softwareName, softwareVersion]);
55

56
  return (
2✔
57
    <>
58
      <FileInformation file={file} type={type} onRemove={onRemove} />
59
      <h4>Version information</h4>
60
      <div className="flexbox column">
61
        {[
62
          { key: 'fileSystem', title: 'Software filesystem', setter: setFileSystem, value: fileSystem },
63
          { key: 'softwareName', title: 'Software name', setter: setSoftwareName, value: softwareName },
64
          { key: 'softwareVersion', title: 'Software version', setter: setSoftwareVersion, value: softwareVersion }
65
        ].map(({ key, title, setter, value: currentValue }, index) => (
66
          <TextField autoFocus={!index} fullWidth key={key} label={title} onChange={({ target: { value } }) => setter(value)} value={currentValue} />
6✔
67
        ))}
68
      </div>
69
    </>
70
  );
71
};
72

73
const checkDestinationValidity = destination => (destination.length ? /^(?:\/|[a-z]+:\/\/)/.test(destination) : true);
58✔
74

75
export const ArtifactInformation = ({ advanceOnboarding, creation = {}, deviceTypes = [], onboardingState, onRemove, updateCreation }) => {
7!
76
  const { destination = '', file, name = '', selectedDeviceTypes = [], type } = creation;
36✔
77
  const deviceTypeRef = useRef();
36✔
78
  const releaseNameRef = useRef();
36✔
79
  const destinationRef = useRef();
36✔
80
  // eslint-disable-next-line no-unused-vars
81
  const size = useWindowSize();
36✔
82

83
  const debouncedName = useDebounce(name, TIMEOUTS.debounceDefault);
36✔
84

85
  useEffect(() => {
36✔
86
    const nextDestination = onboardingState.complete ? destination : '/data/www/localhost/htdocs';
2✔
87
    updateCreation({
2✔
88
      destination: nextDestination,
89
      isValid: checkDestinationValidity(nextDestination) && selectedDeviceTypes.length && name,
4!
90
      finalStep: false
91
    });
92
  }, []);
93

94
  useEffect(() => {
36✔
95
    if (debouncedName.length) {
2✔
96
      advanceOnboarding(onboardingSteps.UPLOAD_NEW_ARTIFACT_DIALOG_RELEASE_NAME);
1✔
97
    }
98
  }, [debouncedName]);
99

100
  const onSelectionChanged = ({ currentValue = '', selection = [] }) => {
36!
101
    if (currentValue.length > 3) {
3!
102
      advanceOnboarding(onboardingSteps.UPLOAD_NEW_ARTIFACT_DIALOG_DEVICE_TYPE);
×
103
    }
104
    updateCreation({
3✔
105
      customDeviceTypes: currentValue,
106
      isValid: (currentValue.length || selection.length) && name && destination,
8✔
107
      selectedDeviceTypes: selection
108
    });
109
  };
110

111
  const onDestinationChange = ({ target: { value } }) =>
36✔
112
    updateCreation({ destination: value, isValid: checkDestinationValidity(value) && selectedDeviceTypes.length && name });
20!
113

114
  let onboardingComponent = null;
36✔
115
  let extraOnboardingComponent = null;
36✔
116
  if (!onboardingState.complete && deviceTypeRef.current && releaseNameRef.current) {
36!
117
    const deviceTypeAnchor = {
×
118
      left: deviceTypeRef.current.parentElement.parentElement.offsetLeft + deviceTypeRef.current.parentElement.parentElement.clientWidth,
119
      top:
120
        deviceTypeRef.current.parentElement.parentElement.offsetTop +
121
        deviceTypeRef.current.parentElement.offsetTop +
122
        deviceTypeRef.current.parentElement.parentElement.clientHeight / 2
123
    };
124
    const releaseNameAnchor = {
×
125
      left: releaseNameRef.current.parentElement.parentElement.offsetLeft + releaseNameRef.current.parentElement.parentElement.clientWidth,
126
      top:
127
        releaseNameRef.current.parentElement.parentElement.offsetTop + releaseNameRef.current.parentElement.offsetTop + releaseNameRef.current.clientHeight / 2
128
    };
129
    const destinationAnchor = {
×
130
      left: destinationRef.current.parentElement.parentElement.offsetLeft + destinationRef.current.parentElement.parentElement.clientWidth,
131
      top: destinationRef.current.parentElement.parentElement.offsetTop + destinationRef.current.parentElement.parentElement.clientHeight / 2
132
    };
133
    extraOnboardingComponent = getOnboardingComponentFor(
×
134
      onboardingSteps.UPLOAD_NEW_ARTIFACT_DIALOG_DESTINATION,
135
      onboardingState,
136
      { anchor: destinationAnchor, place: 'right' },
137
      extraOnboardingComponent
138
    );
139
    onboardingComponent = getOnboardingComponentFor(
×
140
      onboardingSteps.UPLOAD_NEW_ARTIFACT_DIALOG_RELEASE_NAME,
141
      onboardingState,
142
      { anchor: releaseNameAnchor, place: 'right' },
143
      onboardingComponent
144
    );
145
    onboardingComponent = getOnboardingComponentFor(
×
146
      onboardingSteps.UPLOAD_NEW_ARTIFACT_DIALOG_DEVICE_TYPE,
147
      onboardingState,
148
      { anchor: deviceTypeAnchor, place: 'right' },
149
      onboardingComponent
150
    );
151
  }
152

153
  const isValidDestination = checkDestinationValidity(destination);
36✔
154
  return (
36✔
155
    <div className="flexbox column">
156
      <FileInformation file={file} type={type} onRemove={onRemove} />
157
      <TextField
158
        autoFocus={true}
159
        error={!isValidDestination}
160
        fullWidth
161
        helperText={!isValidDestination && <div className="warning">Destination has to be an absolute path</div>}
45✔
162
        inputProps={{ style: { marginTop: 16 } }}
163
        InputLabelProps={{ shrink: true }}
164
        label="Destination directory where the file will be installed on your devices"
165
        onChange={onDestinationChange}
166
        placeholder="Example: /opt/installed-by-single-file"
167
        inputRef={destinationRef}
168
        value={destination}
169
      />
170
      <h4>Artifact information</h4>
171
      <FormControl>
172
        <InputLabel htmlFor="release-name" style={{ alignItems: 'center', display: 'flex' }}>
173
          Release name
174
          <Tooltip key="release-name-tip" title={<ReleaseTooltip />} placement="bottom" arrow leaveDelay={300}>
175
            <InfoIcon fontSize="small" classes={{ root: 'margin-left-small' }} />
176
          </Tooltip>
177
        </InputLabel>
178
        <Input
179
          defaultValue={name}
180
          className="release-name-input"
181
          id="release-name"
182
          placeholder="A descriptive name for the software"
183
          onChange={e => updateCreation({ name: e.target.value })}
12✔
184
          inputRef={releaseNameRef}
185
        />
186
      </FormControl>
187
      <ChipSelect
188
        id="compatible-device-type-selection"
189
        inputRef={deviceTypeRef}
190
        label="Device types compatible"
191
        onChange={onSelectionChanged}
192
        placeholder="Enter all device types this software is compatible with"
193
        selection={selectedDeviceTypes}
194
        options={deviceTypes}
195
      />
196
      {onboardingComponent}
197
      {extraOnboardingComponent}
198
    </div>
199
  );
200
};
201

202
const steps = [ArtifactInformation, VersionInformation];
7✔
203

204
export const ArtifactInformationForm = ({ activeStep, ...remainder }) => {
7✔
205
  const Component = steps[activeStep];
38✔
206
  return <Component {...remainder} />;
38✔
207
};
208

209
export default ArtifactInformationForm;
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

© 2025 Coveralls, Inc