@strapi/plugin-documentation 0.0.0-e6cac9fe30 → 0.0.0-e72d2a086dec98188257a55a0d23343685cc0c44

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.
@@ -29,7 +29,7 @@
29
29
  "pages.PluginPage.table.icon.regenerate": "Regenerér {target}",
30
30
  "pages.PluginPage.table.icon.show": "Åben {target}",
31
31
  "pages.PluginPage.table.version": "Version",
32
- "pages.SettingsPage.Button.description": "Konfigurér dokumentations pluginnet",
32
+ "pages.SettingsPage.header.description": "Konfigurér dokumentations pluginnet",
33
33
  "pages.SettingsPage.header.save": "Gem",
34
34
  "pages.SettingsPage.toggle.hint": "Gør dokumentationens endpoint privat",
35
35
  "pages.SettingsPage.toggle.label": "Begrænset adgang",
@@ -29,7 +29,7 @@
29
29
  "pages.PluginPage.table.icon.regenerate": "Regenerate {target}",
30
30
  "pages.PluginPage.table.icon.show": "Open {target}",
31
31
  "pages.PluginPage.table.version": "Version",
32
- "pages.SettingsPage.Button.description": "Configure the documentation plugin",
32
+ "pages.SettingsPage.header.description": "Configure the documentation plugin",
33
33
  "pages.SettingsPage.header.save": "Save",
34
34
  "pages.SettingsPage.toggle.hint": "Make the documentation endpoint private",
35
35
  "pages.SettingsPage.toggle.label": "Restricted Access",
@@ -29,7 +29,7 @@
29
29
  "pages.PluginPage.table.icon.regenerate": "Regenerar {target}",
30
30
  "pages.PluginPage.table.icon.show": "Abrir {target}",
31
31
  "pages.PluginPage.table.version": "Versión",
32
- "pages.SettingsPage.Button.description": "Configura el plugin de documentación",
32
+ "pages.SettingsPage.header.description": "Configura el plugin de documentación",
33
33
  "pages.SettingsPage.header.save": "Guardar",
34
34
  "pages.SettingsPage.toggle.hint": "Hacer que la documentación sea privada",
35
35
  "pages.SettingsPage.toggle.label": "Acceso restringido",
@@ -29,7 +29,7 @@
29
29
  "pages.PluginPage.table.icon.regenerate": "{target} 재생성",
30
30
  "pages.PluginPage.table.icon.show": "{target} 열기",
31
31
  "pages.PluginPage.table.version": "버전",
32
- "pages.SettingsPage.Button.description": "도큐멘테이션 플러그인 설정",
32
+ "pages.SettingsPage.header.description": "도큐멘테이션 플러그인 설정",
33
33
  "pages.SettingsPage.header.save": "저장",
34
34
  "pages.SettingsPage.toggle.hint": "도큐멘테이션 엔드포인트를 비공개로 설정합니다.",
35
35
  "pages.SettingsPage.toggle.label": "액세스 제한",
@@ -29,7 +29,7 @@
29
29
  "pages.PluginPage.table.icon.regenerate": "Wygeneruj ponownie {target}",
30
30
  "pages.PluginPage.table.icon.show": "Otwórz {target}",
31
31
  "pages.PluginPage.table.version": "Wersja",
32
- "pages.SettingsPage.Button.description": "Skonfiguruj plugin dokumentacji",
32
+ "pages.SettingsPage.header.description": "Skonfiguruj plugin dokumentacji",
33
33
  "pages.SettingsPage.header.save": "Zapisz",
34
34
  "pages.SettingsPage.toggle.hint": "Ustaw endpoint dokumentacji na prywatny",
35
35
  "pages.SettingsPage.toggle.label": "Dostęp ograniczony",
