@forsakringskassan/vue-lib-template 1.0.2 → 1.0.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/files/_agents/skills/documentation/SKILL.md +118 -0
- package/files/_agents/skills/documentation/template.md +33 -0
- package/files/_vscode/extensions.json +10 -0
- package/files/_vscode/settings.json +13 -0
- package/files/api-extractor.lib.json +1 -1
- package/files/api-extractor.selectors.json +1 -1
- package/files/cypress/support/component.ts +37 -2
- package/files/cypress/tsconfig.json +2 -1
- package/files/cypress/types/mocha.d.ts +15 -0
- package/files/docs/package.json +2 -2
- package/files/package.json +16 -37
- package/files/renovate.json +1 -3
- package/hooks/install.mjs +15 -0
- package/package.json +28 -10
- /package/files/etc/{vue-lib-template.api.md → lib.api.md} +0 -0
- /package/files/etc/{vue-lib-template-selectors.api.md → selectors.api.md} +0 -0
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: documentation
|
|
3
|
+
description: Write component documentation.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
Documentation in this repository uses [`@forsakringskassan/docs-generator`](https://forsakringskassan.github.io/docs-generator/latest/) (source: https://github.com/forsakringskassan/docs-generator) to generate a documentation site.
|
|
7
|
+
When in doubt, you may consult the linked site to find the documentation of the tool itself.
|
|
8
|
+
|
|
9
|
+
The `docs/` folder holds:
|
|
10
|
+
|
|
11
|
+
- Build scripts (`docs/build.mts`).
|
|
12
|
+
- Site sourcecode (`docs/src/`).
|
|
13
|
+
- Markdown content.
|
|
14
|
+
|
|
15
|
+
After building the contents are available in the `public/` folder.
|
|
16
|
+
Files are 1:1 mapped between the `docs/` and `public/` folder, e.g. `docs/components/foo.md` generates `public/components/foo.html`.
|
|
17
|
+
|
|
18
|
+
## Commands
|
|
19
|
+
|
|
20
|
+
- `npm run -w docs build` - Build documentation.
|
|
21
|
+
- `npm start -w docs` - Start a webserver hosting the documentation at `http://localhost:8080/`.
|
|
22
|
+
|
|
23
|
+
If available, use the Chrome Devtools MCP server to access the site.
|
|
24
|
+
|
|
25
|
+
## Writing documentation
|
|
26
|
+
|
|
27
|
+
Component documentation is written in Markdown format (`.md`) in the `docs/components` folder.
|
|
28
|
+
Each component should have an associated Markdown file with the same name as the component (e.g. `AwesomeComponent.vue` should have the `AwesomeComponent.md` file).
|
|
29
|
+
Unless instructed otherwise, use Swedish language when writing content.
|
|
30
|
+
Markdown files should be formatted with Prettier.
|
|
31
|
+
|
|
32
|
+
Use [`template.md`](./template.md) as a template.
|
|
33
|
+
|
|
34
|
+
The Frontmatter block contains the properties:
|
|
35
|
+
|
|
36
|
+
- `title` - the document title, should be a human readable name of the component
|
|
37
|
+
- `status` - component status, use `Experimental`, `Draft` or `Produktionsklar` only. If unsure which one to use, ask for clarification.
|
|
38
|
+
- `layout` - must be set to `component` for component documentation.
|
|
39
|
+
- `component` - name of the Vue component.
|
|
40
|
+
|
|
41
|
+
It may optionally contain these properties:
|
|
42
|
+
|
|
43
|
+
- `short-title` - a shorter `title` used in the navigation, use this when the regular title is long and/or causes the layout to overflow.
|
|
44
|
+
- `search.terms` - an array of optional keywords the search function should index for this page.
|
|
45
|
+
|
|
46
|
+
There should not be an h1 heading in the document, it is injected automatically from the `title` property.
|
|
47
|
+
After the preamble and example, start using h2 headings.
|
|
48
|
+
|
|
49
|
+
Remove sections not relevant to the component, e.g. if it does not have translatable text skip the "Textnycklar" section.
|
|
50
|
+
|
|
51
|
+
## Examples
|
|
52
|
+
|
|
53
|
+
Each component documentation should have an example after the preamble.
|
|
54
|
+
Prefer "live examples" over regular runnable examples.
|
|
55
|
+
|
|
56
|
+
If the component has a "live example", a file with the `LiveExample.vue` suffix, include it with an `import` code fence:
|
|
57
|
+
|
|
58
|
+
````md
|
|
59
|
+
```import live-example
|
|
60
|
+
FilenameLiveExample.vue
|
|
61
|
+
```
|
|
62
|
+
````
|
|
63
|
+
|
|
64
|
+
If a live example is not present but the component instead have regular example files, files with the `Example.vue` suffix, include it with an `import` code fence:
|
|
65
|
+
|
|
66
|
+
````md
|
|
67
|
+
```import
|
|
68
|
+
FilenameExample.vue
|
|
69
|
+
```
|
|
70
|
+
````
|
|
71
|
+
|
|
72
|
+
If there are no examples, ask for clarification what to do.
|
|
73
|
+
If multiple examples (live examples or regular), ask for clarification which file should be included.
|
|
74
|
+
|
|
75
|
+
## API
|
|
76
|
+
|
|
77
|
+
Each component should include the API section and the special `api` container:
|
|
78
|
+
|
|
79
|
+
```md
|
|
80
|
+
::: api
|
|
81
|
+
vue:ComponentName
|
|
82
|
+
:::
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
This will insert the generated API documentation for the Vue component with the matching name.
|
|
86
|
+
|
|
87
|
+
## Grouping related components
|
|
88
|
+
|
|
89
|
+
A set of related components may optionally be grouped in a subfolder.
|
|
90
|
+
|
|
91
|
+
```
|
|
92
|
+
example-group
|
|
93
|
+
├── AnotherComponent.md
|
|
94
|
+
├── AwesomeComponent.md
|
|
95
|
+
└── index.json
|
|
96
|
+
```
|
|
97
|
+
|
|
98
|
+
Each group must have an `index.json` containing the group title (human readable):
|
|
99
|
+
|
|
100
|
+
```json
|
|
101
|
+
{
|
|
102
|
+
"title": "Example group"
|
|
103
|
+
}
|
|
104
|
+
```
|
|
105
|
+
|
|
106
|
+
## Moving files
|
|
107
|
+
|
|
108
|
+
If a Markdown file is being moved, the Frontmatter block of the file must add the `redirect_from` property:
|
|
109
|
+
|
|
110
|
+
```
|
|
111
|
+
---
|
|
112
|
+
title: Fantastisk komponent
|
|
113
|
+
redirect_from:
|
|
114
|
+
- old/old-page.html
|
|
115
|
+
```
|
|
116
|
+
|
|
117
|
+
The property is an array of old paths (relative to the `public/` folder).
|
|
118
|
+
If the property already exists, add more entries.
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
---
|
|
2
|
+
title: Komponentens namn
|
|
3
|
+
status: Draft
|
|
4
|
+
layout: component
|
|
5
|
+
component: ComponentName
|
|
6
|
+
---
|
|
7
|
+
|
|
8
|
+
A short preamble describing the what the component is and is used for.
|
|
9
|
+
|
|
10
|
+
```import
|
|
11
|
+
ComponentNameExample.vue
|
|
12
|
+
```
|
|
13
|
+
|
|
14
|
+
## Tänk på att
|
|
15
|
+
|
|
16
|
+
- Some bullet points with remarks
|
|
17
|
+
- Do's and don'ts
|
|
18
|
+
|
|
19
|
+
## Copy
|
|
20
|
+
|
|
21
|
+
- Some bullets points with guidelines about writing copy
|
|
22
|
+
|
|
23
|
+
## Textnycklar
|
|
24
|
+
|
|
25
|
+
::: api
|
|
26
|
+
translation:ComponentName
|
|
27
|
+
:::
|
|
28
|
+
|
|
29
|
+
## API
|
|
30
|
+
|
|
31
|
+
::: api
|
|
32
|
+
vue:ComponentName
|
|
33
|
+
:::
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
{
|
|
2
|
+
"css.validate": false,
|
|
3
|
+
"less.validate": false,
|
|
4
|
+
"scss.validate": false,
|
|
5
|
+
"eslint.enable": true,
|
|
6
|
+
"prettier.requireConfig": true,
|
|
7
|
+
"editor.renderWhitespace": "boundary",
|
|
8
|
+
"editor.defaultFormatter": "esbenp.prettier-vscode",
|
|
9
|
+
"explorer.fileNesting.enabled": true,
|
|
10
|
+
"explorer.fileNesting.patterns": {
|
|
11
|
+
"tsconfig.json": "tsconfig.*"
|
|
12
|
+
}
|
|
13
|
+
}
|
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
"tsconfigFilePath": "<projectFolder>/tsconfig.selectors.json"
|
|
9
9
|
},
|
|
10
10
|
"apiReport": {
|
|
11
|
-
"reportFileName": "
|
|
11
|
+
"reportFileName": "selectors.api.md"
|
|
12
12
|
},
|
|
13
13
|
"dtsRollup": {
|
|
14
14
|
"publicTrimmedFilePath": "<projectFolder>/dist/types/selectors.d.ts"
|
|
@@ -33,8 +33,12 @@ Cypress.Commands.add("mount", (component, options = {}) => {
|
|
|
33
33
|
setRunningContext(app);
|
|
34
34
|
|
|
35
35
|
/* handle warnings as errors */
|
|
36
|
-
app.config.warnHandler = (msg
|
|
37
|
-
|
|
36
|
+
app.config.warnHandler = (msg) => {
|
|
37
|
+
const mochaRunner = Cypress.mocha.getRunner();
|
|
38
|
+
const body = mochaRunner.test?.body ?? "";
|
|
39
|
+
if (!body.includes("<expectedException")) {
|
|
40
|
+
cy.wrap(`Vue warning: ${msg}`).should("be.empty");
|
|
41
|
+
}
|
|
38
42
|
};
|
|
39
43
|
},
|
|
40
44
|
});
|
|
@@ -42,4 +46,35 @@ Cypress.Commands.add("mount", (component, options = {}) => {
|
|
|
42
46
|
return mount(component, options);
|
|
43
47
|
});
|
|
44
48
|
|
|
49
|
+
const uncaughtErrors: string[] = [];
|
|
50
|
+
|
|
51
|
+
Cypress.on("uncaught:exception", (err) => {
|
|
52
|
+
const mochaRunner = Cypress.mocha.getRunner();
|
|
53
|
+
const currentTest = mochaRunner.test;
|
|
54
|
+
|
|
55
|
+
const body = currentTest?.body ?? "";
|
|
56
|
+
const match = body.match(
|
|
57
|
+
/<expectedException>([\s\S]*?)<\/expectedException>|<expectedException\s*\/>/i,
|
|
58
|
+
);
|
|
59
|
+
const message = match ? match[1].trim() : null;
|
|
60
|
+
if (message?.length === 0 || (message && err.message.includes(message))) {
|
|
61
|
+
return false;
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
const testName =
|
|
65
|
+
currentTest?.fullTitle() ?? currentTest?.title ?? "<unknown>";
|
|
66
|
+
|
|
67
|
+
uncaughtErrors.push(testName);
|
|
68
|
+
|
|
69
|
+
return true;
|
|
70
|
+
});
|
|
71
|
+
|
|
72
|
+
after(() => {
|
|
73
|
+
if (uncaughtErrors.length > 0) {
|
|
74
|
+
throw new Error(
|
|
75
|
+
`⚠️ Suite failed because an uncaught exception occurred earlier in: ${uncaughtErrors}`,
|
|
76
|
+
);
|
|
77
|
+
}
|
|
78
|
+
});
|
|
79
|
+
|
|
45
80
|
injectSpritesheet();
|
package/files/docs/package.json
CHANGED
|
@@ -8,10 +8,10 @@
|
|
|
8
8
|
},
|
|
9
9
|
"devDependencies": {
|
|
10
10
|
"@fkui/vue": "6.55.0",
|
|
11
|
-
"@forsakringskassan/docs-generator": "3.6.
|
|
11
|
+
"@forsakringskassan/docs-generator": "3.6.2",
|
|
12
12
|
"@tsconfig/node24": "24.0.5",
|
|
13
13
|
"@tsconfig/recommended": "1.0.13",
|
|
14
14
|
"http-server": "14.1.1",
|
|
15
|
-
"vue": "3.5.
|
|
15
|
+
"vue": "3.5.42"
|
|
16
16
|
}
|
|
17
17
|
}
|
package/files/package.json
CHANGED
|
@@ -1,23 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "${name}",
|
|
3
3
|
"version": "${version}",
|
|
4
|
-
"description": "${description}",
|
|
5
|
-
"keywords": [
|
|
6
|
-
"template",
|
|
7
|
-
"vue",
|
|
8
|
-
"cloneman",
|
|
9
|
-
"library"
|
|
10
|
-
],
|
|
11
|
-
"homepage": "https://github.com/Forsakringskassan/vue-lib-template#readme",
|
|
12
|
-
"bugs": {
|
|
13
|
-
"url": "https://github.com/Forsakringskassan/vue-lib-template/issues"
|
|
14
|
-
},
|
|
15
|
-
"repository": {
|
|
16
|
-
"type": "git",
|
|
17
|
-
"url": "git+https://github.com/Forsakringskassan/vue-lib-template.git"
|
|
18
|
-
},
|
|
19
|
-
"license": "MIT",
|
|
20
|
-
"author": "Försäkringskassan",
|
|
21
4
|
"exports": {
|
|
22
5
|
".": {
|
|
23
6
|
"types": "./dist/types/index.d.ts",
|
|
@@ -93,29 +76,29 @@
|
|
|
93
76
|
"@forsakringskassan/commitlint-config": "4.2.8",
|
|
94
77
|
"@forsakringskassan/cypress-axe": "5.1.5",
|
|
95
78
|
"@forsakringskassan/cypress-visual-regression": "5.1.0",
|
|
96
|
-
"@forsakringskassan/docs-generator": "3.6.
|
|
79
|
+
"@forsakringskassan/docs-generator": "3.6.2",
|
|
97
80
|
"@forsakringskassan/docs-live-example": "3.0.1",
|
|
98
|
-
"@forsakringskassan/eslint-config": "15.
|
|
99
|
-
"@forsakringskassan/eslint-config-cli": "15.
|
|
100
|
-
"@forsakringskassan/eslint-config-cypress": "15.
|
|
101
|
-
"@forsakringskassan/eslint-config-jest": "15.
|
|
102
|
-
"@forsakringskassan/eslint-config-typescript": "15.
|
|
103
|
-
"@forsakringskassan/eslint-config-typescript-typeinfo": "15.
|
|
104
|
-
"@forsakringskassan/eslint-config-vitest": "15.
|
|
105
|
-
"@forsakringskassan/eslint-config-vue": "15.
|
|
81
|
+
"@forsakringskassan/eslint-config": "15.9.0",
|
|
82
|
+
"@forsakringskassan/eslint-config-cli": "15.9.0",
|
|
83
|
+
"@forsakringskassan/eslint-config-cypress": "15.9.0",
|
|
84
|
+
"@forsakringskassan/eslint-config-jest": "15.9.0",
|
|
85
|
+
"@forsakringskassan/eslint-config-typescript": "15.9.0",
|
|
86
|
+
"@forsakringskassan/eslint-config-typescript-typeinfo": "15.9.0",
|
|
87
|
+
"@forsakringskassan/eslint-config-vitest": "15.9.0",
|
|
88
|
+
"@forsakringskassan/eslint-config-vue": "15.9.0",
|
|
106
89
|
"@forsakringskassan/prettier-config": "3.7.8",
|
|
107
90
|
"@forsakringskassan/stylelint-config": "3.4.5",
|
|
108
|
-
"@forsakringskassan/vite-lib-config": "5.10.
|
|
91
|
+
"@forsakringskassan/vite-lib-config": "5.10.2",
|
|
109
92
|
"@forsakringskassan/vitest-config-jsdom": "2.7.0",
|
|
110
|
-
"@forsakringskassan/vue-lib-template": "1.0.
|
|
93
|
+
"@forsakringskassan/vue-lib-template": "1.0.4",
|
|
111
94
|
"@html-validate/release-scripts": "7.6.8",
|
|
112
95
|
"@types/node": "24.13.3",
|
|
113
96
|
"@typescript/native": "npm:typescript@7.0.2",
|
|
114
|
-
"@vue/server-renderer": "3.5.
|
|
115
|
-
"@vue/test-utils": "2.
|
|
116
|
-
"cloneman": "1.
|
|
97
|
+
"@vue/server-renderer": "3.5.42",
|
|
98
|
+
"@vue/test-utils": "2.5.0",
|
|
99
|
+
"cloneman": "1.22.0",
|
|
117
100
|
"core-js": "3.50.0",
|
|
118
|
-
"cypress": "15.21.
|
|
101
|
+
"cypress": "15.21.1",
|
|
119
102
|
"cypress-html-validate": "9.0.0",
|
|
120
103
|
"html-validate": "11.10.0",
|
|
121
104
|
"html-validate-markdown": "6.0.0",
|
|
@@ -128,7 +111,7 @@
|
|
|
128
111
|
"typescript": "npm:@typescript/typescript6@6.0.2",
|
|
129
112
|
"vite": "8.2.2",
|
|
130
113
|
"vitest": "4.1.11",
|
|
131
|
-
"vue": "3.5.
|
|
114
|
+
"vue": "3.5.42",
|
|
132
115
|
"vue-tsc": "3.3.11"
|
|
133
116
|
},
|
|
134
117
|
"peerDependencies": {
|
|
@@ -149,9 +132,5 @@
|
|
|
149
132
|
"fsevents": false,
|
|
150
133
|
"unrs-resolver": true
|
|
151
134
|
},
|
|
152
|
-
"cloneman": {
|
|
153
|
-
"template": "@forsakringskassan/vue-lib-template",
|
|
154
|
-
"version": "1.0.2"
|
|
155
|
-
},
|
|
156
135
|
"externalDependencies": []
|
|
157
136
|
}
|
package/files/renovate.json
CHANGED
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @param {import("cloneman").InstallContext} context
|
|
3
|
+
*/
|
|
4
|
+
export default async (context) => {
|
|
5
|
+
const { getParameter, updateJsonFile } = context;
|
|
6
|
+
|
|
7
|
+
/* write repository url to "package.json" */
|
|
8
|
+
const repoUrl = getParameter("repo-url");
|
|
9
|
+
await updateJsonFile("package.json", {
|
|
10
|
+
repository: {
|
|
11
|
+
type: "git",
|
|
12
|
+
url: repoUrl,
|
|
13
|
+
},
|
|
14
|
+
});
|
|
15
|
+
};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@forsakringskassan/vue-lib-template",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.4",
|
|
4
4
|
"description": "Vue library template based on Cloneman",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"template",
|
|
@@ -24,19 +24,20 @@
|
|
|
24
24
|
},
|
|
25
25
|
"cloneman": {
|
|
26
26
|
"boilerplateFiles": [
|
|
27
|
+
".agents/skills/documentation/SKILL.md",
|
|
28
|
+
".agents/skills/documentation/template.md",
|
|
27
29
|
".editorconfig",
|
|
28
30
|
".gitignore",
|
|
29
31
|
".htmlvalidate.json",
|
|
30
32
|
".htmlvalidateignore",
|
|
31
33
|
".prettierignore",
|
|
32
|
-
"
|
|
33
|
-
"
|
|
34
|
-
"Jenkinsfile",
|
|
35
|
-
"LICENSE.md",
|
|
36
|
-
"README.md",
|
|
34
|
+
".vscode/extensions.json",
|
|
35
|
+
".vscode/settings.json",
|
|
37
36
|
"api-extractor.lib.json",
|
|
38
37
|
"api-extractor.selectors.json",
|
|
39
38
|
"babel.config.js",
|
|
39
|
+
"CHANGELOG.md",
|
|
40
|
+
"CODEOWNERS",
|
|
40
41
|
"cypress.config.ts",
|
|
41
42
|
"cypress/fixtures/example.json",
|
|
42
43
|
"cypress/support/commands/forced-colors.ts",
|
|
@@ -47,6 +48,7 @@
|
|
|
47
48
|
"cypress/tsconfig.json",
|
|
48
49
|
"cypress/types/cy-mount.d.ts",
|
|
49
50
|
"cypress/types/forced-colors.d.ts",
|
|
51
|
+
"cypress/types/mocha.d.ts",
|
|
50
52
|
"docs/build.mts",
|
|
51
53
|
"docs/components/AwesomeComponent.md",
|
|
52
54
|
"docs/components/index.md",
|
|
@@ -56,13 +58,16 @@
|
|
|
56
58
|
"docs/src/setup.ts",
|
|
57
59
|
"docs/tsconfig.json",
|
|
58
60
|
"eslint.config.mjs",
|
|
59
|
-
"etc/
|
|
60
|
-
"etc/
|
|
61
|
+
"etc/lib.api.md",
|
|
62
|
+
"etc/selectors.api.md",
|
|
63
|
+
"Jenkinsfile",
|
|
64
|
+
"LICENSE.md",
|
|
65
|
+
"README.md",
|
|
61
66
|
"renovate.json",
|
|
67
|
+
"src/awesome-component-logic.ts",
|
|
62
68
|
"src/AwesomeComponent.cy.ts",
|
|
63
69
|
"src/AwesomeComponent.vue",
|
|
64
70
|
"src/AwesomeComponentLogic.spec.ts",
|
|
65
|
-
"src/awesome-component-logic.ts",
|
|
66
71
|
"src/examples/DummyExample.vue",
|
|
67
72
|
"src/index.ts",
|
|
68
73
|
"src/local.scss",
|
|
@@ -76,13 +81,18 @@
|
|
|
76
81
|
"vite.config.mts"
|
|
77
82
|
],
|
|
78
83
|
"managedFiles": [
|
|
84
|
+
".agents/skills/documentation/SKILL.md",
|
|
85
|
+
".agents/skills/documentation/template.md",
|
|
79
86
|
".editorconfig",
|
|
80
87
|
".gitignore",
|
|
81
88
|
".htmlvalidate.json",
|
|
82
89
|
".prettierignore",
|
|
90
|
+
".vscode/extensions.json",
|
|
91
|
+
".vscode/settings.json",
|
|
83
92
|
"api-extractor.lib.json",
|
|
84
93
|
"api-extractor.selectors.json",
|
|
85
94
|
"babel.config.js",
|
|
95
|
+
"cypress.config.ts",
|
|
86
96
|
"cypress/fixtures/example.json",
|
|
87
97
|
"cypress/support/commands/forced-colors.ts",
|
|
88
98
|
"cypress/support/common.ts",
|
|
@@ -92,7 +102,7 @@
|
|
|
92
102
|
"cypress/tsconfig.json",
|
|
93
103
|
"cypress/types/cy-mount.d.ts",
|
|
94
104
|
"cypress/types/forced-colors.d.ts",
|
|
95
|
-
"cypress.
|
|
105
|
+
"cypress/types/mocha.d.ts",
|
|
96
106
|
"docs/build.mts",
|
|
97
107
|
"docs/package.json",
|
|
98
108
|
"docs/src/main.scss",
|
|
@@ -123,6 +133,14 @@
|
|
|
123
133
|
"!@fkui/tsconfig",
|
|
124
134
|
"@forsakringskassan/*-api",
|
|
125
135
|
"fk-icons"
|
|
136
|
+
],
|
|
137
|
+
"parameters": [
|
|
138
|
+
{
|
|
139
|
+
"key": "repo-url",
|
|
140
|
+
"description": "URL to repository",
|
|
141
|
+
"help": null,
|
|
142
|
+
"required": true
|
|
143
|
+
}
|
|
126
144
|
]
|
|
127
145
|
}
|
|
128
146
|
}
|
|
File without changes
|
|
File without changes
|