Compare commits

...

183 Commits

Author SHA1 Message Date
ShubhamRwt
504bdb8e6c fixed gh pages 2022-03-01 12:44:13 +05:30
ShubhamRwt
0b6f4fb7e6 Fixing the docmentation for 1.3.4 2022-02-25 16:37:16 +05:30
ShubhamRwt
8748254d5a fixes for releasing 1.3.4 2022-02-22 14:56:21 +05:30
ShubhamRwt
7917565654 fixes for releasing 1.3.4 2022-02-22 14:22:38 +05:30
ShubhamRwt
30b41b0d70 Releasing 1.3.4 2022-02-22 13:49:22 +05:30
ShubhamRwt
a421b6d83a Releasing 1.3.4 2022-02-22 13:40:35 +05:30
ShubhamRwt
a8665290a0 Releasing 1.3.4 2022-02-21 15:25:20 +05:30
ShubhamRwt
61af76927e Release notes for 1.3.4 2022-02-21 15:14:33 +05:30
Shubham Rawat
2ffe3d5b8e Merge pull request #432 from Swagger2Markup/revert-431-signing
Revert "Added signing"
2022-02-18 22:03:47 +05:30
Shubham Rawat
03b5c42696 Revert "Added signing" 2022-02-18 22:03:27 +05:30
Shubham Rawat
f9b812a58d Merge pull request #431 from ShubhamRwt/signing
Added signing
2022-02-18 22:00:21 +05:30
ShubhamRwt
16cd99aece changes 2022-02-18 21:51:07 +05:30
ShubhamRwt
368bed514e github action file changes 2022-02-18 17:10:50 +05:30
Shubham Rawat
1492c40fc2 Merge pull request #430 from ShubhamRwt/github
github action file
2022-02-17 16:20:52 +05:30
Shubham Rawat
dafa73832e Update gradle-build.yml 2022-02-17 16:18:03 +05:30
Shubham Rawat
702a2cb180 Update gradle-build.yml 2022-02-17 15:38:54 +05:30
ShubhamRwt
89dbbc284b github action file 2022-02-17 15:30:04 +05:30
Shubham Rawat
6023d015b6 Merge pull request #429 from ShubhamRwt/1.3.x
Changing the build.gradle file
2022-02-17 15:22:55 +05:30
ShubhamRwt
ea2e61cfd9 Changing the build.gradle 2022-02-17 15:22:06 +05:30
ShubhamRwt
bdcbd0069c Changing the build.gradle 2022-02-17 15:15:54 +05:30
austek
859312b7d2 Remove OpenApi2Markup for 1.3.x release 2020-11-11 06:00:16 +00:00
Stefan Larsson
9de5ad0157 Fix Javadoc, added missing parameters and replaced with valid html (#415) 2020-11-05 08:45:30 +01:00
Aaron Watry
61df613cd2 tests: Update swagger petstore URLs from http to https to fix failing tests (#411)
Accessing the http URLs was doing a 302 redirect to https.

Co-authored-by: Aaron Watry <aaron.watry@advarra.com>
2020-10-02 09:57:43 +02:00
Sergei Khramkov
b70d6ca9ca Fixed the description of getMax in PropertyAdapter (#412)
Co-authored-by: Sergey.Khramkov <Sergey.Khramkov@nexign-systems.com>
2020-10-02 09:57:25 +02:00
Robert Winkler
0e15676cb7 Fixed failing test. 2020-06-16 11:36:27 +02:00
Robert Winkler
5f419a0d02 Removed SwaggerPageBreakLocations for backward compability. 2020-06-16 11:27:38 +02:00
Robert Winkler
a0efe7dd26 Removed SwaggerPageBreakLocations for backward compability. 2020-06-16 11:23:57 +02:00
Robert Winkler
21afb5adcd Removed SwaggerPageBreakLocations for backward compability. 2020-06-16 11:19:37 +02:00
Robert Winkler
7d0d73cd51 Moved classes for backward compability. 2020-06-16 11:07:28 +02:00
Robert Winkler
e8a51345a8 Delimiters should use the system line separator by default 2020-06-16 09:40:31 +02:00
Robert Winkler
f471774da9 Updated release notes. 2020-06-16 09:39:23 +02:00
Robert Winkler
0facccf009 Moved Swagger2MarkupConfig back into the main package for backward compability. 2020-06-16 09:35:09 +02:00
Robert Winkler
835c8fec03 Moved Swagger2MarkupConfig back into the main package for backward compability. 2020-06-16 09:18:04 +02:00
Robert Winkler
eea093acd4 Merge remote-tracking branch 'origin/master' 2020-06-15 13:07:14 +02:00
Robert Winkler
b32bfb3e54 Moved Swagger2MarkupConfig back into the main package for backward compability. 2020-06-15 12:25:19 +02:00
Robert Winkler
65f330baae Updated to 2.0.0-SNAPSHOT 2020-06-15 11:24:26 +02:00
Klaus Schwartz
b43a677744 Issue #248: Added a curl request example (#408)
* Issue #248 Add a curl request example

added configurable 3 kinds of request examples:

- basic (default, no source highlight)
- curl (bash source highlight)
- Invoke-WebRequest (powershell source highlight)

* updated default.properties to support curl example request feature

Issue #248 Add a curl request example

added configurable 3 kinds of request examples:

- basic (default, no source highlight)
- curl (bash source highlight)
- Invoke-WebRequest (powershell source highlight)

* added few tests, fixed extra space before query "?" delimiter, added builder configuration methods

Issue #248 Add a curl request example

* fix missig headers in example, fix Content-Type header name spelling

Issue #248 Add a curl request example
2020-06-10 15:42:27 +02:00
Paolo Patierno
4b69d6a150 Added support for MIME types with structured syntax suffixes (#410) 2020-06-08 15:47:44 +02:00
Robert Winkler
4a3ee6c5ca Feature/open api v3 support (#405) 2020-03-06 08:31:21 +01:00
Ali Ustek
69baeb6339 Merge pull request #400 from kolbdaniel1/patch-1
renamed jCenter() repository to jcenter()
2020-01-29 19:00:36 +00:00
Daniel
f7fe2b0cca renamed jCenter() repository to jcenter() 2020-01-29 14:39:45 +01:00
Ali Ustek
f853550748 Migrated markup document builder (#374)
* Initial commit

* Updated documentation

* Test travis CI

* Added library to bintray

* Updated documentation

* Updated documentation

* Updated documentation

* Published Version 1.1 to Maven Central

* Updated Bintray Badge

* Updated Bintray Badge

* Fixed maven pom issue

* Fixed issue: Comma should be escapes when constructing table in csv format in asciidoc
Fixed issue: logback.xml on the classpath

* New version number

* New version number

* Added Apache2 Copyright Header

* Updated documentation

* Updated documentation

* Updates documentation

* Fix Markdown level 3 title

* Fixed SECTION_TITLE_LEVEL3 in Markdown enum

* Added twitter batch

* Updated documentation

* Added method sectionTitleLevel4

* Added Artifactory Gradle Plugin in order to deploy snapshots to oss.jfrog.org

* Added artifactoryPublish task to TravisCI to publish SNAPSHOTS to OSS Artifactory

* Fixed coveralls badge

* Introduced new commands : anchor(anchor), crossReference(anchor, text)
Refactored writeToFile for robustness
Cleanups and fixes

* Enhanced support for tables

* Introduce inline commands : inlineAnchor, inlineCrossReference for easier markup composition

* More tests

* Renamed inline* to *AsString

* Implemented anchors and crossReferences for Markdown (GFM style)

* Updated readme

* Fixed anchor normalization

* Cleanups

* Cleanups

* Fixed replacing error

* Renamed TableColumnSpec to MarkupTableColumn

* Travis Secure Environment variables must be escaped

* Fixed travis.yml

* Fixed travis.yml

* fixed anchor normalization (again). Asciidoc anchor normalization differs between title and custom anchors => introducted crossReferenceTitle

* fixed tests compilation

* Update dependency-management-plugin to work with Gradle versions newer than 2.5

* Update Gradle wrapper to 2.10

* Fixed inter-document cross-references

* renamed crossReference -> crossReferenceAnchor and crossReferenceTitle -> crossReference as it's the default behavior
introduced addFilenameExtension (e.g. needed for inter-document cross-references)
fixed anchor normalization (support for ASCII characters in AsciiDoc)
Several workarounds with inter-document cross-references
Removed documentTitleWithAttributes as it's no use as-is

* Support for inter-document cross-references in Markdown

* fixed #9 Refactor anchor and cross-reference interface and implementation

* Updated asciidoctor-gradle-plugin: and asciidoctorj-pdf Gradle plugins to newer versions.

* [Bug] The document title must not have a anchor in front of it.

* Ignore punctuation in normalizeAnchor
Added new functions to create sections with a custom anchor not directly derived from the title

* Use paragrah local hardbreaks instead of global attribute

* fixed normalization and provided tests for normalization (finally) !

* missing Mockito in Gradle
fixed tests

* anchor normalization better manages beginning and ending escape characters, and intermediate punctuation

* introduce text, italicText, boldText
remove *AsString builders, use a new MarkupDocBuilder with toString() method instead

* Create a builder instance from another builder instance, for easier composition

* introduce forceLineBreak on all *Line methods

* Introduce new sectionTitleWithAnchor* to allow users to create titles without anchor, with a custom anchor (will be normalized anyway), or with an auto-generated anchor.

* sectionTitleWithAnchor* consistency fix when anchor == null => auto-generate anchor

* Introduce global builder configuration .withAnchorPrefix
Introduce copy() method to easily duplicate builders with configuration

* Introduce Markup-dependent specifiers on tables

* Added public interface complete documentation

* Added 2 newlines at the end of generated output when output are files. This protect the final AsciiDoc when you later include these files.

* MarkupTableColumn documentation enhancements

* Added importMarkup(markupText, levelOffset)

* Check for levelOffset < 0 in importMarkup(markupText, levelOffset)

* Support for levelOffset < 0 in importMarkup

* Use Reader in importMarkup instead of a String

* MAX_TITLE_LEVEL = 4 -> 5

* Added new interface methods to support java.nio.file.Path parameters

* Added new block methods (supporting title and admonitions)
Refactored listing() and method() methods
Does not flush buffer anymore when writeToFile

* Renamed addfileExtension to addFileExtension

* logging fix

* Support level 5 titles.
Added sectionTitleLevel(int level, String title) for convenience.

* Line separators (Mac, Windows, Linux) of input data are replaced by the system line separator.

* Removed source folder mainpjava.

* Fixed AbstractMarkupDocBuilderTest on windows machines by setting newLine to a fixed value.

* Added validation that input values are not null and empty.

* Added the functionality to provide a custom line separator which should be used.

* Added Mac line separator.

* Removed io.spring.gradle:dependency-management-plugin

* Added default line separator if provided lineSeparator is null.

* Updated versions of commons-collection, commons-lang3, commons-codec and slf4j-api.

* Removed Guava library.

* New lines in Table headers are replaced by a whitespace
New lines in Table cells are replaced by the configured line separator.

* Opens MarkupDocBuilders for additional/external markup builders (includes an example for Confluence wiki markup)

* Make changes Java 1.7 compatible.

* Adds a markup builder for Atlassian's Jira/Confluence wiki markup.

* Updated README.

* Renamed ATLASSIAN to ATLASSIAN_WIKI

* Updated publishing and coverage gradle scripts.

* Updated publishing gradle script.

* Moved source code which does not belong to the external API into an internal package.

* Copy newLine in copy() method + non regression test

* simplify empty constructors
added missing copyright headers

* factored importMarkupStyle1/2 + Style2 tests
removed deprecated tableWithHeaderRow
refactored ConfluenceMarkupBuilder

* copy with optional copyBuffer

* Added assertj-diff.

* fixing ConfluenceMarkupBuilder
fixed MarkdownBuilder with null block styles

* remove FILE_EXTENSION from Markups, use MarkupLanguage::getFileNameExtensions instead

* fixed documentTitle level for ConfluenceMarkupBuilder

* fixed LINE_BREAK for ConfluenceMarkupBuilder

* fixed empty cells for ConfluenceMarkupBuilder

* fixed crossReferences for ConfluenceMarkupBuilder

* cleanups

* removed deprecated writeToFile*

* Support column headers style generically in MarkupTableColumn

* Use DiffAssertions to check generated markup result in tests

* Introduce MarkupLanguage conversion in importMarkup. Currently support Markdown -> AsciiDoc.

* remove unnecessary newlines when importMarkup text is blank

* removed hardbreaks from AsciiDoc paragraph()

* fixed tests after removing hardbreaks

* better cell formatting : content trimming and newLines management

* fixed pipe escaping management in ConfluenceMarkup cell formatter (does not escape pipe in links in cells)
fixed corner cases in Regexp replacements (quoting)

* added OpenOption parameter in writeToFile()

* Fixed MarkupDocBuilderTests on windows by fixing line separator to LineSeparator.UNIX

* Adapted group id, versioning and root package to other swagger2markup projects

* introduced paragraph(text, hardbreaks), force line breaks on each line for Markdown and ConfluenceMarkup

* ImportMarkup, writeToFile and writeToFileWithoutExtension don't throw IOExceptions anymore, but RuntimeExceptions.

* Upgrade to Java8

* Fixed JavaDoc

* Fixed JavaDoc
Removed commons-collection by using Java8 Streams

* Updated readme

* Updated readme

* reintroduce literalTextLine(text)
rename listing -> listingBlock

* Support <> in cross-reference texts in AsciiDoc

* fixed sectionTitleWithAnchor and auto-generated anchor (and fixed tests)
fixed ConfluenceBuilder : missing replaceNewLinesWithWhiteSpace on title/anchor, removed extra newLine

* supports for blank value for text and textLine only to support adding simple spaces to document

* Released v1.0.0

* Updated readme

* Updated readme

* Updated readme

* Updated readme

* Updated readme

* Changed bold to ** and italic to __ so that special chars in the text are possible

* Updated version to 1.1.0-SNAPSHOT

* Release v1.0.0

* Updated bintray badge

* Updated docs

* Add support for page breaks

* Add page breaks to unit tests

* Updated version from 1.1.0 to 1.1.1-SNAPSHOT

* Released v1.1.1

* Updated README

* Improve code blocks in markdown (#28)

* Prepare release 1.1.2

* Update AbstractMarkupDocBuilder.java (#29)

Support relative file names both of "filename" and "./filename" while `writeToFileWithoutExtension`

* Issue #21: AsciidocBuilder should enable option to set pegdown timeout (#31)

* Upgraded gradle (#33)

* upgrade to gradle 5.6.3

* update dependencies versions

* Moved markup-document-builder files and folders into swagger2markup-builder/

* Fix merge problems from markup-document-builder

* correct expected file for instagram/overview.adoc

* fix paths to examples files in documentation files
2019-10-30 08:13:52 +01:00
Ali Ustek
75fa8f788c Moved docs to documentation module (#373) 2019-10-29 12:49:09 +01:00
Ali Ustek
7a86fdaba3 Updated version numbers and turn on strict conflict resolution (#371) 2019-10-29 12:48:43 +01:00
Ali Ustek
1566b22489 Convert project to be multi-module (#372) 2019-10-29 08:15:17 +01:00
Ali Ustek
ed026f3587 Upgraded to gradle 5.6.3 (#370) 2019-10-24 10:02:22 +02:00
Robert Winkler
6e8e4ce780 Updated READE 2019-06-27 13:02:46 +02:00
mona
60b7d90ad2 get label for operation.deprecated (#363) 2019-06-03 22:54:51 +02:00
guangp
da83465f19 add hostname in uri section of every operation, it is configurable. (#356)
* add hostname in uri section of every operation, it is configurable.

* modify java docs

* test hostname conf
2019-03-21 15:41:58 +01:00
alexmartinsrj
7ae0b64d8e Update labels_pt_BR.properties (#359)
translate of some untraslated words.
2019-03-21 15:41:24 +01:00
Sridhar Jonnalagadda
f8cbf7801d Issue #21: AsciidocBuilder should enable option to set pegdown timeout (#353) 2018-11-21 13:04:22 +01:00
Maciej Swiderski
7fbd49c5ea Issue #349 - Add support for generating example for request data based on media type (#350) 2018-11-05 10:43:03 +01:00
Valy Diarrassouba
8717e26f76 Allow to define freeform with additionalProperties: {} (#346) (#347) 2018-10-22 12:48:02 +02:00
aspekt23
483d6c3d17 Issue 291 support for title property in definitions (#348)
* Implemented preference for definition title if it is present

* Fixed failing test data
2018-10-22 12:43:09 +02:00
parrrot
03fb52fb8e Bugfix/issue336 (#345)
* added if branches for "header" parameter for examples and generated proper format

* modified expected test files to include new format of request header
2018-10-18 09:21:28 +02:00
MarosPataky
e574f0e65f Added support for minItems, maxItems property in parameters section o… (#341)
* Added support for minItems, maxItems property in parameters section of specification

* Added values for min/max items for all languages (for now, no translations are provided)

* Fixed issues with NPE and failing tests

* Added translations for min_items and max_items
2018-10-15 10:14:03 +02:00
MarosPataky
e9b04c712d Added support for enums with Integer type (#342)
* Added support for enums for Integer type, changed enums test data to reflect the change

* Fixed test failures that were caused by missing "format" part of integer type description
2018-10-15 10:13:24 +02:00
Martin Waßmann
b4c7c8860c Better generated examples for strings (#329)
* Generate examples based on string format

The following static examples are generated:
* byte: Ynl0ZQ== (base64 of byte)
* date: 1970-01-01
* date-time: 1970-01-01T00:00:00Z
* email: email@example.com
* password: secret
* uuid: f81d4fae-7dec-11d0-a765-00a0c91e6bf6

* Use first enum value as example

* Also generate string examples for path and query parameter

* Test example generation for custom string format
2018-08-06 12:50:07 +02:00
Bennet Schulz
815c161b7e fix typo in documentation (#330) 2018-08-06 10:31:18 +02:00
Łukasz Kolek
ecaaaeb049 fix: polish translation corrected from UTF-8 to encoded properites (#324) 2018-07-12 15:24:56 +02:00
Barry Ostroff
647846762d Generate examples for inline responses (#314)
* Handle untyped inlines - swagger parser no longer defaults untyped to object types
* Handle object inlines - generates a name based on method and response code
* Handle object inlines with titles - generates a name from the title
2018-05-01 21:35:43 +02:00
Michał Dul
655a15c722 Polish language translation (#311)
* Polish language translation

* language builder adjusted
2018-04-29 11:42:18 +02:00
Robert Winkler
6297b859dd Use old gitHubPages plugin 2018-04-27 13:42:29 +02:00
Robert Winkler
19f05c68f8 Prepare release v1.3.3 2018-04-27 12:59:23 +02:00
Robert Winkler
5a12bd9cce Added release notes for v1.3.3 2018-04-27 12:42:36 +02:00
Barry Ostroff
e22b374bdd Resolve issue #298 - Move to latest swagger parser (#308)
* Move to swagger-parser version 1.0.33

* Move to swagger-parser version 1.0.34

* Move to swagger-parser version 1.0.35

* Replace deprecated getSchema() method
2018-04-20 19:04:33 +02:00
Barry Ostroff
fe3749d499 Include required parameters in example request (#307)
* Include required parameters in example request

* Fix unit tests

* Add unit tests for swagger required parameters
2018-04-13 09:04:33 +02:00
Robert Winkler
85ef7f252d Updated to snapshot version. 2018-03-13 16:04:51 +01:00
Robert Winkler
f16b563a82 Prepare release v1.3.2 2017-12-11 09:20:18 +01:00
g00de
8e22dd817e make examples always start newline if there is other content before the example (#294) 2017-12-08 19:02:58 +01:00
Robert Winkler
569f3c02cd Fixed build script 2017-12-04 15:38:17 +01:00
Robert Winkler
e8c2099e4c Prepare release v1.3.2 2017-12-04 14:47:58 +01:00
ctytgat
1646fefd56 Fix crash on empty tables (#293)
* https://github.com/Swagger2Markup/swagger2markup-cli/issues/17

* https://github.com/Swagger2Markup/swagger2markup-cli/issues/17
add test case
2017-12-01 12:31:12 +01:00
bassettb
aad387802e Fix list parsing in properties file (#290)
Move up the code that enables list delimiters so that it comes before any list properties are parsed.
2017-11-15 08:33:07 +01:00
Frederik Hahne
034d0a2f50 replace deprecated gh pages plugin (#285) 2017-11-14 08:05:55 +01:00
Frederik Hahne
d2c78304c6 Description for api keys are no parsed and written (#281)
* Description for api keys are no parsed and written

close #259

* fix markdown converter tests

* fix asciidoc converter tests
2017-10-09 10:53:31 +02:00
Frederik Hahne
247857a843 Issue #162: adoc content in tables (#280)
* adoc content in tables

some dependency update and cleanup

close #162

* fix analysis remarks
2017-10-05 19:40:28 +02:00
brischniz
038ff3a40e ExternalDocs section will now be rendered in result document (#263)
* Typo fixed

* ExternalDocs section will now be rendered in result document
2017-07-17 09:13:41 +02:00
Magnus Larsson
6d8776332f Property refs are resolved as links and not as text (#265)
* Property refs are resolved as links and not as text

* Update static docs in tests to match change in code

* Remove unnecessary if check
2017-07-17 09:12:45 +02:00
Robert Winkler
4ea24b0297 Fixed typo in german language file 2017-07-11 09:01:41 +02:00
Robert Winkler
12570ecb00 Issue #254: The wildcard Mediatype */* is escaped now 2017-05-15 13:01:51 +02:00
Eugeniy Lykov
7b68aecbd7 Improve russian translation (#251)
* Improve russian translation

* Improve russian translation

Complete translation and correct errors.
2017-05-15 08:45:39 +02:00
Robert Winkler
7ce62a8a3d Updated version to 1.3.2-SNAPSHOT 2017-03-20 12:33:14 +01:00
Robert Winkler
d8c3cf725d Release 1.3.1 2017-03-20 12:28:44 +01:00
Robert Winkler
aecc531d84 Added gradle.properties to set file.encoding and sun.jnu.encoding to UTF-8 2017-03-17 09:25:30 +01:00
shardings
f107779542 Fix request path and query params' example support. (#247)
Fix request path and query params' example support.
2017-03-16 09:01:45 +01:00
shardings
70bf17011c Improve the zh_CN translation. (#246)
For human:
default_column: 默认列 -> 默认值
example_column: 例子 -> 样例
schema_column: 架构 -> 类型
overview: 概观 -> 概览
2017-03-14 16:40:01 +01:00
Robert Winkler
86ae19fe2a Update version to 1.3.1-SNAPSHOT 2017-02-20 08:39:59 +01:00
Robert Winkler
e8235c4c35 Updated README 2017-02-20 08:38:20 +01:00
Robert Winkler
63b5cd3bfb Release 1.3.0 2017-02-20 08:37:02 +01:00
Robert Winkler
12e851c127 Refactored Swagger2MarkupConfigBuilder 2017-02-03 09:33:49 +01:00
kruffin
20fa72b613 Multi-Valued Dynamic Content Folders (#240)
* Adds in the capability to have array valued properties. Mostly only affects extensions that may
need this. It is disabled by default and should work the same as it currently does. Array values
can be enabled by setting a separator character in the "swagger2markup.documentFolderSeparator"
configuration attribute.

* Modifications from code review:

* Altered the "documentFolderSeparator" name to "listDelimiter"
* Added an additional property to enable/disable the list delimiter "listDelimiterEnabled"
* Defaulted the "listDelimiter" to ','
* Updated logic that assumed the configuration was derived from AbstractConfiguration to explicitly check before casting
* Added a couple "withListDelimiter" methods to the builder

* Modifies the list delimiter parsing logic (how the delimiter is determined from properties) to be more
of a Java 8 style.
2017-02-03 09:06:49 +01:00
jbrugge
36bee8070a Fix position reference for parameters table. (#241) 2017-02-02 08:57:04 +01:00
fooinha
9a85612b8a * fix NPE for response headers with relative definitions 2017-01-21 10:34:08 +01:00
Robert Winkler
2bc18f7d90 Updated RELEASENOTES 2017-01-19 14:24:41 +01:00
Robert Winkler
6f6428543d The Number Formatter must use the Locale of the Swagger2MarkupConfig output language. 2017-01-19 14:17:17 +01:00
Robert Winkler
d03087c1b8 Fixed version in changelog 2017-01-19 14:00:39 +01:00
Robert Winkler
d2d47cf8ee Updated javslang from 2.0.4 to 2.0.5
Updated paleo-core from 0.10.1 to 0.10.2
Updated swagger-parser from v1.0.23 to v1.0.25
2017-01-19 13:59:23 +01:00
Robert Winkler
7a0f4490de Updated copyright statement 2017-01-19 11:30:50 +01:00
Cas Eliëns
d2b3c9472a Close #180. 2017-01-19 10:24:04 +01:00
Cas Eliëns
3a0b9a00a3 Improve generated examples for arrays 2017-01-19 10:24:04 +01:00
Cas Eliëns
d5cf4ad9e5 Add unit test for #180 2017-01-19 10:24:04 +01:00
Cas Eliëns
2899b2f263 Use shorter sorting syntax and update javadoc 2017-01-13 14:12:41 +01:00
Cas Eliëns
7475321e97 Add ISAAC to 'Companies who use Swagger2Markup' 2017-01-13 14:12:33 +01:00
Cas Eliëns
88a24d7bdd Add space between schema type and format 2017-01-09 12:19:41 +01:00
Robert Winkler
f798a51edc Release v1.2.0 2017-01-05 14:27:53 +01:00
Robert Winkler
81edab38f3 The notBlank validation of the type should tell which parameter is not valid. 2017-01-03 15:58:43 +01:00
Robert Winkler
039607a294 Updated version to 1.2.0-SNAPSHOT 2017-01-03 15:27:32 +01:00
Cas Eliëns
2f33522e6d Issue #214 Added support for page breaks (#226)
* Added support for page breaks
* Added documentation and config file support for page breaks and regex
2017-01-03 11:21:31 +01:00
Cas Eliëns
76c54a713a use raw JSON object instead of converting to string 2017-01-02 13:47:02 +01:00
Cas Eliëns
dcebed2d42 split reused code into methods 2017-01-02 13:47:02 +01:00
Cas Eliëns
dbf9afa8da Remove unused import 2017-01-02 13:47:02 +01:00
Cas Eliëns
f7f397b5f2 Improve printing for different ways of defining examples 2017-01-02 13:47:02 +01:00
Cas Eliëns
44f852ad42 Improve example printing for $ref'd examples 2017-01-02 13:47:02 +01:00
Cas Eliëns
e1be2f2130 Great Expectations 2017-01-02 13:47:02 +01:00
Cas Eliëns
8468607703 Improve example rendering for hardcoded examples 2017-01-02 13:47:02 +01:00
Cas Eliëns
f981318142 Example responses now display correctly 2017-01-02 13:47:02 +01:00
Cas Eliëns
e1d0d7b293 Add FIXME comment 2017-01-02 13:47:02 +01:00
Cas Eliëns
d118a0cf74 Further work on Swagger2Markup/swagger2markup#223 2017-01-02 13:47:02 +01:00
Cas Eliëns
7cb1095465 Begin work on Swagger2Markup/swagger2markup#223 2017-01-02 13:47:02 +01:00
Cas Eliëns
595b885b9a Close Swagger2Markup/swagger2markup#220 2016-12-20 14:07:27 +01:00
Cas Eliëns
b1c219bc1b Remove unused code, optimize imports, fix Codacy issues
* Begin working on Swagger2Markup/swagger2markup#215

* Begin looking for methods that need to be modified for Swagger2Markup/swagger2markup#215

* Begin working on Swagger2Markup/swagger2markup#215

* Begin looking for methods that need to be modified for Swagger2Markup/swagger2markup#215

* Work on implementing regex sorting

* Add regex ordering translations and unit test

* Improve Regex grouping

* Make regex sorting test more like a real-world example

* Remove unused imports

* Improve code style consistency

* Improve code style consistency

* Remove empty statement

* Resolve some Codacy issues

* Remove empty constructors

* Remove unused fields

* Merge nested IF statements

* Improve method scopes

* Remove unused classes

* Remove unused imports

* Remove fixed TODO comment

* Fix codacy issues

* Fix codacy issues (reverted from commit 43f27e7fc6)

* Improve code style consistency

* Resolve some Codacy issues

* Remove empty constructors

* Remove unused fields

* Merge nested IF statements

* Improve method scopes

* Remove unused classes

* Remove unused imports

* Remove fixed TODO comment

* Fix codacy issues
2016-12-19 16:04:17 +01:00
Cas Eliëns
852b2ac3b4 PR#218 Improve code style consistency
Improved code style consistency
2016-12-13 10:44:31 +01:00
Cas Eliëns
937cded2aa Issue #215: Path grouping via a RegEx pattern
* Begin working on Swagger2Markup/swagger2markup#215

* Begin looking for methods that need to be modified for Swagger2Markup/swagger2markup#215

* Begin working on Swagger2Markup/swagger2markup#215

* Begin looking for methods that need to be modified for Swagger2Markup/swagger2markup#215

* Work on implementing regex sorting

* Add regex ordering translations and unit test

* Improve Regex grouping

* Make regex sorting test more like a real-world example

* Remove unused imports
2016-12-13 09:58:12 +01:00
Robert Winkler
022d2453d2 Issee #216: Replace slash with system file separator in unit tests. 2016-12-09 09:17:55 +01:00
Robert Winkler
e5a187cc24 Updated version to 1.1.2-SNAPSHOT 2016-11-30 09:18:22 +01:00
Robert Winkler
83bb63321a Updated markup-document-builder from 1.0.0 to 1.1.0 2016-11-30 08:20:04 +01:00
Robert Winkler
cd5b5c9240 Refactored ParameterAdapter and created MarkupDocBuilderUtils. 2016-11-18 12:36:39 +01:00
Robert Winkler
2096ec0d5d Refactored ParameterAdapter and moved ParameterAdapter and PropertyAdapter into a new package. 2016-11-16 12:54:32 +01:00
Robert Winkler
25d4311237 Added a modularized Swagger spec test 2016-11-16 12:54:03 +01:00
Robert Winkler
7e07c2fc81 Fixed method name in DefinitionsDocument 2016-11-15 14:50:45 +01:00
Robert Winkler
5a8a618e6b Refactored document resolver and added tests. 2016-11-15 14:47:11 +01:00
Robert Winkler
f072fc99b9 Refactored Documents. Documents are also components now and can be composed of components. 2016-11-15 11:12:17 +01:00
Robert Winkler
54e881fc58 Fixed wrong import in SecuritySchemeComponent 2016-11-14 16:14:16 +01:00
Robert Winkler
cd6a3ed724 Refactored Components to be more functional. 2016-11-14 16:08:24 +01:00
Robert Winkler
5a00dde912 Refactored Components to be more functional. 2016-11-14 16:02:49 +01:00
Robert Winkler
876d7b2f7b Moved code into BodyParameterComponent 2016-11-11 14:21:43 +01:00
Robert Winkler
4b74ec0e54 Moved code into PathOperationComponent 2016-11-11 13:30:04 +01:00
Robert Winkler
a719e33332 Moved code into SecuritySchemeComponent 2016-11-11 10:29:51 +01:00
Robert Winkler
86a727f097 Refactored DocumentBuilder into components. 2016-11-10 15:48:03 +01:00
Robert Winkler
2670780076 Enhancement #206 Updated to markup-document-builder v1.1.0 which renders bold text as **text** and italic text as __text__. 2016-11-10 12:42:52 +01:00
Robert Winkler
ebf9912269 Bug #205: Fix ordering of operations when grouped by tags. 2016-11-10 12:41:26 +01:00
Robert Winkler
11549ab64e Bug #205: Fix ordering of operations when grouped by tags. 2016-11-10 10:43:12 +01:00
Robert Winkler
d128146952 Added a component API to split a document into components and improve component testability 2016-11-09 16:30:02 +01:00
Robert Winkler
686abd8842 Added a component API to split a document into components and improve component testability 2016-11-09 15:02:28 +01:00
Robert Winkler
551aeed835 Removed ListUtils and changed MapUtils.toKeySet to MapUtils.toSortedMap 2016-11-08 12:28:27 +01:00
Robert Winkler
5b1a1a2bcf Migrated some collections to Javaslang 2016-11-08 10:18:07 +01:00
Robert Winkler
09d2474a9a Added javaslang and paleo-core to improve Table rendering 2016-11-04 15:32:17 +01:00
Robert Winkler
5c00e5493c Removed ExternalLocation model from inlineSchema test. 2016-11-04 15:32:17 +01:00
Robert Winkler
c343af8f5a Updated Gradle to v3.1 2016-11-04 15:32:17 +01:00
yewton
4af7eb5b89 Add support for Japanese 2016-11-02 08:45:42 +01:00
Robert Winkler
aa9a340144 Added a config parameter which allows to prepend the basePath to all paths. 2016-11-01 14:42:46 +01:00
Robert Winkler
35ae68ceee Fixed german and spanish language files 2016-11-01 08:55:04 +01:00
Robert Winkler
560fb4ece6 Added language file for Portuguese (Brazilian) 2016-11-01 08:30:28 +01:00
Cleydson Júnior
8eb494cd5b Converting special characters to ASCII escape codes 2016-11-01 07:05:19 +01:00
Cleydson Júnior
0766336a56 Adding support for Brazilian Portuguese 2016-11-01 07:05:19 +01:00
TzeKai Lee
24352f4d1c Add format tests on request param in query and body 2016-10-28 09:07:56 +02:00
TzeKei Lee
adb0fee973 Added displaying format for string type and definitions only contains string or integer type. 2016-10-28 09:07:56 +02:00
Robert Winkler
13a7113aa7 Fixes #197 Converted ZH-language file from UTF-8 to latin1 using native2asciidoc 2016-10-25 15:25:27 +02:00
Robert Winkler
e882975726 Updated README 2016-10-18 15:27:06 +02:00
Robert Winkler
12209fe923 Updated version to 1.1.0 2016-10-18 15:14:05 +02:00
Robert Winkler
8a63744198 Updated releases notes 2016-10-18 15:11:52 +02:00
James Bassett
5871f0c9b0 Added support for exclusiveMin and exclusiveMax 2016-10-14 07:12:53 +02:00
James Bassett
908f524c64 Updated min/max value to format correctly based on the data type 2016-10-12 08:47:54 +02:00
Francisco José Bermejo Herrera
9fa0ee3def Add support for Spanish language 2016-10-03 13:46:12 +02:00
Robert Winkler
35e9450f74 Updated docker documentation 2016-09-23 10:29:46 +02:00
Robert Winkler
6033ea5a98 Updated docker documentation 2016-09-23 10:21:02 +02:00
Robert Winkler
6f24c3cb39 Merge remote-tracking branch 'origin/master' 2016-09-23 08:54:37 +02:00
Robert Winkler
e975e49d3e Added docker documentation 2016-09-23 08:54:18 +02:00
Robert Winkler
c5cfe10fa6 Merge pull request #187 from KristinaGen/master
update labels_ru
2016-09-14 09:55:56 +02:00
KristinaGen
7c988460f0 update labels_ru 2016-09-13 16:20:57 +02:00
Robert Winkler
21f1892de0 Added chinese language 2016-09-12 10:02:02 +02:00
Robert Winkler
b97344849d Merge pull request #186 from mingkaili/patch-1
labels_zh.properties
2016-09-12 09:49:43 +02:00
Mingkai Lee
935d48d4cc labels_zh.properties
Add chinese labels.properties. Add chinese language.
2016-09-12 10:26:16 +08:00
Robert Winkler
73ba233f9e Merge pull request #181 from iwannayoyo/Remove_empty_columns
eliminate empty columns in tables
2016-08-31 10:20:25 +02:00
Chris Hartman
ff955d392b eliminate empty columns in tables 2016-08-25 16:43:17 -04:00
Robert Winkler
19fde31f67 Merge pull request #177 from mhswisscom/Fix_without_reformat
recursive examples patch without reformatting
2016-08-25 13:49:45 +02:00
Marc Habegger
b3f368ac37 recursive examples patch without reformatting 2016-08-25 13:33:27 +02:00
Robert Winkler
c5efb401b4 Added releaseVersion to build.gradle and documentation.gradle scripts so that the AsciiDoc documentation always refers to the release version and not to the SNAPSHOT version. 2016-08-04 12:10:08 +02:00
Robert Winkler
f386e6ed91 Updated version to 1.0.2-SNAPSHOT 2016-08-04 10:28:30 +02:00
Robert Winkler
55b323c063 Merge pull request #171 from zerok/fix/emptycontact
Allow empty contact objects
2016-08-04 10:25:14 +02:00
Robert Winkler
6f286b52d8 Prepare release v1.0.1 2016-08-04 10:03:08 +02:00
Horst Gutmann
4850673b96 Allow empty contact objects
According to the spec the contact object can be empty (it doesn't have
any required properties). Previously, the markup generation failed in
that situation due to an empty paragraph being generated. This change
fixes that.
2016-08-04 10:00:33 +02:00
518 changed files with 39771 additions and 12810 deletions

82
.github/workflows/gradle-build.yml vendored Normal file
View File

@@ -0,0 +1,82 @@
# This workflow will build a Java project with Gradle
# For more information see: https://help.github.com/actions/language-and-framework-guides/building-and-testing-java-with-gradle
name: Build
on:
push:
branches: [ 1.3.x ]
pull_request:
branches: [ 1.3.x ]
jobs:
validation:
name: "Gradle wrapper validation"
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2.3.5
- uses: gradle/wrapper-validation-action@v1.0.4
build:
name: "Build and publish"
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2.3.5
with:
fetch-depth: 0 # Shallow clones should be disabled for a better relevancy of analysis
- name: Set up JDK 11
uses: actions/setup-java@v2
with:
java-version: '11'
distribution: 'temurin'
- name: Cache SonarCloud packages
uses: actions/cache@v2.1.6
if: env.SONAR_TOKEN != null && env.SONAR_TOKEN != ''
env:
SONAR_TOKEN: ${{ secrets.SONAR_TOKEN }}
with:
path: ~/.sonar/cache
key: ${{ runner.os }}-sonar
restore-keys: ${{ runner.os }}-sonar
- name: Build
id: gradle
uses: eskatos/gradle-command-action@v1
with:
arguments: check
wrapper-cache-enabled: true
dependencies-cache-enabled: true
configuration-cache-enabled: true
- name: "Comment build scan url"
uses: actions/github-script@v5
if: github.event_name == 'pull_request' && failure()
with:
github-token: ${{secrets.GITHUB_TOKEN}}
script: |
github.issues.createComment({
issue_number: context.issue.number,
owner: context.repo.owner,
repo: context.repo.repo,
body: '❌ ${{ github.workflow }} failed: ${{ steps.gradle.outputs.build-scan-url }}'
})
- name: Publish Unit Test Results
uses: EnricoMi/publish-unit-test-result-action/composite@v1
if: always()
with:
files: '**/test-results/**/*.xml'
- name: Analyze with SonarCloud
continue-on-error: true
if: env.SONAR_TOKEN != null && env.SONAR_TOKEN != ''
uses: eskatos/gradle-command-action@v1
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} # Needed to get PR information, if any
SONAR_TOKEN: ${{ secrets.SONAR_TOKEN }}
with:
arguments: sonarqube -Psonar.organization=swagger2markup
dependencies-cache-enabled: true
configuration-cache-enabled: true
- name: Publish to Sonatype
if: ${{ github.event_name == 'push' && github.ref == 'refs/heads/1.3.x' }}
uses: eskatos/gradle-command-action@v1
env:
ORG_GRADLE_PROJECT_sonatypeUsername: ${{ secrets.SONATYPE_USER }}
ORG_GRADLE_PROJECT_sonatypePassword : ${{ secrets.SONATYPE_PASSWORD }}
with:
arguments: publishToSonatype
dependencies-cache-enabled: true
configuration-cache-enabled: true

View File

@@ -1,6 +1,6 @@
language: java
jdk:
- oraclejdk8
- openjdk8
before_install:
- chmod +x gradlew
after_success:

View File

@@ -7,6 +7,17 @@ image:https://travis-ci.org/Swagger2Markup/swagger2markup.svg?branch=master["Bui
== Overview
NOTE: Dear community,
unfortunately I can't maintain Swagger2Markup alone anymore. There are many interesting new topics:
1) Swagger v3 support
2) Fixing bugs
2) Merge Swagger2Markup repositories and create a new multi-module repository.
Any help is welcome.
Kind regards,
Robert
The primary goal of this project is to *simplify the generation of an up-to-date RESTful API documentation by combining documentation that's been hand-written with auto-generated API documentation* produced by https://github.com/swagger-api[Swagger]. The result is intended to be an *up-to-date, easy-to-read, on- and offline user guide*, comparable to https://developer.github.com/v3/[GitHub's API documentation]. The output of Swagger2Markup can be used as an alternative to https://github.com/swagger-api/swagger-ui[swagger-ui] and can be served as static content.
NOTE: The Swagger Specification has been donated to to the https://openapis.org/[Open API Initiative (OAI)] and has been renamed to the https://github.com/OAI/OpenAPI-Specification[OpenAPI Specification].
@@ -22,12 +33,12 @@ The project requires at least JDK 8.
== Example
image::src/docs/asciidoc/images/Swagger2Markup.PNG[]
image::swagger2markup-documentation/src/docs/asciidoc/images/Swagger2Markup.PNG[]
image::src/docs/asciidoc/images/Swagger2Markup_definitions.PNG[]
image::swagger2markup-documentation/src/docs/asciidoc/images/Swagger2Markup_definitions.PNG[]
== Reference documentation
- http://swagger2markup.github.io/swagger2markup/1.0.1/[Reference Documentation]
- http://swagger2markup.github.io/swagger2markup/1.3.4/[Reference Documentation]
- https://github.com/Swagger2Markup/swagger2markup/blob/master/RELEASENOTES.adoc[Release notes]
- https://github.com/Swagger2Markup/spring-swagger2markup-demo[Demo using Swagger2Markup, Spring Boot, Springfox and spring-restdocs]
@@ -54,6 +65,8 @@ If youd like an enhancement to be made to Swagger2Markup, pull requests are m
* http://www.appdirect.com/[AppDirect] -- The leading commerce platform for selling cloud services.
* http://www.wescale.com[wescale]
* http://taskassure.com[TaskAssure]
* https://www.isaac.nl[ISAAC]
* https://www.spreadshirt.de[Spreadshirt]
== License

View File

@@ -3,6 +3,21 @@
== Version 0.1.0
* Initial version with support for AsciiDoc and Markdown
=== Version 0.1.1
* Signed jar files
=== Version 0.1.2
* Removed logback from compile dependency
=== Version 0.1.3
* Removed commons.io from compile dependency
=== Version 0.1.4
* Fixed SECTION_TITLE_LEVEL3 in Markdown enum
=== Version 0.1.5
* Added SECTION_TITLE_LEVEL4
== Version 0.2.0
* This version is not downward compatible. This version supports includes of example files and JSON/XML Schema files. See documentation.
@@ -95,3 +110,63 @@
=== Version 1.0.1
* Enhancement: Support to render validation constraints of properties
* Enhancement: Possibility to disable rendering of the security chapter below operations
== Version 1.1.0
* PR #177: Fixed rendering of recursive examples
* PR #186: Add support for Chinese language
* PR #190: Add support for Spanish language
* PR #192: Updated min/max value to format correctly based on the data type
* PR #193: Added support for exclusiveMin and exclusiveMax
* Changed bold to ** and italic to __ so that special chars in the text are possible
=== Version 1.1.1
* Issue #194: Added a config parameter which allows to prepend the basePath to all paths.
* Updated swagger-parser from v1.0.16 to v1.0.23
* Added javslang v2.0.4 as a dependency
* Added paleo-core v0.10.1 as a dependency
* Updated markup-document-builder from 1.0.0 to 1.1.0
* PR #201: Add support for Brazilian Portuguese language
* PR #202: Add support for Japanese language
* Issue #205: Fixed the option to influence resource ordering
* Issue #198: Chinese chinese language encoding
* Issue #207: Properties that start with an underscore are displayed correctly now
* Refactored Swagger2Markup to use a Component-Based design. A document can be composed of components and components can be composed of other components.
* Added a method to add page breaks.
== Version 1.1.2
* Improve code blocks in markdown
== Version 1.2.0
* Issue #214: Add page break locations
* Issue #223: Improve example rendering
* Issue #215: Add ability to group operations by RegEx
* Added new configuration options: pageBreakLocations, headerRegex
* Added new valid value for configuration headerRegex: REGEX
* Updated markup-document-builder from 1.1.0 to 1.1.1
== Version 1.3.0
* Updated javslang from 2.0.4 to 2.0.5
* Updated paleo-core from 0.10.1 to 0.10.2
* Updated swagger-parser from v1.0.23 to v1.0.25
* Decimal numbers are formatted into locale-specific strings
=== Version 1.3.1
* PR #247: Fix request path and query params example support.
=== Version 1.3.2
* PR #290: Fixed list parsing in properties file
* PR #293: Fixed crash on empty tables
* Updated markup-document-builder from 1.1.1 to 1.1.2
=== Version 1.3.3
* Updated swagger-parser from v1.0.25 to 1.0.35
* PR #294: Examples always start with a newline if there is other content in the same cell
* PR 307: Include required parameters in example request
=== Version 1.3.4
* Moved from bintray to Sonatype
* Introduced Github actions
* Certain bug fixes
* Added support for MIME types with structured syntax suffixes (#410)

View File

@@ -1,67 +1,117 @@
buildscript {
plugins {
id "org.sonarqube" version "2.7"
id "me.champeau.gradle.jmh" version "0.4.8"
id 'org.asciidoctor.convert' version '1.6.0'
id "org.ajoberstar.github-pages" version "1.7.2"
id "io.github.gradle-nexus.publish-plugin" version "1.1.0"
}
apply plugin: 'idea'
apply from: "${rootDir}/libraries.gradle"
ext {
releaseVersion = '1.3.4'
}
allprojects {
apply plugin: 'jacoco'
apply plugin: 'me.champeau.gradle.jmh'
version = '1.3.4'
group 'io.github.swagger2markup'
description = 'swagger2markup Build'
repositories {
jcenter()
mavenCentral()
}
dependencies {
classpath 'org.asciidoctor:asciidoctor-gradle-plugin:1.5.3'
classpath 'org.asciidoctor:asciidoctorj-pdf:1.5.0-alpha.10.1'
classpath 'org.kt3k.gradle.plugin:coveralls-gradle-plugin:2.0.1'
classpath 'com.jfrog.bintray.gradle:gradle-bintray-plugin:1.6'
classpath "org.jfrog.buildinfo:build-info-extractor-gradle:4.0.0"
classpath "org.ajoberstar:gradle-git:1.3.2"
}
//artifactoryPublish.skip = true // apply to all projects except the root
ext {
coreProjects = subprojects.findAll {
p -> !p.name.endsWith("-bom")
}
}
description = 'swagger2markup Build'
version = '1.0.1'
group = 'io.github.swagger2markup'
apply plugin: 'java'
apply plugin: 'eclipse'
apply from: 'gradle/publishing.gradle'
apply from: 'gradle/coverage.gradle'
apply from: 'gradle/documentation.gradle'
configure(project.coreProjects) {
apply plugin: 'signing'
apply plugin: 'java'
apply plugin: 'maven'
apply plugin: 'maven-publish'
apply from: "${rootDir}/publishing.gradle"
apply plugin: 'jacoco'
tasks.withType(JavaCompile) {
sourceCompatibility = "1.8"
targetCompatibility = "1.8"
options.deprecation = true
options.encoding = 'UTF-8'
options.compilerArgs << "-Xlint:unchecked"
}
repositories {
maven {
url "https://oss.jfrog.org/artifactory/oss-snapshot-local"
tasks.withType(JavaCompile) {
sourceCompatibility = "11"
targetCompatibility = "11"
options.deprecation = true
options.encoding = 'UTF-8'
options.compilerArgs += ["-Xlint:unchecked", "-parameters"]
}
tasks.withType(Javadoc){
options.encoding = 'UTF-8'
}
jmh {
duplicateClassesStrategy = 'warn'
}
configurations.all {
resolutionStrategy {
failOnVersionConflict()
}
}
jcenter()
mavenCentral()
//mavenLocal()
}
dependencies {
compile 'io.github.swagger2markup:markup-document-builder:1.0.0'
compile 'io.swagger:swagger-compat-spec-parser:1.0.18'
compile 'org.apache.commons:commons-configuration2:2.0'
compile 'commons-beanutils:commons-beanutils:1.9.2'
compile 'org.apache.commons:commons-collections4:4.1'
testCompile 'junit:junit:4.11'
testCompile 'org.asciidoctor:asciidoctorj:1.5.4'
testCompile 'ch.qos.logback:logback-classic:1.1.2'
testCompile 'org.assertj:assertj-core:3.4.0'
testCompile 'io.github.robwin:assertj-diff:0.1.1'
nexusPublishing {
repositories {
sonatype()
}
}
sonarqube {
properties {
property "sonar.host.url", "https://sonarcloud.io"
property "sonar.organization", "swagger2markup"
property "sonar.projectName", "swagger2markup"
property "sonar.projectKey", "Swagger2Markup_swagger2markup"
property "sonar.links.homepage", "https://github.com/Swagger2Markup/swagger2markup"
property "sonar.links.ci", "https://travis-ci.org/Swagger2Markup/swagger2markup"
property "sonar.links.scm", "https://github.com/Swagger2Markup/swagger2markup"
property "sonar.links.issue", "https://github.com/Swagger2Markup/swagger2markup/issues"
property "sonar.language", "java"
}
}
def allTestCoverageFile = "$buildDir/jacoco/allTestCoverage.exec"
task jacocoMergeTest(type: JacocoMerge) {
destinationFile = file(allTestCoverageFile)
executionData = project.fileTree(dir: '.', include: '**/build/jacoco/test.exec')
}
task jacocoMerge(dependsOn: ['jacocoMergeTest']) {
// used to run the other merge tasks
}
subprojects {
sonarqube {
properties {
property "sonar.jacoco.reportPaths", allTestCoverageFile
}
}
afterEvaluate {
// exclude subprojects that don't produce a jar file or by design.
if (!project.name.equals('swagger2markup-bom') && !project.name.equals('swagger2markup-documentation')) {
jar {
inputs.property('moduleName', moduleName)
manifest.attributes(
'Automatic-Module-Name': moduleName
)
}
}
}
}
tasks.check.dependsOn tasks.jacocoTestReport
test {
if (System.properties['http.proxyHost']) {
systemProperty 'http.proxyHost', System.properties['http.proxyHost']
systemProperty 'http.proxyPort', System.properties['http.proxyPort']
systemProperty 'http.nonProxyHosts', System.properties['http.nonProxyHosts']
}
systemProperty 'file.encoding', 'UTF-8'
}
task wrapper(type: Wrapper) {
gradleVersion = '2.12'
dependsOn(subprojects.test) // required by cobertura to aggregate report
}

2
gradle.properties Normal file
View File

@@ -0,0 +1,2 @@
systemProp.file.encoding=UTF-8
systemProp.sun.jnu.encoding=UTF-8

View File

@@ -1,13 +0,0 @@
apply plugin: 'jacoco'
apply plugin: 'com.github.kt3k.coveralls'
jacocoTestReport {
reports {
xml.enabled = true // coveralls plugin depends on xml format report
html.enabled = true
}
}
tasks.coveralls {
dependsOn 'check'
}

View File

@@ -1,34 +0,0 @@
apply plugin: 'org.asciidoctor.convert'
apply plugin: 'org.ajoberstar.github-pages'
asciidoctor {
sources {
include 'index.adoc'
}
backends = ['html5', 'pdf']
attributes = [
doctype: 'book',
toc: 'left',
toclevels: '3',
numbered: '',
sectlinks: '',
sectanchors: '',
hardbreaks: '',
]
}
publishGhPages.dependsOn asciidoctor
githubPages {
repoUri = 'https://github.com/Swagger2Markup/swagger2markup.git'
credentials {
username = project.hasProperty('githubUser') ? project.githubUser : System.getenv('GITHUB_USER')
password = project.hasProperty('githubPassword') ? project.githubPassword : System.getenv('GITHUB_PASSWORD')
}
pages {
from file(asciidoctor.outputDir.path + '/html5')
into project.version
}
}

View File

@@ -1,151 +0,0 @@
import java.text.SimpleDateFormat
apply plugin: 'maven-publish'
apply plugin: 'com.jfrog.bintray'
apply plugin: "com.jfrog.artifactory"
Date buildTimeAndDate = new Date()
ext {
buildDate = new SimpleDateFormat('yyyy-MM-dd').format(buildTimeAndDate)
buildTime = new SimpleDateFormat('HH:mm:ss.SSSZ').format(buildTimeAndDate)
projectUrl = 'https://github.com/Swagger2Markup/swagger2markup'
licenseUrl = 'https://github.com/Swagger2Markup/swagger2markup/blob/master/LICENSE.txt'
scmUrl = 'https://github.com/Swagger2Markup/swagger2markup.git'
issuesUrl = 'https://github.com/Swagger2Markup/swagger2markup/issues'
}
task sourcesJar(type: Jar, dependsOn: classes) {
classifier = 'sources'
from sourceSets.main.allSource
}
task javadocJar(type: Jar, dependsOn: javadoc) {
classifier = 'javadoc'
from javadoc.destinationDir
}
artifacts {
archives sourcesJar
archives javadocJar
}
jar {
manifest {
attributes(
'Created-By': System.properties['java.version'] + " (" + System.properties['java.vendor'] + " " + System.properties['java.vm.version'] + ")",
'Built-With': "gradle-${project.getGradle().getGradleVersion()}, groovy-${GroovySystem.getVersion()}",
'Build-Time': "${new Date().format("yyyy-MM-dd'T'HH:mm:ssZ")}",
'Specification-Title': "${project.name}",
'Specification-Version': project.version.toString(),
'Implementation-Title': "${project.name}",
'Implementation-Version': project.version.toString()
)
}
}
if (!project.hasProperty('bintrayUsername')) ext.bintrayUsername = ''
if (!project.hasProperty('bintrayApiKey')) ext.bintrayApiKey = ''
if (!project.hasProperty('gpgPassphrase')) ext.gpgPassphrase = ''
if (!project.hasProperty('ossUser')) ext.ossUser = ''
if (!project.hasProperty('ossPassword')) ext.ossPassword = ''
publishing {
publications {
mavenJava(MavenPublication) {
from components.java
pom.withXml {
def devs = ['RobWin': 'Robert Winkler']
def root = asNode()
root.dependencies.'*'.findAll() {
it.scope.text() == 'runtime' && project.configurations.compile.allDependencies.find { dep ->
dep.name == it.artifactId.text()
}
}.each() {
it.scope*.value = 'compile'
}
root.appendNode('name', project.name)
root.appendNode('packaging', 'jar')
root.appendNode('url', projectUrl)
root.appendNode('description', project.description)
def license = root.appendNode('licenses').appendNode('license')
license.appendNode('name', 'Apache-2.0')
license.appendNode('url', licenseUrl)
license.appendNode('distribution', 'repo')
root.appendNode('scm').appendNode('url', scmUrl)
def developers = root.appendNode('developers')
devs.each {
def d = developers.appendNode('developer')
d.appendNode('id', it.key)
d.appendNode('name', it.value)
}
}
artifact sourcesJar
artifact javadocJar
}
}
}
bintray {
user = project.bintrayUsername
key = project.bintrayApiKey
dryRun = false //Whether to run this as dry-run, without deploying
publish = true //If version should be auto published after an upload
publications = ['mavenJava']
pkg {
repo = 'Maven'
name = 'swagger2markup'
userOrg = 'swagger2markup'
websiteUrl = projectUrl
issueTrackerUrl = issuesUrl
vcsUrl = scmUrl
desc = rootProject.description
licenses = ['Apache-2.0']
version {
vcsTag = rootProject.version
gpg {
sign = true //Determines whether to GPG sign the files. The default is false
passphrase = project.gpgPassphrase //Optional. The passphrase for GPG signing'
}
mavenCentralSync {
sync = true //Optional (true by default). Determines whether to sync the version to Maven Central.
user = ossUser //OSS user token
password = ossPassword //OSS user password
}
}
}
}
artifactory {
contextUrl = 'https://oss.jfrog.org'
resolve {
repository {
repoKey = 'libs-release'
}
}
publish {
repository {
repoKey = 'oss-snapshot-local' //The Artifactory repository key to publish to
//when using oss.jfrog.org the credentials are from Bintray. For local build we expect them to be found in
//~/.gradle/gradle.properties, otherwise to be set in the build server
username = project.hasProperty('bintrayUsername') ? project.bintrayUsername : System.getenv('BINTRAY_USER')
password = project.hasProperty('bintrayApiKey') ? project.bintrayApiKey : System.getenv('BINTRAY_KEY')
}
defaults {
publications('mavenJava')
}
}
if (System.properties['https.proxyHost']) {
clientConfig.proxy.host = System.properties['https.proxyHost']
clientConfig.proxy.port = System.properties['https.proxyPort'].toInteger()
}
}
tasks.artifactoryPublish {
dependsOn 'check'
}

Binary file not shown.

View File

@@ -1,6 +1,6 @@
#Thu Mar 31 16:29:35 CEST 2016
#Mon Oct 21 16:35:38 BST 2019
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-2.12-all.zip
distributionUrl=https\://services.gradle.org/distributions/gradle-5.6.3-all.zip

100
gradlew vendored
View File

@@ -1,4 +1,4 @@
#!/usr/bin/env bash
#!/usr/bin/env sh
##############################################################################
##
@@ -6,42 +6,6 @@
##
##############################################################################
# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
DEFAULT_JVM_OPTS=""
APP_NAME="Gradle"
APP_BASE_NAME=`basename "$0"`
# Use the maximum available, or set MAX_FD != -1 to use that value.
MAX_FD="maximum"
warn ( ) {
echo "$*"
}
die ( ) {
echo
echo "$*"
echo
exit 1
}
# OS specific support (must be 'true' or 'false').
cygwin=false
msys=false
darwin=false
case "`uname`" in
CYGWIN* )
cygwin=true
;;
Darwin* )
darwin=true
;;
MINGW* )
msys=true
;;
esac
# Attempt to set APP_HOME
# Resolve links: $0 may be a link
PRG="$0"
@@ -60,6 +24,46 @@ cd "`dirname \"$PRG\"`/" >/dev/null
APP_HOME="`pwd -P`"
cd "$SAVED" >/dev/null
APP_NAME="Gradle"
APP_BASE_NAME=`basename "$0"`
# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
DEFAULT_JVM_OPTS=""
# Use the maximum available, or set MAX_FD != -1 to use that value.
MAX_FD="maximum"
warn () {
echo "$*"
}
die () {
echo
echo "$*"
echo
exit 1
}
# OS specific support (must be 'true' or 'false').
cygwin=false
msys=false
darwin=false
nonstop=false
case "`uname`" in
CYGWIN* )
cygwin=true
;;
Darwin* )
darwin=true
;;
MINGW* )
msys=true
;;
NONSTOP* )
nonstop=true
;;
esac
CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
# Determine the Java command to use to start the JVM.
@@ -85,7 +89,7 @@ location of your Java installation."
fi
# Increase the maximum file descriptors if we can.
if [ "$cygwin" = "false" -a "$darwin" = "false" ] ; then
if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then
MAX_FD_LIMIT=`ulimit -H -n`
if [ $? -eq 0 ] ; then
if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then
@@ -150,11 +154,19 @@ if $cygwin ; then
esac
fi
# Split up the JVM_OPTS And GRADLE_OPTS values into an array, following the shell quoting and substitution rules
function splitJvmOpts() {
JVM_OPTS=("$@")
# Escape application args
save () {
for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done
echo " "
}
eval splitJvmOpts $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS
JVM_OPTS[${#JVM_OPTS[*]}]="-Dorg.gradle.appname=$APP_BASE_NAME"
APP_ARGS=$(save "$@")
exec "$JAVACMD" "${JVM_OPTS[@]}" -classpath "$CLASSPATH" org.gradle.wrapper.GradleWrapperMain "$@"
# Collect all arguments for the java command, following the shell quoting and substitution rules
eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS"
# by default we should be in the correct project dir, but when run from Finder on Mac, the cwd is wrong
if [ "$(uname)" = "Darwin" ] && [ "$HOME" = "$PWD" ]; then
cd "$(dirname "$0")"
fi
exec "$JAVACMD" "$@"

14
gradlew.bat vendored
View File

@@ -8,14 +8,14 @@
@rem Set local scope for the variables with windows NT shell
if "%OS%"=="Windows_NT" setlocal
@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
set DEFAULT_JVM_OPTS=
set DIRNAME=%~dp0
if "%DIRNAME%" == "" set DIRNAME=.
set APP_BASE_NAME=%~n0
set APP_HOME=%DIRNAME%
@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
set DEFAULT_JVM_OPTS=
@rem Find java.exe
if defined JAVA_HOME goto findJavaFromJavaHome
@@ -46,10 +46,9 @@ echo location of your Java installation.
goto fail
:init
@rem Get command-line arguments, handling Windowz variants
@rem Get command-line arguments, handling Windows variants
if not "%OS%" == "Windows_NT" goto win9xME_args
if "%@eval[2+2]" == "4" goto 4NT_args
:win9xME_args
@rem Slurp the command line arguments.
@@ -60,11 +59,6 @@ set _SKIP=2
if "x%~1" == "x" goto execute
set CMD_LINE_ARGS=%*
goto execute
:4NT_args
@rem Get arguments from the 4NT Shell from JP Software
set CMD_LINE_ARGS=%$
:execute
@rem Setup the command line

52
libraries.gradle Normal file
View File

@@ -0,0 +1,52 @@
// Allows centralized definition of the version of artifacts to
// use. In that respect it serves a role similar to <dependencyManagement> in Maven
ext {
implLibraries = [:]
testLibraries = [:]
dependencyOverrides = [:]
}
implLibraries = [
asciiDocJApi : "org.asciidoctor:asciidoctorj-api:2.2.0",
commonsBeanUtils : "commons-beanutils:commons-beanutils:1.9.4",
commonsCodec : "commons-codec:commons-codec:1.13",
commonsCollections4: "org.apache.commons:commons-collections4:4.4",
commonsConf2 : "org.apache.commons:commons-configuration2:2.6",
commonsLang3 : "org.apache.commons:commons-lang3:3.9",
commonsIO : "commons-io:commons-io:2.6",
commonsText : "org.apache.commons:commons-text:1.8",
guava : 'com.google.guava:guava:27.0.1-android',
jacksonDatabind : 'com.fasterxml.jackson.core:jackson-databind:2.9.10',
mark2Ascii : "nl.jworks.markdown_to_asciidoc:markdown_to_asciidoc:1.1",
paleo : "ch.netzwerg:paleo-core:0.14.0",
pegdown : "org.pegdown:pegdown:1.6.0",
slf4j : "org.slf4j:slf4j-api:1.7.28",
swaggerV2 : "io.swagger:swagger-parser:1.0.47",
swaggerV2Converter : "io.swagger.parser.v3:swagger-parser-v2-converter:2.0.15",
swaggerV3 : "io.swagger.parser.v3:swagger-parser:2.0.15",
vavr : "io.vavr:vavr:0.10.2"
]
testLibraries = [
asciiDocJ : "org.asciidoctor:asciidoctorj:2.2.0",
assertj : "org.assertj:assertj-core:3.13.2",
assertjDiff: "io.github.robwin:assertj-diff:0.1.1",
junit : "junit:junit:4.12",
logback : "ch.qos.logback:logback-classic:1.2.3",
mockito : "org.mockito:mockito-core:3.1.0"
]
dependencyOverrides = [
assertj : testLibraries.assertj,
commonsCodec : implLibraries.commonsCodec,
commonsIO : implLibraries.commonsIO,
commonsLang3 : implLibraries.commonsLang3,
findBugs : 'com.google.code.findbugs:jsr305:3.0.2',
guava : implLibraries.guava,
jaksonCore : 'com.github.fge:jackson-coreutils:1.8',
jacksonDatabind: implLibraries.jacksonDatabind,
jnrConstants : 'com.github.jnr:jnr-constants:0.9.12',
jnrEnxio : 'com.github.jnr:jnr-enxio:0.19',
jnrPosix : 'com.github.jnr:jnr-posix:3.0.49',
jodaTime : 'joda-time:joda-time:2.9.9',
slf4j : implLibraries.slf4j,
]

91
publishing.gradle Normal file
View File

@@ -0,0 +1,91 @@
import java.text.SimpleDateFormat
Date buildTimeAndDate = new Date()
ext {
buildDate = new SimpleDateFormat('yyyy-MM-dd').format(buildTimeAndDate)
buildTime = new SimpleDateFormat('HH:mm:ss.SSSZ').format(buildTimeAndDate)
licenseUrl = 'https://github.com/Swagger2Markup/swagger2markup/blob/master/LICENSE.txt'
scmUrl = 'https://github.com/Swagger2Markup/swagger2markup.git'
}
def projectArtifactId = 'swagger2markup'
def projectUrl = 'https://github.com/Swagger2Markup/swagger2markup'
def licenseUrl = 'https://github.com/Swagger2Markup/swagger2markup/blob/master/LICENSE.txt'
def scmUrl = 'https://github.com/Swagger2Markup/swagger2markup.git'
def issuesUrl = 'https://github.com/Swagger2Markup/swagger2markup/issues'
jar {
manifest {
attributes(
'Built-By': 'Robert Winkler',
'Created-By': System.properties['java.version'] + " (" + System.properties['java.vendor'] + " " + System.properties['java.vm.version'] + ")",
'Build-Date': project.buildDate,
'Build-Time': project.buildTime,
'Specification-Title': projectArtifactId,
'Specification-Version': project.version,
'Implementation-Title': projectArtifactId,
'Implementation-Version': project.version
)
}
}
task sourcesJar(type: Jar) {
from sourceSets.main.allJava
archiveClassifier = 'sources'
}
task javadocJar(type: Jar) {
from javadoc
archiveClassifier = 'javadoc'
}
artifacts {
archives sourcesJar
archives javadocJar
}
signing {
sign publishing.publications
}
publishing {
publications {
mavenJava(MavenPublication) {
from components.java
pom.withXml {
def devs = ['RobWin': 'Robert Winkler',
'austek': 'Ali Ustek']
def root = asNode()
root.dependencies.'*'.findAll() {
it.scope.text() == 'runtime' && project.configurations.compile.allDependencies.find { dep ->
dep.name == it.artifactId.text()
}
}.each() {
it.scope*.value = 'compile'
}
root.appendNode('name', projectArtifactId)
root.appendNode('packaging', 'jar')
root.appendNode('url', projectUrl)
root.appendNode('description', project.description)
def license = root.appendNode('licenses').appendNode('license')
license.appendNode('name', 'Apache-2.0')
license.appendNode('url', licenseUrl)
license.appendNode('distribution', 'repo')
root.appendNode('scm').appendNode('url', scmUrl)
def developers = root.appendNode('developers')
devs.each {
def d = developers.appendNode('developer')
d.appendNode('id', it.key)
d.appendNode('name', it.value)
}
}
artifact sourcesJar
artifact javadocJar
}
}
}

View File

@@ -1 +1,9 @@
rootProject.name = 'swagger2markup'
rootProject.name = 'swagger2markup'
include 'swagger2markup-asciidoc'
include 'swagger2markup-bom'
include 'swagger2markup-builder'
include 'swagger2markup-documentation'
include 'swagger2markup'
include 'swagger2markup-core'

View File

@@ -1,211 +0,0 @@
/*
* Copyright 2016 Robert Winkler
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.github.swagger2markup;
import io.github.swagger2markup.markup.builder.LineSeparator;
import io.github.swagger2markup.markup.builder.MarkupLanguage;
import io.github.swagger2markup.model.PathOperation;
import io.swagger.models.parameters.Parameter;
import java.util.Comparator;
/**
* Swagger2Markup configuration interface.
*/
public interface Swagger2MarkupConfig {
/**
* Specifies the markup language which should be used to generate the files.
*/
MarkupLanguage getMarkupLanguage();
/**
* Specifies the markup language used in Swagger descriptions.<br>
* By default, {@link io.github.swagger2markup.markup.builder.MarkupLanguage#MARKDOWN} is assumed.
*/
MarkupLanguage getSwaggerMarkupLanguage();
/**
* Include generated examples into the documents.
*/
boolean isGeneratedExamplesEnabled();
/**
* In addition to the Definitions file, also create separate definition files for each model definition.
*/
boolean isSeparatedDefinitionsEnabled();
/**
* In addition to the Paths file, also create separate operation files for each operation.
*/
boolean isSeparatedOperationsEnabled();
/**
* Specifies if the operations should be grouped by tags or stay as-is.
*/
GroupBy getPathsGroupedBy();
/**
* Specifies labels language of output files.
*/
Language getOutputLanguage();
/**
* Specifies if inline schemas are detailed
*/
boolean isInlineSchemaEnabled();
/**
* Specifies tag ordering.
*/
OrderBy getTagOrderBy();
/**
* Specifies a custom comparator function to order tags.
*/
Comparator<String> getTagOrdering();
/**
* Specifies operation ordering.
*/
OrderBy getOperationOrderBy();
/**
* Specifies a custom comparator function to order operations.
*/
Comparator<PathOperation> getOperationOrdering();
/**
* Specifies definition ordering.
*/
OrderBy getDefinitionOrderBy();
/**
* Specifies a custom comparator function to order definitions.
*/
Comparator<String> getDefinitionOrdering();
/**
* Specifies parameter ordering.
*/
OrderBy getParameterOrderBy();
/**
* Specifies a custom comparator function to order parameters.
*/
Comparator<Parameter> getParameterOrdering();
/**
* Specifies property ordering.
*/
OrderBy getPropertyOrderBy();
/**
* Specifies a custom comparator function to order properties.
*/
Comparator<String> getPropertyOrdering();
/**
* Specifies response ordering.
*/
OrderBy getResponseOrderBy();
/**
* Specifies a custom comparator function to order responses.
*/
Comparator<String> getResponseOrdering();
/**
* Enable use of inter-document cross-references when needed.
*/
boolean isInterDocumentCrossReferencesEnabled();
/**
* Inter-document cross-references optional prefix.
*/
String getInterDocumentCrossReferencesPrefix();
/**
* Optionally isolate the body parameter, if any, from other parameters.
*/
boolean isFlatBodyEnabled();
/**
* Optionally disable the security section for path sections
*/
boolean isPathSecuritySectionEnabled();
/**
* Optionally prefix all anchors for uniqueness.
*/
String getAnchorPrefix();
/**
* Overview document name (without extension).
*
* @return the overview document name (without extension)
*/
String getOverviewDocument();
/**
* Paths document name (without extension).
*
* @return the paths document name (without extension)
*/
String getPathsDocument();
/**
* Definitions document name (without extension).
*
* @return the definitions document name (without extension)
*/
String getDefinitionsDocument();
/**
* Security document name (without extension).
*
* @return the security document name (without extension)
*/
String getSecurityDocument();
/**
* Separated operations sub-folder name.
*
* @return the operations sub-folder name
*/
String getSeparatedOperationsFolder();
/**
* Separated definitions sub-folder name.
*
* @return the definitions sub-folder name
*/
String getSeparatedDefinitionsFolder();
/**
* Specifies the line separator which should be used.
*
* @return the line separator
*/
LineSeparator getLineSeparator();
/**
* Returns properties for extensions.
*
* @return the extension properties
*/
Swagger2MarkupProperties getExtensionsProperties();
}

View File

@@ -1,707 +0,0 @@
/*
* Copyright 2016 Robert Winkler
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.github.swagger2markup.builder;
import com.google.common.base.Function;
import com.google.common.collect.Ordering;
import io.github.swagger2markup.*;
import io.github.swagger2markup.markup.builder.LineSeparator;
import io.github.swagger2markup.markup.builder.MarkupLanguage;
import io.github.swagger2markup.model.PathOperation;
import io.swagger.models.HttpMethod;
import io.swagger.models.parameters.Parameter;
import org.apache.commons.configuration2.*;
import org.apache.commons.configuration2.builder.fluent.Configurations;
import org.apache.commons.configuration2.ex.ConfigurationException;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.Validate;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.Comparator;
import java.util.Map;
import java.util.Optional;
import java.util.Properties;
import static io.github.swagger2markup.Swagger2MarkupProperties.*;
public class Swagger2MarkupConfigBuilder {
private static final Logger logger = LoggerFactory.getLogger(Swagger2MarkupConfigBuilder.class);
private static final String PROPERTIES_DEFAULT = "io/github/swagger2markup/config/default.properties";
static final Ordering<PathOperation> OPERATION_METHOD_NATURAL_ORDERING = Ordering
.explicit(HttpMethod.POST, HttpMethod.GET, HttpMethod.PUT, HttpMethod.DELETE, HttpMethod.PATCH, HttpMethod.HEAD, HttpMethod.OPTIONS)
.onResultOf(new Function<PathOperation, HttpMethod>() {
public HttpMethod apply(PathOperation operation) {
return operation.getMethod();
}
});
static final Ordering<PathOperation> OPERATION_PATH_NATURAL_ORDERING = Ordering
.natural()
.onResultOf(new Function<PathOperation, String>() {
public String apply(PathOperation operation) {
return operation.getPath();
}
});
static final Ordering<Parameter> PARAMETER_IN_NATURAL_ORDERING = Ordering
.explicit("header", "path", "query", "formData", "body")
.onResultOf(new Function<Parameter, String>() {
public String apply(Parameter parameter) {
return parameter.getIn();
}
});
static final Ordering<Parameter> PARAMETER_NAME_NATURAL_ORDERING = Ordering
.natural()
.onResultOf(new Function<Parameter, String>() {
public String apply(Parameter parameter) {
return parameter.getName();
}
});
DefaultSwagger2MarkupConfig config = new DefaultSwagger2MarkupConfig();
public Swagger2MarkupConfigBuilder() {
this(new PropertiesConfiguration());
}
public Swagger2MarkupConfigBuilder(Properties properties) {
this(ConfigurationConverter.getConfiguration(properties));
}
public Swagger2MarkupConfigBuilder(Map<String, String> map) {
this(new MapConfiguration(map));
}
public Swagger2MarkupConfigBuilder(Configuration configuration) {
CompositeConfiguration compositeConfiguration = new CompositeConfiguration();
compositeConfiguration.addConfiguration(new SystemConfiguration());
compositeConfiguration.addConfiguration(configuration);
compositeConfiguration.addConfiguration(getDefaultConfiguration());
Swagger2MarkupProperties swagger2MarkupProperties = new Swagger2MarkupProperties(compositeConfiguration);
config.markupLanguage = swagger2MarkupProperties.getRequiredMarkupLanguage(MARKUP_LANGUAGE);
config.swaggerMarkupLanguage = swagger2MarkupProperties.getRequiredMarkupLanguage(SWAGGER_MARKUP_LANGUAGE);
config.generatedExamplesEnabled = swagger2MarkupProperties.getRequiredBoolean(GENERATED_EXAMPLES_ENABLED);
config.separatedDefinitionsEnabled = swagger2MarkupProperties.getRequiredBoolean(SEPARATED_DEFINITIONS_ENABLED);
config.separatedOperationsEnabled = swagger2MarkupProperties.getRequiredBoolean(SEPARATED_OPERATIONS_ENABLED);
config.pathsGroupedBy = swagger2MarkupProperties.getGroupBy(PATHS_GROUPED_BY);
config.outputLanguage = swagger2MarkupProperties.getLanguage(OUTPUT_LANGUAGE);
config.inlineSchemaEnabled = swagger2MarkupProperties.getRequiredBoolean(INLINE_SCHEMA_ENABLED);
config.interDocumentCrossReferencesEnabled = swagger2MarkupProperties.getRequiredBoolean(INTER_DOCUMENT_CROSS_REFERENCES_ENABLED);
config.interDocumentCrossReferencesPrefix = swagger2MarkupProperties.getString(INTER_DOCUMENT_CROSS_REFERENCES_PREFIX, null);
config.flatBodyEnabled = swagger2MarkupProperties.getRequiredBoolean(FLAT_BODY_ENABLED);
config.pathSecuritySectionEnabled = swagger2MarkupProperties.getRequiredBoolean(PATH_SECURITY_SECTION_ENABLED);
config.anchorPrefix = swagger2MarkupProperties.getString(ANCHOR_PREFIX, null);
config.overviewDocument = swagger2MarkupProperties.getRequiredString(OVERVIEW_DOCUMENT);
config.pathsDocument = swagger2MarkupProperties.getRequiredString(PATHS_DOCUMENT);
config.definitionsDocument = swagger2MarkupProperties.getRequiredString(DEFINITIONS_DOCUMENT);
config.securityDocument = swagger2MarkupProperties.getRequiredString(SECURITY_DOCUMENT);
config.separatedOperationsFolder = swagger2MarkupProperties.getRequiredString(SEPARATED_OPERATIONS_FOLDER);
config.separatedDefinitionsFolder = swagger2MarkupProperties.getRequiredString(SEPARATED_DEFINITIONS_FOLDER);
config.tagOrderBy = swagger2MarkupProperties.getOrderBy(TAG_ORDER_BY);
config.operationOrderBy = swagger2MarkupProperties.getOrderBy(OPERATION_ORDER_BY);
config.definitionOrderBy = swagger2MarkupProperties.getOrderBy(DEFINITION_ORDER_BY);
config.parameterOrderBy = swagger2MarkupProperties.getOrderBy(PARAMETER_ORDER_BY);
config.propertyOrderBy = swagger2MarkupProperties.getOrderBy(PROPERTY_ORDER_BY);
config.responseOrderBy = swagger2MarkupProperties.getOrderBy(RESPONSE_ORDER_BY);
Optional<String> lineSeparator = swagger2MarkupProperties.getString(LINE_SEPARATOR);
if(lineSeparator.isPresent() && StringUtils.isNoneBlank(lineSeparator.get())){
config.lineSeparator = LineSeparator.valueOf(lineSeparator.get());
}
Configuration swagger2markupConfiguration = compositeConfiguration.subset(PROPERTIES_PREFIX);
Configuration extensionsConfiguration = swagger2markupConfiguration.subset(EXTENSION_PREFIX);
config.extensionsProperties = new Swagger2MarkupProperties(extensionsConfiguration);
}
/**
* Loads the default properties from the classpath.
*
* @return the default properties
*/
private Configuration getDefaultConfiguration() {
Configurations configs = new Configurations();
try {
return configs.properties(PROPERTIES_DEFAULT);
} catch (ConfigurationException e) {
throw new RuntimeException(String.format("Can't load default properties '%s'", PROPERTIES_DEFAULT), e);
}
}
/**
* Builds the Swagger2MarkupConfig.
*
* @return the Swagger2MarkupConfig
*/
public Swagger2MarkupConfig build() {
buildNaturalOrdering();
return config;
}
private void buildNaturalOrdering() {
if (config.tagOrderBy == OrderBy.NATURAL)
config.tagOrdering = Ordering.natural();
if (config.operationOrderBy == OrderBy.NATURAL)
config.operationOrdering = OPERATION_PATH_NATURAL_ORDERING.compound(OPERATION_METHOD_NATURAL_ORDERING);
if (config.definitionOrderBy == OrderBy.NATURAL)
config.definitionOrdering = Ordering.natural();
if (config.parameterOrderBy == OrderBy.NATURAL)
config.parameterOrdering = PARAMETER_IN_NATURAL_ORDERING.compound(PARAMETER_NAME_NATURAL_ORDERING);
if (config.propertyOrderBy == OrderBy.NATURAL)
config.propertyOrdering = Ordering.natural();
if (config.responseOrderBy == OrderBy.NATURAL)
config.responseOrdering = Ordering.natural();
}
/**
* Specifies the markup language which should be used to generate the files.
*
* @param markupLanguage the markup language which is used to generate the files
* @return this builder
*/
public Swagger2MarkupConfigBuilder withMarkupLanguage(MarkupLanguage markupLanguage) {
Validate.notNull(markupLanguage, "%s must not be null", "markupLanguage");
config.markupLanguage = markupLanguage;
return this;
}
/**
* Specifies the markup language used in Swagger descriptions.
*
* @param swaggerMarkupLanguage the markup language used in Swagger descriptions
* @return this builder
*/
public Swagger2MarkupConfigBuilder withSwaggerMarkupLanguage(MarkupLanguage swaggerMarkupLanguage) {
Validate.notNull(swaggerMarkupLanguage, "%s must not be null", "swaggerMarkupLanguage");
config.swaggerMarkupLanguage = swaggerMarkupLanguage;
return this;
}
/**
* Include generated examples into the documents.
*
* @return this builder
*/
public Swagger2MarkupConfigBuilder withGeneratedExamples() {
config.generatedExamplesEnabled = true;
return this;
}
/**
* In addition to the Definitions file, also create separate definition files for each model definition.
*
* @return this builder
*/
public Swagger2MarkupConfigBuilder withSeparatedDefinitions() {
config.separatedDefinitionsEnabled = true;
return this;
}
/**
* In addition to the Paths file, also create separate operation files for each operation.
*
* @return this builder
*/
public Swagger2MarkupConfigBuilder withSeparatedOperations() {
config.separatedOperationsEnabled = true;
return this;
}
/**
* Specifies if the paths should be grouped by tags or stay as-is.
*
* @param pathsGroupedBy the GroupBy enum
* @return this builder
*/
public Swagger2MarkupConfigBuilder withPathsGroupedBy(GroupBy pathsGroupedBy) {
Validate.notNull(pathsGroupedBy, "%s must not be null", "pathsGroupedBy");
config.pathsGroupedBy = pathsGroupedBy;
return this;
}
/**
* Specifies labels language of output files.
*
* @param language the enum
* @return this builder
*/
public Swagger2MarkupConfigBuilder withOutputLanguage(Language language) {
Validate.notNull(language, "%s must not be null", "language");
config.outputLanguage = language;
return this;
}
/**
* Disable inline schema support.
*
* @return this builder
*/
public Swagger2MarkupConfigBuilder withoutInlineSchema() {
config.inlineSchemaEnabled = false;
return this;
}
/**
* Specifies tag ordering.<br>
* By default tag ordering == {@link io.github.swagger2markup.OrderBy#NATURAL}.<br>
* Use {@link #withTagOrdering(Comparator)} to set a custom ordering.
*
* @param orderBy tag ordering
* @return this builder
*/
public Swagger2MarkupConfigBuilder withTagOrdering(OrderBy orderBy) {
Validate.notNull(orderBy, "%s must not be null", "orderBy");
Validate.isTrue(orderBy != OrderBy.CUSTOM, "You must provide a custom comparator if orderBy == OrderBy.CUSTOM");
config.tagOrderBy = orderBy;
return this;
}
/**
* Specifies a custom comparator function to order tags.
*
* @param tagOrdering tag ordering
* @return this builder
*/
public Swagger2MarkupConfigBuilder withTagOrdering(Comparator<String> tagOrdering) {
Validate.notNull(tagOrdering, "%s must not be null", "tagOrdering");
config.tagOrderBy = OrderBy.CUSTOM;
config.tagOrdering = tagOrdering;
return this;
}
/**
* Specifies operation ordering.<br>
* By default operation ordering == {@link io.github.swagger2markup.OrderBy#AS_IS}.<br>
* Use {@link #withOperationOrdering(Comparator)} to set a custom ordering.
*
* @param orderBy operation ordering
* @return this builder
*/
public Swagger2MarkupConfigBuilder withOperationOrdering(OrderBy orderBy) {
Validate.notNull(orderBy, "%s must not be null", "orderBy");
Validate.isTrue(orderBy != OrderBy.CUSTOM, "You must provide a custom comparator if orderBy == OrderBy.CUSTOM");
config.operationOrderBy = orderBy;
return this;
}
/**
* Specifies a custom comparator function to order operations.
*
* @param operationOrdering operation ordering
* @return this builder
*/
public Swagger2MarkupConfigBuilder withOperationOrdering(Comparator<PathOperation> operationOrdering) {
Validate.notNull(operationOrdering, "%s must not be null", "operationOrdering");
config.operationOrderBy = OrderBy.CUSTOM;
config.operationOrdering = operationOrdering;
return this;
}
/**
* Specifies definition ordering.<br>
* By default definition ordering == {@link io.github.swagger2markup.OrderBy#NATURAL}.<br>
* Use {@link #withDefinitionOrdering(Comparator)} to set a custom ordering.
*
* @param orderBy definition ordering
* @return this builder
*/
public Swagger2MarkupConfigBuilder withDefinitionOrdering(OrderBy orderBy) {
Validate.notNull(orderBy, "%s must not be null", "orderBy");
Validate.isTrue(orderBy != OrderBy.CUSTOM, "You must provide a custom comparator if orderBy == OrderBy.CUSTOM");
config.definitionOrderBy = orderBy;
return this;
}
/**
* Specifies a custom comparator function to order definitions.
*
* @param definitionOrdering definition ordering
* @return this builder
*/
public Swagger2MarkupConfigBuilder withDefinitionOrdering(Comparator<String> definitionOrdering) {
Validate.notNull(definitionOrdering, "%s must not be null", "definitionOrdering");
config.definitionOrderBy = OrderBy.CUSTOM;
config.definitionOrdering = definitionOrdering;
return this;
}
/**
* Specifies parameter ordering.<br>
* By default parameter ordering == {@link OrderBy#NATURAL}.<br>
* Use {@link #withParameterOrdering(Comparator)} to set a custom ordering.
*
* @param orderBy parameter ordering
* @return this builder
*/
public Swagger2MarkupConfigBuilder withParameterOrdering(OrderBy orderBy) {
Validate.notNull(orderBy, "%s must not be null", "orderBy");
Validate.isTrue(orderBy != OrderBy.CUSTOM, "You must provide a custom comparator if orderBy == OrderBy.CUSTOM");
config.parameterOrderBy = orderBy;
return this;
}
/**
* Specifies a custom comparator function to order parameters.
*
* @param parameterOrdering parameter ordering
* @return this builder
*/
public Swagger2MarkupConfigBuilder withParameterOrdering(Comparator<Parameter> parameterOrdering) {
Validate.notNull(parameterOrdering, "%s must not be null", "parameterOrdering");
config.parameterOrderBy = OrderBy.CUSTOM;
config.parameterOrdering = parameterOrdering;
return this;
}
/**
* Specifies property ordering.<br>
* By default property ordering == {@link io.github.swagger2markup.OrderBy#NATURAL}.<br>
* Use {@link #withPropertyOrdering(Comparator)} to set a custom ordering.
*
* @param orderBy property ordering
* @return this builder
*/
public Swagger2MarkupConfigBuilder withPropertyOrdering(OrderBy orderBy) {
Validate.notNull(orderBy, "%s must not be null", "orderBy");
Validate.isTrue(orderBy != OrderBy.CUSTOM, "You must provide a custom comparator if orderBy == OrderBy.CUSTOM");
config.propertyOrderBy = orderBy;
return this;
}
/**
* Specifies a custom comparator function to order properties.
*
* @param propertyOrdering property ordering
* @return this builder
*/
public Swagger2MarkupConfigBuilder withPropertyOrdering(Comparator<String> propertyOrdering) {
Validate.notNull(propertyOrdering, "%s must not be null", "propertyOrdering");
config.propertyOrderBy = OrderBy.CUSTOM;
config.propertyOrdering = propertyOrdering;
return this;
}
/**
* Specifies response ordering.<br>
* By default response ordering == {@link io.github.swagger2markup.OrderBy#NATURAL}.<br>
* Use {@link #withResponseOrdering(Comparator)} to set a custom ordering.
*
* @param orderBy response ordering
* @return this builder
*/
public Swagger2MarkupConfigBuilder withResponseOrdering(OrderBy orderBy) {
Validate.notNull(orderBy, "%s must not be null", "orderBy");
Validate.isTrue(orderBy != OrderBy.CUSTOM, "You must provide a custom comparator if orderBy == OrderBy.CUSTOM");
config.responseOrderBy = orderBy;
return this;
}
/**
* Specifies a custom comparator function to order responses.
*
* @param responseOrdering response ordering
* @return this builder
*/
public Swagger2MarkupConfigBuilder withResponseOrdering(Comparator<String> responseOrdering) {
Validate.notNull(responseOrdering, "%s must not be null", "responseOrdering");
config.responseOrderBy = OrderBy.CUSTOM;
config.responseOrdering = responseOrdering;
return this;
}
/**
* Enable use of inter-document cross-references when needed.
*
* @param prefix Prefix to document in all inter-document cross-references.
* @return this builder
*/
public Swagger2MarkupConfigBuilder withInterDocumentCrossReferences(String prefix) {
Validate.notNull(prefix, "%s must not be null", "prefix");
config.interDocumentCrossReferencesEnabled = true;
config.interDocumentCrossReferencesPrefix = prefix;
return this;
}
/**
* Enable use of inter-document cross-references when needed.
*
* @return this builder
*/
public Swagger2MarkupConfigBuilder withInterDocumentCrossReferences() {
config.interDocumentCrossReferencesEnabled = true;
return this;
}
/**
* Optionally isolate the body parameter, if any, from other parameters.
*
* @return this builder
*/
public Swagger2MarkupConfigBuilder withFlatBody() {
config.flatBodyEnabled = true;
return this;
}
/**
* Optionally disable the security section for path sections
*
* @return this builder
*/
public Swagger2MarkupConfigBuilder withoutPathSecuritySection() {
config.pathSecuritySectionEnabled = false;
return this;
}
/**
* Optionally prefix all anchors for uniqueness.
*
* @param anchorPrefix anchor prefix.
* @return this builder
*/
public Swagger2MarkupConfigBuilder withAnchorPrefix(String anchorPrefix) {
Validate.notNull(anchorPrefix, "%s must no be null", "anchorPrefix");
config.anchorPrefix = anchorPrefix;
return this;
}
/**
* Specifies the line separator which should be used.
*
* @param lineSeparator the lineSeparator
* @return this builder
*/
public Swagger2MarkupConfigBuilder withLineSeparator(LineSeparator lineSeparator) {
Validate.notNull(lineSeparator, "%s must no be null", "lineSeparator");
config.lineSeparator = lineSeparator;
return this;
}
static class DefaultSwagger2MarkupConfig implements Swagger2MarkupConfig{
private MarkupLanguage markupLanguage;
private MarkupLanguage swaggerMarkupLanguage;
private boolean generatedExamplesEnabled;
private boolean separatedDefinitionsEnabled;
private boolean separatedOperationsEnabled;
private GroupBy pathsGroupedBy;
private Language outputLanguage;
private boolean inlineSchemaEnabled;
private OrderBy tagOrderBy;
private Comparator<String> tagOrdering;
private OrderBy operationOrderBy;
private Comparator<PathOperation> operationOrdering;
private OrderBy definitionOrderBy;
private Comparator<String> definitionOrdering;
private OrderBy parameterOrderBy;
private Comparator<Parameter> parameterOrdering;
private OrderBy propertyOrderBy;
private Comparator<String> propertyOrdering;
private OrderBy responseOrderBy;
private Comparator<String> responseOrdering;
private boolean interDocumentCrossReferencesEnabled;
private String interDocumentCrossReferencesPrefix;
private boolean flatBodyEnabled;
private boolean pathSecuritySectionEnabled;
private String anchorPrefix;
private LineSeparator lineSeparator;
private String overviewDocument;
private String pathsDocument;
private String definitionsDocument;
private String securityDocument;
private String separatedOperationsFolder;
private String separatedDefinitionsFolder;
private Swagger2MarkupProperties extensionsProperties;
@Override
public MarkupLanguage getMarkupLanguage() {
return markupLanguage;
}
@Override
public MarkupLanguage getSwaggerMarkupLanguage() {
return swaggerMarkupLanguage;
}
@Override
public boolean isGeneratedExamplesEnabled() {
return generatedExamplesEnabled;
}
@Override
public boolean isSeparatedDefinitionsEnabled() {
return separatedDefinitionsEnabled;
}
@Override
public boolean isSeparatedOperationsEnabled() {
return separatedOperationsEnabled;
}
@Override
public GroupBy getPathsGroupedBy() {
return pathsGroupedBy;
}
@Override
public Language getOutputLanguage() {
return outputLanguage;
}
@Override
public boolean isInlineSchemaEnabled() {
return inlineSchemaEnabled;
}
@Override
public OrderBy getTagOrderBy() {
return tagOrderBy;
}
@Override
public Comparator<String> getTagOrdering() {
return tagOrdering;
}
@Override
public OrderBy getOperationOrderBy() {
return operationOrderBy;
}
@Override
public Comparator<PathOperation> getOperationOrdering() {
return operationOrdering;
}
@Override
public OrderBy getDefinitionOrderBy() {
return definitionOrderBy;
}
@Override
public Comparator<String> getDefinitionOrdering() {
return definitionOrdering;
}
@Override
public OrderBy getParameterOrderBy() {
return parameterOrderBy;
}
@Override
public Comparator<Parameter> getParameterOrdering() {
return parameterOrdering;
}
@Override
public OrderBy getPropertyOrderBy() {
return propertyOrderBy;
}
@Override
public Comparator<String> getPropertyOrdering() {
return propertyOrdering;
}
@Override
public OrderBy getResponseOrderBy() {
return responseOrderBy;
}
@Override
public Comparator<String> getResponseOrdering() {
return responseOrdering;
}
@Override
public boolean isInterDocumentCrossReferencesEnabled() {
return interDocumentCrossReferencesEnabled;
}
@Override
public String getInterDocumentCrossReferencesPrefix() {
return interDocumentCrossReferencesPrefix;
}
@Override
public boolean isFlatBodyEnabled() {
return flatBodyEnabled;
}
@Override
public boolean isPathSecuritySectionEnabled() {
return pathSecuritySectionEnabled;
}
@Override
public String getAnchorPrefix() {
return anchorPrefix;
}
@Override
public String getOverviewDocument() {
return overviewDocument;
}
@Override
public String getPathsDocument() {
return pathsDocument;
}
@Override
public String getDefinitionsDocument() {
return definitionsDocument;
}
@Override
public String getSecurityDocument() {
return securityDocument;
}
@Override
public String getSeparatedOperationsFolder() {
return separatedOperationsFolder;
}
@Override
public String getSeparatedDefinitionsFolder() {
return separatedDefinitionsFolder;
}
@Override
public LineSeparator getLineSeparator() {
return lineSeparator;
}
@Override
public Swagger2MarkupProperties getExtensionsProperties() {
return extensionsProperties;
}
}
}

View File

@@ -1,61 +0,0 @@
/*
* Copyright 2016 Robert Winkler
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.github.swagger2markup.internal.document;
import io.github.swagger2markup.markup.builder.MarkupDocBuilder;
import java.nio.charset.Charset;
import java.nio.file.OpenOption;
import java.nio.file.Path;
public class MarkupDocument {
private MarkupDocBuilder markupDocBuilder;
public MarkupDocument(MarkupDocBuilder markupDocBuilder) {
this.markupDocBuilder = markupDocBuilder;
}
/**
* Returns a string representation of the document.
*/
public String toString() {
return markupDocBuilder.toString();
}
/**
* Writes the content of the builder to a file.<br>
* An extension identifying the markup language will be automatically added to file name.
*
* @param file the generated file
* @param charset the the charset to use for encoding
* @param options the file open options
*/
public void writeToFile(Path file, Charset charset, OpenOption... options) {
markupDocBuilder.writeToFile(file, charset, options);
}
/**
* Writes the content of the builder to a file.
*
* @param file the generated file
* @param charset the the charset to use for encoding
* @param options the file open options
*/
public void writeToFileWithoutExtension(Path file, Charset charset, OpenOption... options) {
markupDocBuilder.writeToFileWithoutExtension(file, charset, options);
}
}

View File

@@ -1,336 +0,0 @@
/*
* Copyright 2016 Robert Winkler
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.github.swagger2markup.internal.document.builder;
import io.github.swagger2markup.Swagger2MarkupConverter;
import io.github.swagger2markup.Swagger2MarkupExtensionRegistry;
import io.github.swagger2markup.internal.document.MarkupDocument;
import io.github.swagger2markup.internal.type.ObjectType;
import io.github.swagger2markup.internal.type.ObjectTypePolymorphism;
import io.github.swagger2markup.internal.type.Type;
import io.github.swagger2markup.internal.utils.ModelUtils;
import io.github.swagger2markup.markup.builder.MarkupDocBuilder;
import io.github.swagger2markup.spi.DefinitionsDocumentExtension;
import io.swagger.models.Model;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.collections4.MapUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.Validate;
import java.io.File;
import java.nio.charset.StandardCharsets;
import java.nio.file.Path;
import java.util.*;
import static io.github.swagger2markup.internal.utils.MapUtils.toKeySet;
import static io.github.swagger2markup.spi.DefinitionsDocumentExtension.Context;
import static io.github.swagger2markup.spi.DefinitionsDocumentExtension.Position;
import static io.github.swagger2markup.utils.IOUtils.normalizeName;
import static org.apache.commons.lang3.StringUtils.defaultString;
import static org.apache.commons.lang3.StringUtils.isNotBlank;
/**
* @author Robert Winkler
*/
public class DefinitionsDocumentBuilder extends MarkupDocumentBuilder {
/* Discriminator is only displayed for inheriting definitions */
private static final boolean ALWAYS_DISPLAY_DISCRIMINATOR = false;
private static final String DEFINITIONS_ANCHOR = "definitions";
private final String DEFINITIONS;
private final String DISCRIMINATOR_COLUMN;
private final String POLYMORPHISM_COLUMN;
private final Map<ObjectTypePolymorphism.Nature, String> POLYMORPHISM_NATURE;
private final String TYPE_COLUMN;
private static final List<String> IGNORED_DEFINITIONS = Collections.singletonList("Void");
public DefinitionsDocumentBuilder(Swagger2MarkupConverter.Context context, Swagger2MarkupExtensionRegistry extensionRegistry, Path outputPath) {
super(context, extensionRegistry, outputPath);
final ResourceBundle labels = ResourceBundle.getBundle("io/github/swagger2markup/lang/labels", config.getOutputLanguage().toLocale());
DEFINITIONS = labels.getString("definitions");
POLYMORPHISM_COLUMN = labels.getString("polymorphism.column");
DISCRIMINATOR_COLUMN = labels.getString("polymorphism.discriminator");
POLYMORPHISM_NATURE = new HashMap<ObjectTypePolymorphism.Nature, String>() {{
put(ObjectTypePolymorphism.Nature.COMPOSITION, labels.getString("polymorphism.nature.COMPOSITION"));
put(ObjectTypePolymorphism.Nature.INHERITANCE, labels.getString("polymorphism.nature.INHERITANCE"));
}};
TYPE_COLUMN = labels.getString("type_column");
if (config.isSeparatedDefinitionsEnabled()) {
if (logger.isDebugEnabled()) {
logger.debug("Create separated definition files is enabled.");
}
Validate.notNull(outputPath, "Output directory is required for separated definition files!");
} else {
if (logger.isDebugEnabled()) {
logger.debug("Create separated definition files is disabled.");
}
}
}
/**
* Builds the definitions MarkupDocument.
*
* @return the definitions MarkupDocument
*/
@Override
public MarkupDocument build() {
if (MapUtils.isNotEmpty(globalContext.getSwagger().getDefinitions())) {
applyDefinitionsDocumentExtension(new Context(Position.DOCUMENT_BEFORE, this.markupDocBuilder));
buildDefinitionsTitle(DEFINITIONS);
applyDefinitionsDocumentExtension(new Context(Position.DOCUMENT_BEGIN, this.markupDocBuilder));
buildDefinitionsSection();
applyDefinitionsDocumentExtension(new Context(Position.DOCUMENT_END, this.markupDocBuilder));
applyDefinitionsDocumentExtension(new Context(Position.DOCUMENT_AFTER, this.markupDocBuilder));
}
return new MarkupDocument(markupDocBuilder);
}
private void buildDefinitionsSection() {
Set<String> definitionNames = toKeySet(globalContext.getSwagger().getDefinitions(), config.getDefinitionOrdering());
for (String definitionName : definitionNames) {
Model model = globalContext.getSwagger().getDefinitions().get(definitionName);
if (isNotBlank(definitionName)) {
if (checkThatDefinitionIsNotInIgnoreList(definitionName)) {
buildDefinition(definitionName, model);
if (logger.isInfoEnabled()) {
logger.info("Definition processed : '{}'", definitionName);
}
} else {
if (logger.isDebugEnabled()) {
logger.debug("Definition was ignored : '{}'", definitionName);
}
}
}
}
}
private void buildDefinitionsTitle(String title) {
this.markupDocBuilder.sectionTitleWithAnchorLevel1(title, DEFINITIONS_ANCHOR);
}
/**
* Apply extension context to all DefinitionsContentExtension
*
* @param context context
*/
private void applyDefinitionsDocumentExtension(Context context) {
for (DefinitionsDocumentExtension extension : extensionRegistry.getDefinitionsDocumentExtensions()) {
extension.apply(context);
}
}
/**
* Create the definition filename depending on the generation mode
*
* @param definitionName definition name
* @return definition filename
*/
private String resolveDefinitionDocument(String definitionName) {
if (config.isSeparatedDefinitionsEnabled())
return new File(config.getSeparatedDefinitionsFolder(), markupDocBuilder.addFileExtension(normalizeName(definitionName))).getPath();
else
return markupDocBuilder.addFileExtension(config.getDefinitionsDocument());
}
/**
* Generate definition files depending on the generation mode
*
* @param definitionName definition name to process
* @param model definition model to process
*/
private void buildDefinition(String definitionName, Model model) {
if (config.isSeparatedDefinitionsEnabled()) {
MarkupDocBuilder defDocBuilder = copyMarkupDocBuilder();
buildDefinition(definitionName, model, defDocBuilder);
Path definitionFile = outputPath.resolve(resolveDefinitionDocument(definitionName));
defDocBuilder.writeToFileWithoutExtension(definitionFile, StandardCharsets.UTF_8);
if (logger.isInfoEnabled()) {
logger.info("Separate definition file produced : '{}'", definitionFile);
}
definitionRef(definitionName, this.markupDocBuilder);
} else {
buildDefinition(definitionName, model, this.markupDocBuilder);
}
}
/**
* Checks that the definition is not in the list of ignored definitions.
*
* @param definitionName the name of the definition
* @return true if the definition can be processed
*/
private boolean checkThatDefinitionIsNotInIgnoreList(String definitionName) {
return !IGNORED_DEFINITIONS.contains(definitionName);
}
/**
* Builds a concrete definition
*
* @param definitionName the name of the definition
* @param model the Swagger Model of the definition
* @param docBuilder the docbuilder do use for output
*/
private void buildDefinition(String definitionName, Model model, MarkupDocBuilder docBuilder) {
applyDefinitionsDocumentExtension(new Context(Position.DEFINITION_BEFORE, docBuilder, definitionName, model));
buildDefinitionTitle(definitionName, definitionName, docBuilder);
applyDefinitionsDocumentExtension(new Context(Position.DEFINITION_BEGIN, docBuilder, definitionName, model));
buildDescriptionParagraph(model, docBuilder);
inlineDefinitions(typeSection(definitionName, model, docBuilder), definitionName, docBuilder);
applyDefinitionsDocumentExtension(new Context(Position.DEFINITION_END, docBuilder, definitionName, model));
applyDefinitionsDocumentExtension(new Context(Position.DEFINITION_AFTER, docBuilder, definitionName, model));
}
/**
* Builds a cross-reference to a separated definition file.
*
* @param definitionName definition name to target
* @param docBuilder the docbuilder do use for output
*/
private void definitionRef(String definitionName, MarkupDocBuilder docBuilder) {
buildDefinitionTitle(copyMarkupDocBuilder().crossReference(new DefinitionDocumentResolverDefault().apply(definitionName), definitionName, definitionName).toString(), "ref-" + definitionName, docBuilder);
}
/**
* Builds definition title
*
* @param title definition title
* @param anchor optional anchor (null => auto-generate from title)
* @param docBuilder the docbuilder do use for output
*/
private void buildDefinitionTitle(String title, String anchor, MarkupDocBuilder docBuilder) {
docBuilder.sectionTitleWithAnchorLevel2(title, anchor);
}
/**
* Builds the type informations of a definition
*
* @param definitionName name of the definition to display
* @param model model of the definition to display
* @param docBuilder the docbuilder do use for output
* @return a list of inlined types.
*/
private List<ObjectType> typeSection(String definitionName, Model model, MarkupDocBuilder docBuilder) {
List<ObjectType> inlineDefinitions = new ArrayList<>();
Type modelType = ModelUtils.resolveRefType(ModelUtils.getType(model, globalContext.getSwagger().getDefinitions(), new DefinitionDocumentResolverFromDefinition()));
if (!(modelType instanceof ObjectType)) {
modelType = createInlineType(modelType, definitionName, definitionName + " " + "inline", inlineDefinitions);
}
if (modelType instanceof ObjectType) {
ObjectType objectType = (ObjectType) modelType;
MarkupDocBuilder typeInfos = copyMarkupDocBuilder();
switch (objectType.getPolymorphism().getNature()) {
case COMPOSITION:
typeInfos.italicText(POLYMORPHISM_COLUMN).textLine(COLON + POLYMORPHISM_NATURE.get(objectType.getPolymorphism().getNature()));
break;
case INHERITANCE:
typeInfos.italicText(POLYMORPHISM_COLUMN).textLine(COLON + POLYMORPHISM_NATURE.get(objectType.getPolymorphism().getNature()));
typeInfos.italicText(DISCRIMINATOR_COLUMN).textLine(COLON + objectType.getPolymorphism().getDiscriminator());
break;
case NONE:
if (ALWAYS_DISPLAY_DISCRIMINATOR) {
if (StringUtils.isNotBlank(objectType.getPolymorphism().getDiscriminator()))
typeInfos.italicText(DISCRIMINATOR_COLUMN).textLine(COLON + objectType.getPolymorphism().getDiscriminator());
}
default: break;
}
String typeInfosString = typeInfos.toString();
if (StringUtils.isNotBlank(typeInfosString))
docBuilder.paragraph(typeInfosString, true);
inlineDefinitions.addAll(buildPropertiesTable(((ObjectType) modelType).getProperties(), definitionName, new DefinitionDocumentResolverFromDefinition(), docBuilder));
} else if (modelType != null) {
MarkupDocBuilder typeInfos = copyMarkupDocBuilder();
typeInfos.italicText(TYPE_COLUMN).textLine(COLON + modelType.displaySchema(docBuilder));
docBuilder.paragraph(typeInfos.toString());
}
return inlineDefinitions;
}
private void buildDescriptionParagraph(Model model, MarkupDocBuilder docBuilder) {
modelDescription(model, docBuilder);
}
private void modelDescription(Model model, MarkupDocBuilder docBuilder) {
String description = model.getDescription();
if (isNotBlank(description)) {
buildDescriptionParagraph(description, docBuilder);
}
}
/**
* Builds the title of an inline schema.
* Inline definitions should never been referenced in TOC because they have no real existence, so they are just text.
*
* @param title inline schema title
* @param anchor inline schema anchor
* @param docBuilder the docbuilder do use for output
*/
private void addInlineDefinitionTitle(String title, String anchor, MarkupDocBuilder docBuilder) {
docBuilder.anchor(anchor, null);
docBuilder.newLine();
docBuilder.boldTextLine(title);
}
/**
* Builds inline schema definitions
*
* @param definitions all inline definitions to display
* @param uniquePrefix unique prefix to prepend to inline object names to enforce unicity
* @param docBuilder the docbuilder do use for output
*/
private void inlineDefinitions(List<ObjectType> definitions, String uniquePrefix, MarkupDocBuilder docBuilder) {
if (CollectionUtils.isNotEmpty(definitions)) {
for (ObjectType definition : definitions) {
addInlineDefinitionTitle(definition.getName(), definition.getUniqueName(), docBuilder);
List<ObjectType> localDefinitions = buildPropertiesTable(definition.getProperties(), uniquePrefix, new DefinitionDocumentResolverFromDefinition(), docBuilder);
for (ObjectType localDefinition : localDefinitions)
inlineDefinitions(Collections.singletonList(localDefinition), localDefinition.getUniqueName(), docBuilder);
}
}
}
/**
* Overrides definition document resolver functor for inter-document cross-references from definitions files.
* This implementation simplify the path between two definitions because all definitions are in the same path.
*/
class DefinitionDocumentResolverFromDefinition extends DefinitionDocumentResolverDefault {
public DefinitionDocumentResolverFromDefinition() {
}
public String apply(String definitionName) {
String defaultResolver = super.apply(definitionName);
if (defaultResolver != null && config.isSeparatedDefinitionsEnabled())
return defaultString(config.getInterDocumentCrossReferencesPrefix()) + markupDocBuilder.addFileExtension(normalizeName(definitionName));
else
return defaultResolver;
}
}
}

View File

@@ -1,357 +0,0 @@
/*
* Copyright 2016 Robert Winkler
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.github.swagger2markup.internal.document.builder;
import io.github.swagger2markup.Swagger2MarkupConfig;
import io.github.swagger2markup.Swagger2MarkupConverter;
import io.github.swagger2markup.Swagger2MarkupExtensionRegistry;
import io.github.swagger2markup.internal.document.MarkupDocument;
import io.github.swagger2markup.internal.type.*;
import io.github.swagger2markup.internal.utils.PropertyUtils;
import io.github.swagger2markup.markup.builder.MarkupDocBuilder;
import io.github.swagger2markup.markup.builder.MarkupDocBuilders;
import io.github.swagger2markup.markup.builder.MarkupLanguage;
import io.github.swagger2markup.markup.builder.MarkupTableColumn;
import io.github.swagger2markup.utils.IOUtils;
import io.swagger.models.properties.Property;
import io.swagger.util.Json;
import org.apache.commons.collections4.MapUtils;
import org.apache.commons.lang3.BooleanUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.File;
import java.io.IOException;
import java.io.StringReader;
import java.nio.file.Path;
import java.util.*;
import static io.github.swagger2markup.internal.utils.MapUtils.toKeySet;
import static org.apache.commons.lang3.StringUtils.defaultString;
import static org.apache.commons.lang3.StringUtils.isNotBlank;
/**
* @author Robert Winkler
*/
public abstract class MarkupDocumentBuilder {
protected static final String COLON = " : ";
protected final String DEFAULT_COLUMN;
protected final String MAXLENGTH_COLUMN;
protected final String MINLENGTH_COLUMN;
protected final String LENGTH_COLUMN;
protected final String PATTERN_COLUMN;
protected final String MINVALUE_COLUMN;
protected final String MAXVALUE_COLUMN;
protected final String EXAMPLE_COLUMN;
protected final String SCHEMA_COLUMN;
protected final String NAME_COLUMN;
protected final String DESCRIPTION_COLUMN;
protected final String SCOPES_COLUMN;
protected final String DESCRIPTION;
protected final String PRODUCES;
protected final String CONSUMES;
protected final String TAGS;
protected final String NO_CONTENT;
protected final String FLAGS_COLUMN;
protected final String FLAGS_REQUIRED;
protected final String FLAGS_OPTIONAL;
protected final String FLAGS_READ_ONLY;
protected Logger logger = LoggerFactory.getLogger(getClass());
protected Swagger2MarkupConverter.Context globalContext;
protected Swagger2MarkupExtensionRegistry extensionRegistry;
protected Swagger2MarkupConfig config;
protected MarkupDocBuilder markupDocBuilder;
protected Path outputPath;
MarkupDocumentBuilder(Swagger2MarkupConverter.Context globalContext, Swagger2MarkupExtensionRegistry extensionRegistry, Path outputPath) {
this.globalContext = globalContext;
this.extensionRegistry = extensionRegistry;
this.config = globalContext.getConfig();
this.outputPath = outputPath;
this.markupDocBuilder = MarkupDocBuilders.documentBuilder(config.getMarkupLanguage(), config.getLineSeparator()).withAnchorPrefix(config.getAnchorPrefix());
ResourceBundle labels = ResourceBundle.getBundle("io/github/swagger2markup/lang/labels", config.getOutputLanguage().toLocale());
DEFAULT_COLUMN = labels.getString("default_column");
MINLENGTH_COLUMN = labels.getString("minlength_column");
MAXLENGTH_COLUMN = labels.getString("maxlength_column");
LENGTH_COLUMN = labels.getString("length_column");
PATTERN_COLUMN = labels.getString("pattern_column");
MINVALUE_COLUMN = labels.getString("minvalue_column");
MAXVALUE_COLUMN = labels.getString("maxvalue_column");
EXAMPLE_COLUMN = labels.getString("example_column");
FLAGS_COLUMN = labels.getString("flags.column");
FLAGS_REQUIRED = labels.getString("flags.required");
FLAGS_OPTIONAL = labels.getString("flags.optional");
FLAGS_READ_ONLY = labels.getString("flags.read_only");
SCHEMA_COLUMN = labels.getString("schema_column");
NAME_COLUMN = labels.getString("name_column");
DESCRIPTION_COLUMN = labels.getString("description_column");
SCOPES_COLUMN = labels.getString("scopes_column");
DESCRIPTION = DESCRIPTION_COLUMN;
PRODUCES = labels.getString("produces");
CONSUMES = labels.getString("consumes");
TAGS = labels.getString("tags");
NO_CONTENT = labels.getString("no_content");
}
/**
* Builds the MarkupDocument.
*
* @return the built MarkupDocument
* @throws IOException if the files to include are not readable
*/
public abstract MarkupDocument build() throws IOException;
/**
* Returns a RefType to a new inlined type named with {@code name} and {@code uniqueName}.<br>
* The returned RefType point to the new inlined type which is added to the {@code inlineDefinitions} collection.<br>
* The function is recursive and support collections (ArrayType and MapType).<br>
* The function is transparent : {@code type} is returned as-is if type is not inlinable or if !config.isInlineSchemaEnabled().<br>
*
* @param type type to inline
* @param name name of the created inline ObjectType
* @param uniqueName unique name of the created inline ObjectType
* @param inlineDefinitions a non null collection of inline ObjectType
* @return the type referencing the newly created inline ObjectType. Can be a RefType, an ArrayType or a MapType
*/
protected Type createInlineType(Type type, String name, String uniqueName, List<ObjectType> inlineDefinitions) {
if (!config.isInlineSchemaEnabled())
return type;
if (type instanceof ObjectType) {
return createInlineObjectType(type, name, uniqueName, inlineDefinitions);
} else if (type instanceof ArrayType) {
ArrayType arrayType = (ArrayType)type;
arrayType.setOfType(createInlineType(arrayType.getOfType(), name, uniqueName, inlineDefinitions));
return arrayType;
} else if (type instanceof MapType) {
MapType mapType = (MapType)type;
if (mapType.getValueType() instanceof ObjectType)
mapType.setValueType(createInlineType(mapType.getValueType(), name, uniqueName, inlineDefinitions));
return mapType;
} else {
return type;
}
}
protected Type createInlineObjectType(Type type, String name, String uniqueName, List<ObjectType> inlineDefinitions) {
if (type instanceof ObjectType) {
ObjectType objectType = (ObjectType)type;
if (MapUtils.isNotEmpty(objectType.getProperties())) {
if (objectType.getName() == null) {
objectType.setName(name);
objectType.setUniqueName(uniqueName);
}
inlineDefinitions.add(objectType);
return new RefType(objectType);
} else
return type;
} else
return type;
}
/**
* Build a generic property table
*
* @param properties properties to display
* @param uniquePrefix unique prefix to prepend to inline object names to enforce unicity
* @param definitionDocumentResolver definition document resolver to apply to property type cross-reference
* @param docBuilder the docbuilder do use for output
* @return a list of inline schemas referenced by some properties, for later display
*/
protected List<ObjectType> buildPropertiesTable(Map<String, Property> properties, String uniquePrefix, DefinitionDocumentResolver definitionDocumentResolver, MarkupDocBuilder docBuilder) {
List<ObjectType> inlineDefinitions = new ArrayList<>();
List<List<String>> cells = new ArrayList<>();
List<MarkupTableColumn> cols = Arrays.asList(
new MarkupTableColumn(NAME_COLUMN).withWidthRatio(3).withHeaderColumn(false).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^3"),
new MarkupTableColumn(DESCRIPTION_COLUMN).withWidthRatio(11).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^11"),
new MarkupTableColumn(SCHEMA_COLUMN).withWidthRatio(4).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^4"));
if (MapUtils.isNotEmpty(properties)) {
Set<String> propertyNames = toKeySet(properties, config.getPropertyOrdering());
for (String propertyName : propertyNames) {
Property property = properties.get(propertyName);
Type propertyType = PropertyUtils.getType(property, definitionDocumentResolver);
propertyType = createInlineType(propertyType, propertyName, uniquePrefix + " " + propertyName, inlineDefinitions);
Object example = PropertyUtils.getExample(config.isGeneratedExamplesEnabled(), property, markupDocBuilder);
Object defaultValue = PropertyUtils.getDefaultValue(property);
Integer maxlength = PropertyUtils.getMaxlength(property);
Integer minlength = PropertyUtils.getMinlength(property);
String pattern = PropertyUtils.getPattern(property);
Double minValue = PropertyUtils.getMin(property);
Double maxValue = PropertyUtils.getMax(property);
MarkupDocBuilder propertyNameContent = copyMarkupDocBuilder();
propertyNameContent.boldTextLine(propertyName, true);
if (BooleanUtils.isTrue(property.getRequired()))
propertyNameContent.italicText(FLAGS_REQUIRED.toLowerCase());
else
propertyNameContent.italicText(FLAGS_OPTIONAL.toLowerCase());
if (BooleanUtils.isTrue(property.getReadOnly())) {
propertyNameContent.newLine(true);
propertyNameContent.italicText(FLAGS_READ_ONLY.toLowerCase());
}
MarkupDocBuilder descriptionContent = copyMarkupDocBuilder();
String description = defaultString(swaggerMarkupDescription(property.getDescription()));
if (isNotBlank(description.toString()))
descriptionContent.text(description);
if(defaultValue != null){
if (isNotBlank(descriptionContent.toString()))
descriptionContent.newLine(true);
descriptionContent.boldText(DEFAULT_COLUMN).text(COLON).literalText(Json.pretty(defaultValue));
}
if (minlength != null && maxlength != null) {
// combination of minlength/maxlength
if (isNotBlank(descriptionContent.toString()))
descriptionContent.newLine(true);
String lengthRange = minlength + " - " + maxlength;
if (minlength.equals(maxlength)) {
lengthRange = minlength.toString();
}
descriptionContent.boldText(LENGTH_COLUMN).text(COLON).literalText(lengthRange);
} else {
if(minlength != null){
if (isNotBlank(descriptionContent.toString()))
descriptionContent.newLine(true);
descriptionContent.boldText(MINLENGTH_COLUMN).text(COLON).literalText(minlength.toString());
}
if(maxlength != null){
if (isNotBlank(descriptionContent.toString()))
descriptionContent.newLine(true);
descriptionContent.boldText(MAXLENGTH_COLUMN).text(COLON).literalText(maxlength.toString());
}
}
if(pattern != null){
if (isNotBlank(descriptionContent.toString()))
descriptionContent.newLine(true);
descriptionContent.boldText(PATTERN_COLUMN).text(COLON).literalText(Json.pretty(pattern));
}
if(minValue != null){
if (isNotBlank(descriptionContent.toString()))
descriptionContent.newLine(true);
descriptionContent.boldText(MINVALUE_COLUMN).text(COLON).literalText(minValue.toString());
}
if(maxValue != null){
if (isNotBlank(descriptionContent.toString()))
descriptionContent.newLine(true);
descriptionContent.boldText(MAXVALUE_COLUMN).text(COLON).literalText(maxValue.toString());
}
if (example != null) {
if (isNotBlank(description) || defaultValue != null)
descriptionContent.newLine(true);
descriptionContent.boldText(EXAMPLE_COLUMN).text(COLON).literalText(Json.pretty(example));
}
List<String> content = Arrays.asList(
propertyNameContent.toString(),
descriptionContent.toString(),
propertyType.displaySchema(docBuilder)
);
cells.add(content);
}
docBuilder.tableWithColumnSpecs(cols, cells);
} else {
docBuilder.textLine(NO_CONTENT);
}
return inlineDefinitions;
}
protected MarkupDocBuilder copyMarkupDocBuilder() {
return markupDocBuilder.copy(false);
}
protected String boldText(String text) {
return copyMarkupDocBuilder().boldText(text).toString();
}
protected String italicText(String text) {
return copyMarkupDocBuilder().italicText(text).toString();
}
protected String literalText(String text) {
return copyMarkupDocBuilder().literalText(text).toString();
}
/**
* Returns converted markup text from Swagger.
*
* @param markupText text to convert, or null
* @return converted markup text, or null if {@code markupText} == null
*/
protected String swaggerMarkupDescription(String markupText) {
if (markupText == null)
return null;
return copyMarkupDocBuilder().importMarkup(new StringReader(markupText), globalContext.getConfig().getSwaggerMarkupLanguage()).toString().trim();
}
protected void buildDescriptionParagraph(String description, MarkupDocBuilder docBuilder) {
if (isNotBlank(description)) {
docBuilder.paragraph(swaggerMarkupDescription(description));
}
}
/**
* Default {@code DefinitionDocumentResolver} functor
*/
class DefinitionDocumentResolverDefault implements DefinitionDocumentResolver {
public DefinitionDocumentResolverDefault() {
}
public String apply(String definitionName) {
if (!config.isInterDocumentCrossReferencesEnabled() || outputPath == null)
return null;
else if (config.isSeparatedDefinitionsEnabled())
return defaultString(config.getInterDocumentCrossReferencesPrefix()) + new File(config.getSeparatedDefinitionsFolder(), markupDocBuilder.addFileExtension(IOUtils.normalizeName(definitionName))).getPath();
else
return defaultString(config.getInterDocumentCrossReferencesPrefix()) + markupDocBuilder.addFileExtension(config.getDefinitionsDocument());
}
}
}

View File

@@ -1,224 +0,0 @@
/*
* Copyright 2016 Robert Winkler
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.github.swagger2markup.internal.document.builder;
import io.github.swagger2markup.Swagger2MarkupConverter;
import io.github.swagger2markup.Swagger2MarkupExtensionRegistry;
import io.github.swagger2markup.internal.document.MarkupDocument;
import io.github.swagger2markup.markup.builder.MarkupDocBuilder;
import io.github.swagger2markup.spi.OverviewDocumentExtension;
import io.swagger.models.*;
import java.nio.file.Path;
import java.util.ArrayList;
import java.util.List;
import java.util.ResourceBundle;
import static io.github.swagger2markup.spi.OverviewDocumentExtension.Context;
import static io.github.swagger2markup.spi.OverviewDocumentExtension.Position;
import static org.apache.commons.collections4.CollectionUtils.isNotEmpty;
import static org.apache.commons.lang3.StringUtils.*;
public class OverviewDocumentBuilder extends MarkupDocumentBuilder {
private static final String OVERVIEW_ANCHOR = "overview";
private final String OVERVIEW;
private final String CURRENT_VERSION;
private final String VERSION;
private final String CONTACT_INFORMATION;
private final String CONTACT_NAME;
private final String CONTACT_EMAIL;
private final String LICENSE_INFORMATION;
private final String LICENSE;
private final String LICENSE_URL;
private final String TERMS_OF_SERVICE;
private final String URI_SCHEME;
private final String HOST;
private final String BASE_PATH;
private final String SCHEMES;
public OverviewDocumentBuilder(Swagger2MarkupConverter.Context context, Swagger2MarkupExtensionRegistry extensionRegistry, Path outputPath){
super(context, extensionRegistry, outputPath);
ResourceBundle labels = ResourceBundle.getBundle("io/github/swagger2markup/lang/labels", config.getOutputLanguage().toLocale());
OVERVIEW = labels.getString("overview");
CURRENT_VERSION = labels.getString("current_version");
VERSION = labels.getString("version");
CONTACT_INFORMATION = labels.getString("contact_information");
CONTACT_NAME = labels.getString("contact_name");
CONTACT_EMAIL = labels.getString("contact_email");
LICENSE_INFORMATION = labels.getString("license_information");
LICENSE = labels.getString("license");
LICENSE_URL = labels.getString("license_url");
TERMS_OF_SERVICE = labels.getString("terms_of_service");
URI_SCHEME = labels.getString("uri_scheme");
HOST = labels.getString("host");
BASE_PATH = labels.getString("base_path");
SCHEMES = labels.getString("schemes");
}
/**
* Builds the overview MarkupDocument.
*
* @return the overview MarkupDocument
*/
@Override
public MarkupDocument build(){
Swagger swagger = globalContext.getSwagger();
Info info = swagger.getInfo();
buildDocumentTitle(info.getTitle());
applyOverviewDocumentExtension(new Context(Position.DOCUMENT_BEFORE, this.markupDocBuilder));
buildOverviewTitle(OVERVIEW);
applyOverviewDocumentExtension(new Context(Position.DOCUMENT_BEGIN, this.markupDocBuilder));
buildDescriptionParagraph(info.getDescription(), this.markupDocBuilder);
buildVersionInfoSection(info.getVersion());
buildContactInfoSection(info.getContact());
buildLicenseInfoSection(info.getLicense(), info.getTermsOfService());
buildUriSchemeSection(swagger);
buildTagsSection(swagger.getTags());
buildConsumesSection(swagger.getConsumes());
buildProducesSection(swagger.getProduces());
applyOverviewDocumentExtension(new Context(Position.DOCUMENT_END, this.markupDocBuilder));
applyOverviewDocumentExtension(new Context(Position.DOCUMENT_AFTER, this.markupDocBuilder));
return new MarkupDocument(markupDocBuilder);
}
private void buildDocumentTitle(String title) {
this.markupDocBuilder.documentTitle(title);
}
private void buildOverviewTitle(String title) {
this.markupDocBuilder.sectionTitleWithAnchorLevel1(title, OVERVIEW_ANCHOR);
}
private void buildVersionInfoSection(String version) {
if(isNotBlank(version)){
this.markupDocBuilder.sectionTitleLevel2(CURRENT_VERSION);
MarkupDocBuilder paragraph = copyMarkupDocBuilder();
paragraph.italicText(VERSION).textLine(COLON + version);
this.markupDocBuilder.paragraph(paragraph.toString(), true);
}
}
private void buildContactInfoSection(Contact contact) {
if(contact != null){
this.markupDocBuilder.sectionTitleLevel2(CONTACT_INFORMATION);
MarkupDocBuilder paragraph = copyMarkupDocBuilder();
if(isNotBlank(contact.getName())){
paragraph.italicText(CONTACT_NAME).textLine(COLON + contact.getName());
}
if(isNotBlank(contact.getEmail())){
paragraph.italicText(CONTACT_EMAIL).textLine(COLON + contact.getEmail());
}
this.markupDocBuilder.paragraph(paragraph.toString(), true);
}
}
private void buildLicenseInfoSection(License license, String termOfService) {
if (
(license != null && (isNotBlank(license.getName()) || isNotBlank(license.getUrl()))) ||
(isNotBlank(termOfService))
) {
this.markupDocBuilder.sectionTitleLevel2(LICENSE_INFORMATION);
MarkupDocBuilder paragraph = copyMarkupDocBuilder();
if (license != null && isNotBlank(license.getName())) {
paragraph.italicText(LICENSE).textLine(COLON + license.getName());
}
if (license != null && isNotBlank(license.getUrl())) {
paragraph.italicText(LICENSE_URL).textLine(COLON + license.getUrl());
}
if(isNotBlank(termOfService)){
paragraph.italicText(TERMS_OF_SERVICE).textLine(COLON + termOfService);
}
this.markupDocBuilder.paragraph(paragraph.toString(), true);
}
}
private void buildUriSchemeSection(Swagger swagger) {
if(isNotBlank(swagger.getHost()) || isNotBlank(swagger.getBasePath()) || isNotEmpty(swagger.getSchemes())) {
this.markupDocBuilder.sectionTitleLevel2(URI_SCHEME);
MarkupDocBuilder paragraph = copyMarkupDocBuilder();
if (isNotBlank(swagger.getHost())) {
paragraph.italicText(HOST).textLine(COLON + swagger.getHost());
}
if (isNotBlank(swagger.getBasePath())) {
paragraph.italicText(BASE_PATH).textLine(COLON + swagger.getBasePath());
}
if (isNotEmpty(swagger.getSchemes())) {
List<String> schemes = new ArrayList<>();
for (Scheme scheme : swagger.getSchemes()) {
schemes.add(scheme.toString());
}
paragraph.italicText(SCHEMES).textLine(COLON + join(schemes, ", "));
}
this.markupDocBuilder.paragraph(paragraph.toString(), true);
}
}
private void buildTagsSection(List<Tag> tags) {
if(isNotEmpty(tags)){
this.markupDocBuilder.sectionTitleLevel2(TAGS);
List<String> tagsList = new ArrayList<>();
for(Tag tag : tags){
String name = tag.getName();
String description = tag.getDescription();
if(isNoneBlank(description)){
tagsList.add(name + COLON + description);
}else{
tagsList.add(name);
}
}
this.markupDocBuilder.unorderedList(tagsList);
}
}
private void buildConsumesSection(List<String> consumes) {
if (isNotEmpty(consumes)) {
this.markupDocBuilder.sectionTitleLevel2(CONSUMES);
this.markupDocBuilder.newLine();
for (String consume : consumes) {
this.markupDocBuilder.unorderedListItem(literalText(consume));
}
this.markupDocBuilder.newLine();
}
}
private void buildProducesSection(List<String> produces) {
if (isNotEmpty(produces)) {
this.markupDocBuilder.sectionTitleLevel2(PRODUCES);
this.markupDocBuilder.newLine();
for (String produce : produces) {
this.markupDocBuilder.unorderedListItem(literalText(produce));
}
this.markupDocBuilder.newLine();
}
}
/**
* Apply extension context to all OverviewContentExtension
*
* @param context context
*/
private void applyOverviewDocumentExtension(Context context) {
for (OverviewDocumentExtension extension : extensionRegistry.getOverviewDocumentExtensions()) {
extension.apply(context);
}
}
}

View File

@@ -1,771 +0,0 @@
/*
* Copyright 2016 Robert Winkler
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.github.swagger2markup.internal.document.builder;
import com.google.common.base.Joiner;
import com.google.common.base.Optional;
import com.google.common.collect.Multimap;
import io.github.swagger2markup.GroupBy;
import io.github.swagger2markup.Swagger2MarkupConverter;
import io.github.swagger2markup.Swagger2MarkupExtensionRegistry;
import io.github.swagger2markup.internal.document.MarkupDocument;
import io.github.swagger2markup.internal.type.ObjectType;
import io.github.swagger2markup.internal.type.Type;
import io.github.swagger2markup.internal.utils.ExamplesUtil;
import io.github.swagger2markup.internal.utils.ParameterUtils;
import io.github.swagger2markup.internal.utils.PropertyUtils;
import io.github.swagger2markup.internal.utils.TagUtils;
import io.github.swagger2markup.markup.builder.*;
import io.github.swagger2markup.model.PathOperation;
import io.github.swagger2markup.spi.PathsDocumentExtension;
import io.swagger.models.*;
import io.swagger.models.auth.SecuritySchemeDefinition;
import io.swagger.models.parameters.Parameter;
import io.swagger.models.properties.Property;
import io.swagger.util.Json;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.collections4.MapUtils;
import org.apache.commons.lang3.BooleanUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.Validate;
import org.apache.commons.lang3.text.WordUtils;
import java.io.File;
import java.nio.charset.StandardCharsets;
import java.util.*;
import static io.github.swagger2markup.internal.utils.ListUtils.toSet;
import static io.github.swagger2markup.internal.utils.MapUtils.toKeySet;
import static io.github.swagger2markup.internal.utils.TagUtils.convertTagsListToMap;
import static io.github.swagger2markup.internal.utils.TagUtils.getTagDescription;
import static io.github.swagger2markup.spi.PathsDocumentExtension.Context;
import static io.github.swagger2markup.spi.PathsDocumentExtension.Position;
import static io.github.swagger2markup.utils.IOUtils.normalizeName;
import static org.apache.commons.lang3.StringUtils.defaultString;
import static org.apache.commons.lang3.StringUtils.isNotBlank;
/**
* @author Robert Winkler
*/
public class PathsDocumentBuilder extends MarkupDocumentBuilder {
private final String RESPONSE;
private final String REQUEST;
private final String PATHS;
private final String RESOURCES;
private final String PARAMETERS;
private final String BODY_PARAMETER;
private final String RESPONSES;
private final String HEADERS_COLUMN;
private final String EXAMPLE_REQUEST;
private final String EXAMPLE_RESPONSE;
private final String SECURITY;
private final String TYPE_COLUMN;
private final String HTTP_CODE_COLUMN;
private final String DEPRECATED_OPERATION;
private final String UNKNOWN;
private static final String PATHS_ANCHOR = "paths";
public PathsDocumentBuilder(Swagger2MarkupConverter.Context globalContext, Swagger2MarkupExtensionRegistry extensionRegistry, java.nio.file.Path outputPath) {
super(globalContext, extensionRegistry, outputPath);
ResourceBundle labels = ResourceBundle.getBundle("io/github/swagger2markup/lang/labels", config.getOutputLanguage().toLocale());
RESPONSE = labels.getString("response");
REQUEST = labels.getString("request");
PATHS = labels.getString("paths");
RESOURCES = labels.getString("resources");
PARAMETERS = labels.getString("parameters");
BODY_PARAMETER = labels.getString("body_parameter");
RESPONSES = labels.getString("responses");
HEADERS_COLUMN = labels.getString("headers_column");
EXAMPLE_REQUEST = labels.getString("example_request");
EXAMPLE_RESPONSE = labels.getString("example_response");
SECURITY = labels.getString("security");
TYPE_COLUMN = labels.getString("type_column");
HTTP_CODE_COLUMN = labels.getString("http_code_column");
DEPRECATED_OPERATION = labels.getString("operation.deprecated");
UNKNOWN = labels.getString("unknown");
if (config.isGeneratedExamplesEnabled()) {
if (logger.isDebugEnabled()) {
logger.debug("Include examples is enabled.");
}
} else {
if (logger.isDebugEnabled()) {
logger.debug("Include examples is disabled.");
}
}
if (config.isSeparatedOperationsEnabled()) {
if (logger.isDebugEnabled()) {
logger.debug("Create separated operation files is enabled.");
}
Validate.notNull(outputPath, "Output directory is required for separated operation files!");
} else {
if (logger.isDebugEnabled()) {
logger.debug("Create separated operation files is disabled.");
}
}
}
/**
* Builds the paths MarkupDocument.
*
* @return the paths MarkupDocument
*/
@Override
public MarkupDocument build() {
Map<String, Path> paths = globalContext.getSwagger().getPaths();
if (MapUtils.isNotEmpty(paths)) {
applyPathsDocumentExtension(new Context(Position.DOCUMENT_BEFORE, this.markupDocBuilder));
buildPathsTitle();
applyPathsDocumentExtension(new Context(Position.DOCUMENT_BEGIN, this.markupDocBuilder));
buildsPathsSection(paths);
applyPathsDocumentExtension(new Context(Position.DOCUMENT_END, this.markupDocBuilder));
applyPathsDocumentExtension(new Context(Position.DOCUMENT_AFTER, this.markupDocBuilder));
}
return new MarkupDocument(markupDocBuilder);
}
private void buildsPathsSection(Map<String, Path> paths) {
Set<PathOperation> pathOperations = toPathOperationsSet(paths);
if (CollectionUtils.isNotEmpty(pathOperations)) {
if (config.getPathsGroupedBy() == GroupBy.AS_IS) {
for (PathOperation operation : pathOperations) {
buildOperation(operation);
}
} else {
Multimap<String, PathOperation> operationsGroupedByTag = TagUtils.groupOperationsByTag(pathOperations, config.getTagOrdering(), config.getOperationOrdering());
Map<String, Tag> tagsMap = convertTagsListToMap(globalContext.getSwagger().getTags());
for (String tagName : operationsGroupedByTag.keySet()) {
this.markupDocBuilder.sectionTitleWithAnchorLevel2(WordUtils.capitalize(tagName), tagName + "_resource");
Optional<String> tagDescription = getTagDescription(tagsMap, tagName);
if (tagDescription.isPresent()) {
this.markupDocBuilder.paragraph(tagDescription.get());
}
for (PathOperation operation : operationsGroupedByTag.get(tagName)) {
buildOperation(operation);
}
}
}
}
}
/**
* Builds the path title depending on the operationsGroupedBy configuration setting.
*/
private void buildPathsTitle() {
if (config.getPathsGroupedBy() == GroupBy.AS_IS) {
buildPathsTitle(PATHS);
} else {
buildPathsTitle(RESOURCES);
}
}
/**
* Converts the Swagger paths into a list PathOperations.
*
* @param paths the Swagger paths
* @return the path operations
*/
private Set<PathOperation> toPathOperationsSet(Map<String, Path> paths) {
Set<PathOperation> pathOperations;
if (config.getOperationOrdering() != null) {
pathOperations = new TreeSet<>(config.getOperationOrdering());
} else {
pathOperations = new LinkedHashSet<>();
}
for (Map.Entry<String, Path> path : paths.entrySet()) {
Map<HttpMethod, Operation> operations = path.getValue().getOperationMap(); // TODO AS_IS does not work because of https://github.com/swagger-api/swagger-core/issues/1696
if (MapUtils.isNotEmpty(operations)) {
for (Map.Entry<HttpMethod, Operation> operation : operations.entrySet()) {
pathOperations.add(new PathOperation(operation.getKey(), path.getKey(), operation.getValue()));
}
}
}
return pathOperations;
}
private void buildPathsTitle(String title) {
this.markupDocBuilder.sectionTitleWithAnchorLevel1(title, PATHS_ANCHOR);
}
/**
* Apply extension context to all OperationsContentExtension.
*
* @param context context
*/
private void applyPathsDocumentExtension(Context context) {
for (PathsDocumentExtension extension : extensionRegistry.getPathsDocumentExtensions()) {
extension.apply(context);
}
}
/**
* Create the operation filename depending on the generation mode
*
* @param operation operation
* @return operation filename
*/
private String resolveOperationDocument(PathOperation operation) {
if (config.isSeparatedOperationsEnabled())
return new File(config.getSeparatedOperationsFolder(), this.markupDocBuilder.addFileExtension(normalizeName(operation.getId()))).getPath();
else
return this.markupDocBuilder.addFileExtension(config.getPathsDocument());
}
/**
* Builds a path operation depending on generation mode.
*
* @param operation operation
*/
private void buildOperation(PathOperation operation) {
if (config.isSeparatedOperationsEnabled()) {
MarkupDocBuilder pathDocBuilder = copyMarkupDocBuilder();
buildOperation(operation, pathDocBuilder);
java.nio.file.Path operationFile = outputPath.resolve(resolveOperationDocument(operation));
pathDocBuilder.writeToFileWithoutExtension(operationFile, StandardCharsets.UTF_8);
if (logger.isInfoEnabled()) {
logger.info("Separate operation file produced : '{}'", operationFile);
}
buildOperationRef(operation, this.markupDocBuilder);
} else {
buildOperation(operation, this.markupDocBuilder);
}
if (logger.isInfoEnabled()) {
logger.info("Operation processed : '{}' (normalized id = '{}')", operation, normalizeName(operation.getId()));
}
}
/**
* Builds a path operation.
*
* @param operation the Swagger Operation
* @param docBuilder the docbuilder do use for output
*/
private void buildOperation(PathOperation operation, MarkupDocBuilder docBuilder) {
if (operation != null) {
applyPathsDocumentExtension(new Context(Position.OPERATION_BEFORE, docBuilder, operation));
buildDeprecatedSection(operation, docBuilder);
buildOperationTitle(operation, docBuilder);
applyPathsDocumentExtension(new Context(Position.OPERATION_BEGIN, docBuilder, operation));
buildDescriptionSection(operation, docBuilder);
inlineDefinitions(buildParametersSection(operation, docBuilder), operation.getPath() + " " + operation.getMethod(), docBuilder);
inlineDefinitions(buildBodyParameterSection(operation, docBuilder), operation.getPath() + " " + operation.getMethod(), docBuilder);
inlineDefinitions(buildResponsesSection(operation, docBuilder), operation.getPath() + " " + operation.getMethod(), docBuilder);
buildConsumesSection(operation, docBuilder);
buildProducesSection(operation, docBuilder);
buildTagsSection(operation, docBuilder);
if (config.isPathSecuritySectionEnabled()) {
buildSecuritySchemeSection(operation, docBuilder);
}
buildExamplesSection(operation, docBuilder);
applyPathsDocumentExtension(new Context(Position.OPERATION_END, docBuilder, operation));
applyPathsDocumentExtension(new Context(Position.OPERATION_AFTER, docBuilder, operation));
}
}
/**
* Builds a cross-reference to a separated operation file
*
* @param operation the Swagger Operation
* @param docBuilder the docbuilder do use for output
*/
private void buildOperationRef(PathOperation operation, MarkupDocBuilder docBuilder) {
String document;
if (!config.isInterDocumentCrossReferencesEnabled() || outputPath == null)
document = null;
else if (config.isSeparatedOperationsEnabled())
document = defaultString(config.getInterDocumentCrossReferencesPrefix()) + resolveOperationDocument(operation);
else
document = defaultString(config.getInterDocumentCrossReferencesPrefix()) + resolveOperationDocument(operation);
buildOperationTitle(copyMarkupDocBuilder().crossReference(document, operation.getId(), operation.getTitle()).toString(), "ref-" + operation.getId(), docBuilder);
}
/**
* Builds a warning if method is deprecated.
*
* @param operation the Swagger Operation
* @param docBuilder the docbuilder do use for output
*/
private void buildDeprecatedSection(PathOperation operation, MarkupDocBuilder docBuilder) {
Boolean deprecated = operation.getOperation().isDeprecated();
if (deprecated != null && deprecated) {
docBuilder.block(DEPRECATED_OPERATION, MarkupBlockStyle.EXAMPLE, null, MarkupAdmonition.CAUTION);
}
}
/**
* Adds the operation title to the document. If the operation has a summary, the title is the summary.
* Otherwise the title is the method of the operation and the URL of the operation.
*
* @param operation the Swagger Operation
* @param docBuilder the docbuilder do use for output
*/
private void buildOperationTitle(PathOperation operation, MarkupDocBuilder docBuilder) {
buildOperationTitle(operation.getTitle(), operation.getId(), docBuilder);
if (operation.getTitle().equals(operation.getOperation().getSummary())) {
docBuilder.block(operation.getMethod() + " " + operation.getPath(), MarkupBlockStyle.LITERAL);
}
}
/**
* Adds a operation title to the document.
*
* @param title the operation title
* @param anchor optional anchor (null => auto-generate from title)
* @param docBuilder the MarkupDocBuilder to use
*/
private void buildOperationTitle(String title, String anchor, MarkupDocBuilder docBuilder) {
if (config.getPathsGroupedBy() == GroupBy.AS_IS) {
docBuilder.sectionTitleWithAnchorLevel2(title, anchor);
} else {
docBuilder.sectionTitleWithAnchorLevel3(title, anchor);
}
}
/**
* Adds a operation section title to the document.
*
* @param title the section title
* @param docBuilder the MarkupDocBuilder to use
*/
private void buildSectionTitle(String title, MarkupDocBuilder docBuilder) {
if (config.getPathsGroupedBy() == GroupBy.AS_IS) {
docBuilder.sectionTitleLevel3(title);
} else {
docBuilder.sectionTitleLevel4(title);
}
}
/**
* Adds a example title to the document.
*
* @param title the section title
* @param docBuilder the MarkupDocBuilder to use
*/
private void buildExampleTitle(String title, MarkupDocBuilder docBuilder) {
if (config.getPathsGroupedBy() == GroupBy.AS_IS) {
docBuilder.sectionTitleLevel4(title);
} else {
docBuilder.sectionTitleLevel5(title);
}
}
/**
* Adds a operation description to the document.
*
* @param operation the Swagger Operation
* @param docBuilder the docbuilder do use for output
*/
private void buildDescriptionSection(PathOperation operation, MarkupDocBuilder docBuilder) {
MarkupDocBuilder descriptionBuilder = copyMarkupDocBuilder();
applyPathsDocumentExtension(new Context(Position.OPERATION_DESCRIPTION_BEGIN, descriptionBuilder, operation));
buildDescriptionParagraph(operation.getOperation().getDescription(), descriptionBuilder);
applyPathsDocumentExtension(new Context(Position.OPERATION_DESCRIPTION_END, descriptionBuilder, operation));
String descriptionContent = descriptionBuilder.toString();
applyPathsDocumentExtension(new Context(Position.OPERATION_DESCRIPTION_BEFORE, docBuilder, operation));
if (isNotBlank(descriptionContent)) {
buildSectionTitle(DESCRIPTION, docBuilder);
docBuilder.text(descriptionContent);
}
applyPathsDocumentExtension(new Context(Position.OPERATION_DESCRIPTION_AFTER, docBuilder, operation));
}
/**
* Filter parameters to display in parameters section
*
* @param parameter parameter to filter
* @return true if parameter can be displayed
*/
private boolean filterParameter(Parameter parameter) {
return (!config.isFlatBodyEnabled() || !StringUtils.equals(parameter.getIn(), "body"));
}
private List<ObjectType> buildParametersSection(PathOperation operation, MarkupDocBuilder docBuilder) {
List<Parameter> parameters = operation.getOperation().getParameters();
if (config.getParameterOrdering() != null)
Collections.sort(parameters, config.getParameterOrdering());
List<ObjectType> inlineDefinitions = new ArrayList<>();
boolean hasParameters = false;
if (CollectionUtils.isNotEmpty(parameters)) {
for (Parameter p : parameters) {
if (filterParameter(p)) {
hasParameters = true;
break;
}
}
}
MarkupDocBuilder parametersBuilder = copyMarkupDocBuilder();
applyPathsDocumentExtension(new Context(Position.OPERATION_DESCRIPTION_BEGIN, parametersBuilder, operation));
if (hasParameters) {
List<List<String>> cells = new ArrayList<>();
List<MarkupTableColumn> cols = Arrays.asList(
new MarkupTableColumn(TYPE_COLUMN).withWidthRatio(2).withHeaderColumn(false).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^2"),
new MarkupTableColumn(NAME_COLUMN).withWidthRatio(3).withHeaderColumn(false).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^3"),
new MarkupTableColumn(DESCRIPTION_COLUMN).withWidthRatio(9).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^9"),
new MarkupTableColumn(SCHEMA_COLUMN).withWidthRatio(4).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^4"),
new MarkupTableColumn(DEFAULT_COLUMN).withWidthRatio(2).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^2"));
for (Parameter parameter : parameters) {
if (filterParameter(parameter)) {
Type type = ParameterUtils.getType(parameter, globalContext.getSwagger().getDefinitions(), new DefinitionDocumentResolverFromOperation());
type = createInlineType(type, parameter.getName(), operation.getId() + " " + parameter.getName(), inlineDefinitions);
String parameterType = WordUtils.capitalize(parameter.getIn());
MarkupDocBuilder parameterNameContent = copyMarkupDocBuilder();
parameterNameContent.boldTextLine(parameter.getName(), true);
if (parameter.getRequired())
parameterNameContent.italicText(FLAGS_REQUIRED.toLowerCase());
else
parameterNameContent.italicText(FLAGS_OPTIONAL.toLowerCase());
Object defaultValue = ParameterUtils.getDefaultValue(parameter);
List<String> content = Arrays.asList(
boldText(parameterType),
parameterNameContent.toString(),
defaultString(swaggerMarkupDescription(parameter.getDescription())),
type.displaySchema(markupDocBuilder),
defaultValue != null ? literalText(Json.pretty(defaultValue)) : "");
cells.add(content);
}
}
parametersBuilder.tableWithColumnSpecs(cols, cells);
}
applyPathsDocumentExtension(new Context(Position.OPERATION_DESCRIPTION_END, parametersBuilder, operation));
String parametersContent = parametersBuilder.toString();
applyPathsDocumentExtension(new Context(Position.OPERATION_PARAMETERS_BEFORE, docBuilder, operation));
if (isNotBlank(parametersContent)) {
buildSectionTitle(PARAMETERS, docBuilder);
docBuilder.text(parametersContent);
}
applyPathsDocumentExtension(new Context(Position.OPERATION_PARAMETERS_AFTER, docBuilder, operation));
return inlineDefinitions;
}
/**
* Builds the body parameter section, if {@code Swagger2MarkupConfig.isIsolatedBody()} is true
*
* @param operation the Swagger Operation
* @param docBuilder the docbuilder do use for output
* @return a list of inlined types.
*/
private List<ObjectType> buildBodyParameterSection(PathOperation operation, MarkupDocBuilder docBuilder) {
List<ObjectType> inlineDefinitions = new ArrayList<>();
if (config.isFlatBodyEnabled()) {
List<Parameter> parameters = operation.getOperation().getParameters();
if (CollectionUtils.isNotEmpty(parameters)) {
for (Parameter parameter : parameters) {
if (StringUtils.equals(parameter.getIn(), "body")) {
Type type = ParameterUtils.getType(parameter, globalContext.getSwagger().getDefinitions(), new DefinitionDocumentResolverFromOperation());
if (!(type instanceof ObjectType)) {
type = createInlineType(type, parameter.getName(), operation.getId() + " " + parameter.getName(), inlineDefinitions);
}
buildSectionTitle(BODY_PARAMETER, docBuilder);
if (isNotBlank(parameter.getDescription())) {
buildDescriptionParagraph(parameter.getDescription(), docBuilder);
}
MarkupDocBuilder typeInfos = copyMarkupDocBuilder();
typeInfos.italicText(NAME_COLUMN).textLine(COLON + parameter.getName());
typeInfos.italicText(FLAGS_COLUMN).textLine(COLON + (BooleanUtils.isTrue(parameter.getRequired()) ? FLAGS_REQUIRED.toLowerCase() : FLAGS_OPTIONAL.toLowerCase()));
if (!(type instanceof ObjectType)) {
typeInfos.italicText(TYPE_COLUMN).textLine(COLON + type.displaySchema(docBuilder));
}
docBuilder.paragraph(typeInfos.toString(), true);
if (type instanceof ObjectType) {
inlineDefinitions.addAll(buildPropertiesTable(((ObjectType) type).getProperties(), operation.getId(), new DefinitionDocumentResolverFromOperation(), docBuilder));
}
}
}
}
}
return inlineDefinitions;
}
private void buildConsumesSection(PathOperation operation, MarkupDocBuilder docBuilder) {
List<String> consumes = operation.getOperation().getConsumes();
if (CollectionUtils.isNotEmpty(consumes)) {
buildSectionTitle(CONSUMES, docBuilder);
docBuilder.newLine();
for (String consume : consumes) {
docBuilder.unorderedListItem(literalText(consume));
}
docBuilder.newLine();
}
}
private void buildProducesSection(PathOperation operation, MarkupDocBuilder docBuilder) {
List<String> produces = operation.getOperation().getProduces();
if (CollectionUtils.isNotEmpty(produces)) {
buildSectionTitle(PRODUCES, docBuilder);
docBuilder.newLine();
for (String produce : produces) {
docBuilder.unorderedListItem(literalText(produce));
}
docBuilder.newLine();
}
}
private void buildTagsSection(PathOperation operation, MarkupDocBuilder docBuilder) {
if (config.getPathsGroupedBy() == GroupBy.AS_IS) {
List<String> tags = operation.getOperation().getTags();
if (CollectionUtils.isNotEmpty(tags)) {
buildSectionTitle(TAGS, docBuilder);
Set<String> tagsSet = toSet(tags, config.getTagOrdering());
docBuilder.unorderedList(new ArrayList<>(tagsSet));
}
}
}
/**
* Builds the example section of a Swagger Operation.
*
* @param operation the Swagger Operation
* @param docBuilder the docbuilder do use for output
*/
private void buildExamplesSection(PathOperation operation, MarkupDocBuilder docBuilder) {
Map<String, Object> generatedRequestExampleMap = ExamplesUtil.generateRequestExampleMap(config.isGeneratedExamplesEnabled(), operation, globalContext.getSwagger().getDefinitions(), markupDocBuilder);
Map<String, Object> generatedResponseExampleMap = ExamplesUtil.generateResponseExampleMap(config.isGeneratedExamplesEnabled(), operation.getOperation(), globalContext.getSwagger().getDefinitions(), markupDocBuilder);
exampleMap(generatedRequestExampleMap, EXAMPLE_REQUEST, REQUEST, docBuilder);
exampleMap(generatedResponseExampleMap, EXAMPLE_RESPONSE, RESPONSE, docBuilder);
}
private void exampleMap(Map<String, Object> exampleMap, String operationSectionTitle, String sectionTitle, MarkupDocBuilder docBuilder) {
if (exampleMap.size() > 0) {
buildSectionTitle(operationSectionTitle, docBuilder);
for (Map.Entry<String, Object> entry : exampleMap.entrySet()) {
buildExampleTitle(sectionTitle + " " + entry.getKey(), docBuilder);
docBuilder.listingBlock(Json.pretty(entry.getValue()), "json");
}
}
}
/**
* Builds the security section of a Swagger Operation.
*
* @param operation the Swagger Operation
* @param docBuilder the MarkupDocBuilder document builder
*/
private void buildSecuritySchemeSection(PathOperation operation, MarkupDocBuilder docBuilder) {
List<Map<String, List<String>>> securitySchemes = operation.getOperation().getSecurity();
MarkupDocBuilder securityBuilder = copyMarkupDocBuilder();
applyPathsDocumentExtension(new Context(Position.OPERATION_SECURITY_BEGIN, securityBuilder, operation));
if (CollectionUtils.isNotEmpty(securitySchemes)) {
Map<String, SecuritySchemeDefinition> securityDefinitions = globalContext.getSwagger().getSecurityDefinitions();
List<List<String>> cells = new ArrayList<>();
List<MarkupTableColumn> cols = Arrays.asList(
new MarkupTableColumn(TYPE_COLUMN).withWidthRatio(3).withHeaderColumn(false).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^3"),
new MarkupTableColumn(NAME_COLUMN).withWidthRatio(4).withHeaderColumn(false).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^4"),
new MarkupTableColumn(SCOPES_COLUMN).withWidthRatio(13).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^13"));
for (Map<String, List<String>> securityScheme : securitySchemes) {
for (Map.Entry<String, List<String>> securityEntry : securityScheme.entrySet()) {
String securityKey = securityEntry.getKey();
String type = UNKNOWN;
if (securityDefinitions != null && securityDefinitions.containsKey(securityKey)) {
type = securityDefinitions.get(securityKey).getType();
}
List<String> content = Arrays.asList(boldText(type), boldText(copyMarkupDocBuilder().crossReference(securityDocumentResolver(), securityKey, securityKey).toString()),
Joiner.on(",").join(securityEntry.getValue()));
cells.add(content);
}
}
securityBuilder.tableWithColumnSpecs(cols, cells);
}
applyPathsDocumentExtension(new Context(Position.OPERATION_SECURITY_END, securityBuilder, operation));
String securityContent = securityBuilder.toString();
applyPathsDocumentExtension(new Context(Position.OPERATION_SECURITY_BEFORE, docBuilder, operation));
if (isNotBlank(securityContent)) {
buildSectionTitle(SECURITY, docBuilder);
docBuilder.text(securityContent);
}
applyPathsDocumentExtension(new Context(Position.OPERATION_SECURITY_AFTER, docBuilder, operation));
}
/**
* Resolve Security document for use in cross-references.
*
* @return document or null if cross-reference is not inter-document
*/
private String securityDocumentResolver() {
if (!config.isInterDocumentCrossReferencesEnabled() || outputPath == null)
return null;
else
return defaultString(config.getInterDocumentCrossReferencesPrefix()) + markupDocBuilder.addFileExtension(config.getSecurityDocument());
}
private List<ObjectType> buildResponsesSection(PathOperation operation, MarkupDocBuilder docBuilder) {
Map<String, Response> responses = operation.getOperation().getResponses();
List<ObjectType> inlineDefinitions = new ArrayList<>();
MarkupDocBuilder responsesBuilder = copyMarkupDocBuilder();
applyPathsDocumentExtension(new Context(Position.OPERATION_RESPONSES_BEGIN, responsesBuilder, operation));
if (MapUtils.isNotEmpty(responses)) {
List<MarkupTableColumn> responseCols = Arrays.asList(
new MarkupTableColumn(HTTP_CODE_COLUMN).withWidthRatio(2).withHeaderColumn(false).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^2"),
new MarkupTableColumn(DESCRIPTION_COLUMN).withWidthRatio(14).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^14"),
new MarkupTableColumn(SCHEMA_COLUMN).withWidthRatio(4).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^4"));
List<List<String>> cells = new ArrayList<>();
Set<String> responseNames = toKeySet(responses, config.getResponseOrdering());
for (String responseName : responseNames) {
Response response = responses.get(responseName);
String schemaContent = NO_CONTENT;
if (response.getSchema() != null) {
Property property = response.getSchema();
Type type = PropertyUtils.getType(property, new DefinitionDocumentResolverFromOperation());
type = createInlineType(type, RESPONSE + " " + responseName, operation.getId() + " " + RESPONSE + " " + responseName, inlineDefinitions);
schemaContent = type.displaySchema(markupDocBuilder);
}
MarkupDocBuilder descriptionBuilder = copyMarkupDocBuilder();
descriptionBuilder.text(defaultString(swaggerMarkupDescription(response.getDescription())));
Map<String, Property> headers = response.getHeaders();
if (MapUtils.isNotEmpty(headers)) {
descriptionBuilder.newLine(true).boldText(HEADERS_COLUMN).text(COLON);
for (Map.Entry<String, Property> header : headers.entrySet()) {
descriptionBuilder.newLine(true);
Property headerProperty = header.getValue();
Type propertyType = PropertyUtils.getType(headerProperty, null);
String headerDescription = defaultString(swaggerMarkupDescription(headerProperty.getDescription()));
Object defaultValue = PropertyUtils.getDefaultValue(headerProperty);
descriptionBuilder
.literalText(header.getKey())
.text(String.format(" (%s)", propertyType.displaySchema(markupDocBuilder)));
if (isNotBlank(headerDescription) || defaultValue != null) {
descriptionBuilder.text(COLON);
if (isNotBlank(headerDescription) && !headerDescription.endsWith("."))
headerDescription += ".";
descriptionBuilder.text(headerDescription);
if (defaultValue != null) {
descriptionBuilder.text(" ").boldText(DEFAULT_COLUMN).text(COLON).literalText(Json.pretty(defaultValue));
}
}
}
}
cells.add(Arrays.asList(boldText(responseName), descriptionBuilder.toString(), schemaContent));
}
responsesBuilder.tableWithColumnSpecs(responseCols, cells);
}
applyPathsDocumentExtension(new Context(Position.OPERATION_RESPONSES_END, responsesBuilder, operation));
String responsesContent = responsesBuilder.toString();
applyPathsDocumentExtension(new Context(Position.OPERATION_RESPONSES_BEFORE, docBuilder, operation));
if (isNotBlank(responsesContent)) {
buildSectionTitle(RESPONSES, docBuilder);
docBuilder.text(responsesContent);
}
applyPathsDocumentExtension(new Context(Position.OPERATION_RESPONSES_AFTER, docBuilder, operation));
return inlineDefinitions;
}
/**
* Builds the title of an inline schema.
* Inline definitions should never been referenced in TOC because they have no real existence, so they are just text.
*
* @param title inline schema title
* @param anchor inline schema anchor
* @param docBuilder the docbuilder do use for output
*/
private void addInlineDefinitionTitle(String title, String anchor, MarkupDocBuilder docBuilder) {
docBuilder.anchor(anchor);
docBuilder.newLine();
docBuilder.boldTextLine(title);
}
/**
* Builds inline schema definitions
*
* @param definitions all inline definitions to display
* @param uniquePrefix unique prefix to prepend to inline object names to enforce unicity
* @param docBuilder the docbuilder do use for output
*/
private void inlineDefinitions(List<ObjectType> definitions, String uniquePrefix, MarkupDocBuilder docBuilder) {
if (CollectionUtils.isNotEmpty(definitions)) {
for (ObjectType definition : definitions) {
addInlineDefinitionTitle(definition.getName(), definition.getUniqueName(), docBuilder);
List<ObjectType> localDefinitions = buildPropertiesTable(definition.getProperties(), uniquePrefix, new DefinitionDocumentResolverFromOperation(), docBuilder);
for (ObjectType localDefinition : localDefinitions)
inlineDefinitions(Collections.singletonList(localDefinition), localDefinition.getUniqueName(), docBuilder);
}
}
}
/**
* Overrides definition document resolver functor for inter-document cross-references from operations files.
* This implementation adapt the relative paths to definitions files
*/
class DefinitionDocumentResolverFromOperation extends DefinitionDocumentResolverDefault {
public DefinitionDocumentResolverFromOperation() {
}
public String apply(String definitionName) {
String defaultResolver = super.apply(definitionName);
if (defaultResolver != null && config.isSeparatedOperationsEnabled())
return defaultString(config.getInterDocumentCrossReferencesPrefix()) + new File("..", defaultResolver).getPath();
else
return defaultResolver;
}
}
}

View File

@@ -1,155 +0,0 @@
/*
* Copyright 2016 Robert Winkler
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.github.swagger2markup.internal.document.builder;
import com.google.common.collect.Ordering;
import io.github.swagger2markup.Swagger2MarkupConverter;
import io.github.swagger2markup.Swagger2MarkupExtensionRegistry;
import io.github.swagger2markup.internal.document.MarkupDocument;
import io.github.swagger2markup.markup.builder.MarkupDocBuilder;
import io.github.swagger2markup.markup.builder.MarkupLanguage;
import io.github.swagger2markup.markup.builder.MarkupTableColumn;
import io.github.swagger2markup.spi.SecurityDocumentExtension;
import io.swagger.models.auth.ApiKeyAuthDefinition;
import io.swagger.models.auth.OAuth2Definition;
import io.swagger.models.auth.SecuritySchemeDefinition;
import org.apache.commons.collections4.MapUtils;
import java.nio.file.Path;
import java.util.*;
import static io.github.swagger2markup.internal.utils.MapUtils.toKeySet;
import static io.github.swagger2markup.spi.SecurityDocumentExtension.Context;
import static io.github.swagger2markup.spi.SecurityDocumentExtension.Position;
import static org.apache.commons.lang3.StringUtils.isNotBlank;
/**
* @author Robert Winkler
*/
public class SecurityDocumentBuilder extends MarkupDocumentBuilder {
private static final String SECURITY_ANCHOR = "securityScheme";
private final String SECURITY;
private final String TYPE;
private final String NAME;
private final String IN;
private final String FLOW;
private final String AUTHORIZATION_URL;
private final String TOKEN_URL;
public SecurityDocumentBuilder(Swagger2MarkupConverter.Context context, Swagger2MarkupExtensionRegistry extensionRegistry, Path outputPath) {
super(context, extensionRegistry, outputPath);
ResourceBundle labels = ResourceBundle.getBundle("io/github/swagger2markup/lang/labels", config.getOutputLanguage().toLocale());
SECURITY = labels.getString("security");
TYPE = labels.getString("security_type");
NAME = labels.getString("security_name");
IN = labels.getString("security_in");
FLOW = labels.getString("security_flow");
AUTHORIZATION_URL = labels.getString("security_authorizationUrl");
TOKEN_URL = labels.getString("security_tokenUrl");
}
/**
* Builds the security MarkupDocument.
*
* @return the security MarkupDocument
*/
@Override
public MarkupDocument build(){
Map<String, SecuritySchemeDefinition> definitions = globalContext.getSwagger().getSecurityDefinitions();
if (MapUtils.isNotEmpty(definitions)) {
applySecurityDocumentExtension(new Context(Position.DOCUMENT_BEFORE, this.markupDocBuilder));
buildSecurityTitle(SECURITY);
applySecurityDocumentExtension(new Context(Position.DOCUMENT_BEGIN, this.markupDocBuilder));
buildSecuritySchemeDefinitionsSection(definitions);
applySecurityDocumentExtension(new Context(Position.DOCUMENT_END, this.markupDocBuilder));
applySecurityDocumentExtension(new Context(Position.DOCUMENT_AFTER, this.markupDocBuilder));
}
return new MarkupDocument(markupDocBuilder);
}
private void buildSecurityTitle(String title) {
this.markupDocBuilder.sectionTitleWithAnchorLevel1(title, SECURITY_ANCHOR);
}
private void buildSecuritySchemeDefinitionsSection(Map<String, SecuritySchemeDefinition> securitySchemes) {
Set<String> securitySchemeNames = toKeySet(securitySchemes, null); // TODO : provide a dedicated ordering configuration for security schemes
for (String securitySchemeName : securitySchemeNames) {
SecuritySchemeDefinition securityScheme = securitySchemes.get(securitySchemeName);
applySecurityDocumentExtension(new Context(Position.SECURITY_SCHEME_BEFORE, markupDocBuilder, securitySchemeName, securityScheme));
buildSecuritySchemeDefinitionTitle(securitySchemeName);
applySecurityDocumentExtension(new Context(Position.SECURITY_SCHEME_BEGIN, markupDocBuilder, securitySchemeName, securityScheme));
buildDescriptionParagraph(securityScheme.getDescription(), this.markupDocBuilder);
buildSecurityScheme(securityScheme);
applySecurityDocumentExtension(new Context(Position.SECURITY_SCHEME_END, markupDocBuilder, securitySchemeName, securityScheme));
applySecurityDocumentExtension(new Context(Position.SECURITY_SCHEME_AFTER, markupDocBuilder, securitySchemeName, securityScheme));
}
}
private MarkupDocBuilder buildSecuritySchemeDefinitionTitle(String securitySchemeName) {
return markupDocBuilder.sectionTitleWithAnchorLevel2(securitySchemeName);
}
private void buildSecurityScheme(SecuritySchemeDefinition securityScheme) {
String type = securityScheme.getType();
MarkupDocBuilder paragraph = copyMarkupDocBuilder();
paragraph.italicText(TYPE).textLine(COLON + type);
if (securityScheme instanceof ApiKeyAuthDefinition) {
paragraph.italicText(NAME).textLine(COLON + ((ApiKeyAuthDefinition) securityScheme).getName());
paragraph.italicText(IN).textLine(COLON + ((ApiKeyAuthDefinition) securityScheme).getIn());
markupDocBuilder.paragraph(paragraph.toString(), true);
} else if (securityScheme instanceof OAuth2Definition) {
OAuth2Definition oauth2Scheme = (OAuth2Definition) securityScheme;
String flow = oauth2Scheme.getFlow();
paragraph.italicText(FLOW).textLine(COLON + flow);
if (isNotBlank(oauth2Scheme.getAuthorizationUrl())) {
paragraph.italicText(AUTHORIZATION_URL).textLine(COLON + oauth2Scheme.getAuthorizationUrl());
}
if (isNotBlank(oauth2Scheme.getTokenUrl())) {
paragraph.italicText(TOKEN_URL).textLine(COLON + oauth2Scheme.getTokenUrl());
}
List<List<String>> cells = new ArrayList<>();
List<MarkupTableColumn> cols = Arrays.asList(
new MarkupTableColumn(NAME_COLUMN).withWidthRatio(3).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^3"),
new MarkupTableColumn(DESCRIPTION_COLUMN).withWidthRatio(17).withMarkupSpecifiers(MarkupLanguage.ASCIIDOC, ".^17"));
for (Map.Entry<String, String> scope : oauth2Scheme.getScopes().entrySet()) {
List<String> content = Arrays.asList(scope.getKey(), scope.getValue());
cells.add(content);
}
markupDocBuilder.paragraph(paragraph.toString(), true);
markupDocBuilder.tableWithColumnSpecs(cols, cells);
} else {
markupDocBuilder.paragraph(paragraph.toString(), true);
}
}
/**
* Apply extension context to all SecurityContentExtension
*
* @param context context
*/
private void applySecurityDocumentExtension(Context context) {
for (SecurityDocumentExtension extension : extensionRegistry.getSecurityDocumentExtensions()) {
extension.apply(context);
}
}
}

View File

@@ -1,300 +0,0 @@
/*
* Copyright 2016 Robert Winkler
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.github.swagger2markup.internal.utils;
import io.github.swagger2markup.markup.builder.MarkupDocBuilder;
import io.github.swagger2markup.model.PathOperation;
import io.swagger.models.*;
import io.swagger.models.parameters.*;
import io.swagger.models.properties.ArrayProperty;
import io.swagger.models.properties.MapProperty;
import io.swagger.models.properties.Property;
import io.swagger.models.properties.RefProperty;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
public class ExamplesUtil {
private static Logger logger = LoggerFactory.getLogger(ExamplesUtil.class);
/**
* Generates a Map of response examples
*
* @param generateMissingExamples specifies the missing examples should be generated
* @param operation the Swagger Operation
* @param definitions the map of definitions
* @param markupDocBuilder the markup builder
* @return map containing response examples.
*/
public static Map<String, Object> generateResponseExampleMap(boolean generateMissingExamples, Operation operation, Map<String, Model> definitions, MarkupDocBuilder markupDocBuilder) {
Map<String, Object> examples = new LinkedHashMap<>();
Map<String, Response> responses = operation.getResponses();
if (responses != null)
for (Map.Entry<String, Response> responseEntry : responses.entrySet()) {
Response response = responseEntry.getValue();
Object example = response.getExamples();
if (example == null) {
Property schema = response.getSchema();
if (schema != null) {
example = schema.getExample();
if (example == null && schema instanceof RefProperty) {
String simpleRef = ((RefProperty) schema).getSimpleRef();
example = generateExampleForRefModel(generateMissingExamples, simpleRef, definitions, markupDocBuilder);
}
if (example == null && generateMissingExamples) {
example = PropertyUtils.generateExample(schema, markupDocBuilder);
}
}
}
if (example != null)
examples.put(responseEntry.getKey(), example);
}
return examples;
}
/**
* Generates examples for request
*
* @param generateMissingExamples specifies the missing examples should be generated
* @param pathOperation the Swagger Operation
* @param definitions the map of definitions
* @param markupDocBuilder the markup builder
* @return an Optional with the example content
*/
public static Map<String, Object> generateRequestExampleMap(boolean generateMissingExamples, PathOperation pathOperation, Map<String, Model> definitions, MarkupDocBuilder markupDocBuilder) {
Operation operation = pathOperation.getOperation();
List<Parameter> parameters = operation.getParameters();
Map<String, Object> examples = new LinkedHashMap<>();
// Path example should always be included (if generateMissingExamples):
if (generateMissingExamples)
examples.put("path", pathOperation.getPath());
for (Parameter parameter : parameters) {
Object example = null;
if (parameter instanceof BodyParameter) {
example = ((BodyParameter) parameter).getExamples();
if (example == null) {
Model schema = ((BodyParameter) parameter).getSchema();
if (schema instanceof RefModel) {
String simpleRef = ((RefModel) schema).getSimpleRef();
example = generateExampleForRefModel(generateMissingExamples, simpleRef, definitions, markupDocBuilder);
} else if (generateMissingExamples) {
if (schema instanceof ComposedModel) {
example = exampleMapForProperties(getPropertiesForComposedModel(
(ComposedModel) schema, definitions), definitions, markupDocBuilder);
} else if (schema instanceof ArrayModel) {
example = generateExampleForArrayModel((ArrayModel) schema, definitions, markupDocBuilder);
} else {
example = schema.getExample();
if (example == null) {
example = exampleMapForProperties(schema.getProperties(), definitions, markupDocBuilder);
}
}
}
}
} else if (parameter instanceof AbstractSerializableParameter) {
if (generateMissingExamples) {
Object abstractSerializableParameterExample;
abstractSerializableParameterExample = ((AbstractSerializableParameter) parameter).getExample();
if (abstractSerializableParameterExample == null) {
Property item = ((AbstractSerializableParameter) parameter).getItems();
if (item != null) {
abstractSerializableParameterExample = item.getExample();
if (abstractSerializableParameterExample == null) {
abstractSerializableParameterExample = PropertyUtils.generateExample(item, markupDocBuilder);
}
}
if (abstractSerializableParameterExample == null) {
abstractSerializableParameterExample = ParameterUtils.generateExample((AbstractSerializableParameter)parameter);
}
}
if (parameter instanceof PathParameter) {
String pathExample = (String) examples.get("path");
pathExample = pathExample.replace('{' + parameter.getName() + '}', String.valueOf(abstractSerializableParameterExample));
example = pathExample;
} else {
example = abstractSerializableParameterExample;
}
if (parameter instanceof QueryParameter) {
//noinspection unchecked
@SuppressWarnings("unchecked")
Map<String, Object> queryExampleMap = (Map<String, Object>) examples.get("query");
if (queryExampleMap == null) {
queryExampleMap = new LinkedHashMap<>();
}
queryExampleMap.put(parameter.getName(), abstractSerializableParameterExample);
example = queryExampleMap;
}
}
} else if (parameter instanceof RefParameter) {
String simpleRef = ((RefParameter) parameter).getSimpleRef();
example = generateExampleForRefModel(generateMissingExamples, simpleRef, definitions, markupDocBuilder);
}
if (example != null)
examples.put(parameter.getIn(), example);
}
return examples;
}
/**
* Generates an example object from a simple reference
*
* @param generateMissingExamples specifies the missing examples should be generated
* @param simpleRef the simple reference string
* @param definitions the map of definitions
* @param markupDocBuilder the markup builder
* @return returns an Object or Map of examples
*/
public static Object generateExampleForRefModel(boolean generateMissingExamples, String simpleRef, Map<String, Model> definitions, MarkupDocBuilder markupDocBuilder) {
Model model = definitions.get(simpleRef);
Object example = null;
if (model != null) {
example = model.getExample();
if (example == null && generateMissingExamples) {
if (model instanceof ComposedModel) {
example = exampleMapForProperties(getPropertiesForComposedModel((ComposedModel) model, definitions), definitions, markupDocBuilder);
} else {
example = exampleMapForProperties(model.getProperties(), definitions, markupDocBuilder);
}
}
}
return example;
}
private static Map<String, Property> getPropertiesForComposedModel(ComposedModel model, Map<String, Model> definitions) {
Map<String, Property> combinedProperties;
if (model.getParent() instanceof RefModel) {
Map<String, Property> parentProperties = definitions.get(((RefModel) model.getParent()).getSimpleRef()).getProperties();
if (parentProperties == null) {
return null;
} else {
combinedProperties = new LinkedHashMap<>(parentProperties);
}
} else {
combinedProperties = new LinkedHashMap<>(model.getParent().getProperties());
}
Map<String, Property> childProperties;
if (model.getChild() instanceof RefModel) {
childProperties = definitions.get(((RefModel) model.getChild()).getSimpleRef()).getProperties();
} else {
childProperties = model.getChild().getProperties();
}
if (childProperties != null) {
combinedProperties.putAll(childProperties);
}
return combinedProperties;
}
/**
* Generates a map of examples from a map of properties. If defined examples are found, those are used. Otherwise,
* examples are generated from the type.
*
* @param properties the map of properties
* @param definitions the map of definitions
* @param markupDocBuilder the markup builder
*
* @return a Map of examples
*/
public static Map<String, Object> exampleMapForProperties(Map<String, Property> properties, Map<String, Model> definitions, MarkupDocBuilder markupDocBuilder) {
Map<String, Object> exampleMap = new LinkedHashMap<>();
if (properties != null) {
for (Map.Entry<String, Property> property : properties.entrySet()) {
Object exampleObject = property.getValue().getExample();
if (exampleObject == null) {
if (property.getValue() instanceof RefProperty) {
exampleObject = generateExampleForRefModel(true, ((RefProperty) property.getValue()).getSimpleRef(), definitions, markupDocBuilder);
} else if (property.getValue() instanceof ArrayProperty) {
exampleObject = generateExampleForArrayProperty((ArrayProperty) property.getValue(), definitions, markupDocBuilder);
} else if (property.getValue() instanceof MapProperty) {
exampleObject = generateExampleForMapProperty((MapProperty) property.getValue(), markupDocBuilder);
}
if (exampleObject == null) {
Property valueProperty = property.getValue();
exampleObject = PropertyUtils.generateExample(valueProperty, markupDocBuilder);
}
}
exampleMap.put(property.getKey(), exampleObject);
}
}
return exampleMap;
}
public static Object generateExampleForMapProperty(MapProperty property, MarkupDocBuilder markupDocBuilder) {
if (property.getExample() != null) {
return property.getExample();
}
Map<String, Object> exampleMap = new LinkedHashMap<>();
Property valueProperty = property.getAdditionalProperties();
if (valueProperty.getExample() != null) {
return valueProperty.getExample();
}
exampleMap.put("string", PropertyUtils.generateExample(valueProperty, markupDocBuilder));
return exampleMap;
}
public static Object generateExampleForArrayModel(ArrayModel model, Map<String, Model> definitions, MarkupDocBuilder markupDocBuilder) {
if (model.getExample() != null) {
return model.getExample();
} else if (model.getProperties() != null) {
return new Object[]{exampleMapForProperties(model.getProperties(), definitions, markupDocBuilder)};
} else {
Property itemProperty = model.getItems();
if (itemProperty.getExample() != null) {
return new Object[]{itemProperty.getExample()};
} else if (itemProperty instanceof ArrayProperty) {
return new Object[]{generateExampleForArrayProperty((ArrayProperty) itemProperty, definitions, markupDocBuilder)};
} else if (itemProperty instanceof RefProperty) {
return new Object[]{generateExampleForRefModel(true, ((RefProperty) itemProperty).getSimpleRef(), definitions, markupDocBuilder)};
} else {
return new Object[]{PropertyUtils.generateExample(itemProperty, markupDocBuilder)};
}
}
}
/**
* Generates examples from an ArrayProperty
*
* @param value ArrayProperty
* @param definitions map of definitions
* @param markupDocBuilder the markup builder
* @return array of Object
*/
public static Object[] generateExampleForArrayProperty(ArrayProperty value, Map<String, Model> definitions, MarkupDocBuilder markupDocBuilder) {
Property property = value.getItems();
if (property.getExample() != null) {
return new Object[]{property.getExample()};
} else if (property instanceof ArrayProperty) {
return new Object[]{generateExampleForArrayProperty((ArrayProperty) property, definitions, markupDocBuilder)};
} else if (property instanceof RefProperty) {
return new Object[]{generateExampleForRefModel(true, ((RefProperty) property).getSimpleRef(), definitions, markupDocBuilder)};
} else {
return new Object[]{PropertyUtils.generateExample(property, markupDocBuilder)};
}
}
}

View File

@@ -1,117 +0,0 @@
/*
* Copyright 2016 Robert Winkler
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.github.swagger2markup.internal.utils;
import com.google.common.base.Function;
import io.github.swagger2markup.internal.type.*;
import io.swagger.models.Model;
import io.swagger.models.parameters.AbstractSerializableParameter;
import io.swagger.models.parameters.BodyParameter;
import io.swagger.models.parameters.Parameter;
import io.swagger.models.parameters.RefParameter;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.Validate;
import java.util.List;
import java.util.Map;
public final class ParameterUtils {
/**
* Retrieves the type of a parameter, or otherwise null
*
* @param parameter the parameter
* @param definitionDocumentResolver the defintion document resolver
* @return the type of the parameter, or otherwise null
*/
public static Type getType(Parameter parameter, Map<String, Model> definitions, Function<String, String> definitionDocumentResolver){
Validate.notNull(parameter, "parameter must not be null!");
Type type = null;
if(parameter instanceof BodyParameter){
BodyParameter bodyParameter = (BodyParameter)parameter;
Model model = bodyParameter.getSchema();
if(model != null){
type = ModelUtils.getType(model, definitions, definitionDocumentResolver);
}else{
type = new BasicType("string", null);
}
}
else if(parameter instanceof AbstractSerializableParameter){
AbstractSerializableParameter serializableParameter = (AbstractSerializableParameter)parameter;
@SuppressWarnings("unchecked")
List<String> enums = serializableParameter.getEnum();
if(CollectionUtils.isNotEmpty(enums)){
type = new EnumType(null, enums);
}else{
type = new BasicType(serializableParameter.getType(), null, serializableParameter.getFormat());
}
if(serializableParameter.getType().equals("array")){
String collectionFormat = serializableParameter.getCollectionFormat();
type = new ArrayType(null, PropertyUtils.getType(serializableParameter.getItems(), definitionDocumentResolver), collectionFormat);
}
}
else if(parameter instanceof RefParameter){
String refName = ((RefParameter)parameter).getSimpleRef();
type = new RefType(definitionDocumentResolver.apply(refName), new ObjectType(refName, null /* FIXME, not used for now */));
}
return type;
}
/**
* Retrieves the default value of a parameter, or otherwise returns null
*
* @param parameter the parameter
* @return the default value of the parameter, or otherwise null
*/
public static Object getDefaultValue(Parameter parameter){
Validate.notNull(parameter, "parameter must not be null!");
Object defaultValue = null;
if(parameter instanceof AbstractSerializableParameter){
AbstractSerializableParameter serializableParameter = (AbstractSerializableParameter)parameter;
defaultValue = serializableParameter.getDefaultValue();
}
return defaultValue;
}
/**
* Generate a default example value for parameter.
*
* @param parameter parameter
* @return a generated example for the parameter
*/
public static Object generateExample(AbstractSerializableParameter parameter) {
switch (parameter.getType()) {
case "integer":
return 0;
case "number":
return 0.0;
case "boolean":
return true;
case "string":
return "string";
default:
return parameter.getType();
}
}
}

View File

@@ -1,325 +0,0 @@
/*
* Copyright 2016 Robert Winkler
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.github.swagger2markup.internal.utils;
import com.google.common.base.Function;
import io.github.swagger2markup.internal.type.*;
import io.github.swagger2markup.markup.builder.MarkupDocBuilder;
import io.swagger.models.properties.*;
import io.swagger.models.refs.RefFormat;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.Validate;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import static org.apache.commons.lang3.StringUtils.isNotBlank;
public final class PropertyUtils {
/**
* Retrieves the type and format of a property.
*
* @param property the property
* @param definitionDocumentResolver the definition document resolver
* @return the type of the property
*/
public static Type getType(Property property, Function<String, String> definitionDocumentResolver) {
Validate.notNull(property, "property must not be null");
Type type;
if (property instanceof RefProperty) {
RefProperty refProperty = (RefProperty) property;
if (refProperty.getRefFormat() == RefFormat.RELATIVE)
type = new ObjectType(refProperty.getTitle(), null); // FIXME : Workaround for https://github.com/swagger-api/swagger-parser/issues/177
else
type = new RefType(definitionDocumentResolver.apply(refProperty.getSimpleRef()), new ObjectType(refProperty.getSimpleRef(), null /* FIXME, not used for now */));
} else if (property instanceof ArrayProperty) {
ArrayProperty arrayProperty = (ArrayProperty) property;
Property items = arrayProperty.getItems();
if (items == null)
type = new ArrayType(arrayProperty.getTitle(), new ObjectType(null, null)); // FIXME : Workaround for Swagger parser issue with composed models (https://github.com/Swagger2Markup/swagger2markup/issues/150)
else
type = new ArrayType(arrayProperty.getTitle(), getType(items, definitionDocumentResolver));
} else if (property instanceof MapProperty) {
MapProperty mapProperty = (MapProperty) property;
Property additionalProperties = mapProperty.getAdditionalProperties();
if (additionalProperties == null)
type = new MapType(mapProperty.getTitle(), new ObjectType(null, null)); // FIXME : Workaround for Swagger parser issue with composed models (https://github.com/Swagger2Markup/swagger2markup/issues/150)
else
type = new MapType(mapProperty.getTitle(), getType(additionalProperties, definitionDocumentResolver));
} else if (property instanceof StringProperty) {
StringProperty stringProperty = (StringProperty) property;
List<String> enums = stringProperty.getEnum();
if (CollectionUtils.isNotEmpty(enums)) {
type = new EnumType(stringProperty.getTitle(), enums);
} else {
type = new BasicType(stringProperty.getType(), stringProperty.getTitle());
}
} else if (property instanceof ObjectProperty) {
type = new ObjectType(property.getTitle(), ((ObjectProperty) property).getProperties());
} else {
if (isNotBlank(property.getFormat())) {
type = new BasicType(property.getType(), property.getTitle(), property.getFormat());
} else {
type = new BasicType(property.getType(), property.getTitle());
}
}
return type;
}
/**
* Retrieves the default value of a property, or otherwise returns null.
*
* @param property the property
* @return the default value of the property, or otherwise null
*/
public static Object getDefaultValue(Property property) {
Validate.notNull(property, "property must not be null");
Object defaultValue = null;
if (property instanceof BooleanProperty) {
BooleanProperty booleanProperty = (BooleanProperty) property;
defaultValue = booleanProperty.getDefault();
} else if (property instanceof StringProperty) {
StringProperty stringProperty = (StringProperty) property;
defaultValue = stringProperty.getDefault();
} else if (property instanceof DoubleProperty) {
DoubleProperty doubleProperty = (DoubleProperty) property;
defaultValue = doubleProperty.getDefault();
} else if (property instanceof FloatProperty) {
FloatProperty floatProperty = (FloatProperty) property;
defaultValue = floatProperty.getDefault();
} else if (property instanceof IntegerProperty) {
IntegerProperty integerProperty = (IntegerProperty) property;
defaultValue = integerProperty.getDefault();
} else if (property instanceof LongProperty) {
LongProperty longProperty = (LongProperty) property;
defaultValue = longProperty.getDefault();
} else if (property instanceof UUIDProperty) {
UUIDProperty uuidProperty = (UUIDProperty) property;
defaultValue = uuidProperty.getDefault();
}
return defaultValue;
}
/**
* Retrieves the minLength of a property, or otherwise returns null.
*
* @param property the property
* @return the minLength of the property, or otherwise null
*/
public static Integer getMinlength(Property property) {
Validate.notNull(property, "property must not be null");
Integer minLength = null;
if (property instanceof StringProperty) {
StringProperty stringProperty = (StringProperty) property;
minLength = stringProperty.getMinLength();
} else if (property instanceof UUIDProperty) {
UUIDProperty uuidProperty = (UUIDProperty) property;
minLength = uuidProperty.getMinLength();
}
return minLength;
}
/**
* Retrieves the maxLength of a property, or otherwise returns null.
*
* @param property the property
* @return the maxLength of the property, or otherwise null
*/
public static Integer getMaxlength(Property property) {
Validate.notNull(property, "property must not be null");
Integer maxLength = null;
if (property instanceof StringProperty) {
StringProperty stringProperty = (StringProperty) property;
maxLength = stringProperty.getMaxLength();
} else if (property instanceof UUIDProperty) {
UUIDProperty uuidProperty = (UUIDProperty) property;
maxLength = uuidProperty.getMaxLength();
}
return maxLength;
}
/**
* Retrieves the pattern of a property, or otherwise returns null.
*
* @param property the property
* @return the pattern of the property, or otherwise null
*/
public static String getPattern(Property property) {
Validate.notNull(property, "property must not be null");
String pattern = null;
if (property instanceof StringProperty) {
StringProperty stringProperty = (StringProperty) property;
pattern = stringProperty.getPattern();
} else if (property instanceof UUIDProperty) {
UUIDProperty uuidProperty = (UUIDProperty) property;
pattern = uuidProperty.getPattern();
}
return pattern;
}
/**
* Retrieves the minimum value of a property, or otherwise returns null.
*
* @param property the property
* @return the minimum value of the property, or otherwise null
*/
public static Double getMin(Property property) {
Validate.notNull(property, "property must not be null");
Double min = null;
if (property instanceof DoubleProperty) {
DoubleProperty doubleProperty = (DoubleProperty) property;
min = doubleProperty.getMinimum();
} else if (property instanceof FloatProperty) {
FloatProperty floatProperty = (FloatProperty) property;
min = floatProperty.getMinimum();
} else if (property instanceof IntegerProperty) {
IntegerProperty integerProperty = (IntegerProperty) property;
min = integerProperty.getMinimum();
} else if (property instanceof LongProperty) {
LongProperty longProperty = (LongProperty) property;
min = longProperty.getMinimum();
}
return min;
}
/**
* Retrieves the minimum value of a property, or otherwise returns null.
*
* @param property the property
* @return the minimum value of the property, or otherwise null
*/
public static Double getMax(Property property) {
Validate.notNull(property, "property must not be null");
Double max = null;
if (property instanceof DoubleProperty) {
DoubleProperty doubleProperty = (DoubleProperty) property;
max = doubleProperty.getMaximum();
} else if (property instanceof FloatProperty) {
FloatProperty floatProperty = (FloatProperty) property;
max = floatProperty.getMaximum();
} else if (property instanceof IntegerProperty) {
IntegerProperty integerProperty = (IntegerProperty) property;
max = integerProperty.getMaximum();
} else if (property instanceof LongProperty) {
LongProperty longProperty = (LongProperty) property;
max = longProperty.getMaximum();
}
return max;
}
/**
* Return example display string for the given {@code property}.
*
* @param generateMissingExamples specifies if missing examples should be generated
* @param property property
* @param markupDocBuilder doc builder
* @return property example display string
*/
public static Object getExample(boolean generateMissingExamples, Property property, MarkupDocBuilder markupDocBuilder) {
Validate.notNull(property, "property must not be null");
Object examplesValue = null;
if (property.getExample() != null) {
examplesValue = property.getExample();
} else if (property instanceof MapProperty) {
Property additionalProperty = ((MapProperty) property).getAdditionalProperties();
if (additionalProperty.getExample() != null) {
examplesValue = additionalProperty.getExample();
} else if (generateMissingExamples) {
Map<String, Object> exampleMap = new HashMap<>();
exampleMap.put("string", generateExample(additionalProperty, markupDocBuilder));
examplesValue = exampleMap;
}
} else if (property instanceof ArrayProperty) {
if (generateMissingExamples) {
Property itemProperty = ((ArrayProperty) property).getItems();
List<Object> exampleArray = new ArrayList<>();
exampleArray.add(generateExample(itemProperty, markupDocBuilder));
examplesValue = exampleArray;
}
} else if (generateMissingExamples) {
examplesValue = generateExample(property, markupDocBuilder);
}
return examplesValue;
}
/**
* Generate a default example value for property.
*
* @param property property
* @param markupDocBuilder doc builder
* @return a generated example for the property
*/
public static Object generateExample(Property property, MarkupDocBuilder markupDocBuilder) {
switch (property.getType()) {
case "integer":
return 0;
case "number":
return 0.0;
case "boolean":
return true;
case "string":
return "string";
case "ref":
if (property instanceof RefProperty) {
return markupDocBuilder.copy(false).crossReference(((RefProperty) property).getSimpleRef()).toString();
}
default:
return property.getType();
}
}
/**
* Convert a string {@code value} to specified {@code type}.
*
* @param value value to convert
* @param type target conversion type
* @return converted value as object
*/
public static Object convertExample(String value, String type) {
if (value == null) {
return null;
}
try {
switch (type) {
case "integer":
return Integer.valueOf(value);
case "number":
return Float.valueOf(value);
case "boolean":
return Boolean.valueOf(value);
case "string":
return value;
default:
return value;
}
} catch (NumberFormatException e) {
throw new RuntimeException(String.format("Value '%s' cannot be converted to '%s'", value, type), e);
}
}
}

View File

@@ -1,101 +0,0 @@
/*
* Copyright 2016 Robert Winkler
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.github.swagger2markup.internal.utils;
import com.google.common.base.Optional;
import com.google.common.collect.Multimap;
import com.google.common.collect.MultimapBuilder;
import com.google.common.collect.Ordering;
import io.github.swagger2markup.model.PathOperation;
import io.swagger.models.Tag;
import org.apache.commons.lang3.Validate;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.*;
public class TagUtils {
private static Logger LOG = LoggerFactory.getLogger(TagUtils.class);
/**
* Converts the global Tag list into a Map where the tag name is the key and the Tag the value.
*
* @param tags the List of tags
* @return the Map of tags
*/
public static Map<String, Tag> convertTagsListToMap(List<Tag> tags) {
if (tags == null) {
tags = new ArrayList<>();
}
Map<String, Tag> tagsMap = new HashMap<>();
for (Tag tag : tags) tagsMap.put(tag.getName(), tag);
return tagsMap;
}
/**
* Retrieves the optional description of a tag.
*
* @param tagsMap the Map of tags
* @param tagName the name of the tag
* @return the optional description of the tag
*/
public static Optional<String> getTagDescription(Map<String, Tag> tagsMap, String tagName) {
Tag tag = tagsMap.get(tagName);
if(tag != null){
return Optional.fromNullable(tag.getDescription());
}
return Optional.absent();
}
/**
* Groups the operations by tag. The key of the Multimap is the tag name.
* The value of the Multimap is a PathOperation
*
* @param allOperations all operations
* @param tagOrdering comparator for tags
* @param operationOrdering comparator for operations, for a given tag
* @return Operations grouped by Tag
*/
public static Multimap<String, PathOperation> groupOperationsByTag(Set<PathOperation> allOperations, Comparator<String> tagOrdering, Comparator<PathOperation> operationOrdering) {
MultimapBuilder.MultimapBuilderWithKeys<String> multimapBuilderWithKeys;
if (tagOrdering == null)
multimapBuilderWithKeys = MultimapBuilder.SortedSetMultimapBuilder.treeKeys(Ordering.<String>natural()); // FIXME as-is sorting not supported because of limitations in MultiMap::hashkeys(). Replaced with Ordering.natural()
else
multimapBuilderWithKeys = MultimapBuilder.SortedSetMultimapBuilder.treeKeys(tagOrdering);
Multimap<String, PathOperation> operationsGroupedByTag;
if (operationOrdering == null)
operationsGroupedByTag = multimapBuilderWithKeys.hashSetValues().build();
else
operationsGroupedByTag = multimapBuilderWithKeys.treeSetValues(operationOrdering).build();
for (PathOperation operation : allOperations) {
List<String> tags = operation.getOperation().getTags();
Validate.notEmpty(tags, "Can't GroupBy.TAGS > Operation '%s' has not tags", operation);
for (String tag : tags) {
if (LOG.isInfoEnabled()) {
LOG.info("Added path operation '{}' to tag '{}'", operation, tag);
}
operationsGroupedByTag.put(tag, operation);
}
}
return operationsGroupedByTag;
}
}

View File

@@ -1,79 +0,0 @@
/*
* Copyright 2016 Robert Winkler
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.github.swagger2markup.model;
import io.swagger.models.HttpMethod;
import io.swagger.models.Operation;
import static org.apache.commons.lang3.StringUtils.isBlank;
public class PathOperation {
protected HttpMethod method;
protected String path;
protected Operation operation;
public PathOperation(HttpMethod method, String path, Operation operation) {
this.method = method;
this.path = path;
this.operation = operation;
}
public HttpMethod getMethod() {
return method;
}
public String getPath() {
return path;
}
/**
* Returns the display title for an operation
* @return the operation title
*/
public String getTitle() {
String operationName = operation.getSummary();
if (isBlank(operationName)) {
operationName = getMethod().toString() + " " + getPath();
}
return operationName;
}
/**
* Returns an unique id for the operation.<br>
* Use {@code <operation id>}, then {@code <operation path> lowercase(<operation method>)} if operation id is not set.
*
* @return operation unique id
*/
public String getId() {
String id = operation.getOperationId();
if (id == null)
id = getPath() + " " + getMethod().toString().toLowerCase();
return id;
}
public Operation getOperation() {
return operation;
}
@Override
public String toString() {
return getId();
}
}

View File

@@ -1,552 +0,0 @@
/*
* Copyright 2016 Robert Winkler
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.github.swagger2markup;
import io.github.swagger2markup.assertions.DiffUtils;
import io.github.swagger2markup.builder.Swagger2MarkupConfigBuilder;
import org.apache.commons.io.FileUtils;
import org.apache.commons.io.IOUtils;
import org.junit.Before;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.IOException;
import java.net.URISyntaxException;
import java.nio.charset.Charset;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.List;
import static java.util.Arrays.asList;
import static org.assertj.core.api.Assertions.failBecauseExceptionWasNotThrown;
import static org.assertj.core.api.BDDAssertions.assertThat;
public class AsciidocConverterTest {
private static final Logger LOG = LoggerFactory.getLogger(AsciidocConverterTest.class);
private static final String[] EXPECTED_FILES = new String[]{"definitions.adoc", "overview.adoc", "paths.adoc", "security.adoc"};
private List<String> expectedFiles;
@Before
public void setUp(){
expectedFiles = new ArrayList<>(asList(EXPECTED_FILES));
}
@Test
public void testSwagger2AsciiDocConversionAsString() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/yaml/swagger_petstore.yaml").toURI());
//When
String asciiDocAsString = Swagger2MarkupConverter.from(file).build()
.toString();
//Then
assertThat(asciiDocAsString).isNotEmpty();
}
@Test
public void testSwagger2AsciiDocConversion() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/yaml/swagger_petstore.yaml").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/default");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConverter.from(file).build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/default").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocConversion.html");
}
@Test
public void testSwagger2AsciiDocConversionInstagram() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/yaml/swagger_instagram.yaml").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/instagram");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConverter.from(file).build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/instagram").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocConversionInstagram.html");
}
@Test
public void testSwagger2AsciiDocConversionWithInterDocumentCrossReferences() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/yaml/swagger_petstore.yaml").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/idxref");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.withInterDocumentCrossReferences()
.build();
Swagger2MarkupConverter.from(file).withConfig(config).build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/idxref").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocConversionWithInterDocumentCrossReferences.html");
}
@Test
public void testSwagger2AsciiDocConversionFromString() throws IOException, URISyntaxException {
//Given
String swaggerJsonString = IOUtils.toString(getClass().getResourceAsStream("/yaml/swagger_petstore.yaml"));
Path outputDirectory = Paths.get("build/test/asciidoc/default");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConverter.from(swaggerJsonString).build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/default").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocConversion.html");
}
@Test
public void testSwagger2AsciiDocConversionWithExamples() throws IOException, URISyntaxException {
//Given
String swaggerJsonString = IOUtils.toString(getClass().getResourceAsStream("/json/swagger_examples.json"));
Path outputDirectory = Paths.get("build/test/asciidoc/examples");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.withoutInlineSchema()
.build();
Swagger2MarkupConverter.from(swaggerJsonString)
.withConfig(config)
.build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/examples").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocConversionWithExamples.html");
}
@Test
public void testSwagger2AsciiDocConversionWithGeneratedExamples() throws IOException, URISyntaxException {
//Given
String swaggerJsonString = IOUtils.toString(getClass().getResourceAsStream("/json/swagger_examples.json"));
Path outputDirectory = Paths.get("build/test/asciidoc/generated_examples");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.withoutInlineSchema()
.withGeneratedExamples()
.build();
Swagger2MarkupConverter.from(swaggerJsonString)
.withConfig(config)
.build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/generated_examples").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocConversionWithGeneratedExamples.html");
}
@Test
public void testSwagger2AsciiDocWithInlineSchema() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/yaml/swagger_inlineSchema.yaml").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/inline_schema");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.build();
Swagger2MarkupConverter.from(file)
.withConfig(config)
.build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/inline_schema").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocWithInlineSchema.html");
}
@Test
public void testSwagger2AsciiDocWithInlineSchemaAndFlatBody() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/yaml/swagger_inlineSchema.yaml").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/inline_schema_flat_body");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.withFlatBody()
.build();
Swagger2MarkupConverter.from(file)
.withConfig(config)
.build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/inline_schema_flat_body").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocWithInlineSchemaAndFlatBody.html");
}
@Test
public void testSwagger2AsciiDocGroupedByTags() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/yaml/swagger_petstore.yaml").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/group_by_tags");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.withPathsGroupedBy(GroupBy.TAGS)
.build();
Swagger2MarkupConverter.from(file)
.withConfig(config)
.build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/group_by_tags").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocGroupedByTags.html");
}
@Test
public void testSwagger2AsciiDocGroupedByTagsWithMissingTag() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/json/swagger_missing_tag.json").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/generated");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
try {
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.withPathsGroupedBy(GroupBy.TAGS)
.build();
Swagger2MarkupConverter.from(file)
.withConfig(config)
.build()
.toFolder(outputDirectory);
// If NullPointerException was not thrown, test would fail the specified message
failBecauseExceptionWasNotThrown(NullPointerException.class);
} catch (Exception e) {
assertThat(e).hasMessage("Can't GroupBy.TAGS > Operation 'updatePet' has not tags");
}
}
@Test
public void testSwagger2AsciiDocConversionDoesNotContainUriScheme() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/yaml/swagger_should_not_contain_uri_scheme.yaml").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/generated");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConverter.from(file).build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
assertThat(new String(Files.readAllBytes(outputDirectory.resolve("overview.adoc"))))
.doesNotContain("=== URI scheme");
}
@Test
public void testSwagger2AsciiDocConversionContainsUriScheme() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/yaml/swagger_should_contain_uri_scheme.yaml").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/generated");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConverter.from(file).build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
assertThat(new String(Files.readAllBytes(outputDirectory.resolve("overview.adoc"))))
.contains("=== URI scheme");
}
@Test
public void testSwagger2AsciiDocConversionWithSeparatedDefinitions() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/yaml/swagger_petstore.yaml").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/generated");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.withSeparatedDefinitions()
.build();
Swagger2MarkupConverter.from(file).withConfig(config).build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
expectedFiles.add("definitions");
assertThat(files).hasSize(5).containsAll(expectedFiles);
Path definitionsDirectory = outputDirectory.resolve("definitions");
String[] definitions = definitionsDirectory.toFile().list();
assertThat(definitions).hasSize(5).containsAll(
asList("Category.adoc", "Order.adoc", "Pet.adoc", "Tag.adoc", "User.adoc"));
}
@Test
public void testSwagger2AsciiDocConversionWithSeparatedOperations() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/yaml/swagger_petstore.yaml").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/generated");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.withSeparatedOperations()
.build();
Swagger2MarkupConverter.from(file).withConfig(config).build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
expectedFiles.add("operations");
assertThat(files).hasSize(5).containsAll(expectedFiles);
Path pathsDirectory = outputDirectory.resolve("operations");
String[] paths = pathsDirectory.toFile().list();
assertThat(paths).hasSize(18);
}
@Test
public void testSwagger2AsciiDocConversionWithRussianOutputLanguage() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/yaml/swagger_petstore.yaml").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/generated");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.withOutputLanguage(Language.RU)
.build();
Swagger2MarkupConverter.from(file)
.withConfig(config)
.build()
.toFolder(outputDirectory);
//Then
assertThat(new String(Files.readAllBytes(outputDirectory.resolve("definitions.adoc")), Charset.forName("UTF-8")))
.contains("== Определения");
}
@Test
public void testSwagger2AsciiDocConversionWithFrenchOutputLanguage() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/yaml/swagger_petstore.yaml").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/generated");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.withOutputLanguage(Language.FR)
.build();
Swagger2MarkupConverter.from(file)
.withConfig(config)
.build()
.toFolder(outputDirectory);
//Then
assertThat(new String(Files.readAllBytes(outputDirectory.resolve("overview.adoc")), Charset.forName("UTF-8")))
.contains("== Sch\u00E9ma d'URI");
}
@Test
public void testSwagger2AsciiDocConversionWithMaps() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/json/swagger_maps.json").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/maps");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.build();
Swagger2MarkupConverter.from(file)
.withConfig(config)
.build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/maps").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocConversionWithMaps.html");
}
@Test
public void testSwagger2AsciiDocConversionWithEnums() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/json/swagger_enums.json").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/enums");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.build();
Swagger2MarkupConverter.from(file)
.withConfig(config)
.build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/enums").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocConversionWithEnums.html");
}
@Test
public void testSwagger2AsciiDocConversionWithValidators() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/json/swagger_validators.json").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/validators");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.build();
Swagger2MarkupConverter.from(file)
.withConfig(config)
.build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/validators").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocConversionWithValidators.html");
}
@Test
public void testSwagger2AsciiDocConversionWithPolymorphism() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/json/swagger_polymorphism.json").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/polymorphism");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.build();
Swagger2MarkupConverter.from(file)
.withConfig(config)
.build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/polymorphism").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocConversionWithPolymorphism.html");
}
@Test
public void testSwagger2AsciiDocConversionWithPolymorphismAsIsOrdering() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/json/swagger_polymorphism.json").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/polymorphismAsIsOrdering");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.withPropertyOrdering(OrderBy.AS_IS)
.build();
Swagger2MarkupConverter.from(file)
.withConfig(config)
.build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/polymorphismAsIsOrdering").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocConversionWithPolymorphismAsIsOrdering.html");
}
@Test
public void testSwagger2AsciiDocConversionWithResponseHeaders() throws IOException, URISyntaxException {
//Given
Path file = Paths.get(AsciidocConverterTest.class.getResource("/yaml/swagger_response_headers.yaml").toURI());
Path outputDirectory = Paths.get("build/test/asciidoc/response_headers");
FileUtils.deleteQuietly(outputDirectory.toFile());
//When
Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
.build();
Swagger2MarkupConverter.from(file)
.withConfig(config)
.build()
.toFolder(outputDirectory);
//Then
String[] files = outputDirectory.toFile().list();
assertThat(files).hasSize(4).containsAll(expectedFiles);
Path expectedFilesDirectory = Paths.get(AsciidocConverterTest.class.getResource("/expected/asciidoc/response_headers").toURI());
DiffUtils.assertThatAllFilesAreEqual(expectedFilesDirectory, outputDirectory, "testSwagger2AsciiDocConversionWithResponseHeaders.html");
}
}

View File

@@ -1,105 +0,0 @@
[[_definitions]]
== Definitions
[[_category]]
=== Category
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_|The name of the category +
*Default* : `"DefaultCategory"` +
*Length* : `0 - 255` +
*Pattern* : `"[A-Za-zäöüÄÖÜß]{0,255}"` +
*Example* : `"FoobarCategory"`|string
|===
[[_order]]
=== Order
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*complete* +
_optional_||boolean
|*id* +
_optional_||integer(int64)
|*petId* +
_optional_||integer(int64)
|*quantity* +
_optional_|*Default* : `0` +
*Minimum value* : `0.0` +
*Maximum value* : `10000.0` +
*Example* : `10`|integer(int32)
|*shipDate* +
_optional_||string(date-time)
|*status* +
_optional_|Order Status|enum (Ordered, Cancelled)
|===
[[_pet]]
=== Pet
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*category* +
_optional_||<<_category,Category>>
|*id* +
_optional_||integer(int64)
|*name* +
_required_|*Example* : `"doggie"`|string
|*photoUrls* +
_required_||< string > array
|*status* +
_optional_|pet status in the store,|enum (Dead, Alive)
|*tags* +
_optional_||< <<_tag,Tag>> > array
|===
[[_tag]]
=== Tag
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===
[[_user]]
=== User
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*email* +
_optional_||string
|*firstName* +
_optional_||string
|*id* +
_optional_||integer(int64)
|*lastName* +
_optional_||string
|*password* +
_optional_||string
|*phone* +
_optional_||string
|*userStatus* +
_optional_|User Status|integer(int32)
|*username* +
_optional_||string
|===

View File

@@ -1,19 +0,0 @@
[[_definitions]]
== Definitions
[[_enumstring]]
=== EnumString
Enum string
_Type_ : enum (ADDED, REMOVED, CHANGED)
[[_simplestring]]
=== SimpleString
Simple string
_Type_ : string

View File

@@ -1,57 +0,0 @@
[[_paths]]
== Paths
[[_createstate]]
=== Create state
....
POST /state
....
==== Description
Return state
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Path*|*oldState* +
_required_|Old State as raw string|enum (ADDED, REMOVED, CHANGED)|
|*Body*|*StateModel* +
_optional_|State as enum in object|<<_createstate_statemodel,StateModel>>|
|===
[[_createstate_statemodel]]
*StateModel*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*value* +
_optional_|State value|enum (ADDED, REMOVED, CHANGED)
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|OK|enum (ADDED, REMOVED, CHANGED)
|===
==== Consumes
* `application/json`
==== Produces
* `*/*`

View File

@@ -1,132 +0,0 @@
[[_definitions]]
== Definitions
[[_category]]
=== Category
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_|*Example* : `123`|integer(int64)
|*name* +
_optional_|*Example* : `"Canines"`|string
|===
[[_complexobject]]
=== ComplexObject
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*subObject* +
_optional_||object
|===
[[_identified]]
=== Identified
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|===
[[_order]]
=== Order
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*complete* +
_optional_||boolean
|*id* +
_optional_|*Example* : `77`|integer(int64)
|*petId* +
_optional_||integer(int64)
|*quantity* +
_optional_||integer(int32)
|*shipDate* +
_optional_||string(date-time)
|*status* +
_optional_|Order Status +
*Example* : `"DONE"`|string
|===
[[_pet]]
=== Pet
Test description
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*category* +
_optional_||<<_category,Category>>
|*id* +
_optional_||integer(int64)
|*name* +
_required_|*Example* : `"doggie"`|string
|*nicknames* +
_optional_||< string, string > map
|*photoUrls* +
_required_||< string > array
|*status* +
_optional_|pet status in the store|string
|*tags* +
_optional_||< <<_tag,Tag>> > array
|*weight* +
_optional_|the weight of the pet|number
|===
[[_tag]]
=== Tag
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===
[[_user]]
=== User
[%hardbreaks]
_Polymorphism_ : Composition
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*email* +
_optional_||string
|*firstName* +
_optional_||string
|*id* +
_optional_||integer(int64)
|*lastName* +
_optional_||string
|*password* +
_optional_||string
|*phone* +
_optional_||string
|*pictures* +
_optional_||< string(byte) > array
|*userStatus* +
_optional_|User Status|integer(int32)
|*username* +
_optional_||string
|===

View File

@@ -1,20 +0,0 @@
[[_definitions]]
== Definitions
[[_ref-category]]
=== <<_category,Category>>
[[_ref-order]]
=== <<_order,Order>>
[[_ref-pet]]
=== <<_pet,Pet>>
[[_ref-tag]]
=== <<_tag,Tag>>
[[_ref-user]]
=== <<_user,User>>

View File

@@ -1,15 +0,0 @@
[[_tag]]
=== Tag
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===

View File

@@ -1,827 +0,0 @@
[[_paths]]
== Paths
[[_addpet]]
=== Add a new pet to the store
....
POST /pets
....
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Body*|*body* +
_optional_|Pet object that needs to be added to the store|<<_pet,Pet>>|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*405*|Invalid input|No Content
|===
==== Consumes
* `application/json`
* `application/xml`
==== Produces
* `application/json`
* `application/xml`
==== Tags
* pet
==== Security
[options="header", cols=".^3,.^4,.^13"]
|===
|Type|Name|Scopes
|*oauth2*|*<<_petstore_auth,petstore_auth>>*|write_pets,read_pets
|===
[[_updatepet]]
=== Update an existing pet
....
PUT /pets
....
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Body*|*body* +
_optional_|Pet object that needs to be added to the store|<<_pet,Pet>>|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*400*|Invalid ID supplied|No Content
|*404*|Pet not found|No Content
|*405*|Validation exception|No Content
|===
==== Consumes
* `application/json`
* `application/xml`
==== Produces
* `application/json`
* `application/xml`
==== Tags
* pet
==== Security
[options="header", cols=".^3,.^4,.^13"]
|===
|Type|Name|Scopes
|*oauth2*|*<<_petstore_auth,petstore_auth>>*|write_pets,read_pets
|===
[[_findpetsbystatus]]
=== Finds Pets by status
....
GET /pets/findByStatus
....
==== Description
Multiple status values can be provided with comma seperated strings
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Query*|*status* +
_optional_|Status values that need to be considered for filter|< string > array(multi)|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|successful operation +
*Headers* : +
`X-Rate-Limit-Limit` (integer) : The number of allowed requests in the current period. +
`X-Rate-Limit-Remaining` (integer) : The number of remaining requests in the current period. +
`X-Rate-Limit-Reset` (integer) : The number of seconds left in the current period.|< <<_pet,Pet>> > array
|*400*|Invalid status value|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* pet
==== Security
[options="header", cols=".^3,.^4,.^13"]
|===
|Type|Name|Scopes
|*oauth2*|*<<_petstore_auth,petstore_auth>>*|write_pets,read_pets
|===
[[_findpetsbytags]]
=== Finds Pets by tags
....
GET /pets/findByTags
....
==== Description
Muliple tags can be provided with comma seperated strings. Use tag1, tag2, tag3 for testing.
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Query*|*tags* +
_optional_|Tags to filter by|< string > array(multi)|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|successful operation +
*Headers* : +
`X-Rate-Limit-Limit` (integer) : The number of allowed requests in the current period. +
`X-Rate-Limit-Remaining` (integer) : The number of remaining requests in the current period. +
`X-Rate-Limit-Reset` (integer) : The number of seconds left in the current period.|< <<_pet,Pet>> > array
|*400*|Invalid tag value|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* pet
==== Security
[options="header", cols=".^3,.^4,.^13"]
|===
|Type|Name|Scopes
|*oauth2*|*<<_petstore_auth,petstore_auth>>*|write_pets,read_pets
|===
[[_updatepetwithform]]
=== Updates a pet in the store with form data
....
POST /pets/{petId}
....
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Path*|*petId* +
_required_|ID of pet that needs to be updated|string|
|*FormData*|*name* +
_required_|Updated name of the pet|string|
|*FormData*|*status* +
_required_|Updated status of the pet|string|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*405*|Invalid input|No Content
|===
==== Consumes
* `application/x-www-form-urlencoded`
==== Produces
* `application/json`
* `application/xml`
==== Tags
* pet
==== Security
[options="header", cols=".^3,.^4,.^13"]
|===
|Type|Name|Scopes
|*oauth2*|*<<_petstore_auth,petstore_auth>>*|write_pets,read_pets
|===
[[_getpetbyid]]
=== Find pet by ID
....
GET /pets/{petId}
....
==== Description
Returns a pet when ID &lt; 10. ID &gt; 10 or nonintegers will simulate API error conditions
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Path*|*petId* +
_required_|ID of pet that needs to be fetched|integer(int64)|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|successful operation +
*Headers* : +
`X-Rate-Limit-Limit` (integer) : The number of allowed requests in the current period. +
`X-Rate-Limit-Remaining` (integer) : The number of remaining requests in the current period. +
`X-Rate-Limit-Reset` (integer) : The number of seconds left in the current period.|<<_pet,Pet>>
|*400*|Invalid ID supplied|No Content
|*404*|Pet not found|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* pet
==== Security
[options="header", cols=".^3,.^4,.^13"]
|===
|Type|Name|Scopes
|*apiKey*|*<<_api_key,api_key>>*|
|*oauth2*|*<<_petstore_auth,petstore_auth>>*|write_pets,read_pets
|===
[[_deletepet]]
=== Deletes a pet
....
DELETE /pets/{petId}
....
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Header*|*api_key* +
_required_||string|
|*Path*|*petId* +
_required_|Pet id to delete|integer(int64)|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*400*|Invalid pet value|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* pet
==== Security
[options="header", cols=".^3,.^4,.^13"]
|===
|Type|Name|Scopes
|*oauth2*|*<<_petstore_auth,petstore_auth>>*|write_pets,read_pets
|===
[[_placeorder]]
=== Place an order for a pet
....
POST /stores/order
....
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Body*|*body* +
_optional_|order placed for purchasing the pet|<<_order,Order>>|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|successful operation +
*Headers* : +
`X-Rate-Limit-Limit` (integer) : The number of allowed requests in the current period. +
`X-Rate-Limit-Remaining` (integer) : The number of remaining requests in the current period. +
`X-Rate-Limit-Reset` (integer) : The number of seconds left in the current period.|<<_order,Order>>
|*400*|Invalid Order|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* store
[[_getorderbyid]]
=== Find purchase order by ID
....
GET /stores/order/{orderId}
....
==== Description
For valid response try integer IDs with value &lt;= 5 or &gt; 10. Other values will generated exceptions
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Path*|*orderId* +
_required_|ID of pet that needs to be fetched|string|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|successful operation +
*Headers* : +
`X-Rate-Limit-Limit` (integer) : The number of allowed requests in the current period. +
`X-Rate-Limit-Remaining` (integer) : The number of remaining requests in the current period. +
`X-Rate-Limit-Reset` (integer) : The number of seconds left in the current period.|<<_order,Order>>
|*400*|Invalid ID supplied|No Content
|*404*|Order not found|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* store
[[_deleteorder]]
=== Delete purchase order by ID
....
DELETE /stores/order/{orderId}
....
==== Description
For valid response try integer IDs with value &lt; 1000. Anything above 1000 or nonintegers will generate API errors
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Path*|*orderId* +
_required_|ID of the order that needs to be deleted|string|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*400*|Invalid ID supplied|No Content
|*404*|Order not found|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* store
[[_createuser]]
=== Create user
....
POST /users
....
==== Description
This can only be done by the logged in user.
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Body*|*body* +
_optional_|Created user object|<<_user,User>>|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*default*|successful operation|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* user
[[_createuserswitharrayinput]]
=== Creates list of users with given input array
....
POST /users/createWithArray
....
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Body*|*body* +
_optional_|List of user object|< <<_user,User>> > array|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*default*|successful operation|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* user
[[_createuserswithlistinput]]
=== Creates list of users with given input array
....
POST /users/createWithList
....
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Body*|*body* +
_optional_|List of user object|< <<_user,User>> > array|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*default*|successful operation|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* user
[[_loginuser]]
=== Logs user into the system
....
GET /users/login
....
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Query*|*password* +
_optional_|The password for login in clear text|string|
|*Query*|*username* +
_optional_|The user name for login|string|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|successful operation +
*Headers* : +
`X-Rate-Limit-Limit` (integer) : The number of allowed requests in the current period. +
`X-Rate-Limit-Remaining` (integer) : The number of remaining requests in the current period. +
`X-Rate-Limit-Reset` (integer) : The number of seconds left in the current period.|string
|*400*|Invalid username/password supplied|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* user
[[_logoutuser]]
=== Logs out current logged in user session
....
GET /users/logout
....
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*default*|successful operation|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* user
[[_getuserbyname]]
=== Get user by user name
....
GET /users/{username}
....
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Path*|*username* +
_required_|The name that needs to be fetched. Use user1 for testing.|string|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|successful operation +
*Headers* : +
`X-Rate-Limit-Limit` (integer) : The number of allowed requests in the current period. +
`X-Rate-Limit-Remaining` (integer) : The number of remaining requests in the current period. +
`X-Rate-Limit-Reset` (integer) : The number of seconds left in the current period.|<<_user,User>>
|*400*|Invalid username supplied|No Content
|*404*|User not found|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* user
[[_updateuser]]
=== Updated user
....
PUT /users/{username}
....
==== Description
This can only be done by the logged in user.
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Path*|*username* +
_required_|name that need to be deleted|string|
|*Body*|*body* +
_optional_|Updated user object|<<_user,User>>|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*400*|Invalid user supplied|No Content
|*404*|User not found|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* user
[[_deleteuser]]
=== Delete user
....
DELETE /users/{username}
....
==== Description
This can only be done by the logged in user.
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Path*|*username* +
_required_|The name that needs to be deleted|string|
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*400*|Invalid username supplied|No Content
|*404*|User not found|No Content
|===
==== Produces
* `application/json`
* `application/xml`
==== Tags
* user

View File

@@ -1,137 +0,0 @@
[[_definitions]]
== Definitions
[[_category]]
=== Category
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_|*Example* : `123`|integer(int64)
|*name* +
_optional_|*Example* : `"Canines"`|string
|===
[[_complexobject]]
=== ComplexObject
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*subObject* +
_optional_|*Example* : `"object"`|object
|===
[[_identified]]
=== Identified
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_|*Example* : `0`|integer(int64)
|===
[[_order]]
=== Order
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*complete* +
_optional_|*Example* : `true`|boolean
|*id* +
_optional_|*Example* : `77`|integer(int64)
|*petId* +
_optional_|*Example* : `0`|integer(int64)
|*quantity* +
_optional_|*Example* : `0`|integer(int32)
|*shipDate* +
_optional_|*Example* : `"string"`|string(date-time)
|*status* +
_optional_|Order Status +
*Example* : `"DONE"`|string
|===
[[_pet]]
=== Pet
Test description
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*category* +
_optional_|*Example* : `"<<_category>>"`|<<_category,Category>>
|*id* +
_optional_|*Example* : `0`|integer(int64)
|*name* +
_required_|*Example* : `"doggie"`|string
|*nicknames* +
_optional_|*Example* : `{
"string" : "string"
}`|< string, string > map
|*photoUrls* +
_required_|*Example* : `[ "string" ]`|< string > array
|*status* +
_optional_|pet status in the store +
*Example* : `"string"`|string
|*tags* +
_optional_|*Example* : `[ "<<_tag>>" ]`|< <<_tag,Tag>> > array
|*weight* +
_optional_|the weight of the pet +
*Example* : `0.0`|number
|===
[[_tag]]
=== Tag
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_|*Example* : `0`|integer(int64)
|*name* +
_optional_|*Example* : `"string"`|string
|===
[[_user]]
=== User
[%hardbreaks]
_Polymorphism_ : Composition
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*email* +
_optional_|*Example* : `"string"`|string
|*firstName* +
_optional_|*Example* : `"string"`|string
|*id* +
_optional_|*Example* : `0`|integer(int64)
|*lastName* +
_optional_|*Example* : `"string"`|string
|*password* +
_optional_|*Example* : `"string"`|string
|*phone* +
_optional_|*Example* : `"string"`|string
|*pictures* +
_optional_|*Example* : `[ "string" ]`|< string(byte) > array
|*userStatus* +
_optional_|User Status +
*Example* : `0`|integer(int32)
|*username* +
_optional_|*Example* : `"string"`|string
|===

View File

@@ -1,105 +0,0 @@
[[_definitions]]
== Definitions
[[_category]]
=== Category
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_|The name of the category +
*Default* : `"DefaultCategory"` +
*Length* : `0 - 255` +
*Pattern* : `"[A-Za-zäöüÄÖÜß]{0,255}"` +
*Example* : `"FoobarCategory"`|string
|===
[[_order]]
=== Order
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*complete* +
_optional_||boolean
|*id* +
_optional_||integer(int64)
|*petId* +
_optional_||integer(int64)
|*quantity* +
_optional_|*Default* : `0` +
*Minimum value* : `0.0` +
*Maximum value* : `10000.0` +
*Example* : `10`|integer(int32)
|*shipDate* +
_optional_||string(date-time)
|*status* +
_optional_|Order Status|enum (Ordered, Cancelled)
|===
[[_pet]]
=== Pet
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*category* +
_optional_||<<_category,Category>>
|*id* +
_optional_||integer(int64)
|*name* +
_required_|*Example* : `"doggie"`|string
|*photoUrls* +
_required_||< string > array
|*status* +
_optional_|pet status in the store,|enum (Dead, Alive)
|*tags* +
_optional_||< <<_tag,Tag>> > array
|===
[[_tag]]
=== Tag
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===
[[_user]]
=== User
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*email* +
_optional_||string
|*firstName* +
_optional_||string
|*id* +
_optional_||integer(int64)
|*lastName* +
_optional_||string
|*password* +
_optional_||string
|*phone* +
_optional_||string
|*userStatus* +
_optional_|User Status|integer(int32)
|*username* +
_optional_||string
|===

View File

@@ -1,29 +0,0 @@
[[_securityscheme]]
== Security
[[_petstore_auth]]
=== petstore_auth
[%hardbreaks]
_Type_ : oauth2
_Flow_ : implicit
_Token URL_ : http://petstore.swagger.io/api/oauth/dialog
[options="header", cols=".^3,.^17"]
|===
|Name|Description
|write_pets|modify pets in your account
|read_pets|read your pets
|===
[[_api_key]]
=== api_key
[%hardbreaks]
_Type_ : apiKey
_Name_ : api_key
_In_ : HEADER

View File

@@ -1,105 +0,0 @@
[[_definitions]]
== Definitions
[[_category]]
=== Category
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_|The name of the category +
*Default* : `"DefaultCategory"` +
*Length* : `0 - 255` +
*Pattern* : `"[A-Za-zäöüÄÖÜß]{0,255}"` +
*Example* : `"FoobarCategory"`|string
|===
[[_order]]
=== Order
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*complete* +
_optional_||boolean
|*id* +
_optional_||integer(int64)
|*petId* +
_optional_||integer(int64)
|*quantity* +
_optional_|*Default* : `0` +
*Minimum value* : `0.0` +
*Maximum value* : `10000.0` +
*Example* : `10`|integer(int32)
|*shipDate* +
_optional_||string(date-time)
|*status* +
_optional_|Order Status|enum (Ordered, Cancelled)
|===
[[_pet]]
=== Pet
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*category* +
_optional_||<<definitions.adoc#_category,Category>>
|*id* +
_optional_||integer(int64)
|*name* +
_required_|*Example* : `"doggie"`|string
|*photoUrls* +
_required_||< string > array
|*status* +
_optional_|pet status in the store,|enum (Dead, Alive)
|*tags* +
_optional_||< <<definitions.adoc#_tag,Tag>> > array
|===
[[_tag]]
=== Tag
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===
[[_user]]
=== User
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*email* +
_optional_||string
|*firstName* +
_optional_||string
|*id* +
_optional_||integer(int64)
|*lastName* +
_optional_||string
|*password* +
_optional_||string
|*phone* +
_optional_||string
|*userStatus* +
_optional_|User Status|integer(int32)
|*username* +
_optional_||string
|===

View File

@@ -1,29 +0,0 @@
[[_securityscheme]]
== Security
[[_petstore_auth]]
=== petstore_auth
[%hardbreaks]
_Type_ : oauth2
_Flow_ : implicit
_Token URL_ : http://petstore.swagger.io/api/oauth/dialog
[options="header", cols=".^3,.^17"]
|===
|Name|Description
|write_pets|modify pets in your account
|read_pets|read your pets
|===
[[_api_key]]
=== api_key
[%hardbreaks]
_Type_ : apiKey
_Name_ : api_key
_In_ : HEADER

View File

@@ -1,280 +0,0 @@
[[_definitions]]
== Definitions
[[_error]]
=== Error
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*error-code* +
_optional_|Error code|integer
|*message* +
_optional_|Error message|string
|===
[[_externallocation]]
=== ExternalLocation
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*Place* +
_optional_|Place|string
|===
[[_inlinedepthschema]]
=== InlineDepthSchema
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*Loop* +
_optional_||<<_inlinedepthschema_loop,Loop>>
|===
[[_inlinedepthschema_loop]]
*Loop*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*p1* +
_optional_|Description p1|string
|*p2* +
_optional_|Description p2|<<_inlinedepthschema_p2,p2>>
|===
[[_inlinedepthschema_p2]]
*p2*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*p2-1* +
_optional_|Description p2-1|string
|*p2-2* +
_optional_|Description p2-2|<<_inlinedepthschema_p2_p2-2,p2-2>>
|===
[[_inlinedepthschema_p2_p2-2]]
*p2-2*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*p2-2-1* +
_optional_|Description p2-2-1|<<_inlinedepthschema_p2_p2-2_p2-2-1,p2-2-1>>
|*p2-2-2* +
_optional_|Description p2-2-2|<<_inlinedepthschema_p2_p2-2_p2-2-2,p2-2-2>>
|===
[[_inlinedepthschema_p2_p2-2_p2-2-1]]
*p2-2-1*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*p2-2-1-1* +
_optional_|Description p2-2-1-1|string
|*p2-2-1-2* +
_optional_|Description p2-2-1-2|boolean
|===
[[_inlinedepthschema_p2_p2-2_p2-2-2]]
*p2-2-2*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*p2-2-2-1* +
_optional_|Description p2-2-2-1|string
|*p2-2-2-2* +
_optional_|Description p2-2-2-2|boolean
|===
[[_inlinepet]]
=== InlinePet
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*category* +
_optional_||<<_inlinepet_category,category>>
|*id* +
_required_||integer(int64)
|*tags* +
_optional_||< <<_inlinepet_tags,tags>> > array
|===
[[_inlinepet_category]]
*category*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===
[[_inlinepet_tags]]
*tags*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===
[[_inlinetitlepet]]
=== InlineTitlePet
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*category* +
_optional_||<<_categorymodel,CategoryModel>>
|*id* +
_required_||integer(int64)
|*tags* +
_optional_||< <<_tagmodel,TagModel>> > array
|===
[[_categorymodel]]
*CategoryModel*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===
[[_tagmodel]]
*TagModel*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===
[[_location]]
=== Location
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*Place* +
_optional_|Place|string
|===
[[_mixedschema]]
=== MixedSchema
mixed collections and objects
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myTable* +
_optional_||< <<_mixedschema_mytable,myTable>> > array
|===
[[_mixedschema_mytable]]
*myTable*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myDict* +
_optional_||< string, <<_mixedschema_mydict,myDict>> > map
|===
[[_mixedschema_mydict]]
*myDict*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*k* +
_optional_||string
|*v* +
_optional_||string
|===
[[_recursivecollectionschema]]
=== RecursiveCollectionSchema
Options k/v pairs list
_Type_ : < < string, <<_recursivecollectionschema_inline,RecursiveCollectionSchema>> > map > array
[[_recursivecollectionschema_inline]]
*RecursiveCollectionSchema*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*key* +
_optional_|option key|string
|*value* +
_optional_|option value|string
|===
[[_titledschema]]
=== TitledSchema
mixed collections and objects
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myTable* +
_optional_||< <<_tablecontent,TableContent>> > array
|===
[[_tablecontent]]
*TableContent*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*emptyObject* +
_optional_||object
|*myDict* +
_optional_||< string, <<_kvpair,KVPair>> > map
|===
[[_kvpair]]
*KVPair*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*k* +
_optional_||string
|*v* +
_optional_||string
|===

View File

@@ -1,370 +0,0 @@
[[_paths]]
== Paths
[[_collectionparameters_post]]
=== Recursive collection parameter
....
POST /CollectionParameters
....
==== Description
Dummy description
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Body*|*Version* +
_optional_|The API version|< < string, <<_collectionparameters_post_version,Version>> > map > array|
|===
[[_collectionparameters_post_version]]
*Version*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*key* +
_optional_|option key|string
|*value* +
_optional_|option value|string
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|Result|< < string, <<_collectionparameters_post_response_200,Response 200>> > map > array
|===
[[_collectionparameters_post_response_200]]
*Response 200*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*key* +
_optional_|option key|string
|*value* +
_optional_|option value|string
|===
==== Tags
* All
[[_launchcommand_post]]
=== LaunchCommand
....
POST /LaunchCommand
....
==== Description
Dummy description
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Query*|*Option* +
_optional_|An optional option|string|
|*Query*|*Version* +
_optional_|The API version|string|
|*Body*|*LaunchCommandRequest* +
_optional_|Launch something new|<<_launchcommand_post_launchcommandrequest,LaunchCommandRequest>>|
|===
[[_launchcommand_post_launchcommandrequest]]
*LaunchCommandRequest*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*Command* +
_required_|Dummy description|<<_launchcommand_post_command,Command>>
|*Location* +
_optional_|Dummy description|<<_location,Location>>
|*Options* +
_optional_|Options k/v pairs|< <<_launchcommand_post_options,Options>> > array
|===
[[_launchcommand_post_command]]
*Command*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*args* +
_optional_|Command arguments|string
|*path* +
_optional_|Command path|string
|===
[[_launchcommand_post_options]]
*Options*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*key* +
_optional_|option key|string
|*value* +
_optional_|option value|string
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|Result +
*Headers* : +
`X-Rate-Limit-Limit` (integer) : The number of allowed requests in the current period. +
`X-Rate-Limit-Remaining` (integer) : The number of remaining requests in the current period. +
`X-Rate-Limit-Reset` (integer) : The number of seconds left in the current period.|<<_launchcommand_post_response_200,Response 200>>
|*400*|Error|<<_error,Error>>
|===
[[_launchcommand_post_response_200]]
*Response 200*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*Location* +
_optional_|<description>|<<_location,Location>>
|*Options* +
_optional_|Options k/v pairs|< <<_launchcommand_post_options,Options>> > array
|*ReservationId* +
_optional_|<description>|string
|===
[[_launchcommand_post_options]]
*Options*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*key* +
_optional_|option key|string
|*value* +
_optional_|option value|string
|===
==== Tags
* All
[[_mixedparameters_post]]
=== Mixed multi-level objects and collection parameter
....
POST /MixedParameters
....
==== Description
Dummy description
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Body*|*Version* +
_optional_|The API version|<<_mixedparameters_post_version,Version>>|
|===
[[_mixedparameters_post_version]]
*Version*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myTable* +
_optional_||< <<_mixedparameters_post_mytable,myTable>> > array
|===
[[_mixedparameters_post_mytable]]
*myTable*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myDict* +
_optional_||< string, <<_mixedparameters_post_mytable_mydict,myDict>> > map
|===
[[_mixedparameters_post_mytable_mydict]]
*myDict*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*k* +
_optional_||string
|*v* +
_optional_||string
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|Result|<<_mixedparameters_post_response_200,Response 200>>
|===
[[_mixedparameters_post_response_200]]
*Response 200*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myTable* +
_optional_||< <<_mixedparameters_post_mytable,myTable>> > array
|===
[[_mixedparameters_post_mytable]]
*myTable*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myDict* +
_optional_||< string, <<_mixedparameters_post_mytable_mydict,myDict>> > map
|===
[[_mixedparameters_post_mytable_mydict]]
*myDict*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*k* +
_optional_||string
|*v* +
_optional_||string
|===
==== Tags
* All
[[_titledparameters_post]]
=== Titled, mixed multi-level objects and collection parameter
....
POST /TitledParameters
....
==== Description
Dummy description
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Body*|*Version* +
_optional_|The API version|<<_request,Request>>|
|===
[[_request]]
*Request*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myTable* +
_optional_||< <<_tablecontent,TableContent>> > array
|===
[[_tablecontent]]
*TableContent*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myDict* +
_optional_||< string, <<_kvpair,KVPair>> > map
|===
[[_kvpair]]
*KVPair*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*k* +
_optional_||string
|*v* +
_optional_||string
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|Result|<<_result,Result>>
|===
[[_result]]
*Result*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myTable* +
_optional_||< <<_tablecontent,TableContent>> > array
|===
[[_tablecontent]]
*TableContent*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myDict* +
_optional_||< string, <<_kvpair,KVPair>> > map
|===
[[_kvpair]]
*KVPair*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*k* +
_optional_||string
|*v* +
_optional_||string
|===
==== Tags
* All

View File

@@ -1,280 +0,0 @@
[[_definitions]]
== Definitions
[[_error]]
=== Error
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*error-code* +
_optional_|Error code|integer
|*message* +
_optional_|Error message|string
|===
[[_externallocation]]
=== ExternalLocation
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*Place* +
_optional_|Place|string
|===
[[_inlinedepthschema]]
=== InlineDepthSchema
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*Loop* +
_optional_||<<_inlinedepthschema_loop,Loop>>
|===
[[_inlinedepthschema_loop]]
*Loop*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*p1* +
_optional_|Description p1|string
|*p2* +
_optional_|Description p2|<<_inlinedepthschema_p2,p2>>
|===
[[_inlinedepthschema_p2]]
*p2*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*p2-1* +
_optional_|Description p2-1|string
|*p2-2* +
_optional_|Description p2-2|<<_inlinedepthschema_p2_p2-2,p2-2>>
|===
[[_inlinedepthschema_p2_p2-2]]
*p2-2*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*p2-2-1* +
_optional_|Description p2-2-1|<<_inlinedepthschema_p2_p2-2_p2-2-1,p2-2-1>>
|*p2-2-2* +
_optional_|Description p2-2-2|<<_inlinedepthschema_p2_p2-2_p2-2-2,p2-2-2>>
|===
[[_inlinedepthschema_p2_p2-2_p2-2-1]]
*p2-2-1*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*p2-2-1-1* +
_optional_|Description p2-2-1-1|string
|*p2-2-1-2* +
_optional_|Description p2-2-1-2|boolean
|===
[[_inlinedepthschema_p2_p2-2_p2-2-2]]
*p2-2-2*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*p2-2-2-1* +
_optional_|Description p2-2-2-1|string
|*p2-2-2-2* +
_optional_|Description p2-2-2-2|boolean
|===
[[_inlinepet]]
=== InlinePet
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*category* +
_optional_||<<_inlinepet_category,category>>
|*id* +
_required_||integer(int64)
|*tags* +
_optional_||< <<_inlinepet_tags,tags>> > array
|===
[[_inlinepet_category]]
*category*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===
[[_inlinepet_tags]]
*tags*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===
[[_inlinetitlepet]]
=== InlineTitlePet
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*category* +
_optional_||<<_categorymodel,CategoryModel>>
|*id* +
_required_||integer(int64)
|*tags* +
_optional_||< <<_tagmodel,TagModel>> > array
|===
[[_categorymodel]]
*CategoryModel*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===
[[_tagmodel]]
*TagModel*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===
[[_location]]
=== Location
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*Place* +
_optional_|Place|string
|===
[[_mixedschema]]
=== MixedSchema
mixed collections and objects
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myTable* +
_optional_||< <<_mixedschema_mytable,myTable>> > array
|===
[[_mixedschema_mytable]]
*myTable*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myDict* +
_optional_||< string, <<_mixedschema_mydict,myDict>> > map
|===
[[_mixedschema_mydict]]
*myDict*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*k* +
_optional_||string
|*v* +
_optional_||string
|===
[[_recursivecollectionschema]]
=== RecursiveCollectionSchema
Options k/v pairs list
_Type_ : < < string, <<_recursivecollectionschema_inline,RecursiveCollectionSchema>> > map > array
[[_recursivecollectionschema_inline]]
*RecursiveCollectionSchema*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*key* +
_optional_|option key|string
|*value* +
_optional_|option value|string
|===
[[_titledschema]]
=== TitledSchema
mixed collections and objects
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myTable* +
_optional_||< <<_tablecontent,TableContent>> > array
|===
[[_tablecontent]]
*TableContent*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*emptyObject* +
_optional_||object
|*myDict* +
_optional_||< string, <<_kvpair,KVPair>> > map
|===
[[_kvpair]]
*KVPair*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*k* +
_optional_||string
|*v* +
_optional_||string
|===

View File

@@ -1,365 +0,0 @@
[[_paths]]
== Paths
[[_collectionparameters_post]]
=== Recursive collection parameter
....
POST /CollectionParameters
....
==== Description
Dummy description
==== Body parameter
The API version
[%hardbreaks]
_Name_ : Version
_Flags_ : optional
_Type_ : < < string, <<_collectionparameters_post_version,Version>> > map > array
[[_collectionparameters_post_version]]
*Version*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*key* +
_optional_|option key|string
|*value* +
_optional_|option value|string
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|Result|< < string, <<_collectionparameters_post_response_200,Response 200>> > map > array
|===
[[_collectionparameters_post_response_200]]
*Response 200*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*key* +
_optional_|option key|string
|*value* +
_optional_|option value|string
|===
==== Tags
* All
[[_launchcommand_post]]
=== LaunchCommand
....
POST /LaunchCommand
....
==== Description
Dummy description
==== Parameters
[options="header", cols=".^2,.^3,.^9,.^4,.^2"]
|===
|Type|Name|Description|Schema|Default
|*Query*|*Option* +
_optional_|An optional option|string|
|*Query*|*Version* +
_optional_|The API version|string|
|===
==== Body parameter
Launch something new
[%hardbreaks]
_Name_ : LaunchCommandRequest
_Flags_ : optional
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*Command* +
_required_|Dummy description|<<_launchcommand_post_command,Command>>
|*Location* +
_optional_|Dummy description|<<_location,Location>>
|*Options* +
_optional_|Options k/v pairs|< <<_launchcommand_post_options,Options>> > array
|===
[[_launchcommand_post_command]]
*Command*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*args* +
_optional_|Command arguments|string
|*path* +
_optional_|Command path|string
|===
[[_launchcommand_post_options]]
*Options*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*key* +
_optional_|option key|string
|*value* +
_optional_|option value|string
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|Result +
*Headers* : +
`X-Rate-Limit-Limit` (integer) : The number of allowed requests in the current period. +
`X-Rate-Limit-Remaining` (integer) : The number of remaining requests in the current period. +
`X-Rate-Limit-Reset` (integer) : The number of seconds left in the current period.|<<_launchcommand_post_response_200,Response 200>>
|*400*|Error|<<_error,Error>>
|===
[[_launchcommand_post_response_200]]
*Response 200*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*Location* +
_optional_|<description>|<<_location,Location>>
|*Options* +
_optional_|Options k/v pairs|< <<_launchcommand_post_options,Options>> > array
|*ReservationId* +
_optional_|<description>|string
|===
[[_launchcommand_post_options]]
*Options*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*key* +
_optional_|option key|string
|*value* +
_optional_|option value|string
|===
==== Tags
* All
[[_mixedparameters_post]]
=== Mixed multi-level objects and collection parameter
....
POST /MixedParameters
....
==== Description
Dummy description
==== Body parameter
The API version
[%hardbreaks]
_Name_ : Version
_Flags_ : optional
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myTable* +
_optional_||< <<_mixedparameters_post_mytable,myTable>> > array
|===
[[_mixedparameters_post_mytable]]
*myTable*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myDict* +
_optional_||< string, <<_mixedparameters_post_mydict,myDict>> > map
|===
[[_mixedparameters_post_mydict]]
*myDict*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*k* +
_optional_||string
|*v* +
_optional_||string
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|Result|<<_mixedparameters_post_response_200,Response 200>>
|===
[[_mixedparameters_post_response_200]]
*Response 200*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myTable* +
_optional_||< <<_mixedparameters_post_mytable,myTable>> > array
|===
[[_mixedparameters_post_mytable]]
*myTable*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myDict* +
_optional_||< string, <<_mixedparameters_post_mytable_mydict,myDict>> > map
|===
[[_mixedparameters_post_mytable_mydict]]
*myDict*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*k* +
_optional_||string
|*v* +
_optional_||string
|===
==== Tags
* All
[[_titledparameters_post]]
=== Titled, mixed multi-level objects and collection parameter
....
POST /TitledParameters
....
==== Description
Dummy description
==== Body parameter
The API version
[%hardbreaks]
_Name_ : Version
_Flags_ : optional
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myTable* +
_optional_||< <<_tablecontent,TableContent>> > array
|===
[[_tablecontent]]
*TableContent*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myDict* +
_optional_||< string, <<_kvpair,KVPair>> > map
|===
[[_kvpair]]
*KVPair*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*k* +
_optional_||string
|*v* +
_optional_||string
|===
==== Responses
[options="header", cols=".^2,.^14,.^4"]
|===
|HTTP Code|Description|Schema
|*200*|Result|<<_result,Result>>
|===
[[_result]]
*Result*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myTable* +
_optional_||< <<_tablecontent,TableContent>> > array
|===
[[_tablecontent]]
*TableContent*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*myDict* +
_optional_||< string, <<_kvpair,KVPair>> > map
|===
[[_kvpair]]
*KVPair*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*k* +
_optional_||string
|*v* +
_optional_||string
|===
==== Tags
* All

View File

@@ -1,225 +0,0 @@
[[_definitions]]
== Definitions
[[_comment]]
=== Comment
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*created_time* +
_optional_||string
|*from* +
_optional_||<<_miniprofile,MiniProfile>>
|*id* +
_optional_||string
|*text* +
_optional_||string
|===
[[_image]]
=== Image
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*height* +
_optional_||integer
|*url* +
_optional_||string
|*width* +
_optional_||integer
|===
[[_like]]
=== Like
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*first_name* +
_optional_||string
|*id* +
_optional_||string
|*last_name* +
_optional_||string
|*type* +
_optional_||string
|*user_name* +
_optional_||string
|===
[[_location]]
=== Location
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||string
|*latitude* +
_optional_||number
|*longitude* +
_optional_||number
|*name* +
_optional_||string
|===
[[_media]]
=== Media
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*comments:* +
_optional_||<<_media_comments,comments:>>
|*created_time* +
_optional_|Epoc time (ms)|integer
|*filter* +
_optional_||string
|*id* +
_optional_||integer
|*images* +
_optional_||<<_media_images,images>>
|*likes* +
_optional_||<<_media_likes,likes>>
|*location* +
_optional_||<<_location,Location>>
|*tags* +
_optional_||< <<_tag,Tag>> > array
|*type* +
_optional_||string
|*user* +
_optional_||<<_miniprofile,MiniProfile>>
|*users_in_photo* +
_optional_||< <<_miniprofile,MiniProfile>> > array
|*videos* +
_optional_||<<_media_videos,videos>>
|===
[[_media_comments]]
*comments:*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*count* +
_optional_||integer
|*data* +
_optional_||< <<_comment,Comment>> > array
|===
[[_media_images]]
*images*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*low_resolution* +
_optional_||<<_image,Image>>
|*standard_resolution* +
_optional_||<<_image,Image>>
|*thumbnail* +
_optional_||<<_image,Image>>
|===
[[_media_likes]]
*likes*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*count* +
_optional_||integer
|*data* +
_optional_||< <<_miniprofile,MiniProfile>> > array
|===
[[_media_videos]]
*videos*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*low_resolution* +
_optional_||<<_image,Image>>
|*standard_resolution* +
_optional_||<<_image,Image>>
|===
[[_miniprofile]]
=== MiniProfile
A shorter version of User for likes array
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*full_name* +
_optional_||string
|*id* +
_optional_||integer
|*profile_picture* +
_optional_||string
|*user_name* +
_optional_||string
|===
[[_tag]]
=== Tag
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*media_count* +
_optional_||integer
|*name* +
_optional_||string
|===
[[_user]]
=== User
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*bio* +
_optional_||string
|*counts* +
_optional_||<<_user_counts,counts>>
|*full_name* +
_optional_||string
|*id* +
_optional_||integer
|*profile_picture* +
_optional_||string
|*username* +
_optional_||string
|*website* +
_optional_||string
|===
[[_user_counts]]
*counts*
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*follows* +
_optional_||integer
|*follwed_by* +
_optional_||integer
|*media* +
_optional_||integer
|===

File diff suppressed because it is too large Load Diff

View File

@@ -1,24 +0,0 @@
[[_definitions]]
== Definitions
[[_mappinginfo]]
=== MappingInfo
Information about a given HTTP mapping.
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*bean* +
_optional_|Unique name of the bean which handles the given mapping.|string
|*method* +
_optional_|The signature of the method which processes requests to the given mapping.|string
|*tags* +
_optional_||< string, string > map
|*type* +
_optional_|The class which processes requests to the given mapping.|string
|===

View File

@@ -1,117 +0,0 @@
[[_definitions]]
== Definitions
[[_array]]
=== Array
An array
[%hardbreaks]
_Polymorphism_ : Inheritance
_Discriminator_ : collType
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*collType* +
_required_|collection type discriminator|string
|*name* +
_optional_||string
|===
[[_cat]]
=== Cat
A representation of a cat
[%hardbreaks]
_Polymorphism_ : Inheritance
_Discriminator_ : petType
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*huntingSkill* +
_required_|The measured skill for hunting +
*Default* : `"lazy"`|enum (clueless, lazy, adventurous, aggressive)
|*name* +
_optional_|conflicting property with inheriting model (issue #44)|string
|*petType* +
_required_||string
|===
[[_collection]]
=== Collection
Collection parent type without discriminator
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*name* +
_optional_||string
|===
[[_dog]]
=== Dog
A representation of a dog with an alternative discriminator
[%hardbreaks]
_Polymorphism_ : Inheritance
_Discriminator_ : dogType
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*dogType* +
_required_||string
|*name* +
_required_||string
|*packSize* +
_required_|the size of the pack the dog is from +
*Default* : `0` +
*Minimum value* : `0.0`|integer(int32)
|*petType* +
_required_||string
|===
[[_map]]
=== Map
A map without discriminator
[%hardbreaks]
_Polymorphism_ : Composition
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*collType* +
_required_|collection type discriminator|string
|*name* +
_optional_||string
|===
[[_pet]]
=== Pet
Pet parent type with discriminator
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*name* +
_required_||string
|*petType* +
_required_||string
|===

View File

@@ -1,117 +0,0 @@
[[_definitions]]
== Definitions
[[_array]]
=== Array
An array
[%hardbreaks]
_Polymorphism_ : Inheritance
_Discriminator_ : collType
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*name* +
_optional_||string
|*collType* +
_required_|collection type discriminator|string
|===
[[_cat]]
=== Cat
A representation of a cat
[%hardbreaks]
_Polymorphism_ : Inheritance
_Discriminator_ : petType
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*name* +
_optional_|conflicting property with inheriting model (issue #44)|string
|*petType* +
_required_||string
|*huntingSkill* +
_required_|The measured skill for hunting +
*Default* : `"lazy"`|enum (clueless, lazy, adventurous, aggressive)
|===
[[_collection]]
=== Collection
Collection parent type without discriminator
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*name* +
_optional_||string
|===
[[_dog]]
=== Dog
A representation of a dog with an alternative discriminator
[%hardbreaks]
_Polymorphism_ : Inheritance
_Discriminator_ : dogType
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*name* +
_required_||string
|*petType* +
_required_||string
|*dogType* +
_required_||string
|*packSize* +
_required_|the size of the pack the dog is from +
*Default* : `0` +
*Minimum value* : `0.0`|integer(int32)
|===
[[_map]]
=== Map
A map without discriminator
[%hardbreaks]
_Polymorphism_ : Composition
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*name* +
_optional_||string
|*collType* +
_required_|collection type discriminator|string
|===
[[_pet]]
=== Pet
Pet parent type with discriminator
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*name* +
_required_||string
|*petType* +
_required_||string
|===

View File

@@ -1,52 +0,0 @@
[[_definitions]]
== Definitions
[[_category]]
=== Category
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===
[[_pet]]
=== Pet
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*category* +
_optional_||<<_category,Category>>
|*id* +
_optional_||integer(int64)
|*name* +
_required_|*Example* : `"doggie"`|string
|*photoUrls* +
_required_||< string > array
|*status* +
_optional_|pet status in the store,|enum (Dead, Alive)
|*tags* +
_optional_||< <<_tag,Tag>> > array
|===
[[_tag]]
=== Tag
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*id* +
_optional_||integer(int64)
|*name* +
_optional_||string
|===

View File

@@ -1,44 +0,0 @@
= Swagger Petstore
[[_overview]]
== Overview
This is a sample server Petstore server.
http://swagger.io[Learn about Swagger] or join the IRC channel `#swagger` on irc.freenode.net.
For this sample, you can use the api key `special-key` to test the authorization filters
=== Version information
[%hardbreaks]
_Version_ : 1.0.0
=== Contact information
[%hardbreaks]
_Contact_ : apiteam@swagger.io
=== License information
[%hardbreaks]
_License_ : Apache 2.0
_License URL_ : http://www.apache.org/licenses/LICENSE-2.0.html
_Terms of service_ : http://helloreverb.com/terms/
=== URI scheme
[%hardbreaks]
_Host_ : petstore.swagger.io
_BasePath_ : /v2
_Schemes_ : HTTP
=== Tags
* pet : Pet resource
* store : Store resource
* user : User resource

View File

@@ -1,29 +0,0 @@
[[_securityscheme]]
== Security
[[_petstore_auth]]
=== petstore_auth
[%hardbreaks]
_Type_ : oauth2
_Flow_ : implicit
_Token URL_ : http://petstore.swagger.io/api/oauth/dialog
[options="header", cols=".^3,.^17"]
|===
|Name|Description
|write_pets|modify pets in your account
|read_pets|read your pets
|===
[[_api_key]]
=== api_key
[%hardbreaks]
_Type_ : apiKey
_Name_ : api_key
_In_ : HEADER

View File

@@ -1,40 +0,0 @@
[[_definitions]]
== Definitions
[[_samplerequest]]
=== SampleRequest
[options="header", cols=".^3,.^11,.^4"]
|===
|Name|Description|Schema
|*sampleNumberComplete* +
_optional_|sample int with range 0-10 +
*Minimum value* : `0.0` +
*Maximum value* : `10.0`|integer(int32)
|*sampleNumberNoDescription* +
_optional_|*Minimum value* : `0.0` +
*Maximum value* : `10.0`|integer(int32)
|*sampleNumberOnlyMaximum* +
_optional_|sample int with range to 10 +
*Maximum value* : `10.0`|integer(int32)
|*sampleNumberOnlyMinimum* +
_optional_|sample int with range from 0 +
*Minimum value* : `0.0`|integer(int32)
|*sampleStringComplete* +
_optional_|Sample string with range 0-2 and a pattern +
*Length* : `0 - 2` +
*Pattern* : `"[A-Z0-9]{0,2}"`|string
|*sampleStringOnlyMaxLength* +
_optional_|*Maximal length* : `2`|string
|*sampleStringOnlyMinLength* +
_optional_|*Minimum length* : `0`|string
|*sampleStringOnlyPattern* +
_optional_|*Pattern* : `"[A-Z0-9]{0,2}"`|string
|*sampleStringWithNoDescription* +
_optional_|*Length* : `0 - 2` +
*Pattern* : `"[A-Z0-9]{0,2}"`|string
|===

View File

@@ -1,54 +0,0 @@
{
"apiVersion" : "0.0.1-SNAPSHOT",
"swaggerVersion" : "1.2",
"basePath" : "",
"resourcePath" : "/resource/x/v2",
"apis" : [ {
"path" : "/resource/x/v2",
"operations" : [ {
"method" : "POST",
"nickname" : "createX",
"type" : "string",
"parameters" : [ {
"type": "string",
"description" : "The x in JSON format",
"paramType" : "body",
"name" : "body",
"required" : true
} ],
"summary" : "Creates a x x.",
"notes" : "If id already exists, the x is updated.",
"responseMessages" : [ {
"code" : 200,
"message" : "ok"
}, {
"code" : 500,
"message" : "error"
} ],
"consumes" : [ "application/json" ]
} ]
}, {
"path" : "/resource/x/v2/{id}",
"operations" : [ {
"method" : "GET",
"nickname" : "getX",
"type" : "string",
"parameters" : [ {
"type" : "integer",
"description" : "A valid x x UUID",
"paramType" : "path",
"name" : "id",
"required" : true
} ],
"summary" : "Gets the x x with the specified id.",
"responseMessages" : [ {
"code" : 200,
"message" : "ok"
}, {
"code" : 404,
"message" : "not found"
} ],
"produces" : [ "application/json" ]
} ]
} ]
}

View File

@@ -1,883 +0,0 @@
{
"swagger": "2.0",
"info": {
"description": "This is a sample server Petstore server.\n\n[Learn about Swagger](http://swagger.wordnik.com) or join the IRC channel `#swagger` on irc.freenode.net.\n\nFor this sample, you can use the api key `special-key` to test the authorization filters\n",
"version": "1.0.0",
"title": "Swagger Petstore API",
"termsOfService": "http://helloreverb.com/terms/",
"contact": {
"name": "apiteam@wordnik.com"
},
"license": {
"name": "Apache 2.0",
"url": "http://www.apache.org/licenses/LICENSE-2.0.html"
}
},
"host": "petstore.swagger.wordnik.com",
"basePath": "/v2",
"schemes": [
"http"
],
"tags": [
{
"name": "pet",
"description": "Pet resource"
},
{
"name": "store",
"description": "Store resource"
},
{
"name": "user",
"description": "User resource"
}
],
"paths": {
"/pets": {
"post": {
"tags": [
"pet"
],
"summary": "Add a new pet to the store",
"description": "",
"operationId": "addPet",
"consumes": [
"application/json",
"application/xml"
],
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "body",
"name": "body",
"description": "Pet object that needs to be added to the store",
"required": false,
"schema": {
"$ref": "#/definitions/Pet"
}
}
],
"responses": {
"405": {
"description": "Invalid input"
}
},
"security": [
{
"petstore_auth": [
"write_pets",
"read_pets"
]
}
]
},
"put": {
"summary": "Update an existing pet",
"description": "",
"operationId": "updatePet",
"consumes": [
"application/json",
"application/xml"
],
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "body",
"name": "body",
"description": "Pet object that needs to be added to the store",
"required": false,
"schema": {
"$ref": "#/definitions/Pet"
}
}
],
"responses": {
"400": {
"description": "Invalid ID supplied"
},
"404": {
"description": "Pet not found"
},
"405": {
"description": "Validation exception"
}
},
"security": [
{
"petstore_auth": [
"write_pets",
"read_pets"
]
}
]
}
},
"/pets/findByStatus": {
"get": {
"tags": [
"pet"
],
"summary": "Finds Pets by status",
"description": "Multiple status values can be provided with comma seperated strings",
"operationId": "findPetsByStatus",
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "query",
"name": "status",
"description": "Status values that need to be considered for filter",
"required": false,
"type": "array",
"items": {
"type": "string"
},
"collectionFormat": "multi"
}
],
"responses": {
"200": {
"$ref": "#/responses/FoundPets"
},
"400": {
"description": "Invalid status value"
}
},
"security": [
{
"petstore_auth": [
"write_pets",
"read_pets"
]
}
]
}
},
"/pets/findByTags": {
"get": {
"tags": [
"pet"
],
"summary": "Finds Pets by tags",
"description": "Muliple tags can be provided with comma seperated strings. Use tag1, tag2, tag3 for testing.",
"operationId": "findPetsByTags",
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "query",
"name": "tags",
"description": "Tags to filter by",
"required": false,
"type": "array",
"items": {
"type": "string"
},
"collectionFormat": "multi"
}
],
"responses": {
"200": {
"$ref": "#/responses/FoundPets"
},
"400": {
"description": "Invalid tag value"
}
},
"security": [
{
"petstore_auth": [
"write_pets",
"read_pets"
]
}
]
}
},
"/pets/{petId}": {
"get": {
"tags": [
"pet"
],
"summary": "Find pet by ID",
"description": "Returns a pet when ID < 10. ID > 10 or nonintegers will simulate API error conditions",
"operationId": "getPetById",
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"$ref": "#/parameters/petId"
}
],
"responses": {
"200": {
"description": "successful operation",
"schema": {
"$ref": "#/definitions/Pet"
}
},
"400": {
"description": "Invalid ID supplied"
},
"404": {
"description": "Pet not found"
}
},
"security": [
{
"api_key": []
},
{
"petstore_auth": [
"write_pets",
"read_pets"
]
}
]
},
"post": {
"tags": [
"pet"
],
"summary": "Updates a pet in the store with form data",
"description": "",
"operationId": "updatePetWithForm",
"consumes": [
"application/x-www-form-urlencoded"
],
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "path",
"name": "petId",
"description": "ID of pet that needs to be updated",
"required": true,
"type": "string"
},
{
"in": "formData",
"name": "name",
"description": "Updated name of the pet",
"required": true,
"type": "string"
},
{
"in": "formData",
"name": "status",
"description": "Updated status of the pet",
"required": true,
"type": "string"
}
],
"responses": {
"405": {
"description": "Invalid input"
}
},
"security": [
{
"petstore_auth": [
"write_pets",
"read_pets"
]
}
]
},
"delete": {
"tags": [
"pet"
],
"summary": "Deletes a pet",
"description": "",
"operationId": "deletePet",
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "header",
"name": "api_key",
"description": "",
"required": true,
"type": "string"
},
{
"in": "path",
"name": "petId",
"description": "Pet id to delete",
"required": true,
"type": "integer",
"format": "int64"
}
],
"responses": {
"400": {
"description": "Invalid pet value"
}
},
"security": [
{
"petstore_auth": [
"write_pets",
"read_pets"
]
}
]
}
},
"/stores/order": {
"post": {
"tags": [
"store"
],
"summary": "Place an order for a pet",
"description": "",
"operationId": "placeOrder",
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "body",
"name": "body",
"description": "order placed for purchasing the pet",
"required": false,
"schema": {
"$ref": "#/definitions/Order"
}
}
],
"responses": {
"200": {
"description": "successful operation",
"schema": {
"$ref": "#/definitions/Order"
}
},
"400": {
"description": "Invalid Order"
}
}
}
},
"/stores/order/{orderId}": {
"get": {
"tags": [
"store"
],
"summary": "Find purchase order by ID",
"description": "For valid response try integer IDs with value <= 5 or > 10. Other values will generated exceptions",
"operationId": "getOrderById",
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "path",
"name": "orderId",
"description": "ID of pet that needs to be fetched",
"required": true,
"type": "string"
}
],
"responses": {
"200": {
"description": "successful operation",
"schema": {
"$ref": "#/definitions/Order"
}
},
"400": {
"description": "Invalid ID supplied"
},
"404": {
"description": "Order not found"
}
}
},
"delete": {
"tags": [
"store"
],
"summary": "Delete purchase order by ID",
"description": "For valid response try integer IDs with value < 1000. Anything above 1000 or nonintegers will generate API errors",
"operationId": "deleteOrder",
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "path",
"name": "orderId",
"description": "ID of the order that needs to be deleted",
"required": true,
"type": "string"
}
],
"responses": {
"400": {
"description": "Invalid ID supplied"
},
"404": {
"description": "Order not found"
}
}
}
},
"/users": {
"post": {
"tags": [
"user"
],
"summary": "Create user",
"description": "This can only be done by the logged in user.",
"operationId": "createUser",
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "body",
"name": "body",
"description": "Created user object",
"required": false,
"schema": {
"$ref": "#/definitions/User"
}
}
],
"responses": {
"default": {
"description": "successful operation"
}
}
}
},
"/users/createWithArray": {
"post": {
"tags": [
"user"
],
"summary": "Creates list of users with given input array",
"description": "",
"operationId": "createUsersWithArrayInput",
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "body",
"name": "body",
"description": "List of user object",
"required": false,
"schema": {
"type": "array",
"items": {
"$ref": "#/definitions/User"
}
}
}
],
"responses": {
"default": {
"description": "successful operation"
}
}
}
},
"/users/createWithList": {
"post": {
"tags": [
"user"
],
"summary": "Creates list of users with given input array",
"description": "",
"operationId": "createUsersWithListInput",
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "body",
"name": "body",
"description": "List of user object",
"required": false,
"schema": {
"type": "array",
"items": {
"$ref": "#/definitions/User"
}
}
}
],
"responses": {
"default": {
"description": "successful operation"
}
}
}
},
"/users/login": {
"get": {
"tags": [
"user"
],
"summary": "Logs user into the system",
"description": "",
"operationId": "loginUser",
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "query",
"name": "username",
"description": "The user name for login",
"required": false,
"type": "string",
"default": "testUser"
},
{
"in": "query",
"name": "password",
"description": "The password for login in clear text",
"required": false,
"type": "string",
"default": "testPassword"
}
],
"responses": {
"200": {
"description": "successful operation",
"schema": {
"type": "string"
}
},
"400": {
"description": "Invalid username/password supplied"
}
}
}
},
"/users/logout": {
"get": {
"tags": [
"user"
],
"summary": "Logs out current logged in user session",
"description": "",
"operationId": "logoutUser",
"produces": [
"application/json",
"application/xml"
],
"responses": {
"default": {
"description": "successful operation"
}
}
}
},
"/users/{username}": {
"get": {
"tags": [
"user"
],
"summary": "Get user by user name",
"description": "",
"operationId": "getUserByName",
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "path",
"name": "username",
"description": "The name that needs to be fetched. Use user1 for testing.",
"required": true,
"type": "string",
"default": "testUser"
}
],
"responses": {
"200": {
"description": "successful operation",
"schema": {
"$ref": "#/definitions/User"
}
},
"400": {
"description": "Invalid username supplied"
},
"404": {
"description": "User not found"
}
}
},
"put": {
"tags": [
"user"
],
"summary": "Updated user",
"description": "This can only be done by the logged in user.",
"operationId": "updateUser",
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "path",
"name": "username",
"description": "name that need to be deleted",
"required": true,
"type": "string"
},
{
"in": "body",
"name": "body",
"description": "Updated user object",
"required": false,
"schema": {
"$ref": "#/definitions/User"
}
}
],
"responses": {
"400": {
"description": "Invalid user supplied"
},
"404": {
"description": "User not found"
}
}
},
"delete": {
"tags": [
"user"
],
"summary": "Delete user",
"description": "This can only be done by the logged in user.",
"operationId": "deleteUser",
"produces": [
"application/json",
"application/xml"
],
"parameters": [
{
"in": "path",
"name": "username",
"description": "The name that needs to be deleted",
"required": true,
"type": "string"
}
],
"responses": {
"400": {
"description": "Invalid username supplied"
},
"404": {
"description": "User not found"
}
}
}
}
},
"securityDefinitions": {
"api_key": {
"type": "apiKey",
"name": "api_key",
"in": "header"
},
"petstore_auth": {
"type": "oauth2",
"authorizationUrl": "http://petstore.swagger.wordnik.com/api/oauth/dialog",
"flow": "implicit",
"scopes": {
"write_pets": "modify pets in your account",
"read_pets": "read your pets"
}
}
},
"responses":{
"FoundPets": {
"description": "successful operation",
"schema": {
"type": "array",
"items": {
"$ref": "#/definitions/Pet"
}
}
}
},
"parameters":{
"petId": {
"in": "path",
"name": "petId",
"description": "ID of the pet",
"required": true,
"type": "integer",
"format": "int64"
}
},
"definitions": {
"Identified": {
"properties": {
"id": {
"type": "integer",
"format": "int64"
}
}
},
"User": {
"allOf": [
{
"$ref": "#/definitions/Identified"
},
{
"properties": {
"username": {
"type": "string"
},
"firstName": {
"type": "string"
},
"lastName": {
"type": "string"
},
"email": {
"type": "string"
},
"password": {
"type": "string"
},
"phone": {
"type": "string"
},
"userStatus": {
"type": "integer",
"format": "int32",
"description": "User Status"
},
"pictures": {
"type": "array",
"items": {
"type": "string",
"format": "byte"
}
}
}
}
]
},
"Category": {
"properties": {
"id": {
"type": "integer",
"format": "int64"
},
"name": {
"type": "string"
}
}
},
"Pet": {
"description" : "Test description",
"required": [
"name",
"photoUrls"
],
"properties": {
"id": {
"type": "integer",
"format": "int64"
},
"category": {
"$ref": "#/definitions/Category"
},
"name": {
"type": "string",
"example": "doggie"
},
"photoUrls": {
"type": "array",
"items": {
"type": "string"
}
},
"tags": {
"type": "array",
"items": {
"$ref": "#/definitions/Tag"
}
},
"status": {
"type": "string",
"description": "pet status in the store"
}
}
},
"Tag": {
"properties": {
"id": {
"type": "integer",
"format": "int64"
},
"name": {
"type": "string"
}
}
},
"Order": {
"properties": {
"id": {
"type": "integer",
"format": "int64"
},
"petId": {
"type": "integer",
"format": "int64"
},
"quantity": {
"type": "integer",
"format": "int32"
},
"shipDate": {
"type": "string",
"format": "date-time"
},
"status": {
"type": "string",
"description": "Order Status"
},
"complete": {
"type": "boolean"
}
}
}
}
}

View File

@@ -1,65 +0,0 @@
{
"swagger": "2.0",
"info": {
"description": "Description",
"version": "Developer build",
"title": "Title"
},
"definitions": {
"SampleRequest": {
"type": "object",
"properties": {
"sampleStringComplete": {
"type": "string",
"description": "Sample string with range 0-2 and a pattern",
"minLength": 0,
"maxLength": 2,
"pattern": "[A-Z0-9]{0,2}"
},
"sampleStringWithNoDescription": {
"type": "string",
"minLength": 0,
"maxLength": 2,
"pattern": "[A-Z0-9]{0,2}"
},
"sampleStringOnlyMinLength": {
"type": "string",
"minLength": 0
},
"sampleStringOnlyMaxLength": {
"type": "string",
"maxLength": 2
},
"sampleStringOnlyPattern": {
"type": "string",
"pattern": "[A-Z0-9]{0,2}"
},
"sampleNumberComplete": {
"type":"integer",
"format":"int32",
"description": "sample int with range 0-10",
"minimum": 0,
"maximum": 10
},
"sampleNumberNoDescription": {
"type":"integer",
"format":"int32",
"minimum": 0,
"maximum": 10
},
"sampleNumberOnlyMinimum": {
"type":"integer",
"format":"int32",
"description": "sample int with range from 0",
"minimum": 0
},
"sampleNumberOnlyMaximum": {
"type":"integer",
"format":"int32",
"description": "sample int with range to 10",
"maximum": 10
}
}
}
}
}

View File

@@ -0,0 +1,25 @@
ext.moduleName="io.github.swagger2markup.asciidoc"
dependencies {
configurations.all {
// resolutionStrategy.force dependencyOverrides.commonsCodec
// resolutionStrategy.force dependencyOverrides.commonsIO
// resolutionStrategy.force dependencyOverrides.commonsLang3
resolutionStrategy.force dependencyOverrides.jnrConstants
resolutionStrategy.force dependencyOverrides.jnrEnxio
resolutionStrategy.force dependencyOverrides.jnrPosix
// resolutionStrategy.force dependencyOverrides.jodaTime
resolutionStrategy.force dependencyOverrides.slf4j
// resolutionStrategy.force dependencyOverrides.jacksonDatabind
// resolutionStrategy.force dependencyOverrides.guava
// resolutionStrategy.force dependencyOverrides.findBugs
// resolutionStrategy.force dependencyOverrides.jaksonCore
}
implementation implLibraries.asciiDocJApi
implementation implLibraries.commonsText
implementation implLibraries.slf4j
testImplementation implLibraries.commonsIO
testImplementation testLibraries.asciiDocJ
testImplementation testLibraries.junit
testImplementation testLibraries.logback
}

View File

@@ -0,0 +1,887 @@
package io.github.swagger2markup.adoc;
import io.github.swagger2markup.adoc.converter.internal.*;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.text.StringEscapeUtils;
import org.asciidoctor.ast.List;
import org.asciidoctor.ast.*;
import org.asciidoctor.converter.ConverterFor;
import org.asciidoctor.converter.StringConverter;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors;
import java.util.stream.LongStream;
import java.util.stream.Stream;
import static io.github.swagger2markup.adoc.converter.internal.Delimiters.*;
@ConverterFor(AsciidocConverter.NAME)
public class AsciidocConverter extends StringConverter {
private Logger logger = LoggerFactory.getLogger(getClass());
public static final String NAME = "adoc";
private final Pattern emptyLineOrStartWith = Pattern.compile("(?m)^\\s*(?:\\r?\\n)|(?m)^\\s+");
private final Pattern coListItemIdPattern = Pattern.compile(".*-(\\d+)");
private final Pattern tableColumnsStylePattern = Pattern.compile("((\\d+)\\*)?([<^>])?(\\.[<^>])?(\\d+)?([adehlmsv])?");
private static final java.util.List<String> attributeToExclude = Arrays.asList(
"localtime",
"filetype",
"asciidoctor-version",
"doctime",
"localyear",
"docdate",
"localdate",
"localdatetime",
"docdatetime",
"backend",
"basebackend",
"doctitle",
"docyear"
);
private static final String[] supportedUrlSchemes = new String[]{
"http",
"https",
"ftp",
"irc",
"mailto"
};
public AsciidocConverter(String backend, Map<String, Object> opts) {
super(backend, opts);
}
/**
* Converts an {@link ContentNode} using the specified transform along
* with additional options. If a transform is not specified, implementations
* typically derive one from the {@link ContentNode#getNodeName()} property.
*
* <p>Implementations are free to decide how to carry out the conversion. In
* the case of the built-in converters, the tranform value is used to
* dispatch to a handler method. The TemplateConverter uses the value of
* the transform to select a template to render.
*
* @param node The concrete instance of FlowNode to convert
* @param transform An optional String transform that hints at which transformation
* should be applied to this node. If a transform is not specified,
* the transform is typically derived from the value of the
* node's node_name property. (optional, default: null)
* @param opts An optional map of options that provide additional hints about
* how to convert the node. (optional, default: empty map)
* @return the converted result
*/
@Override
public String convert(ContentNode node, String transform, Map<Object, Object> opts) {
if (null == transform) {
transform = node.getNodeName();
}
switch (transform) {
case "inline_quoted":
return convertInlineQuoted((PhraseNode) node);
case "paragraph":
return convertParagraph((StructuralNode) node);
case "inline_anchor":
return convertInlineAnchor((PhraseNode) node);
case "section":
return convertSection((Section) node);
case "listing":
return convertListing((Block) node);
case "literal":
return convertLiteral((StructuralNode) node);
case "ulist":
return convertUList((List) node);
case "olist":
return convertOList((List) node);
case "dlist":
return convertDescriptionList((DescriptionList) node);
case "admonition":
return convertAdmonition((Block) node);
case "colist":
return convertCoList((List) node);
case "embedded":
case "document":
return convertEmbedded((Document) node);
case "example":
return convertExample((Block) node);
case "floating_title":
return convertFloatingTitle((StructuralNode) node);
case "image":
return convertImage((StructuralNode) node);
case "inline_break":
return convertInlineBreak(node);
case "inline_button":
return convertInlineButton(node);
case "inline_callout":
return convertInlineCallout(node);
case "inline_footnote":
return convertInlineFootnote(node);
case "inline_image":
return convertInlineImage((PhraseNode) node);
case "inline_indexterm":
return convertInlineIndexTerm(node);
case "inline_kbd":
return convertInlineKbd(node);
case "inline_menu":
return convertInlineMenu(node);
case "open":
return convertOpen((StructuralNode) node);
case "page_break":
return convertPageBreak(node);
case "preamble":
return convertPreamble((StructuralNode) node);
case "quote":
return convertQuote((StructuralNode) node);
case "sidebar":
return convertSidebar((StructuralNode) node);
case "stem":
return convertStem(node);
case "table":
return convertTable((Table) node);
case "thematic_break":
return convertThematicBreak(node);
case "verse":
return convertVerse((StructuralNode) node);
case "video":
return convertVideo(node);
case "toc":
return convertToc(node);
case "pass":
return convertPass(node);
case "audio":
return convertAudio(node);
// didn't exist on html converter
case "list":
return convertList((List) node);
case "list_item":
return convertListItem((ListItem) node);
default:
logger.debug("Don't know how to convert transform: [" + transform + "] Node: " + node);
return null;
}
}
String convertEmbedded(Document node) {
logger.debug("convertEmbedded");
StringBuilder sb = new StringBuilder();
appendId(node, sb);
if (StringUtils.isNotBlank(node.getDoctitle())) {
sb.append(repeat(node.getLevel() + 1,DOCUMENT_TITLE)).append(' ').append(StringEscapeUtils.unescapeHtml4(node.getDoctitle())).append(LINE_SEPARATOR);
}
Map<String, Object> attributes = node.getAttributes();
appendAuthors(sb, attributes);
appendRevisionDetails(sb, attributes);
appendDocumentAttributes(sb, attributes);
appendTrailingNewLine(sb);
appendChildBlocks(node, sb);
return sb.toString();
}
private void appendAuthors(StringBuilder sb, Map<String, Object> attributes) {
Long authorCount = (Long) attributes.getOrDefault("authorcount", 0L);
if (authorCount == 1) {
String author = getAuthorDetail(attributes, "author", "email");
if (StringUtils.isNotBlank(author)) {
sb.append(author).append(LINE_SEPARATOR);
}
} else if (authorCount > 1) {
String authors = LongStream.rangeClosed(1, authorCount)
.mapToObj(i -> getAuthorDetail(attributes, "author_" + i, "email_" + i))
.collect(Collectors.joining("; "));
if (StringUtils.isNotBlank(authors)) {
sb.append(authors).append(LINE_SEPARATOR);
}
}
}
private void appendDocumentAttributes(StringBuilder sb, Map<String, Object> attributes) {
attributes.forEach((k, v) -> {
if (!attributeToExclude.contains(k) && v != null && !v.toString().isEmpty())
sb.append(COLON).append(k).append(COLON).append(" ").append(v).append(LINE_SEPARATOR);
});
}
private void appendRevisionDetails(StringBuilder sb, Map<String, Object> attributes) {
String revDetails = Stream.of(attributes.get("revnumber"), attributes.get("revdate")).filter(Objects::nonNull)
.filter(o -> !o.toString().isEmpty()).map(Object::toString)
.collect(Collectors.joining(", "));
if (!revDetails.isEmpty()) {
sb.append("v").append(revDetails).append(LINE_SEPARATOR);
}
}
private String getAuthorDetail(Map<String, Object> attributes, String authorKey, String emailKey) {
String author = attributes.getOrDefault(authorKey, "").toString();
String email = attributes.getOrDefault(emailKey, "").toString();
if (StringUtils.isNotBlank(email)) {
email = " <" + email + ">";
}
return (author + email).trim();
}
private String convertInlineAnchor(PhraseNode node) {
logger.debug("convertInlineAnchor");
String type = node.getType();
switch (type) {
case "xref": {
String attrs;
String text;
String path = Optional.ofNullable(node.getAttributes().get("path")).orElse("").toString();
if (StringUtils.isNotBlank(path)) {
ArrayList<String> list = new ArrayList<>();
if (StringUtils.isNotBlank(node.getRole())) {
list.add(" class=\"#{node.role}\"");
}
append_link_constraint_attrs(node, list);
attrs = String.join(" ", list);
text = StringUtils.isNotBlank(node.getText()) ? node.getText() : path;
} else {
attrs = StringUtils.isNotBlank(node.getRole()) ? " class=\"" + node.getRole() + "\"" : "";
text = node.getText();
if (StringUtils.isNotBlank(text)) {
text = node.getAttributes().get("refid").toString();
}
}
return node.getTarget() + ATTRIBUTES_BEGIN + text + (StringUtils.isNotBlank(attrs) ? "," + attrs : "") + ATTRIBUTES_END;
}
case "ref":
return node.getId();
case "link": {
ArrayList<String> attrs = new ArrayList<>();
String target = node.getTarget();
String includePrefix = !StringUtils.startsWithAny(target, supportedUrlSchemes) ? "include::" : "";
String text = node.getText();
if (!target.equals(text)) {
attrs.add(text);
}
if (StringUtils.isNotBlank(node.getId())) {
attrs.add("id=\"" + node.getId() + "\"");
}
String role = node.getRole();
if (StringUtils.isNotBlank(role) && !role.equals("bare")) {
attrs.add("role=\"" + role + "\"");
}
String title = node.getAttribute("title", "").toString();
if (StringUtils.isNotBlank(title)) {
attrs.add("title=\"" + title + "\"");
}
return includePrefix + target + ATTRIBUTES_BEGIN + String.join(",", attrs) + ATTRIBUTES_END;
}
case "bibref":
return node.getId() + ATTRIBUTES_BEGIN + (StringUtils.isNotBlank(node.getReftext()) ? node.getReftext() : node.getId()) + ATTRIBUTES_END;
default:
logger.warn("unknown anchor type: " + node.getType());
return null;
}
}
private String convertAdmonition(Block node) {
logger.debug("convertAdmonition");
StringBuilder sb = new StringBuilder();
java.util.List<StructuralNode> blocks = node.getBlocks();
if (blocks.isEmpty()) {
sb.append(node.getStyle()).append(": ").append(node.getSource());
} else {
appendTitle(node, sb);
sb.append(ATTRIBUTES_BEGIN).append(node.getStyle()).append(ATTRIBUTES_END)
.append(LINE_SEPARATOR).append(DELIMITER_EXAMPLE).append(LINE_SEPARATOR);
appendChildBlocks(node, sb);
sb.append(DELIMITER_EXAMPLE).append(LINE_SEPARATOR);
}
return sb.toString();
}
private String convertInlineQuoted(PhraseNode node) {
logger.debug("convertInlineQuoted");
StringBuilder sb = new StringBuilder();
String marker = "";
switch (node.getType()) {
case "monospaced":
marker = "`";
break;
case "emphasis":
marker = "_";
break;
case "strong":
marker = "*";
break;
case "superscript":
marker = "^";
break;
case "subscript":
marker = "~";
break;
case "double":
case "single":
case "mark":
case "asciimath":
case "latexmath":
marker = "";
break;
}
sb.append(marker).append(node.getText()).append(marker);
return sb.toString();
}
private String convertFloatingTitle(StructuralNode node) {
logger.debug("convertFloatingTitle");
return ATTRIBUTES_BEGIN + "discrete" + ATTRIBUTES_END + LINE_SEPARATOR +
repeat(node.getLevel() + 1, TITLE) + ' ' + node.getTitle() + LINE_SEPARATOR;
}
private String convertExample(Block node) {
logger.debug("convertExample");
StringBuilder sb = new StringBuilder();
appendTitle(node, sb);
sb.append(DELIMITER_EXAMPLE).append(LINE_SEPARATOR);
appendChildBlocks(node, sb);
sb.append(DELIMITER_EXAMPLE).append(LINE_SEPARATOR);
return sb.toString();
}
private String convertInlineButton(ContentNode node) {
logger.debug("convertInlineButton: name" + node.getNodeName());
return "convertInlineButton";
}
private String convertInlineCallout(ContentNode node) {
logger.debug("convertInlineCallout: name" + node.getNodeName());
return "convertInlineCallout";
}
private String convertInlineBreak(ContentNode node) {
logger.debug("convertInlineBreak: name" + node.getNodeName());
return "convertInlineBreak";
}
private String convertInlineFootnote(ContentNode node) {
logger.debug("convertInlineFootnote: name" + node.getNodeName());
return "convertInlineFootnote";
}
private String convertInlineImage(PhraseNode node) {
logger.debug("convertInlineImage");
if (node.getType().equals("icon")) {
return (new IconNode(node)).toAsciiDocContent();
} else {
return (new BlockImageNode(node)).toAsciiDocContent();
}
}
private String convertInlineIndexTerm(ContentNode node) {
logger.debug("convertInlineIndexTerm: name" + node.getNodeName());
return "convertInlineIndexTerm";
}
private String convertInlineKbd(ContentNode node) {
logger.debug("convertInlineKbd: name" + node.getNodeName());
return "convertInlineKbd";
}
private String convertInlineMenu(ContentNode node) {
logger.debug("convertInlineMenu: name" + node.getNodeName());
return "convertInlineMenu";
}
private String convertOpen(StructuralNode node) {
logger.debug("convertOpen");
StringBuilder sb = new StringBuilder();
switch (node.getStyle()) {
case "abstract":
sb.append(ATTRIBUTES_BEGIN).append("abstract").append(ATTRIBUTES_END).append(LINE_SEPARATOR);
break;
case "open":
sb.append(DELIMITER_OPEN_BLOCK).append(LINE_SEPARATOR);
}
sb.append(Optional.ofNullable(((Block) node).getSource()).orElse(""));
appendChildBlocks(node, sb);
if ("open".equals(node.getStyle())) {
sb.append(DELIMITER_OPEN_BLOCK).append(LINE_SEPARATOR);
}
return sb.toString();
}
private String convertPageBreak(ContentNode node) {
logger.debug("convertPageBreak: name" + node.getNodeName());
return DELIMITER_PAGE_BREAK + LINE_SEPARATOR;
}
private String convertQuote(StructuralNode node) {
logger.debug("convertQuote");
StringBuilder sb = new StringBuilder();
appendTitle(node, sb);
sb.append(ATTRIBUTES_BEGIN);
java.util.List<String> attrs = new ArrayList<>();
if (StringUtils.isNotBlank(node.getStyle())) {
attrs.add("quote");
}
appendAttributeTo(node, attrs, "attribution");
appendAttributeTo(node, attrs, "citetitle");
sb.append(String.join(",", attrs)).append(ATTRIBUTES_END).append(LINE_SEPARATOR);
java.util.List<StructuralNode> blocks = node.getBlocks();
if (!blocks.isEmpty()) {
sb.append("____").append(LINE_SEPARATOR);
appendChildBlocks(node, sb);
sb.append("____").append(LINE_SEPARATOR);
} else {
sb.append(((Block) node).getSource());
}
return sb.toString();
}
private String convertSidebar(StructuralNode node) {
logger.debug("convertSidebar");
StringBuilder sb = new StringBuilder();
appendTitle(node, sb);
appendChildBlocks(node, sb);
return sb.toString();
}
private String convertStem(ContentNode node) {
logger.debug("convertStem: name" + node.getNodeName());
return "convertStem";
}
private String convertThematicBreak(ContentNode node) {
logger.debug("convertThematicBreak: name" + node.getNodeName());
return DELIMITER_THEMATIC_BREAK + LINE_SEPARATOR;
}
private String convertVerse(StructuralNode node) {
logger.debug("convertVerse");
StringBuilder sb = new StringBuilder();
appendTitle(node, sb);
sb.append(ATTRIBUTES_BEGIN);
java.util.List<String> attrs = new ArrayList<>();
if (StringUtils.isNotBlank(node.getStyle())) {
attrs.add("verse");
}
appendAttributeTo(node, attrs, "attribution");
appendAttributeTo(node, attrs, "citetitle");
sb.append(String.join(",", attrs)).append(ATTRIBUTES_END).append(LINE_SEPARATOR);
String source = ((Block) node).getSource();
boolean matches = emptyLineOrStartWith.matcher(source).find();
if (matches) {
sb.append(DELIMITER_VERSE).append(LINE_SEPARATOR);
}
sb.append(source);
if (matches) {
sb.append(LINE_SEPARATOR).append(DELIMITER_VERSE);
}
appendTrailingNewLine(sb);
return sb.toString();
}
private String convertVideo(ContentNode node) {
logger.debug("convertVideo: name" + node.getNodeName());
return "convertVideo";
}
private String convertToc(ContentNode node) {
logger.debug("convertToc: name" + node.getNodeName());
return "convertToc";
}
private String convertPass(ContentNode node) {
logger.debug("convertPass: name" + node.getNodeName());
return "convertPass";
}
private String convertAudio(ContentNode node) {
logger.debug("convertAudio: name" + node.getNodeName());
return "convertAudio";
}
private String convertCell(Cell node) {
logger.debug("convertCell");
StringBuilder sb = new StringBuilder();
String source = node.getSource();
if (StringUtils.isNotBlank(source)) {
sb.append(source);
}
Document innerDocument = node.getInnerDocument();
if (null != innerDocument) {
appendChildBlocks(innerDocument, sb, false);
}
return sb.toString().replaceAll(LINE_SEPARATOR + LINE_SEPARATOR + "+", LINE_SEPARATOR + LINE_SEPARATOR);
}
private String convertRow(Row node, java.util.List<TableCellStyle> columnStyles, String delimiterTableCell) {
logger.debug("convertRow");
StringBuilder sb = new StringBuilder();
node.getCells().forEach(cell -> {
boolean addNewLine = false;
int colspan = cell.getColspan();
if (colspan != 0) {
addNewLine = true;
sb.append(colspan).append('+');
}
int rowspan = cell.getRowspan();
if (rowspan != 0) {
addNewLine = true;
sb.append('.').append(rowspan).append('+');
}
int index = cell.getColumn().getColumnNumber() - 1;
TableCellStyle tableCellStyle = (columnStyles.size() > index) ? columnStyles.get(index) : null;
boolean hAlignmentAdded = false;
TableCellHorizontalAlignment hAlignment = TableCellHorizontalAlignment.fromName(cell.getHorizontalAlignment().name());
if ((null != hAlignment) && (null == tableCellStyle || hAlignment != tableCellStyle.horizontalAlignment)) {
hAlignmentAdded = true;
addNewLine = true;
sb.append(hAlignment.getDelimiter());
}
TableCellVerticalAlignment vAlignment = TableCellVerticalAlignment.fromName(cell.getVerticalAlignment().name());
if ((null != vAlignment) && (null == tableCellStyle || hAlignmentAdded || vAlignment != tableCellStyle.verticalAlignment)) {
addNewLine = true;
sb.append(vAlignment.getDelimiter());
}
Style style = Style.fromName(cell.getAttribute("style", "").toString());
if (null != style && (null == tableCellStyle || style != tableCellStyle.style)) {
addNewLine = true;
sb.append(style.getShortHand());
}
sb.append(delimiterTableCell).append(convertCell(cell));
if (addNewLine) {
sb.append(LINE_SEPARATOR);
} else {
sb.append(' ');
}
});
return sb.toString();
}
private String convertTable(Table node) {
logger.debug("convertTable");
java.util.List<TableCellStyle> columnStyles = new ArrayList<>();
for (String col : node.getAttribute("cols", "").toString().split(",")) {
Matcher matcher = tableColumnsStylePattern.matcher(col);
if (matcher.find()) {
int multiplier = 1;
String multiplierGroup = matcher.group(2);
if (null != multiplierGroup) {
try {
multiplier = Integer.parseInt(multiplierGroup);
} catch (NumberFormatException ignored) {
}
}
int width = 0;
try {
width = Integer.parseInt(matcher.group(5));
} catch (NumberFormatException ignored) {
}
TableCellStyle tableCellStyle = new TableCellStyle(
TableCellHorizontalAlignment.fromString(matcher.group(3)),
TableCellVerticalAlignment.fromString(matcher.group(4)),
Style.fromString(matcher.group(6)),
width
);
for (int i = 0; i < multiplier; i++) {
columnStyles.add(tableCellStyle);
}
}
}
StringBuilder sb = new StringBuilder();
appendTitle(node, sb);
sb.append(new TableNode(node).toAsciiDocContent());
boolean innerTable = isInnerTable(node);
String tableDelimiter = innerTable ? DELIMITER_INNER_TABLE : DELIMITER_TABLE;
String cellDelimiter = innerTable ? DELIMITER_INNER_TABLE_CELL : DELIMITER_TABLE_CELL;
sb.append(tableDelimiter).append(LINE_SEPARATOR);
appendRows(node.getHeader(), sb, columnStyles, cellDelimiter);
appendRows(node.getBody(), sb, columnStyles, cellDelimiter);
appendRows(node.getFooter(), sb, columnStyles, cellDelimiter);
sb.append(tableDelimiter).append(LINE_SEPARATOR);
return sb.toString();
}
private boolean isInnerTable(ContentNode node) {
if(null != node) {
ContentNode parent = node.getParent();
if (null != parent) {
return parent instanceof Table || isInnerTable(parent);
}
}
return false;
}
private void appendRows(java.util.List<Row> rows, StringBuilder sb, java.util.List<TableCellStyle> columnStyles, String delimiterTableCell) {
rows.forEach(row -> sb.append(convertRow(row, columnStyles, delimiterTableCell)).append(LINE_SEPARATOR));
}
private String convertDescriptionList(DescriptionList node) {
logger.debug("convertDescriptionList");
StringBuilder sb = new StringBuilder();
appendTitle(node, sb);
String style = Optional.ofNullable(node.getStyle()).orElse("");
switch (style) {
case STYLE_HORIZONTAL:
sb.append(ATTRIBUTES_BEGIN).append(STYLE_HORIZONTAL).append(ATTRIBUTES_END).append(LINE_SEPARATOR);
node.getItems().forEach(item -> sb.append(convertDescriptionListEntry(item, node.getLevel(), false)));
break;
case STYLE_Q_AND_A:
sb.append(ATTRIBUTES_BEGIN).append(STYLE_Q_AND_A).append(ATTRIBUTES_END).append(LINE_SEPARATOR);
default:
node.getItems().forEach(item -> sb.append(convertDescriptionListEntry(item, node.getLevel(), true)));
break;
}
appendTrailingNewLine(sb);
return sb.toString();
}
private String convertDescriptionListEntry(DescriptionListEntry node, int level, Boolean descriptionOnNewLine) {
logger.debug("convertDescriptionListEntry");
StringBuilder sb = new StringBuilder();
String delimiter = repeat(level + 1, MARKER_D_LIST_ITEM);
String entryTerms = node.getTerms().stream()
.map(term -> Optional.ofNullable(term.getSource()).orElse(""))
.collect(Collectors.joining(delimiter + LINE_SEPARATOR, "", delimiter));
sb.append(entryTerms);
ListItem description = node.getDescription();
if (null != description) {
if (descriptionOnNewLine) {
sb.append(LINE_SEPARATOR);
}
String desc = Optional.ofNullable(description.getSource()).orElse("");
if (StringUtils.isNotBlank(desc)) {
sb.append(desc).append(LINE_SEPARATOR);
}
appendChildBlocks(description, sb);
}
return sb.toString();
}
private String convertListing(Block node) {
logger.debug("convertListing");
StringBuilder sb = new StringBuilder();
appendTitle(node, sb);
if (STYLE_SOURCE.equals(node.getStyle())) {
sb.append(new SourceNode(node).toAsciiDocContent());
} else {
sb.append(new BlockListingNode(node).toAsciiDocContent());
}
return sb.toString();
}
private String convertUList(List node) {
logger.debug("convertUList");
StringBuilder sb = new StringBuilder();
appendStyle(node, sb);
appendTitle(node, sb);
appendChildBlocks(node, sb);
appendTrailingNewLine(sb);
return sb.toString();
}
private String convertOList(List node) {
logger.debug("convertOList");
StringBuilder sb = new StringBuilder();
java.util.List<String> attrs = new ArrayList<>();
String start = node.getAttribute("start", "").toString();
if (StringUtils.isNotBlank(start)) {
attrs.add("start=" + start);
}
if (node.isOption("reversed")) {
attrs.add("%reversed");
}
if (!attrs.isEmpty()) {
sb.append(ATTRIBUTES_BEGIN).append(String.join(",", attrs)).append(ATTRIBUTES_END).append(LINE_SEPARATOR);
}
appendTitle(node, sb);
appendChildBlocks(node, sb);
appendTrailingNewLine(sb);
return sb.toString();
}
private String convertCoList(List node) {
logger.debug("convertCoList");
StringBuilder result = new StringBuilder();
appendChildBlocks(node, result);
return result.toString();
}
private String convertListItem(ListItem node) {
logger.debug("convertListItem");
StringBuilder sb = new StringBuilder();
String marker = Optional.ofNullable(node.getMarker()).orElse(repeat(node.getLevel(), MARKER_LIST_ITEM));
String coids = node.getAttribute("coids", "").toString();
Matcher matcher = coListItemIdPattern.matcher(coids);
if (matcher.find()) {
marker = marker.replaceAll("\\d+", matcher.group(1));
}
sb.append(marker).append(" ");
if (node.hasAttribute("checkbox")) {
sb.append('[');
if (node.hasAttribute("checked")) {
sb.append('x');
} else {
sb.append(' ');
}
sb.append(']').append(' ');
}
sb.append(Optional.ofNullable(node.getSource()).orElse(""));
appendTrailingNewLine(sb);
appendChildBlocks(node, sb);
return sb.toString();
}
private String convertList(List node) {
logger.debug("convertList");
return node.getContent().toString();
}
private String convertPreamble(StructuralNode node) {
logger.debug("convertPreamble");
return node.getContent().toString();
}
private String convertImage(StructuralNode node) {
logger.debug("convertImage");
StringBuilder sb = new StringBuilder();
appendTitle(node, sb);
appendRoles(node, sb);
sb.append(new BlockImageNode(node).toAsciiDocContent());
return sb.toString();
}
private String convertLiteral(StructuralNode node) {
logger.debug("convertLiteral");
return ATTRIBUTES_BEGIN + node.getContext() + ATTRIBUTES_END + LINE_SEPARATOR +
StringEscapeUtils.unescapeHtml4(node.getContent().toString()) + LINE_SEPARATOR;
}
private String convertParagraph(StructuralNode node) {
logger.debug("convertParagraph");
StringBuilder sb = new StringBuilder();
appendTitle(node, sb);
sb.append(new ParagraphAttributes(node).toAsciiDocContent());
appendSource((Block) node, sb);
appendTrailingNewLine(sb);
return sb.toString();
}
private String convertSection(Section node) {
logger.debug("convertSection");
StringBuilder sb = new StringBuilder();
appendId(node, sb);
sb.append(new DelimitedBlockNode(node).toAsciiDocContent()).append(StringUtils.repeat(TITLE, node.getLevel() + 1))
.append(" ").append(StringEscapeUtils.unescapeHtml4(node.getTitle())).append(LINE_SEPARATOR);
appendChildBlocks(node, sb);
appendTrailingNewLine(sb);
return sb.toString();
}
private void append_link_constraint_attrs(ContentNode node, java.util.List<String> attrs) {
String rel = node.getAttribute("nofollow-option").toString();
String window = node.getAttributes().get("window").toString();
if (StringUtils.isNotBlank(window)) {
attrs.add("target = \"#{window}\"");
if (window.equals("_blank") || (node.getAttributes().containsKey("option-noopener"))) {
if (StringUtils.isNotBlank(rel)) {
attrs.add("rel = \"" + rel + "noopener\"");
} else {
attrs.add(" rel=\"noopener\"");
}
}
} else if (StringUtils.isNotBlank(rel)) {
attrs.add("rel = " + rel + "\"");
}
}
private String repeat(int count, String with) {
return new String(new char[count]).replace("\0", with);
}
private void appendChildBlocks(StructuralNode parentNode, StringBuilder sb) {
appendChildBlocks(parentNode, sb, true);
}
private void appendChildBlocks(StructuralNode parentNode, StringBuilder sb, boolean addTrailingLineSeparator) {
final boolean isParentAListItem = parentNode instanceof ListItem || parentNode instanceof DescriptionListEntry;
parentNode.getBlocks().forEach(childNode -> {
String childNodeValue = childNode.convert();
if (StringUtils.isNotBlank(childNodeValue)) {
if (isParentAListItem && (sb.toString().contains("+" + LINE_SEPARATOR) || !(childNode instanceof List || childNode instanceof DescriptionList))) {
sb.append('+').append(LINE_SEPARATOR);
}
sb.append(childNodeValue);
if (addTrailingLineSeparator && !StringUtils.endsWith(childNodeValue, LINE_SEPARATOR)) {
sb.append(LINE_SEPARATOR);
}
}
});
}
private void appendTrailingNewLine(StringBuilder sb) {
if (!sb.toString().endsWith(LINE_SEPARATOR + LINE_SEPARATOR)) {
sb.append(LINE_SEPARATOR);
}
}
private void appendId(StructuralNode node, StringBuilder sb) {
String id = node.getId();
if (StringUtils.isNotBlank(id)) {
sb.append("[[").append(id).append("]]").append(LINE_SEPARATOR);
}
}
private void appendSource(Block node, StringBuilder sb) {
String source = node.getSource();
if (StringUtils.isNotBlank(source)) {
sb.append(source).append(LINE_SEPARATOR);
}
}
private void appendTitle(StructuralNode node, StringBuilder sb) {
String title = node.getTitle();
if (StringUtils.isNotBlank(title)) {
sb.append(".").append(StringEscapeUtils.unescapeHtml4(title)).append(LINE_SEPARATOR);
}
}
private void appendStyle(StructuralNode node, StringBuilder sb) {
String style = node.getStyle();
if (StringUtils.isNotBlank(style)) {
sb.append(ATTRIBUTES_BEGIN).append(style).append(ATTRIBUTES_END).append(LINE_SEPARATOR);
}
}
private void appendRoles(StructuralNode node, StringBuilder sb) {
java.util.List<String> roles = node.getRoles();
if (!roles.isEmpty()) {
sb.append(ATTRIBUTES_BEGIN).append(".").append(String.join(".", roles))
.append(ATTRIBUTES_END).append(LINE_SEPARATOR);
}
}
private void appendAttributeTo(StructuralNode node, java.util.List<String> attrs, String name) {
String attribution = node.getAttribute(name, "").toString();
if (StringUtils.isNotBlank(attribution)) {
attrs.add(attribution);
}
}
}

View File

@@ -0,0 +1,70 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.asciidoctor.ast.Block;
import org.asciidoctor.ast.StructuralNode;
import java.util.*;
public class BlockImpl extends StructuralNodeImpl implements Block {
private List<String> lines;
public BlockImpl(StructuralNode parent, String context) {
this(parent, context, "");
}
public BlockImpl(StructuralNode parent, String context, Object content) {
this(parent, context, new HashMap<>(), content);
}
public BlockImpl(StructuralNode parent, String context, Map<String, Object> attributes) {
this(parent, context, attributes, "");
}
public BlockImpl(StructuralNode parent, String context, Map<String, Object> attributes, Object content) {
this(parent, context, attributes, new ArrayList<>(), content, new ArrayList<>(), "", new ArrayList<>());
}
public BlockImpl(StructuralNode parent, String context, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, String contentModel, List<String> subs) {
this(parent, context, attributes, roles, content, blocks, calculateLevel(parent), contentModel, subs);
}
public BlockImpl(StructuralNode parent, String context, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, Integer level, String contentModel, List<String> subs) {
super(parent, context, attributes, roles, content, blocks, level, contentModel, subs);
this.lines = new ArrayList<>();
}
@Override
@Deprecated
public List<String> lines() {
return getLines();
}
@Override
public List<String> getLines() {
return lines;
}
@Override
public void setLines(List<String> lines) {
this.lines = lines;
}
@Override
@Deprecated
public String source() {
return getSource();
}
@Override
public String getSource() {
return String.join("\n", lines);
}
@Override
public void setSource(String source) {
setLines(Arrays.asList(source.split("\n")));
}
}

View File

@@ -0,0 +1,112 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.asciidoctor.ast.Cell;
import org.asciidoctor.ast.Column;
import org.asciidoctor.ast.Document;
import org.asciidoctor.ast.Table;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class CellImpl extends ContentNodeImpl implements Cell {
private final int colspan;
private final int rowspan;
private String text;
private String style;
private Document innerDocument;
public CellImpl(Column parent, String text) {
this(parent, "table_cell", new HashMap<>(), new ArrayList<>(), 0, 0);
this.text = text;
}
public CellImpl(Column parent, Document innerDocument) {
this(parent, "table_cell", new HashMap<>(), new ArrayList<>(), 0, 0);
this.innerDocument = innerDocument;
}
public CellImpl(Column parent, String context, Map<String, Object> attributes, List<String> roles, int colspan, int rowspan) {
super(parent, context, attributes, roles);
this.colspan = colspan;
this.rowspan = rowspan;
}
@Override
public Column getColumn() {
return (Column) getParent();
}
@Override
public int getColspan() {
return colspan;
}
@Override
public int getRowspan() {
return rowspan;
}
@Override
public String getText() {
return text;
}
@Override
public String getSource() {
return text;
}
@Override
public void setSource(String source) {
this.text = source;
}
@Override
public Object getContent() {
return text;
}
@Override
public String getStyle() {
return style;
}
@Override
public void setStyle(String style) {
this.style = style;
}
@Override
public Table.HorizontalAlignment getHorizontalAlignment() {
return Table.HorizontalAlignment.valueOf(((String) getAttribute("halign", "left")).toUpperCase());
}
@Override
public void setHorizontalAlignment(Table.HorizontalAlignment halign) {
setAttribute("halign", halign.name().toLowerCase(), true);
}
@Override
public Table.VerticalAlignment getVerticalAlignment() {
return Table.VerticalAlignment.valueOf(((String) getAttribute("valign", "top")).toUpperCase());
}
@Override
public void setVerticalAlignment(Table.VerticalAlignment valign) {
setAttribute("valign", valign.name().toLowerCase(), true);
}
@Override
public Document getInnerDocument() {
return innerDocument;
}
@Override
public void setInnerDocument(Document document) {
this.innerDocument = document;
}
}

View File

@@ -0,0 +1,81 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.asciidoctor.ast.Column;
import org.asciidoctor.ast.Table;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class ColumnImpl extends ContentNodeImpl implements Column {
private String style;
private Number columnNumber = -1;
private Number width = 0;
public ColumnImpl(Table parent) {
this(parent, "table_column", new HashMap<>(), new ArrayList<>());
}
public ColumnImpl(Table parent, String context, Map<String, Object> attributes, List<String> roles) {
super(parent, context, attributes, roles);
}
@Override
public String getStyle() {
return style;
}
@Override
public void setStyle(String style) {
this.style = style;
}
@Override
public Table getTable() {
return (Table) getParent();
}
@Override
public int getColumnNumber() {
return columnNumber.intValue();
}
public void setColumnNumber(Integer columnNumber) {
setAttribute("colnumber", columnNumber, true);
this.columnNumber = columnNumber;
}
@Override
public int getWidth() {
return width.intValue();
}
@Override
public void setWidth(int width) {
setAttribute("width", width, true);
this.width = width;
}
@Override
public Table.HorizontalAlignment getHorizontalAlignment() {
return Table.HorizontalAlignment.valueOf(((String) getAttribute("halign", "left")).toUpperCase());
}
@Override
public void setHorizontalAlignment(Table.HorizontalAlignment halign) {
setAttribute("halign", halign.name().toLowerCase(), true);
}
@Override
public Table.VerticalAlignment getVerticalAlignment() {
return Table.VerticalAlignment.valueOf(((String) getAttribute("valign", "top")).toUpperCase());
}
@Override
public void setVerticalAlignment(Table.VerticalAlignment valign) {
setAttribute("valign", valign.name().toLowerCase(), true);
}
}

View File

@@ -0,0 +1,309 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.asciidoctor.ast.ContentNode;
import org.asciidoctor.ast.Document;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
@SuppressWarnings("SuspiciousMethodCalls")
public abstract class ContentNodeImpl implements ContentNode {
private String id;
private final String context;
private final Map<String, Object> attributes;
private final List<String> roles;
private final ContentNode parent;
public ContentNodeImpl(ContentNode parent, String context) {
this(parent, context, new HashMap<>(), new ArrayList<>());
}
public ContentNodeImpl(ContentNode parent, String context, Map<String, Object> attributes, List<String> roles) {
this.parent = parent;
this.context = context;
this.attributes = attributes;
this.roles = roles;
}
@Override
@Deprecated
public String id() {
return getId();
}
@Override
public String getId() {
return id;
}
@Override
public void setId(String id) {
this.id = id.toLowerCase().replaceAll("\\s+", "_");
}
@Override
@Deprecated
public String context() {
return getContext();
}
@Override
public String getContext() {
return context;
}
@Override
@Deprecated
public ContentNode parent() {
return getParent();
}
@Override
public ContentNode getParent() {
return parent;
}
@Override
@Deprecated
public Document document() {
return getDocument();
}
@Override
public Document getDocument() {
throw new UnsupportedOperationException("Not implemented, yet");
}
@Override
public String getNodeName() {
return getContext();
}
@Override
public boolean isInline() {
return false;
}
@Override
public boolean isBlock() {
return false;
}
@Override
public Map<String, Object> getAttributes() {
return attributes;
}
@Override
@Deprecated
public Object getAttr(Object name, Object defaultValue, boolean inherit) {
return getAttribute(name, defaultValue, inherit);
}
@Override
@Deprecated
public Object getAttr(Object name, Object defaultValue) {
return getAttribute(name, defaultValue);
}
@Override
@Deprecated
public Object getAttr(Object name) {
return getAttribute(name);
}
@Override
public Object getAttribute(Object name, Object defaultValue, boolean inherit) {
return getAttribute(name, defaultValue);
}
@Override
public Object getAttribute(Object name, Object defaultValue) {
return attributes.getOrDefault(name, defaultValue);
}
@Override
public Object getAttribute(Object name) {
return attributes.get(name);
}
@Override
@Deprecated
public boolean isAttr(Object name, Object expected, boolean inherit) {
return isAttribute(name, expected, inherit);
}
@Override
@Deprecated
public boolean isAttr(Object name, Object expected) {
return isAttribute(name, expected);
}
@Override
public boolean isAttribute(Object name, Object expected, boolean inherit) {
return isAttribute(name, expected);
}
@Override
public boolean isAttribute(Object name, Object expected) {
try {
if (attributes.containsKey(name)) {
return attributes.get(name).equals(expected);
} else return false;
} catch (Exception e) {
return false;
}
}
@Override
@Deprecated
public boolean hasAttr(Object name) {
return hasAttribute(name);
}
@Override
@Deprecated
public boolean hasAttr(Object name, boolean inherited) {
return hasAttribute(name, inherited);
}
@Override
public boolean hasAttribute(Object name) {
return attributes.containsKey(name);
}
@Override
public boolean hasAttribute(Object name, boolean inherited) {
return hasAttribute(name);
}
@Override
@Deprecated
public boolean setAttr(Object name, Object value, boolean overwrite) {
return setAttribute(name, value, overwrite);
}
@Override
public boolean setAttribute(Object name, Object value, boolean overwrite) {
return setAttribute((String)name, value, overwrite);
}
public boolean setAttribute(String name, Object value, boolean overwrite) {
try {
if (overwrite) {
attributes.put(name, value);
} else {
attributes.putIfAbsent(name, value);
}
return true;
} catch (Exception e) {
return false;
}
}
public Object removeAttribute(String name){
return attributes.remove(name);
}
public boolean removeAttribute(String name, Object value){
return attributes.remove(name, value);
}
@Override
public boolean isOption(Object name) {
try {
Object o = attributes.get(name + "-option");
return null != o && o.toString().equals("");
}catch (Exception ignored){
return false;
}
}
public boolean setOption(String name){
return setAttribute(name + "-option", "", true);
}
public Object removeOption(String name){
return removeAttribute(name + "-option");
}
@Override
public boolean isRole() {
return false;
}
@Override
public String getRole() {
return String.join(",", roles);
}
@Override
@Deprecated
public String role() {
return getRole();
}
@Override
public List<String> getRoles() {
return roles;
}
@Override
public boolean hasRole(String role) {
return roles.contains(role);
}
@Override
public void addRole(String role) {
roles.add(role);
}
@Override
public void removeRole(String role) {
roles.remove(role);
}
@Override
public boolean isReftext() {
throw new UnsupportedOperationException("Not implemented, yet");
}
@Override
public String getReftext() {
throw new UnsupportedOperationException("Not implemented, yet");
}
@Override
public String iconUri(String name) {
throw new UnsupportedOperationException("Not implemented, yet");
}
@Override
public String mediaUri(String target) {
throw new UnsupportedOperationException("Not implemented, yet");
}
@Override
public String imageUri(String targetImage) {
throw new UnsupportedOperationException("Not implemented, yet");
}
@Override
public String imageUri(String targetImage, String assetDirKey) {
throw new UnsupportedOperationException("Not implemented, yet");
}
@Override
public String readAsset(String path, Map<Object, Object> opts) {
throw new UnsupportedOperationException("Not implemented, yet");
}
@Override
public String normalizeWebPath(String path, String start, boolean preserveUriTarget) {
throw new UnsupportedOperationException("Not implemented, yet");
}
}

View File

@@ -0,0 +1,36 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.asciidoctor.ast.Cursor;
public class CursorImpl implements Cursor {
private int lineno;
public CursorImpl() {
}
@Override
public int getLineNumber() {
return lineno;
}
@Override
public String getPath() {
throw new UnsupportedOperationException("Not implemented, yet");
}
@Override
public String getDir() {
throw new UnsupportedOperationException("Not implemented, yet");
}
@Override
public String getFile() {
throw new UnsupportedOperationException("Not implemented, yet");
}
@Override
public String toString() {
throw new UnsupportedOperationException("Not implemented, yet");
}
}

View File

@@ -0,0 +1,66 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.asciidoctor.ast.DescriptionListEntry;
import org.asciidoctor.ast.ListItem;
import org.asciidoctor.ast.StructuralNode;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class DescriptionListEntryImpl extends StructuralNodeImpl implements DescriptionListEntry {
private final List<ListItem> terms;
private ListItem description;
public DescriptionListEntryImpl(StructuralNode parent) {
this(parent, new ArrayList<>());
}
public DescriptionListEntryImpl(StructuralNode parent, List<ListItem> terms) {
this(parent, terms, null);
}
public DescriptionListEntryImpl(StructuralNode parent, List<ListItem> terms, ListItem description) {
this(parent, null, terms, description);
}
public DescriptionListEntryImpl(StructuralNode parent, Object content, List<ListItem> terms, ListItem description) {
this(parent, new HashMap<>(), new ArrayList<>(), content, new ArrayList<>(), "", new ArrayList<>(), terms, description);
}
public DescriptionListEntryImpl(StructuralNode parent, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, String contentModel, List<String> subs,
List<ListItem> terms, ListItem description) {
this(parent, attributes, roles, content, blocks, null != parent ? parent.getLevel() : 1, contentModel, subs, terms, description);
}
public DescriptionListEntryImpl(StructuralNode parent, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, Integer level, String contentModel,
List<String> subs, List<ListItem> terms, ListItem description) {
super(parent, "dlist_item", attributes, roles, content, blocks, level, contentModel, subs);
this.terms = terms;
this.description = description;
}
@Override
public List<ListItem> getTerms() {
return terms;
}
public boolean addTerm(ListItem term) {
return terms.add(term);
}
@Override
public ListItem getDescription() {
return description;
}
public void setDescription(final ListItem description) {
this.description = description;
}
}

View File

@@ -0,0 +1,72 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.asciidoctor.ast.DescriptionList;
import org.asciidoctor.ast.DescriptionListEntry;
import org.asciidoctor.ast.StructuralNode;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class DescriptionListImpl extends StructuralNodeImpl implements DescriptionList {
public static final String CONTEXT = "dlist";
private List<DescriptionListEntry> items;
public DescriptionListImpl(StructuralNode parent) {
this(parent, new ArrayList<>());
}
public DescriptionListImpl(StructuralNode parent, List<DescriptionListEntry> items) {
this(parent, null, items);
}
public DescriptionListImpl(StructuralNode parent, Object content, List<DescriptionListEntry> items) {
this(parent, new HashMap<>(), new ArrayList<>(), content, new ArrayList<>(), "", new ArrayList<>(), items);
}
public DescriptionListImpl(StructuralNode parent, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, String contentModel,
List<String> subs, List<DescriptionListEntry> items) {
this(parent, attributes, roles, content, blocks, calculateLevel(parent), contentModel, subs, items);
}
public DescriptionListImpl(StructuralNode parent, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, Integer level,
String contentModel, List<String> subs, List<DescriptionListEntry> items) {
super(parent, CONTEXT, attributes, roles, content, blocks, level, contentModel, subs);
this.items = items;
}
@Override
public List<DescriptionListEntry> getItems() {
return items;
}
public void setItems(List<DescriptionListEntry> items) {
this.items = items;
}
public void addEntry(DescriptionListEntry entry) {
this.items.add(entry);
}
@Override
public boolean hasItems() {
return !items.isEmpty();
}
@Override
@Deprecated
public String render() {
return convert();
}
protected static Integer calculateLevel(StructuralNode parent) {
int level = 1;
if (parent instanceof DescriptionList)
level = parent.getLevel() + 1;
return level;
}
}

View File

@@ -0,0 +1,89 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.asciidoctor.ast.Document;
import org.asciidoctor.ast.StructuralNode;
import org.asciidoctor.ast.Title;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class DocumentImpl extends StructuralNodeImpl implements Document {
public DocumentImpl() {
this(null);
}
public DocumentImpl(StructuralNode parent) {
this(parent, "document", "");
}
public DocumentImpl(StructuralNode parent, String context, Object content) {
this(parent, context, new HashMap<>(), new ArrayList<>(), content, new ArrayList<>(), "", new ArrayList<>());
}
public DocumentImpl(StructuralNode parent, String context, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, String contentModel,
List<String> subs) {
this(parent, context, attributes, roles, content, blocks, null != parent ? parent.getLevel() + 1 : 0, contentModel, subs);
}
public DocumentImpl(StructuralNode parent, String context, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, Integer level, String contentModel,
List<String> subs) {
super(parent, context, attributes, roles, content, blocks, level, contentModel, subs);
}
@Override
public boolean isBasebackend(String backend) {
return isAttribute("basebackend", backend);
}
@Override
@Deprecated
public boolean basebackend(String backend) {
return isBasebackend(backend);
}
@Override
public Map<Object, Object> getOptions() {
return null;
}
@Override
public Title getStructuredDoctitle() {
return (Title) getOptions().get("doctitle");
}
@Override
public String getDoctitle() {
return getTitle();
}
@Override
@Deprecated
public String doctitle() {
return getDoctitle();
}
@Override
public int getAndIncrementCounter(String name) {
throw new UnsupportedOperationException("Not implemented, yet");
}
@Override
public int getAndIncrementCounter(String name, int initialValue) {
throw new UnsupportedOperationException("Not implemented, yet");
}
@Override
public boolean isSourcemap() {
throw new UnsupportedOperationException("Not implemented, yet");
}
@Override
public void setSourcemap(boolean state) {
throw new UnsupportedOperationException("Not implemented, yet");
}
}

View File

@@ -0,0 +1,56 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.asciidoctor.ast.List;
import org.asciidoctor.ast.StructuralNode;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
public class ListImpl extends StructuralNodeImpl implements List {
private final java.util.List<StructuralNode> items;
public ListImpl(StructuralNode parent, String context) {
this(parent, context, new ArrayList<>());
}
public ListImpl(StructuralNode parent, String context, java.util.List<StructuralNode> items) {
this(parent, context, null, items);
}
public ListImpl(StructuralNode parent, String context, Object content, java.util.List<StructuralNode> items) {
this(parent, context, new HashMap<>(), new ArrayList<>(), content, new ArrayList<>(), "", new ArrayList<>(), items);
}
public ListImpl(StructuralNode parent, String context, Map<String, Object> attributes, java.util.List<String> roles,
Object content, java.util.List<StructuralNode> blocks,
String contentModel, java.util.List<String> subs, java.util.List<StructuralNode> items) {
this(parent, context, attributes, roles, content, blocks, null != parent ? parent.getLevel() + 1 : 0, contentModel, subs, items);
}
public ListImpl(StructuralNode parent, String context, Map<String, Object> attributes, java.util.List<String> roles,
Object content, java.util.List<StructuralNode> blocks,
Integer level, String contentModel, java.util.List<String> subs, java.util.List<StructuralNode> items) {
super(parent, context, attributes, roles, content, blocks, level, contentModel, subs);
this.items = items;
}
@Override
public java.util.List<StructuralNode> getItems() {
return items;
}
@Override
public boolean hasItems() {
return !items.isEmpty();
}
@Override
@Deprecated
public String render() {
return convert();
}
}

View File

@@ -0,0 +1,63 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.apache.commons.lang3.StringUtils;
import org.asciidoctor.ast.ListItem;
import org.asciidoctor.ast.StructuralNode;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class ListItemImpl extends StructuralNodeImpl implements ListItem {
private final String marker;
private String text;
public ListItemImpl(StructuralNode parent, String text) {
this(parent, "list_item", null, "*", text);
}
public ListItemImpl(StructuralNode parent, String context, Object content, String marker, String text) {
this(parent, context, new HashMap<>(), new ArrayList<>(), content, new ArrayList<>(), "", new ArrayList<>(), marker, text);
}
public ListItemImpl(StructuralNode parent, String context, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, String contentModel,
List<String> subs, String marker, String text) {
this(parent, context, attributes, roles, content, blocks, null != parent ? parent.getLevel() : 1, contentModel, subs, marker, text);
}
public ListItemImpl(StructuralNode parent, String context, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, Integer level,
String contentModel, List<String> subs, String marker, String text) {
super(parent, context, attributes, roles, content, blocks, level, contentModel, subs);
this.marker = marker;
this.text = text;
}
@Override
public String getMarker() {
return marker;
}
@Override
public String getText() {
return text;
}
@Override
public String getSource() {
return text;
}
@Override
public void setSource(String source) {
this.text = source;
}
@Override
public boolean hasText() {
return StringUtils.isNotBlank(text);
}
}

View File

@@ -0,0 +1,38 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.asciidoctor.ast.StructuralNode;
import java.util.List;
import java.util.Map;
public class ParagraphBlockImpl extends BlockImpl {
public static final String CONTEXT = "paragraph";
public ParagraphBlockImpl(StructuralNode parent) {
super(parent, CONTEXT);
}
public ParagraphBlockImpl(StructuralNode parent, Object content) {
super(parent, CONTEXT, content);
}
public ParagraphBlockImpl(StructuralNode parent, Map<String, Object> attributes) {
super(parent, CONTEXT, attributes);
}
public ParagraphBlockImpl(StructuralNode parent, Map<String, Object> attributes, Object content) {
super(parent, CONTEXT, attributes, content);
}
public ParagraphBlockImpl(StructuralNode parent, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, String contentModel, List<String> subs) {
super(parent, CONTEXT, attributes, roles, content, blocks, contentModel, subs);
}
public ParagraphBlockImpl(StructuralNode parent, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, Integer level, String contentModel,
List<String> subs) {
super(parent, CONTEXT, attributes, roles, content, blocks, level, contentModel, subs);
}
}

View File

@@ -0,0 +1,50 @@
package io.github.swagger2markup.adoc.ast.impl;
import io.github.swagger2markup.adoc.AsciidocConverter;
import org.asciidoctor.ast.ContentNode;
import org.asciidoctor.ast.PhraseNode;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class PhraseNodeImpl extends ContentNodeImpl implements PhraseNode {
private final String type;
private final String text;
private final String target;
private final AsciidocConverter converter = new AsciidocConverter(AsciidocConverter.NAME, new HashMap<>());
public PhraseNodeImpl(ContentNode parent, String context, Map<String, Object> attributes, List<String> roles, String type, String text, String target) {
super(parent, context, attributes, roles);
this.type = type;
this.text = text;
this.target = target;
}
@Override
@Deprecated
public String render() {
return convert();
}
@Override
public String convert() {
return converter.convert(this, null, new HashMap<>());
}
@Override
public String getType() {
return type;
}
@Override
public String getText() {
return text;
}
@Override
public String getTarget() {
return target;
}
}

View File

@@ -0,0 +1,21 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.asciidoctor.ast.Cell;
import org.asciidoctor.ast.Row;
import java.util.List;
public class RowImpl implements Row {
private final List<Cell> cells;
public RowImpl(List<Cell> cells) {
this.cells = cells;
}
@Override
public List<Cell> getCells() {
return cells;
}
}

View File

@@ -0,0 +1,118 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.asciidoctor.ast.Section;
import org.asciidoctor.ast.StructuralNode;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class SectionImpl extends StructuralNodeImpl implements Section {
private final Integer index;
private final Integer number;
private final String numeral;
private final String sectionName;
private final boolean special;
private final boolean numbered;
public SectionImpl(StructuralNode parent) {
this(parent, new HashMap<>());
}
public SectionImpl(StructuralNode parent, Map<String, Object> attributes) {
this(parent, "section", null, "");
}
public SectionImpl(StructuralNode parent, String context, Object content, String sectionName) {
this(parent, context, content, null, null, "", sectionName, false, false);
}
public SectionImpl(StructuralNode parent, String context, Object content, Integer index, Integer number, String numeral,
String sectionName, boolean special, boolean numbered) {
this(parent, context, new HashMap<>(), new ArrayList<>(), content, new ArrayList<>(),
"", new ArrayList<>(), index, number, numeral, sectionName, special, numbered);
}
public SectionImpl(StructuralNode parent, String context, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, String contentModel, List<String> subs,
Integer index, Integer number, String numeral, String sectionName, boolean special, boolean numbered) {
this(parent, context, attributes, roles, content, blocks, calculateLevel(parent), contentModel, subs, index, number, numeral, sectionName, special, numbered);
}
public SectionImpl(StructuralNode parent, String context, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, Integer level, String contentModel, List<String> subs,
Integer index, Integer number, String numeral, String sectionName, boolean special, boolean numbered) {
super(parent, context, attributes, roles, content, blocks, level, contentModel, subs);
this.index = index;
this.number = number;
this.numeral = numeral;
this.sectionName = sectionName;
this.special = special;
this.numbered = numbered;
}
@Override
@Deprecated
public int index() {
return getIndex();
}
@Override
public int getIndex() {
return index;
}
@Override
@Deprecated
public int number() {
return getNumber();
}
@Override
@Deprecated
public int getNumber() {
return number;
}
@Override
public String getNumeral() {
return numeral;
}
@Override
@Deprecated
public String sectname() {
return getSectionName();
}
@Override
public String getSectionName() {
return sectionName;
}
@Override
@Deprecated
public boolean special() {
return isSpecial();
}
@Override
public boolean isSpecial() {
return special;
}
@Override
@Deprecated
public boolean numbered() {
return isNumbered();
}
@Override
public boolean isNumbered() {
return numbered;
}
}

View File

@@ -0,0 +1,179 @@
package io.github.swagger2markup.adoc.ast.impl;
import io.github.swagger2markup.adoc.AsciidocConverter;
import org.asciidoctor.ast.Cursor;
import org.asciidoctor.ast.StructuralNode;
import java.util.*;
public class StructuralNodeImpl extends ContentNodeImpl implements StructuralNode {
private String title;
private String caption;
private String style;
private final Object content;
private final List<StructuralNode> blocks;
private Integer level;
private final String contentModel;
private List<String> subs;
private final AsciidocConverter converter = new AsciidocConverter(AsciidocConverter.NAME, new HashMap<>());
public StructuralNodeImpl(StructuralNode parent, String context) {
this(parent, context, new HashMap<>());
}
public StructuralNodeImpl(StructuralNode parent, String context, Map<String, Object> attributes) {
this(parent, context, attributes, null);
}
public StructuralNodeImpl(StructuralNode parent, String context, Object content) {
this(parent, context, new HashMap<>(), content);
}
public StructuralNodeImpl(StructuralNode parent, String context, Map<String, Object> attributes, Object content) {
this(parent, context, attributes, new ArrayList<>(), content, new ArrayList<>(), "", new ArrayList<>());
}
public StructuralNodeImpl(StructuralNode parent, String context, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, String contentModel, List<String> subs) {
this(parent, context, attributes, roles, content, blocks, calculateLevel(parent), contentModel, subs);
}
public StructuralNodeImpl(StructuralNode parent, String context, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, Integer level, String contentModel, List<String> subs) {
super(parent, context, attributes, roles);
this.content = content;
this.blocks = blocks;
this.level = level;
this.contentModel = contentModel;
this.subs = subs;
}
@Override
@Deprecated
public String title() {
return getTitle();
}
@Override
public String getTitle() {
return title;
}
@Override
public void setTitle(String title) {
this.title = title;
}
@Override
public String getCaption() {
return caption;
}
@Override
public void setCaption(String caption) {
this.caption = caption;
}
@Override
@Deprecated
public String style() {
return getStyle();
}
@Override
public String getStyle() {
return style;
}
@Override
public void setStyle(String style) {
this.style = style;
}
@Override
@Deprecated
public List<StructuralNode> blocks() {
return getBlocks();
}
@Override
public List<StructuralNode> getBlocks() {
return blocks;
}
@Override
public void append(StructuralNode block) {
blocks.add(block);
}
@Override
@Deprecated
public Object content() {
return getContent();
}
@Override
public Object getContent() {
return content;
}
@Override
public String convert() {
return converter.convert(this, null, new HashMap<>());
}
@Override
public int getLevel() {
return level;
}
@Override
public Cursor getSourceLocation() {
return new CursorImpl();
}
@Override
public String getContentModel() {
return contentModel;
}
@Override
public List<String> getSubstitutions() {
return subs;
}
@Override
public boolean isSubstitutionEnabled(String substitution) {
return subs.contains(substitution);
}
@Override
public void removeSubstitution(String substitution) {
subs.remove(substitution);
}
@Override
public void addSubstitution(String substitution) {
subs.add(substitution);
}
@Override
public void prependSubstitution(String substitution) {
}
@Override
public void setSubstitutions(String... substitutions) {
subs = Arrays.asList(substitutions);
}
@Override
public List<StructuralNode> findBy(Map<Object, Object> selector) {
throw new UnsupportedOperationException("Not implemented, yet");
}
protected static Integer calculateLevel(StructuralNode parent) {
return null != parent ? parent.getLevel() + 1 : 0;
}
}

View File

@@ -0,0 +1,306 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.asciidoctor.ast.*;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.List;
import java.util.*;
public class TableImpl extends StructuralNodeImpl implements Table {
public static final String OPTION_UNBREAKABLE = "unbreakable";
public static final String OPTION_BREAKABLE = "breakable";
private Logger logger = LoggerFactory.getLogger(getClass());
public static final String CONTEXT = "table";
private static final String FRAME_ATTR = "frame";
private static final String GRID_ATTR = "grid";
private RowList headerRows;
private RowList bodyRows;
private RowList footerRows;
private List<Column> columns = new ArrayList<>();
public TableImpl(StructuralNode parent) {
this(parent, new HashMap<>(), new ArrayList<>());
}
public TableImpl(StructuralNode parent, Map<String, Object> attributes, List<String> roles) {
this(parent, attributes, roles, calculateLevel(parent));
}
public TableImpl(StructuralNode parent, Map<String, Object> attributes, List<String> roles, Integer level) {
this(parent, attributes, roles, null, new ArrayList<>(), level, "", new ArrayList<>());
}
public TableImpl(StructuralNode parent, Map<String, Object> attributes, List<String> roles,
Object content, List<StructuralNode> blocks, Integer level, String contentModel, List<String> subs) {
super(parent, CONTEXT, attributes, roles, content, blocks, level, contentModel, subs);
this.headerRows = new RowList(new ArrayList<>());
this.bodyRows = new RowList(new ArrayList<>());
this.footerRows = new RowList(new ArrayList<>());
}
@Override
public boolean hasHeaderOption() {
return isOption("header");
}
@Override
public String getFrame() {
return (String) getAttribute(FRAME_ATTR, "all");
}
@Override
public void setFrame(String frame) {
setAttribute(FRAME_ATTR, frame, true);
}
@Override
public String getGrid() {
return (String) getAttribute(GRID_ATTR, "all");
}
@Override
public void setGrid(String grid) {
setAttribute(GRID_ATTR, grid, true);
}
@Override
public List<Column> getColumns() {
return columns;
}
@Override
public List<Row> getHeader() {
return headerRows;
}
public void setHeaderRow(Row row) {
headerRows.clear();
headerRows.add(row);
scanRowForColumns(row);
}
public void setHeaderRow(List<Cell> cells) {
setHeaderRow(new RowImpl(cells));
}
public void setHeaderRow(String... documentContents) {
headerRows.clear();
headerRows.add(generateRow(documentContents));
}
public RowImpl generateRow(Document... innerDocs) {
List<Cell> cells = new ArrayList<>();
for (int i = 0; i < innerDocs.length; i++) {
Column column = null;
try {
column = columns.get(i);
} catch (Exception ignored) {
}
if (null == column) {
ColumnImpl newColumn = new ColumnImpl(this);
newColumn.setColumnNumber(i + 1);
column = newColumn;
addColumnAt(column, i);
}
cells.add(new CellImpl(column, innerDocs[i]));
}
return new RowImpl(cells);
}
public RowImpl generateRow(String... documentContents) {
Document[] documents = Arrays.stream(documentContents).map(documentContent -> {
Document innerDoc = new DocumentImpl();
Block paragraph = new ParagraphBlockImpl(innerDoc);
paragraph.setSource(documentContent);
innerDoc.append(paragraph);
return innerDoc;
}).toArray(Document[]::new);
return generateRow(documents);
}
@Override
public List<Row> getBody() {
return bodyRows;
}
public void setBodyRows(List<Row> rows) {
bodyRows.clear();
bodyRows.addAll(rows);
bodyRows.forEach(this::scanRowForColumns);
}
public void addRow(Row row) {
bodyRows.add(row);
scanRowForColumns(row);
}
public void addRow(List<Cell> cells) {
bodyRows.add(new RowImpl(cells));
}
public RowImpl addRow(Document... documentContents) {
RowImpl row = generateRow(documentContents);
bodyRows.add(row);
return row;
}
public RowImpl addRow(String... documentContents) {
RowImpl row = generateRow(documentContents);
bodyRows.add(row);
return row;
}
@Override
public List<Row> getFooter() {
return footerRows;
}
public void setFooterRow(Row row) {
footerRows.clear();
footerRows.add(row);
scanRowForColumns(row);
}
public void setFooterRow(String... documentContents) {
footerRows.clear();
footerRows.add(generateRow(documentContents));
}
private void scanRowForColumns(Row row) {
row.getCells().forEach(cell -> {
Column column = cell.getColumn();
int i = column.getColumnNumber() - 1;
addColumnAt(column, i);
});
}
private void addColumnAt(Column column, int i) {
if (columns.size() >= i) {
columns.add(i, column);
} else {
while (columns.size() < i) {
columns.add(columns.size(), null);
}
columns.add(column);
}
}
public void setFooterRow(List<Cell> cells) {
setFooterRow(new RowImpl(cells));
}
class RowList extends AbstractList<Row> {
private final List<Row> rubyArray;
private RowList(List<Row> rubyArray) {
this.rubyArray = rubyArray;
}
@Override
public int size() {
return rubyArray.size();
}
@Override
public boolean isEmpty() {
return rubyArray.isEmpty();
}
@Override
public boolean contains(Object o) {
return rubyArray.contains(o);
}
@Override
public boolean add(Row row) {
boolean changed = false;
try {
changed = rubyArray.add(row);
setAttribute("rowcount", size(), true);
} catch (Exception e) {
logger.debug("Couldn't add row", e);
}
return changed;
}
@Override
public boolean remove(Object o) {
if (!(o instanceof RowImpl)) {
return false;
}
try {
boolean changed = rubyArray.remove(o);
setAttribute("rowcount", size(), true);
return changed;
} catch (Exception e) {
logger.debug("Couldn't add row", e);
return false;
}
}
@Override
public boolean retainAll(Collection<?> c) {
throw new UnsupportedOperationException();
}
@Override
public void clear() {
rubyArray.clear();
setAttribute("rowcount", size(), true);
}
@Override
public Row get(int index) {
return rubyArray.get(index);
}
@Override
public Row set(int index, Row element) {
Row oldRow = get(index);
rubyArray.set(index, element);
return oldRow;
}
@Override
public void add(int index, Row element) {
rubyArray.add(index, element);
setAttribute("rowcount", size(), true);
}
@Override
public Row remove(int index) {
Row removed = rubyArray.remove(index);
setAttribute("rowcount", size(), true);
return removed;
}
@Override
public int indexOf(Object o) {
if (!(o instanceof RowImpl)) {
return -1;
}
return rubyArray.indexOf(o);
}
@Override
public int lastIndexOf(Object o) {
if (!(o instanceof RowImpl)) {
return -1;
}
return rubyArray.lastIndexOf(o);
}
}
protected static Integer calculateLevel(StructuralNode parent) {
int level = 1;
if (parent instanceof Table)
level = parent.getLevel() + 1;
return level;
}
}

View File

@@ -0,0 +1,34 @@
package io.github.swagger2markup.adoc.ast.impl;
import org.asciidoctor.ast.Title;
public class TitleImpl implements Title {
private final String main;
private final String subtitle;
public TitleImpl(String main, String subtitle) {
this.main = main;
this.subtitle = subtitle;
}
@Override
public String getMain() {
return main;
}
@Override
public String getSubtitle() {
return subtitle;
}
@Override
public String getCombined() {
return main + ": " + subtitle;
}
@Override
public boolean isSanitized() {
return false;
}
}

View File

@@ -0,0 +1,50 @@
package io.github.swagger2markup.adoc.converter.internal;
import org.apache.commons.lang3.StringUtils;
import org.asciidoctor.ast.ContentNode;
public class BlockImageNode extends NodeAttributes {
final private String target;
public BlockImageNode(ContentNode node) {
super(node.getAttributes());
target = pop("target").replaceAll("\\s", "{sp}");
}
public String getTarget() {
return target;
}
@Override
public void processPositionalAttributes() {
String attr1 = pop("1", "alt");
if (StringUtils.isNotBlank(attr1)) {
attrs.add(attr1);
}
String attr2 = pop("2", "width");
if (StringUtils.isNotBlank(attr2)) {
attrs.add(attr2);
}
String attr3 = pop("3", "height");
if (StringUtils.isNotBlank(attr3)) {
attrs.add(attr3);
}
}
@Override
void processAttributes() {
attributes.forEach((k, v) -> {
if (!k.equals("role") && null != v) {
attrs.add(k + "=" + v);
}
});
}
@Override
public String processAsciiDocContent() {
return "image::" + target + '[' + String.join(",", attrs) + ']';
}
}

View File

@@ -0,0 +1,31 @@
package io.github.swagger2markup.adoc.converter.internal;
import org.asciidoctor.ast.Block;
import java.util.List;
import static io.github.swagger2markup.adoc.converter.internal.Delimiters.*;
public class BlockListingNode extends ParagraphAttributes {
final private Block node;
public BlockListingNode(Block node) {
super(node);
this.node = node;
}
@Override
public String processAsciiDocContent() {
StringBuilder sb = new StringBuilder();
attrsToString(sb, attrs);
sb.append(LINE_SEPARATOR).append(DELIMITER_BLOCK).append(LINE_SEPARATOR).append(node.getSource()).append(LINE_SEPARATOR).append(DELIMITER_BLOCK).append(LINE_SEPARATOR);
return sb.toString();
}
void attrsToString(StringBuilder sb, List<String> list) {
if (!list.isEmpty()) {
sb.append(ATTRIBUTES_BEGIN).append(String.join(",", list)).append(ATTRIBUTES_END).append(LINE_SEPARATOR);
}
}
}

View File

@@ -0,0 +1,45 @@
package io.github.swagger2markup.adoc.converter.internal;
import org.apache.commons.lang3.StringUtils;
import org.asciidoctor.ast.StructuralNode;
import java.util.ArrayList;
import java.util.List;
import static io.github.swagger2markup.adoc.converter.internal.Delimiters.*;
public class DelimitedBlockNode extends ParagraphAttributes {
public DelimitedBlockNode(StructuralNode node) {
super(node);
}
@Override
public void processPositionalAttributes() {
String source = pop("1", "style");
StringBuilder options = new StringBuilder();
List<String> toRemove = new ArrayList<>();
attributes.forEach((k, v) -> {
if (k.endsWith(OPTION_SUFFIX)) {
toRemove.add(k);
options.append('%').append(k.replace(OPTION_SUFFIX, ""));
}
});
toRemove.forEach(attributes::remove);
source += options.toString();
if (StringUtils.isNotBlank(source)) {
attrs.add(source);
}
super.processPositionalAttributes();
}
@Override
public String processAsciiDocContent() {
StringBuilder sb = new StringBuilder();
if (!attrs.isEmpty()) {
sb.append(ATTRIBUTES_BEGIN).append(String.join(",", attrs)).append(ATTRIBUTES_END).append(LINE_SEPARATOR);
}
return sb.toString();
}
}

View File

@@ -0,0 +1,26 @@
package io.github.swagger2markup.adoc.converter.internal;
public class Delimiters {
public static final String ATTRIBUTES_BEGIN = "[";
public static final String ATTRIBUTES_END = "]";
public static final String COLON = ":";
public static final String DELIMITER_BLOCK = "----";
public static final String DELIMITER_EXAMPLE = "====";
public static final String DELIMITER_INNER_TABLE_CELL = "!";
public static final String DELIMITER_INNER_TABLE = "!===";
public static final String DELIMITER_PAGE_BREAK = "<<<";
public static final String DELIMITER_OPEN_BLOCK = "--";
public static final String DELIMITER_SIDEBAR = "****";
public static final String DELIMITER_TABLE = "|===";
public static final String DELIMITER_TABLE_CELL = "|";
public static final String DELIMITER_THEMATIC_BREAK = "'''";
public static final String DELIMITER_VERSE = "____";
public static final String DOCUMENT_TITLE = "=";
public static final String LINE_SEPARATOR = System.getProperty("line.separator");
public static final String MARKER_LIST_ITEM = "*";
public static final String MARKER_D_LIST_ITEM = ":";
public static final String STYLE_HORIZONTAL = "horizontal";
public static final String STYLE_Q_AND_A = "qanda";
public static final String STYLE_SOURCE = "source";
public static final String TITLE = "=";
}

View File

@@ -0,0 +1,38 @@
package io.github.swagger2markup.adoc.converter.internal;
import org.apache.commons.lang3.StringUtils;
import org.asciidoctor.ast.ContentNode;
public class IconNode extends NodeAttributes {
final private String alt;
public IconNode(ContentNode node) {
super(node.getAttributes());
alt = pop("alt", "default-alt");
}
public String getAlt() {
return alt;
}
@Override
void processPositionalAttributes() {
String attr1 = pop("1", "size");
if (StringUtils.isNotBlank(attr1)) {
attrs.add(attr1);
}
}
@Override
void processAttributes() {
attributes.forEach((k, v) -> {
attrs.add(k + "=" + v);
});
}
@Override
String processAsciiDocContent() {
return "icon:" + alt + '[' + String.join(",", attrs) + ']';
}
}

View File

@@ -0,0 +1,64 @@
package io.github.swagger2markup.adoc.converter.internal;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.concurrent.atomic.AtomicReference;
import java.util.stream.Stream;
import static io.github.swagger2markup.adoc.converter.internal.Delimiters.*;
abstract class NodeAttributes {
public static final String TITLE = "title";
final Map<String, Object> attributes;
List<String> attrs = new ArrayList<>();
NodeAttributes(Map<String, Object> attributes) {
this.attributes = attributes;
}
public String pop(String... keys) {
AtomicReference<String> value = new AtomicReference<>("");
Stream.of(keys).forEach(key -> {
try {
String tmpValue = attributes.remove(key).toString();
if (null != tmpValue && !tmpValue.isEmpty() && value.get().isEmpty()) {
value.set(tmpValue);
}
} catch (NullPointerException ignored) {
}
});
return value.get();
}
String pop(String key) {
try {
String value = attributes.remove(key).toString();
if (null == value) {
value = "";
}
return value;
} catch (NullPointerException ignored) {
return "";
}
}
final public String toAsciiDocContent() {
processPositionalAttributes();
processAttributes();
return processAsciiDocContent();
}
abstract void processPositionalAttributes();
abstract void processAttributes();
String processAsciiDocContent() {
StringBuilder sb = new StringBuilder();
if (!attrs.isEmpty()) {
sb.append(ATTRIBUTES_BEGIN).append(String.join(",", attrs)).append(ATTRIBUTES_END).append(LINE_SEPARATOR);
}
return sb.toString();
}
}

View File

@@ -0,0 +1,63 @@
package io.github.swagger2markup.adoc.converter.internal;
import org.apache.commons.lang3.StringUtils;
import org.asciidoctor.ast.StructuralNode;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.ArrayList;
import java.util.List;
public class ParagraphAttributes extends NodeAttributes {
public static final String OPTION_SUFFIX = "-option";
private Logger logger = LoggerFactory.getLogger(getClass());
public ParagraphAttributes(StructuralNode node) {
super(node.getAttributes());
}
@Override
public void processPositionalAttributes() {
String attr1 = pop("1", "style");
if (StringUtils.isNotBlank(attr1)) {
attrs.add(attr1);
}
}
@Override
void processAttributes() {
String id = pop("id");
if (StringUtils.isNotBlank(id)) {
id = "#" + id;
}
String roles = String.join(".", pop("role").split(" "));
if (StringUtils.isNotBlank(roles)) {
roles = "." + roles;
}
StringBuilder options = new StringBuilder();
List<String> namedAttributes = new ArrayList<>();
attributes.forEach((k, v) -> {
if (k.equals(TITLE)) {
logger.debug("Skipping attribute: " + TITLE);
} else if (k.endsWith(OPTION_SUFFIX)) {
options.append('%').append(k.replace(OPTION_SUFFIX, ""));
} else if (null != v) {
if(v.toString().contains(" ") || v.toString().contains(",")) {
namedAttributes.add(k + "=\"" + v +"\"");
} else {
namedAttributes.add(k + "=" + v);
}
} else {
logger.warn("Don't know how to handle key: " + k);
}
});
String nonNamedAttributes = id + roles + options.toString();
if (StringUtils.isNotBlank(nonNamedAttributes)) {
attrs.add(nonNamedAttributes);
}
attrs.addAll(namedAttributes);
}
}

View File

@@ -0,0 +1,53 @@
package io.github.swagger2markup.adoc.converter.internal;
import org.apache.commons.lang3.StringUtils;
import org.asciidoctor.ast.Block;
import java.util.ArrayList;
import java.util.List;
import static io.github.swagger2markup.adoc.converter.internal.Delimiters.*;
public class SourceNode extends BlockListingNode {
private List<String> sourceAttrs = new ArrayList<>();
private final Block node;
public SourceNode(Block node) {
super(node);
this.node = node;
}
@Override
public void processPositionalAttributes() {
String source = pop("1", "style");
String language = pop("2", "language");
StringBuilder options = new StringBuilder();
List<String> toRemove = new ArrayList<>();
attributes.forEach((k, v) -> {
if (k.endsWith(OPTION_SUFFIX)) {
toRemove.add(k);
options.append('%').append(k.replace(OPTION_SUFFIX, ""));
}
});
toRemove.forEach(attributes::remove);
source += options.toString();
if (StringUtils.isNotBlank(source)) {
sourceAttrs.add(source);
}
if (StringUtils.isNotBlank(language)) {
sourceAttrs.add(language);
}
super.processPositionalAttributes();
}
@Override
public String processAsciiDocContent() {
StringBuilder sb = new StringBuilder();
attrsToString(sb, attrs);
attrsToString(sb, sourceAttrs);
sb.append(LINE_SEPARATOR).append(DELIMITER_BLOCK).append(LINE_SEPARATOR).append(node.getSource()).append(LINE_SEPARATOR).append(DELIMITER_BLOCK).append(LINE_SEPARATOR);
return sb.toString();
}
}

View File

@@ -0,0 +1,35 @@
package io.github.swagger2markup.adoc.converter.internal;
import org.apache.commons.lang3.StringUtils;
public enum Style {
ASCIIDOC("a"), EMPHASIS("e"), HEADER("h"), LITERAL("l"), MONOSPACED("m"), NONE("d"), STRONG("s"), VERSE("v");
String shortHand;
Style(String h) {
this.shortHand = h;
}
public static Style fromString(String text) {
if(StringUtils.isNotBlank(text)) {
for (Style s : Style.values()) {
if (s.shortHand.equalsIgnoreCase(text)) {
return s;
}
}
}
return null;
}
public static Style fromName(String text) {
if(StringUtils.isNotBlank(text)) {
return valueOf(text.toUpperCase());
}
return null;
}
public String getShortHand() {
return shortHand;
}
}

View File

@@ -0,0 +1,35 @@
package io.github.swagger2markup.adoc.converter.internal;
import org.apache.commons.lang3.StringUtils;
public enum TableCellHorizontalAlignment {
LEFT("<"), CENTER("^"), RIGHT(">");
String delimiter;
TableCellHorizontalAlignment(String s) {
this.delimiter = s;
}
public static TableCellHorizontalAlignment fromString(String text) {
if(StringUtils.isNotBlank(text)) {
for (TableCellHorizontalAlignment a : TableCellHorizontalAlignment.values()) {
if (a.delimiter.equalsIgnoreCase(text)) {
return a;
}
}
}
return null;
}
public static TableCellHorizontalAlignment fromName(String text) {
if(StringUtils.isNotBlank(text)) {
return valueOf(text.toUpperCase());
}
return null;
}
public String getDelimiter() {
return delimiter;
}
}

View File

@@ -0,0 +1,15 @@
package io.github.swagger2markup.adoc.converter.internal;
public class TableCellStyle {
public final TableCellHorizontalAlignment horizontalAlignment;
public final TableCellVerticalAlignment verticalAlignment;
public final Style style;
public final int width;
public TableCellStyle(TableCellHorizontalAlignment horizontalAlignment, TableCellVerticalAlignment verticalAlignment, Style style, int width) {
this.horizontalAlignment = horizontalAlignment;
this.verticalAlignment = verticalAlignment;
this.style = style;
this.width = width;
}
}

View File

@@ -0,0 +1,35 @@
package io.github.swagger2markup.adoc.converter.internal;
import org.apache.commons.lang3.StringUtils;
public enum TableCellVerticalAlignment {
TOP(".<"), MIDDLE(".^"), BOTTOM(".>");
String delimiter;
TableCellVerticalAlignment(String s) {
this.delimiter = s;
}
public static TableCellVerticalAlignment fromString(String text) {
if(StringUtils.isNotBlank(text)) {
for (TableCellVerticalAlignment a : TableCellVerticalAlignment.values()) {
if (a.delimiter.equalsIgnoreCase(text)) {
return a;
}
}
}
return null;
}
public static TableCellVerticalAlignment fromName(String text) {
if(StringUtils.isNotBlank(text)) {
return valueOf(text.toUpperCase());
}
return null;
}
public String getDelimiter() {
return delimiter;
}
}

View File

@@ -0,0 +1,15 @@
package io.github.swagger2markup.adoc.converter.internal;
import org.asciidoctor.ast.Table;
public class TableNode extends DelimitedBlockNode {
public TableNode(Table table) {
super(table);
}
@Override
void processAttributes() {
pop("colcount", "rowcount", "tablepcwidth");
super.processAttributes();
}
}

View File

@@ -0,0 +1 @@
io.github.swagger2markup.adoc.AsciiDocConverterRegistry

View File

@@ -0,0 +1,50 @@
package io.github.swagger2markup.adoc;
import org.apache.commons.io.IOUtils;
import org.asciidoctor.Asciidoctor;
import org.asciidoctor.OptionsBuilder;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;
import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.util.Arrays;
import static org.junit.Assert.*;
@RunWith(Parameterized.class)
public class AsciidocConverterTest {
private Asciidoctor asciidoctor = Asciidoctor.Factory.create();
@Parameterized.Parameters(name = "Run {index}: file={0}")
public static Iterable<?> data() {
return Arrays.asList(
"simple.adoc",
"arrows-and-boxes-example.ad",
"brokeninclude.asciidoc",
"changeattribute.adoc",
"chronicles-example.adoc",
"document-with-arrays.adoc"
);
}
@Parameterized.Parameter
public String asciidocFile;
@Test
public void converts_asciidoc_to_asciidoc() throws IOException {
//Given
String originalAsciiDoc = IOUtils.toString(getClass().getResourceAsStream("/asciidoc/original/" + asciidocFile), StandardCharsets.UTF_8);
String expectedAsciiDoc = IOUtils.toString(getClass().getResourceAsStream("/asciidoc/expected/" + asciidocFile), StandardCharsets.UTF_8);
//When
asciidoctor.javaConverterRegistry().register(AsciidocConverter.class, AsciidocConverter.NAME);
String result = asciidoctor.convert(originalAsciiDoc, OptionsBuilder.options().backend(AsciidocConverter.NAME).headerFooter(false).asMap());
//Then
assertEquals(expectedAsciiDoc, result);
}
}

View File

@@ -0,0 +1,34 @@
= Document Title
:tip-caption: Tip
:appendix-caption: Appendix
:appendix-refsig: Appendix
:toc-title: Table of Contents
:iconsdir: ./images/icons
:warning-caption: Warning
:figure-caption: Figure
:attribute-missing: skip
:section-refsig: Section
:toc-placement: auto
:important-caption: Important
:note-caption: Note
:stylesdir: .
:untitled-label: Untitled
:max-include-depth: 64
:caution-caption: Caution
:user-home: .
:max-attribute-value-size: 4096
:safe-mode-level: 20
:safe-mode-name: secure
:table-caption: Table
:part-refsig: Part
:authorcount: 0
:example-caption: Example
:version-label: Version
:last-update-label: Last updated
:doctype: article
:chapter-refsig: Chapter
:attribute-undefined: drop-line
[arrowsAndBoxes]
(User) > (Admin)

View File

@@ -0,0 +1,33 @@
= Title
:tip-caption: Tip
:appendix-caption: Appendix
:appendix-refsig: Appendix
:toc-title: Table of Contents
:iconsdir: ./images/icons
:warning-caption: Warning
:figure-caption: Figure
:attribute-missing: skip
:section-refsig: Section
:toc-placement: auto
:important-caption: Important
:note-caption: Note
:stylesdir: .
:untitled-label: Untitled
:max-include-depth: 64
:caution-caption: Caution
:user-home: .
:max-attribute-value-size: 4096
:safe-mode-level: 20
:safe-mode-name: secure
:table-caption: Table
:part-refsig: Part
:authorcount: 0
:example-caption: Example
:version-label: Version
:last-update-label: Last updated
:doctype: article
:chapter-refsig: Chapter
:attribute-undefined: drop-line
link:b.adoc[]

View File

@@ -0,0 +1,33 @@
= Document Title
:tip-caption: Tip
:appendix-caption: Appendix
:appendix-refsig: Appendix
:toc-title: Table of Contents
:iconsdir: ./images/icons
:warning-caption: Warning
:figure-caption: Figure
:attribute-missing: skip
:section-refsig: Section
:toc-placement: auto
:important-caption: Important
:note-caption: Note
:stylesdir: .
:untitled-label: Untitled
:max-include-depth: 64
:caution-caption: Caution
:user-home: .
:max-attribute-value-size: 4096
:safe-mode-level: 20
:safe-mode-name: secure
:table-caption: Table
:part-refsig: Part
:authorcount: 0
:example-caption: Example
:version-label: Version
:last-update-label: Last updated
:doctype: article
:chapter-refsig: Chapter
:attribute-undefined: drop-line
sample {content}

View File

@@ -0,0 +1,535 @@
= The Dangerous & _Thrilling_ Documentation Chronicles: Based on True Events
Kismet Caméléon; Lazarus het Draeke
v1.0, 2014-01-01
:tip-caption: Tip
:appendix-caption: Appendix
:toclevels: 3
:appendix-refsig: Appendix
:author_2: Lazarus het Draeke
:uri-stbernardusabt12: http://www.sintbernardus.be/stbernardusabt12.php?l=en
:authorinitials: KC
:author_1: Kismet Caméléon
:toc-title: Table of Contents
:iconsdir: ./images/icons
:author: Kismet Caméléon
:warning-caption: Warning
:figure-caption: Figure
:lastname: Caméléon
:attribute-missing: skip
:lastname_1: Caméléon
:section-refsig: Section
:uri-devoxx: https://devoxx.be
:lastname_2: het Draeke
:toc-placement: auto
:important-caption: Important
:authors: Kismet Caméléon, Lazarus het Draeke
:note-caption: Note
:firstname: Kismet
:stylesdir: .
:uri-devoxx-top-talks: https://www.youtube.com/watch?v=1OpAgZvYXLQ&amp;list=PLRsbF2sD7JVq7fv1GZGORShSUIae1ZAPy&amp;index=1
:untitled-label: Untitled
:description: This story chronicles the inexplicable hazards and vicious beasts a team must conquer and vanquish on their journey to discovering the true power of Open Source.
:max-include-depth: 64
:caution-caption: Caution
:listing-caption: Listing
:user-home: .
:max-attribute-value-size: 4096
:safe-mode-level: 20
:safe-mode-name: secure
:table-caption: Table
:part-refsig: Part
:firstname_1: Kismet
:authorcount: 2
:revdate: 2014-01-01
:example-caption: Example
:firstname_2: Lazarus
:version-label: Version
:revnumber: 1.0
:last-update-label: Last updated
:doctype: book
:chapter-refsig: Chapter
:uri-wolpertinger: http://en.wikipedia.org/wiki/Wolpertinger
:organization: Company Name
:authorinitials_1: KC
:authorinitials_2: Lh
:attribute-undefined: drop-line
[abstract]
{description}
[[_its_a_city_under_siege]]
== Its a City Under Siege
This journey begins one late Monday afternoon at {uri-devoxx}[((Devoxx))].
Our team needs coffee, _desperately_, but none of us dare open the theater doors...
During the {uri-devoxx-top-talks}[opening university session], a script-happy warlock inadvertently released a legion of Wolpertingers!
To leave now would mean *code dismemberment and certain death*.
Behold -> the horror!
.Wolpertinger, stuffed
[.left.thumb]
image::wolpertinger.jpg[Wolpertinger,link=http://en.wikipedia.org/wiki/Wolpertinger,pdfwidth=50%]
(((Wolpertinger)))
(((Ravenous Beast,Wolpertinger)))
You may not be familiar with these {uri-wolpertinger}[ravenous beasts].
Trust us, they'll eat your shorts and suck loops from your code.
In light of this danger, we've searched high and wide for the security crew's defensive operations manual.
We can't find it and the DefOps{empty}footnote:defops[DefOps is a portmanteau of "`defensive`" and "`operations`".] werewolves haven't returned from their rendezvous at Bier Central.
They've either eaten each other or fallen victim to the Wolpertingers roaming the streets of ((Antwerp)).
Quick, hit kbd:[Ctrl,Alt,Backspace] or select menu:File[Quit] and let's bail out of here!
WARNING: Working with DefOps{empty}footnote:defops[] werewolves leads to howling and trying to train aggressive regular expressions with Pavlovian reinforcement.
_Weak light from the hallway trickled across the theater, chased by a distant scream._
[[_rendezvous_point]]
=== Rendezvous Point
Come on, [[bier-central,Bier Central]]_Bier Central_, of course!
Did you have to ask?
If you beat me there, order me a {uri-stbernardusabt12}[St. Bernardus Abt 12].
Here's some &#x20ac;.
[[ravages]]
[#ravages]
== The Ravages of Writing
Crystalline XML tags relentlessly bombarded the theater.
.XML tags
[source,xml]
----
<author id="1">
<personname>
<firstname>Lazarus</firstname>
<surname>het Draeke</surname>
</personname>
</author>
----
Despite the assault, we continued our pursuit to draft a DefOps{empty}footnote:defops[] plan.
.DefOps Plan
====
Click btn:[Download Zip] to download the defensive operation plan bundle.
OMG!
Somebody please save us now!
I want my mum -- and an extra-large double macchiato, please.
====
Unfortunately, Lazarus and I had both come to the conclusion that we weren't going to get out of this without corrupted hardrives if we didn't locate caffeine within the next few hours.
[[_a_recipe_for_potion_that_will_ensure_you_win_the_hearts_of_developers]]
=== A Recipe for Potion That Will Ensure You Win the Hearts of Developers
This potion for a sample document contains the following ingredients, which are listed in a very random, chaotically nested order.
.Ingredients for Potion that Demystifies Documents
* all the headings
** syntax highlighted source code
*** non-syntax highlighted source code or just a listing block
* quote block
** verse block
*** table with some cell formatting
**** sequential paragraphs
***** admonition blocks, but use them sparingly
*** bullet list with nesting
** numbered list with nesting
** definition list
*** sidebar
* example block
** block image (no inline images)
*** inline formatting in a paragraph
**** two fresh Burdockian leaves
***** They must be harvested by the light of the teal moons.
Are you square?
[square]
* one
* two
* three
What is there to do?
* [x] Done
* [ ] Next
* Who's counting?
[[_searching_for_burdockian]]
==== Searching for Burdockian
.Steps for finding and preparing Burdockian leaves
. Locate dusty botany
.. Sneeze
... Sneeze some more
. Find section on Burdockian
.. Review its characteristics
... Take a picture of the diagram of its leaves
.... Don't rip out the picture like a troglodyte
..... Don't do it, I'm watching you
. Put on your hiking boots
. Freeze your butt off on the side of a mountain at midnight
Let's skip a few steps and start counting from 10.
[start=10]
. arabic (10)
.. loweralpha (a)
... lowerroman (i)
... lowerroman (ii)
... lowerroman (iii)
... lowerroman (iv)
.... upperalpha (A)
. arabic (11)
It's time for a top 5 list, made using the `reversed` option on an ordered list!
[%reversed]
. Stone Imperial Russian Stout
. Pliny the Elder
. Chimay Grande Réserve (Blue)
. St. Bernardus Abt 12
. Westvleteren 12 (XII)
How about a list with some terms?
* Fruits
Apple::::
The round fruit of a tree of the rose family, which typically has thin red or green skin and crisp flesh.
Yes, I said _flesh_.
Pear::::
A yellowish- or brownish-green edible fruit that is typically narrow at the stalk and wider toward the base, with sweet, slightly gritty flesh.
More flesh.
Mmmmm.
* Vegetables
Carrot::::
An orange-colored root eaten as a vegetable.
Beware, it's a favorite of the Wolpertinger.
[[_are_you_still_here]]
===== Are You Still Here?
.Move, move, move!
[CAUTION]
====
The Wolpertingers can smell your procrastination.
It's not their fault you can't find your boots.
====
[[_sigh]]
====== Sigh…
TIP: Your boots are in your closet.
[[_dawn_on_the_plateau]]
== Dawn on the Plateau
Lazarus was hanging from the bottom limb of a Burdockian tree, licking the bark.
[quote,Mark Tobey]
On pavements and the bark of trees I have found whole worlds.
"`If there are whole worlds on that bark, he just swallowed them,`" Kizmet replied.
[verse,The documentation attorneys]
____
No bark was harmed in the making of this potion.
We're not so sure about a couple ants though.
Nor those worlds...
Crap, I smell an injunction.
____
We'd retrieved the leaves, but we'd obviously lost our minds in the process.
[verse]
Roses are +++<span style="color: #FF0000">red</span>+++.
Violets are +++<span style="color: #0000FF">blue</span>+++__-ish__.
[[_words_seasoned_with_power]]
== Words Seasoned with Power
To _tame_ the [.wild]#wild# wolpertingers, we needed to build a *charm*.
But **ul**timate victory could only be won if we divined the *_true name_* of the __war__lock.
"`What kind of charm?`" Lazarus asked. "`An odoriferous one or a mineral one?`"
Kizmet shrugged. "`The note from Olaf's desk says '`wormwood and licorice,`' but these could be normal groceries for werewolves.`"
"`Well the H~2~O written on the security whiteboard could be part of a shopping list, but I don't think the local bodega also sells e = mc^2^,`" Lazarus replied.
"`Wait!`" Indigo plucked a small vial from her desk's top drawer and held it toward us.
The vial's label read '```e = mc^2^ *_the scent of science_* _smells like a genius_```'.
[[_can_i_get_some_code]]
=== Can I Get Some `Code`?
[%hardbreaks]
Sure.
Have a listing block.
[listing]
----
This is an example of a listing block.
The content inside is rendered as <pre> text.
----
But I'm not giving you any highlighting shazam just yet.
.What is a listing block?
Like literal blocks, the content in listing blocks is displayed exactly as you entered it.
Listing block content is rendered as `<pre>` text.
The `listing` style is applied to an element, such as a paragraph, by setting the `listing` attribute on that element.
Let's get our #((highlighting))# on!
<<<
Install Prawn:
[literal]
$ gem install prawn
Then create your first PDF document in Ruby!
.Generates a basic PDF document using Prawn
[source,ruby]
----
require 'prawn' # <1>
Prawn::Document.generate 'output.pdf' do # <3>
text 'Hello, World!' # <2>
end
----
<1> Imports Prawn library
<3> Adds text “Hello, World!” to first page
<2> Writes PDF to [file]_output.pdf_ after executing all statements
How about some source code that styles code? So meta!
[source,css]
----
code {
padding: 2px 4px;
font-size: 90%;
font-weight: normal;
color: #c7254e;
white-space: nowrap !important;
background-color: #f9f2f4;
border-radius: 4px;
}
----
Where could we go without some Java(TM)?
Naturally, some autosizing is necessary.
[source%autofit,java]
----
package org.javaee7.cdi.events;
import javax.annotation.PostConstruct;
import javax.enterprise.context.SessionScoped;
import javax.enterprise.event.Observes;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import javax.ws.rs.*;
/**
* This session-scoped bean receives greeting strings from the event bus
* and provides access to the collection of these greetings via a REST API.
*
* @author The Duke
* @since 1.0
*/
@SessionScoped
public class GreetingReceiver implements EventReceiver, Serializable {
private List<String> greetings;
@PostConstruct
void init() {
this.greetings = new ArrayList<String>();
}
void receive(@Observes String greet) {
this.greetings.add(greet);
}
@GET
@Produces("application/json")
public List<String> listAll(@QueryParam("start") Integer start, @QueryParam("max") Integer max) {
int numGreetings = this.greetings.size();
if (numGreetings == 0 || max == 0) {
return Collections.<String>emptyList();
}
if (start == null) {
start = 0;
}
if (max == null) {
max = numGreetings;
}
return this.greetings.subList(start, Math.min(max + start, numGreetings));
}
}
----
We already showed you an XML example in <<ravages>>, a language we often rant about over beers at <<bier-central>>.
I'll trade you a little table for some of that bark.
[table%header,grid=rows,cols=4,frame=topbot]
|===
<.<|Column 1
<.<|Column 2
<.<|Column 3
<.<|Column 4
^.<m|Prefix `{vbar}` with `{caret}` to center content horizontally within the cell.
<.>|Prefix `{vbar}` with a `.` and `>` to align content to the bottom of the cell.
^.^|Prefix `{vbar}` with a `^`, `.`, and `^` to place content in the middle of the cell.
>.<|Prefix `{vbar}` with `>` to align content to the right horizontally within the cell.
4+^.<e|This content spans all four columns (`4{plus}`) and is centered horizontally (`{caret}`) within the cell.
|===
Wait.
What?
Where is this story going?
`<span>`:::
an html tag that makes me crazy
align:::
something I never get going in the right direction.
Also has to do with my poor verbal communication skills
float:::
style:::
don't make me laugh
Does anyone have the time?
Tg lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.
Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat.
Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur.
Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborumj.
[[_keeping_it_together]]
== Keeping It Together
On this page we have nested "`keep together`" logic.
The combined block will be shifted to the next page if there isn't room available on this one.
[verse]
First,
we
need
to
waste
several
lines
using
a
verse
to
push
the
next
block
to
its
breaking
point.
.What happens if there is both a field and a method with the same name?
[NOTE]
====
Back to the previous example, suppose that we have both a field and a method with the same name, as in:
.Java class with a field and method that share the same name
[source,java]
----
public class Foo {
public String bar;
public String bar() {
return bar;
}
}
----
*Golo resolves methods first, fields last.*
Hence, the following Golo code will resolve the `bar()` method, not the `bar` field:
.Golo picks the method over the field with the same name
[source,golo]
----
let foo = Foo()
foo: bar("baz") # <1>
println(foo: bar()) # <2>
----
<1> Writes the field
<2> Calls the `bar()` method
====
<<<
Here's a preview of how each heading level is rendered.
[discrete]
= Heading 1 (Level 0)
filler content
[discrete]
== Heading 2 (Level 1)
filler content
[discrete]
=== Heading 3 (Level 2)
filler content
[discrete]
==== Heading 4 (Level 3)
filler content
[discrete]
===== Heading 5 (Level 4)
filler content
[discrete]
====== Heading 6 (Level 5)
filler content
'''
--
Here's some content inside an open block.
--
[[_credits]]
[appendix]
== Credits
.Brought to you with icon:heart[set=fas,role=love] by OpenDevise
[table%footer%header,grid=rows,width=75%,cols="2,2s,^4",frame=topbot]
|===
<.<|Name
<.<|Title
.<|Alias
<.<|Sarah White
<.<|President
.<|http://twitter.com/carbonfray[@carbonfray]
<.<|Dan Allen
<.<|Vice President
.<|http://twitter.com/mojavelinux[@mojavelinux]
3+^.<e|Powered by Open Source
|===
[[_index]]
[index]
== Index

View File

@@ -0,0 +1,48 @@
= Asciidoctor Changelog
:tip-caption: Tip
:appendix-caption: Appendix
:appendix-refsig: Appendix
:toc-title: Table of Contents
:iconsdir: ./images/icons
:warning-caption: Warning
:figure-caption: Figure
:attribute-missing: skip
:section-refsig: Section
:toc-placement: auto
:important-caption: Important
:note-caption: Note
:stylesdir: .
:untitled-label: Untitled
:max-include-depth: 64
:caution-caption: Caution
:user-home: .
:max-attribute-value-size: 4096
:safe-mode-level: 20
:safe-mode-name: secure
:table-caption: Table
:part-refsig: Part
:authorcount: 0
:example-caption: Example
:version-label: Version
:last-update-label: Last updated
:doctype: article
:chapter-refsig: Chapter
:attribute-undefined: drop-line
http://asciidoctor.org[Asciidoctor] is an open source text processor and publishing toolchain for converting http://asciidoctor.org[AsciiDoc] markup into HTML, DocBook and custom formats.
This document provides a high-level view of the changes introduced in Asciidoctor by release.
For a detailed view of what has changed, refer to the https://github.com/asciidoctor/asciidoctor/commits/master[commit history] on GitHub.
[[_0_1_4_2013_09_05_mojavelinux]]
== 0.1.4 (2013-09-05) - @mojavelinux
Performance::
* 15% increase in speed compared to 0.1.3
Enhancements::
* updated xref inline macro to support inter-document references (#417)
Bug Fixes::
* lowercase attribute names passed to API (#508)

View File

@@ -0,0 +1,77 @@
= Simple Inventory API
You <you@your-company.com>
v1.0.0
:tip-caption: Tip
:appendix-caption: Appendix
:appendix-refsig: Appendix
:authorinitials: Y
:toc-title: Table of Contents
:iconsdir: ./images/icons
:author: You
:warning-caption: Warning
:figure-caption: Figure
:attribute-missing: skip
:section-refsig: Section
:toc-placement: auto
:important-caption: Important
:authors: You
:note-caption: Note
:firstname: You
:stylesdir: .
:untitled-label: Untitled
:max-include-depth: 64
:caution-caption: Caution
:user-home: .
:max-attribute-value-size: 4096
:safe-mode-level: 20
:safe-mode-name: secure
:table-caption: Table
:part-refsig: Part
:authorcount: 1
:example-caption: Example
:email: you@your-company.com
:version-label: Version
:revnumber: 1.0.0
:last-update-label: Last updated
:doctype: article
:chapter-refsig: Chapter
:attribute-undefined: drop-line
[[_overview]]
== Overview
This is a simple API
[[_license]]
=== License
[%hardbreaks]
http://www.apache.org/licenses/LICENSE-2.0.html[Apache 2.0]
[[_servers]]
== Servers
* https://{username}.gigantic-server.com:{port}/{basePath}
+
The production API server
+
.Variables
username::
*this* __value__ is assigned by the service provider, in this example `gigantic-server.com`
Possible Values::
Any
Default::
demo
port::
Possible Values::
- 8443
- 443
Default::
8443
basePath::
Possible Values::
Any
Default::
v2

View File

@@ -0,0 +1,4 @@
= Document Title
[arrowsAndBoxes]
(User) > (Admin)

View File

@@ -0,0 +1,3 @@
= Title
include::b.adoc[]

Some files were not shown because too many files have changed in this diff Show More