@@ -0,0 +1,39 @@
1
+ {
2
+ "coming-soon": "Det här innehållet är för närvarande under uppbyggnad och kommer tillbaka om några veckor!",
3
+ "components.Row.open": "Öppen",
4
+ "components.Row.regenerate": "Återskapa",
5
+ "containers.HomePage.Block.title": "Versioner",
6
+ "containers.HomePage.Button.update": "Uppdatera",
7
+ "containers.HomePage.PluginHeader.title": "Dokumentation - Inställningar",
8
+ "containers.HomePage.PopUpWarning.confirm": "Jag förstår",
9
+ "containers.HomePage.PopUpWarning.message": "Är du säker på att du vill ta bort denna versionen?",
10
+ "containers.HomePage.copied": "Token har kopierats till urklipp",
11
+ "containers.HomePage.form.jwtToken": "Hämta din jwt-token",
12
+ "containers.HomePage.form.jwtToken.description": "Kopiera denna token och använd den i swagger för att göra förfrågningar",
13
+ "containers.HomePage.form.password": "Lösenord",
14
+ "containers.HomePage.form.password.inputDescription": "Ställ in lösenordet som ska behövas för att komma åt dokumentationen",
15
+ "containers.HomePage.form.restrictedAccess": "Begränsad åtkomst",
16
+ "containers.HomePage.form.restrictedAccess.inputDescription": "Gör dokumentationensrutten privat. Som standard är åtkomsten publik",
17
+ "containers.HomePage.form.showGeneratedFiles": "Visa genererade filer",
18
+ "containers.HomePage.form.showGeneratedFiles.inputDescription": "Användbart när du vill överskrida den automatiskt genererade dokumentationen. \nPluginet genererar filer uppdelade efter modell och plugin. \nGenom att aktivera det här blir det lättare att anpassa din dokumentation",
19
+ "error.deleteDoc.versionMissing": "Den version du försöker ta bort finns inte.",
20
+ "error.noVersion": "En version krävs",
21
+ "error.regenerateDoc": "Ett fel uppstod när dokumentet återskapades",
22
+ "error.regenerateDoc.versionMissing": "Den version du försöker generera finns inte",
23
+ "notification.delete.success": "Dokument raderat",
24
+ "notification.generate.success": "Dokument genererat",
25
+ "notification.update.success": "Inställningarna har uppdaterats",
26
+ "pages.PluginPage.Button.open": "Öppna dokumentation",
27
+ "pages.PluginPage.header.description": "Konfigurera dokumentationspluginet",
28
+ "pages.PluginPage.table.generated": "Senast genererade",
29
+ "pages.PluginPage.table.icon.regenerate": "Återskapa {target}",
30
+ "pages.PluginPage.table.icon.show": "Öppna {target}",
31
+ "pages.PluginPage.table.version": "Version",
32
+ "pages.SettingsPage.header.description": "Konfigurera dokumentationspluginet",
33
+ "pages.SettingsPage.header.save": "Spara",
34
+ "pages.SettingsPage.toggle.hint": "Gör dokumentationensrutten privat",
35
+ "pages.SettingsPage.toggle.label": "Begränsad åtkomst",
36
+ "plugin.description.long": "Skapa ett OpenAPI-dokument och visualisera din API med SWAGGER UI.",
37
+ "plugin.description.short": "Skapa ett OpenAPI-dokument och visualisera din API med SWAGGER UI.",
38
+ "plugin.name": "Dokumentation"
39
+ }
@@ -1,20 +1,39 @@
1
1
  {
2
- "components.Row.open": "Open",
3
- "components.Row.regenerate": "Regenerate",
4
- "containers.HomePage.Block.title": "Versions",
5
- "containers.HomePage.Button.update": "Update",
6
- "containers.HomePage.PluginHeader.title": "Documentation - Settings",
7
- "containers.HomePage.PopUpWarning.confirm": "I understand",
8
- "containers.HomePage.PopUpWarning.message": "Are you sure you want to delete this version?",
9
- "containers.HomePage.form.password": "Password",
10
- "containers.HomePage.form.password.inputDescription": "Set the password to access the documentation",
11
- "containers.HomePage.form.restrictedAccess": "Restricted access",
12
- "containers.HomePage.form.restrictedAccess.inputDescription": "Make the documentation endpoint private. By default, the access is public",
13
- "containers.HomePage.form.showGeneratedFiles": "Show generated files",
14
- "containers.HomePage.form.showGeneratedFiles.inputDescription": "Useful when you want to override the generated documentation. \nThe plugin will generate files split by model and plugin. \nBy enabling this option it will be easier to customize your documentation",
15
- "error.deleteDoc.versionMissing": "The version you are trying to delete does not exist.",
16
- "error.noVersion": "A version is required",
17
- "error.regenerateDoc": "An error occurred while regenerating the doc",
18
- "error.regenerateDoc.versionMissing": "The version you are trying to generate doesn't exist",
19
- "notification.update.success": "Settings updated successfully"
2
+ "coming-soon": "Bu içerik şuanda düzenleniyor. Bir kaç hafta sonra yayında olacak!",
3
+ "components.Row.open": "",
4
+ "components.Row.regenerate": "Yeniden üret",
5
+ "containers.HomePage.Block.title": "Versiyonlar",
6
+ "containers.HomePage.Button.update": "Güncelle",
7
+ "containers.HomePage.PluginHeader.title": "Dokümantasyon - Ayarlar",
8
+ "containers.HomePage.PopUpWarning.confirm": "Anladım",
9
+ "containers.HomePage.PopUpWarning.message": "Bu versiyonu silmek istediğinden emin misin?",
10
+ "containers.HomePage.copied": "Token panoya kopyalandı",
11
+ "containers.HomePage.form.jwtToken": "JWT tokenını al",
12
+ "containers.HomePage.form.jwtToken.description": "İstek atmak için bu tokenı kopyala ve swaggerda kullan",
13
+ "containers.HomePage.form.password": "Şifre",
14
+ "containers.HomePage.form.password.inputDescription": "Dokümantasyona erişmek için şifreyi belirle",
15
+ "containers.HomePage.form.restrictedAccess": "Kısıtlı erişim",
16
+ "containers.HomePage.form.restrictedAccess.inputDescription": "Dokümantasyon noktasını gizle. Varsayılan olarak erişim herkese açıktır",
17
+ "containers.HomePage.form.showGeneratedFiles": "Üretilen dosyaları göster",
18
+ "containers.HomePage.form.showGeneratedFiles.inputDescription": "Üretilen dokümantasyonun üzerine yazmak istediğinde kullanışlıdır. \nEklenti dosyaları model ve eklentilere göre ayrı olarak üretecektir. \nBu seçeneği etkinleştirerek dokümantasyonu özelleştirmen kolaylaşacaktır.",
19
+ "error.deleteDoc.versionMissing": "Silmek istediğin versiyon bulunmuyor.",
20
+ "error.noVersion": "Bir versiyon gerekli.",
21
+ "error.regenerateDoc": "Dokümanı yeniden üretirken bir hata oluştu",
22
+ "error.regenerateDoc.versionMissing": "Üretmeye çalıştığın versiyon bulunmuyor",
23
+ "notification.delete.success": "Doküman silindi",
24
+ "notification.generate.success": "Doküman üretildi",
25
+ "notification.update.success": "Ayarlar başarıyla güncellendi",
26
+ "pages.PluginPage.Button.open": "Dokümanı aç",
27
+ "pages.PluginPage.header.description": "Dokümantasyon eklentisini ayarla",
28
+ "pages.PluginPage.table.generated": "Son üretilme",
29
+ "pages.PluginPage.table.icon.regenerate": "Yeniden üret: {target}",
30
+ "pages.PluginPage.table.icon.show": "Aç: {target}",
31
+ "pages.PluginPage.table.version": "Versiyon",
32
+ "pages.SettingsPage.header.description": "Dokümantasyon eklentisini ayarla",
33
+ "pages.SettingsPage.header.save": "Kaydet",
34
+ "pages.SettingsPage.toggle.hint": "Dokümantasyon uç noktasını gizli yap",
35
+ "pages.SettingsPage.toggle.label": "Kısıtlı Erişim",
36
+ "plugin.description.long": "Bir OpenAPI Dokümanı oluştur ve SWAGGER UI ile APIni görselleştir.",
37
+ "plugin.description.short": "Bir OpenAPI Dokümanı oluştur ve SWAGGER UI ile APIni görselleştir.",
38
+ "plugin.name": "Dokümantasyon"
20
39
  }
@@ -1,4 +1,5 @@
1
1
  {
2
+ "coming-soon": "此內容目前正在構建,將在幾周後回歸!",
2
3
  "components.Row.open": "開啟",
3
4
  "components.Row.regenerate": "重新產生",
4
5
  "containers.HomePage.Block.title": "版本",
@@ -6,19 +7,33 @@
6
7
  "containers.HomePage.PluginHeader.title": "文件資料 - 設定",
7
8
  "containers.HomePage.PopUpWarning.confirm": "我了解了",
8
9
  "containers.HomePage.PopUpWarning.message": "你確定要刪除這個版本嗎?",
9
- "containers.HomePage.copied": "Token 已經複製到剪貼簿",
10
- "containers.HomePage.form.jwtToken": "存取你的 jwt token",
11
- "containers.HomePage.form.jwtToken.description": "複製這個token並於swagger中使用於發出請求",
10
+ "containers.HomePage.copied": "權杖已經複製到剪貼簿",
11
+ "containers.HomePage.form.jwtToken": "存取你的 jwt 權杖",
12
+ "containers.HomePage.form.jwtToken.description": "複製這個權杖並於 swagger 中使用於發出請求",
12
13
  "containers.HomePage.form.password": "密碼",
13
14
  "containers.HomePage.form.password.inputDescription": "設定密碼存取權限",
14
15
  "containers.HomePage.form.restrictedAccess": "存取受到限制",
15
- "containers.HomePage.form.restrictedAccess.inputDescription": "將endpoints設定為私密的. 預設是對外公開的",
16
+ "containers.HomePage.form.restrictedAccess.inputDescription": "將 endpoints 設定為私密的。預設是對外公開的",
16
17
  "containers.HomePage.form.showGeneratedFiles": "顯示產生的檔案",
17
- "containers.HomePage.form.showGeneratedFiles.inputDescription": "用於覆寫產生的文件檔案時. \n擴充套件會依照model及plugin分別產生檔案. \n啟用這個選項將會方便你客製化文件資料",
18
+ "containers.HomePage.form.showGeneratedFiles.inputDescription": "用於覆寫產生的文件檔案時。\n擴充套件會依照model及plugin分別產生檔案。\n啟用這個選項將會方便你客製化文件資料",
18
19
  "error.deleteDoc.versionMissing": "你想刪除的版本不存在",
19
20
  "error.noVersion": "版本是必填欄位",
20
21
  "error.regenerateDoc": "重新產生文件資料時發生了錯誤",
21
22
  "error.regenerateDoc.versionMissing": "你想產生的版本不存在",
23
+ "notification.delete.success": "文件已刪除",
24
+ "notification.generate.success": "文件已重新產生",
22
25
  "notification.update.success": "更新設定成功",
26
+ "pages.PluginPage.Button.open": "開啟說明文件",
27
+ "pages.PluginPage.header.description": "設定說明文件外掛程式",
28
+ "pages.PluginPage.table.generated": "最後產生時間",
29
+ "pages.PluginPage.table.icon.regenerate": "重新產生 {target}",
30
+ "pages.PluginPage.table.icon.show": "開啟 {target}",
31
+ "pages.PluginPage.table.version": "版本",
32
+ "pages.SettingsPage.header.description": "設定說明文件外掛程式",
33
+ "pages.SettingsPage.header.save": "儲存",
34
+ "pages.SettingsPage.toggle.hint": "將說明文件端點設為私人",
35
+ "pages.SettingsPage.toggle.label": "受限存取",
36
+ "plugin.description.long": "建立 OpenAPI 文件,並透過 SWAGGER UI 可視化您的 API。",
37
+ "plugin.description.short": "建立 OpenAPI 文件,並透過 SWAGGER UI 可視化您的 API。",
23
38
  "plugin.name": "文件資料"
24
39
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@strapi/plugin-documentation",
3
- "version": "0.0.0-e6cac9fe30",
3
+ "version": "0.0.0-e72d2a086dec98188257a55a0d23343685cc0c44",
4
4
  "description": "Create an OpenAPI Document and visualize your API with SWAGGER UI.",
5
5
  "repository": {
6
6
  "type": "git",
@@ -24,8 +24,8 @@
24
24
  "test": "echo \"no tests yet\""
25
25
  },
26
26
  "dependencies": {
27
- "@strapi/helper-plugin": "0.0.0-e6cac9fe30",
28
- "@strapi/utils": "0.0.0-e6cac9fe30",
27
+ "@strapi/helper-plugin": "0.0.0-e72d2a086dec98188257a55a0d23343685cc0c44",
28
+ "@strapi/utils": "0.0.0-e72d2a086dec98188257a55a0d23343685cc0c44",
29
29
  "bcryptjs": "2.4.3",
30
30
  "cheerio": "^1.0.0-rc.12",
31
31
  "fs-extra": "10.0.0",
@@ -36,20 +36,24 @@
36
36
  "react": "^17.0.2",
37
37
  "react-copy-to-clipboard": "^5.1.0",
38
38
  "react-dom": "^17.0.2",
39
- "react-intl": "5.20.2",
39
+ "react-intl": "5.25.1",
40
40
  "react-redux": "7.2.8",
41
41
  "react-router": "^5.2.0",
42
- "react-router-dom": "5.2.0",
42
+ "react-router-dom": "5.3.4",
43
43
  "redux": "^4.0.1",
44
44
  "reselect": "^4.0.0",
45
- "swagger-ui-dist": "4.12.0",
45
+ "swagger-ui-dist": "4.15.5",
46
46
  "yaml": "1.10.2"
47
47
  },
48
48
  "peerDependencies": {
49
49
  "@strapi/strapi": "^4.0.0"
50
50
  },
51
+ "devDependencies": {
52
+ "@testing-library/react": "12.1.4",
53
+ "msw": "0.49.1"
54
+ },
51
55
  "engines": {
52
- "node": ">=14.19.1 <=16.x.x",
56
+ "node": ">=14.19.1 <=18.x.x",
53
57
  "npm": ">=6.0.0"
54
58
  },
55
59
  "strapi": {
@@ -58,5 +62,5 @@
58
62
  "description": "Create an OpenAPI Document and visualize your API with SWAGGER UI.",
59
63
  "kind": "plugin"
60
64
  },
61
- "gitHead": "e6cac9fe309b80c9c59cde56d6b25fc6cd40bc8d"
65
+ "gitHead": "e72d2a086dec98188257a55a0d23343685cc0c44"
62
66
  }
@@ -15,12 +15,13 @@ module.exports = ({ strapi }) => {
15
15
 
16
16
  return {
17
17
  registerDoc(doc) {
18
+ let registeredDoc = doc;
18
19
  // parseYaml
19
20
  if (typeof doc === 'string') {
20
- doc = require('yaml').parse(doc);
21
+ registeredDoc = require('yaml').parse(registeredDoc);
21
22
  }
22
23
  // receive an object we can register it directly
23
- registeredDocs.push(doc);
24
+ registeredDocs.push(registeredDoc);
24
25
  },
25
26
  getDocumentationVersion() {
26
27
  return _.get(config, 'info.version');
@@ -46,7 +46,7 @@ const getPathParams = (routePath) => {
46
46
  description: '',
47
47
  deprecated: false,
48
48
  required: true,
49
- schema: { type: 'string' },
49
+ schema: { type: 'number' },
50
50
  };
51
51
  });
52
52
  };
@@ -20,6 +20,18 @@ const { hasFindMethod, isLocalizedPath } = require('./utils/routes');
20
20
  const getAllSchemasForContentType = ({ routeInfo, attributes, uniqueName }) => {
21
21
  // Store response and request schemas in an object
22
22
  let schemas = {};
23
+ let componentSchemas = {};
24
+ // adds a ComponentSchema to the Schemas so it can be used as Ref
25
+ const addComponentSchema = (schemaName, schema) => {
26
+ if (!Object.keys(schema) || !Object.keys(schema.properties)) {
27
+ return false;
28
+ }
29
+ componentSchemas = {
30
+ ...componentSchemas,
31
+ [schemaName]: schema,
32
+ };
33
+ return true;
34
+ };
23
35
  // Get all the route methods
24
36
  const routeMethods = routeInfo.routes.map((route) => route.method);
25
37
  // Check for localized paths
@@ -56,7 +68,10 @@ const getAllSchemasForContentType = ({ routeInfo, attributes, uniqueName }) => {
56
68
  [`${pascalCase(uniqueName)}LocalizationRequest`]: {
57
69
  required: [...requiredAttributes, 'locale'],
58
70
  type: 'object',
59
- properties: cleanSchemaAttributes(attributesForRequest, { isRequest: true }),
71
+ properties: cleanSchemaAttributes(attributesForRequest, {
72
+ isRequest: true,
73
+ addComponentSchema,
74
+ }),
60
75
  },
61
76
  };
62
77
  }
@@ -71,7 +86,10 @@ const getAllSchemasForContentType = ({ routeInfo, attributes, uniqueName }) => {
71
86
  data: {
72
87
  required: requiredAttributes,
73
88
  type: 'object',
74
- properties: cleanSchemaAttributes(attributesForRequest, { isRequest: true }),
89
+ properties: cleanSchemaAttributes(attributesForRequest, {
90
+ isRequest: true,
91
+ addComponentSchema,
92
+ }),
75
93
  },
76
94
  },
77
95
  },
@@ -84,8 +102,8 @@ const getAllSchemasForContentType = ({ routeInfo, attributes, uniqueName }) => {
84
102
  [`${pascalCase(uniqueName)}LocalizationResponse`]: {
85
103
  type: 'object',
86
104
  properties: {
87
- id: { type: 'string' },
88
- ...cleanSchemaAttributes(attributes),
105
+ id: { type: 'number' },
106
+ ...cleanSchemaAttributes(attributes, { addComponentSchema }),
89
107
  },
90
108
  },
91
109
  };
@@ -97,17 +115,37 @@ const getAllSchemasForContentType = ({ routeInfo, attributes, uniqueName }) => {
97
115
  // Build the list response schema
98
116
  schemas = {
99
117
  ...schemas,
100
- [`${pascalCase(uniqueName)}ListResponse`]: {
118
+ [`${pascalCase(uniqueName)}ListResponseDataItem`]: {
101
119
  type: 'object',
120
+ properties: {
121
+ id: { type: 'number' },
122
+ attributes: {
123
+ type: 'object',
124
+ properties: cleanSchemaAttributes(attributes, {
125
+ addComponentSchema,
126
+ componentSchemaRefName: `#/components/schemas/${pascalCase(
127
+ uniqueName
128
+ )}ListResponseDataItemLocalized`,
129
+ }),
130
+ },
131
+ },
132
+ },
133
+ [`${pascalCase(uniqueName)}ListResponseDataItemLocalized`]: {
134
+ type: 'object',
135
+ properties: {
136
+ id: { type: 'number' },
137
+ attributes: {
138
+ type: 'object',
139
+ properties: cleanSchemaAttributes(attributes, { addComponentSchema }),
140
+ },
141
+ },
142
+ },
143
+ [`${pascalCase(uniqueName)}ListResponse`]: {
102
144
  properties: {
103
145
  data: {
104
146
  type: 'array',
105
147
  items: {
106
- type: 'object',
107
- properties: {
108
- id: { type: 'string' },
109
- attributes: { type: 'object', properties: cleanSchemaAttributes(attributes) },
110
- },
148
+ $ref: `#/components/schemas/${pascalCase(uniqueName)}ListResponseDataItem`,
111
149
  },
112
150
  },
113
151
  meta: {
@@ -131,22 +169,41 @@ const getAllSchemasForContentType = ({ routeInfo, attributes, uniqueName }) => {
131
169
  // Build the response schema
132
170
  schemas = {
133
171
  ...schemas,
134
- [`${pascalCase(uniqueName)}Response`]: {
172
+ [`${pascalCase(uniqueName)}ResponseDataObject`]: {
135
173
  type: 'object',
136
174
  properties: {
137
- data: {
175
+ id: { type: 'number' },
176
+ attributes: {
138
177
  type: 'object',
139
- properties: {
140
- id: { type: 'string' },
141
- attributes: { type: 'object', properties: cleanSchemaAttributes(attributes) },
142
- },
178
+ properties: cleanSchemaAttributes(attributes, {
179
+ addComponentSchema,
180
+ componentSchemaRefName: `#/components/schemas/${pascalCase(
181
+ uniqueName
182
+ )}ResponseDataObjectLocalized`,
183
+ }),
184
+ },
185
+ },
186
+ },
187
+ [`${pascalCase(uniqueName)}ResponseDataObjectLocalized`]: {
188
+ type: 'object',
189
+ properties: {
190
+ id: { type: 'number' },
191
+ attributes: {
192
+ type: 'object',
193
+ properties: cleanSchemaAttributes(attributes, { addComponentSchema }),
194
+ },
195
+ },
196
+ },
197
+ [`${pascalCase(uniqueName)}Response`]: {
198
+ properties: {
199
+ data: {
200
+ $ref: `#/components/schemas/${pascalCase(uniqueName)}ResponseDataObject`,
143
201
  },
144
202
  meta: { type: 'object' },
145
203
  },
146
204
  },
147
205
  };
148
-
149
- return schemas;
206
+ return { ...schemas, ...componentSchemas };
150
207
  };
151
208
 
152
209
  const buildComponentSchema = (api) => {
@@ -2,15 +2,23 @@
2
2
 
3
3
  const _ = require('lodash');
4
4
  const getSchemaData = require('./get-schema-data');
5
-
5
+ const pascalCase = require('./pascal-case');
6
6
  /**
7
7
  * @description - Converts types found on attributes to OpenAPI acceptable data types
8
8
  *
9
9
  * @param {object} attributes - The attributes found on a contentType
10
- * @param {{ typeMap: Map, isRequest: boolean }} opts
10
+ * @param {{ typeMap: Map, isRequest: boolean, addComponentSchema: function, componentSchemaRefName: string }} opts
11
11
  * @returns Attributes using OpenAPI acceptable data types
12
12
  */
13
- const cleanSchemaAttributes = (attributes, { typeMap = new Map(), isRequest = false } = {}) => {
13
+ const cleanSchemaAttributes = (
14
+ attributes,
15
+ {
16
+ typeMap = new Map(),
17
+ isRequest = false,
18
+ addComponentSchema = () => {},
19
+ componentSchemaRefName = '',
20
+ } = {}
21
+ ) => {
14
22
  const attributesCopy = _.cloneDeep(attributes);
15
23
 
16
24
  for (const prop of Object.keys(attributesCopy)) {
@@ -86,43 +94,53 @@ const cleanSchemaAttributes = (attributes, { typeMap = new Map(), isRequest = fa
86
94
  }
87
95
  case 'component': {
88
96
  const componentAttributes = strapi.components[attribute.component].attributes;
89
-
97
+ const rawComponentSchema = {
98
+ type: 'object',
99
+ properties: {
100
+ ...(isRequest ? {} : { id: { type: 'number' } }),
101
+ ...cleanSchemaAttributes(componentAttributes, {
102
+ typeMap,
103
+ isRequest,
104
+ }),
105
+ },
106
+ };
107
+ const refComponentSchema = {
108
+ $ref: `#/components/schemas/${pascalCase(attribute.component)}Component`,
109
+ };
110
+ const componentExists = addComponentSchema(
111
+ `${pascalCase(attribute.component)}Component`,
112
+ rawComponentSchema
113
+ );
114
+ const finalComponentSchema = componentExists ? refComponentSchema : rawComponentSchema;
90
115
  if (attribute.repeatable) {
91
116
  attributesCopy[prop] = {
92
117
  type: 'array',
93
- items: {
94
- type: 'object',
95
- properties: {
96
- ...(isRequest ? {} : { id: { type: 'string' } }),
97
- ...cleanSchemaAttributes(componentAttributes, { typeMap, isRequest }),
98
- },
99
- },
118
+ items: finalComponentSchema,
100
119
  };
101
120
  } else {
102
- attributesCopy[prop] = {
103
- type: 'object',
104
- properties: {
105
- ...(isRequest ? {} : { id: { type: 'string' } }),
106
- ...cleanSchemaAttributes(componentAttributes, {
107
- typeMap,
108
- isRequest,
109
- }),
110
- },
111
- };
121
+ attributesCopy[prop] = finalComponentSchema;
112
122
  }
113
123
  break;
114
124
  }
115
125
  case 'dynamiczone': {
116
126
  const components = attribute.components.map((component) => {
117
127
  const componentAttributes = strapi.components[component].attributes;
118
- return {
128
+ const rawComponentSchema = {
119
129
  type: 'object',
120
130
  properties: {
121
- ...(isRequest ? {} : { id: { type: 'string' } }),
131
+ ...(isRequest ? {} : { id: { type: 'number' } }),
122
132
  __component: { type: 'string' },
123
- ...cleanSchemaAttributes(componentAttributes, { typeMap, isRequest }),
133
+ ...cleanSchemaAttributes(componentAttributes, {
134
+ typeMap,
135
+ isRequest,
136
+ addComponentSchema,
137
+ }),
124
138
  },
125
139
  };
140
+ const refComponentSchema = { $ref: `#/components/schemas/${pascalCase(component)}` };
141
+ const componentExists = addComponentSchema(pascalCase(component), rawComponentSchema);
142
+ const finalComponentSchema = componentExists ? refComponentSchema : rawComponentSchema;
143
+ return finalComponentSchema;
126
144
  });
127
145
 
128
146
  attributesCopy[prop] = {
@@ -171,8 +189,13 @@ const cleanSchemaAttributes = (attributes, { typeMap = new Map(), isRequest = fa
171
189
 
172
190
  if (prop === 'localizations') {
173
191
  attributesCopy[prop] = {
174
- type: 'array',
175
- items: { type: 'object', properties: {} },
192
+ type: 'object',
193
+ properties: {
194
+ data: {
195
+ type: 'array',
196
+ items: componentSchemaRefName.length ? { $ref: componentSchemaRefName } : {},
197
+ },
198
+ },
176
199
  };
177
200
  break;
178
201
  }
@@ -15,7 +15,7 @@ module.exports = (isListOfEntities, attributes) => {
15
15
  items: {
16
16
  type: 'object',
17
17
  properties: {
18
- id: { type: 'string' },
18
+ id: { type: 'number' },
19
19
  attributes: { type: 'object', properties: attributes },
20
20
  },
21
21
  },
@@ -25,7 +25,7 @@ module.exports = (isListOfEntities, attributes) => {
25
25
  return {
26
26
  type: 'object',
27
27
  properties: {
28
- id: { type: 'string' },
28
+ id: { type: 'number' },
29
29
  attributes: { type: 'object', properties: attributes },
30
30
  },
31
31
  };
@@ -14,7 +14,7 @@ module.exports = [
14
14
  {
15
15
  name: 'pagination[withCount]',
16
16
  in: 'query',
17
- description: 'Retun page/pageSize (default: true)',
17
+ description: 'Return page/pageSize (default: true)',
18
18
  deprecated: false,
19
19
  required: false,
20
20
  schema: {
@@ -81,4 +81,25 @@ module.exports = [
81
81
  type: 'string',
82
82
  },
83
83
  },
84
+ {
85
+ name: 'filters',
86
+ in: 'query',
87
+ description: 'Filters to apply',
88
+ deprecated: false,
89
+ required: false,
90
+ schema: {
91
+ type: 'object',
92
+ },
93
+ style: 'deepObject',
94
+ },
95
+ {
96
+ name: 'locale',
97
+ in: 'query',
98
+ description: 'Locale to apply',
99
+ deprecated: false,
100
+ required: false,
101
+ schema: {
102
+ type: 'string',
103
+ },
104
+ },
84
105
  ];