Skip to content

Commit

Permalink
SwiftGen#489 - Added option to generate Objective-C compatible String…
Browse files Browse the repository at this point in the history
…s Swift code
  • Loading branch information
lukaskukacka committed Sep 28, 2018
1 parent 07583c7 commit 68cb890
Show file tree
Hide file tree
Showing 7 changed files with 282 additions and 5 deletions.
3 changes: 3 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,9 @@ Read the [SwiftGen 6.0 Migration Guide](https://github.com/SwiftGen/SwiftGen/blo
* Updated the playgrounds with the new `json`, `plist` and `yaml` commands, and updated the other pages to reflect the template changes.
[David Jennes](https://github.com/djbe)
[#495](https://github.com/SwiftGen/SwiftGen/pull/495)
* Added option to generate Objective-C compatible Strings Swift code using `objcCompatible` parameter.
[Lukas Kukacka](https://github.com/lukaskukacka)
[#489](https://github.com/SwiftGen/SwiftGen/issues/489)

### Internal Changes

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
// swiftlint:disable all
// Generated using SwiftGen, by O.Halligon — https://github.com/SwiftGen/SwiftGen

import Foundation

// swiftlint:disable superfluous_disable_command
// swiftlint:disable file_length

// MARK: - Strings

// swiftlint:disable function_parameter_count identifier_name line_length type_body_length
@objcMembers
internal final class XCTLoc: NSObject {
/// Some alert body there
internal static let alertMessage = XCTLoc.tr("Localizable", "alert_message")
/// Title of the alert
internal static let alertTitle = XCTLoc.tr("Localizable", "alert_title")
/// These are %3$@'s %1$d %2$@.
internal static func objectOwnership(_ p1: Int, _ p2: String, _ p3: String) -> String {
return XCTLoc.tr("Localizable", "ObjectOwnership", p1, p2, p3)
}
/// Hello, my name is %@ and I'm %d
internal static func `private`(_ p1: String, _ p2: Int) -> String {
return XCTLoc.tr("Localizable", "private", p1, p2)
}
/// You have %d apples
internal static func applesCount(_ p1: Int) -> String {
return XCTLoc.tr("Localizable", "apples.count", p1)
}
/// Those %d bananas belong to %@.
internal static func bananasOwner(_ p1: Int, _ p2: String) -> String {
return XCTLoc.tr("Localizable", "bananas.owner", p1, p2)
}
/// Some Reserved Keyword there
internal static let settingsNavigationBarSelf = XCTLoc.tr("Localizable", "settings.navigation-bar.self")
/// DeepSettings
internal static let settingsNavigationBarTitleDeeperThanWeCanHandleNoReallyThisIsDeep = XCTLoc.tr("Localizable", "settings.navigation-bar.title.deeper.than.we.can.handle.no.really.this.is.deep")
/// Settings
internal static let settingsNavigationBarTitleEvenDeeper = XCTLoc.tr("Localizable", "settings.navigation-bar.title.even.deeper")
/// Here you can change some user profile settings.
internal static let settingsUserProfileSectionFooterText = XCTLoc.tr("Localizable", "settings.user_profile_section.footer_text")
/// User Profile Settings
internal static let settingsUserProfileSectionHEADERTITLE = XCTLoc.tr("Localizable", "settings.user_profile_section.HEADER_TITLE")
}
// swiftlint:enable function_parameter_count identifier_name line_length type_body_length

// MARK: - Implementation Details

extension XCTLoc {
private static func tr(_ table: String, _ key: String, _ args: CVarArg...) -> String {
let format = NSLocalizedString(key, tableName: table, bundle: Bundle(for: BundleToken.self), comment: "")
return String(format: format, locale: Locale.current, arguments: args)
}
}

private final class BundleToken {}
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
// swiftlint:disable all
// Generated using SwiftGen, by O.Halligon — https://github.com/SwiftGen/SwiftGen

import Foundation

// swiftlint:disable superfluous_disable_command
// swiftlint:disable file_length

// MARK: - Strings

// swiftlint:disable function_parameter_count identifier_name line_length type_body_length
@objcMembers
internal final class L10n: NSObject {
internal static let alertMessage = L10n.tr("Localizable", "alert_message")
internal static let alertTitle = L10n.tr("Localizable", "alert_title")
internal static func objectOwnership(_ p1: Int, _ p2: String, _ p3: String) -> String {
return L10n.tr("Localizable", "ObjectOwnership", p1, p2, p3)
}
internal static func `private`(_ p1: String, _ p2: Int) -> String {
return L10n.tr("Localizable", "private", p1, p2)
}
internal static func applesCount(_ p1: Int) -> String {
return L10n.tr("Localizable", "apples.count", p1)
}
internal static func bananasOwner(_ p1: Int, _ p2: String) -> String {
return L10n.tr("Localizable", "bananas.owner", p1, p2)
}
internal static let settingsNavigationBarSelf = L10n.tr("Localizable", "settings.navigation-bar.self")
internal static let settingsNavigationBarTitleDeeperThanWeCanHandleNoReallyThisIsDeep = L10n.tr("Localizable", "settings.navigation-bar.title.deeper.than.we.can.handle.no.really.this.is.deep")
internal static let settingsNavigationBarTitleEvenDeeper = L10n.tr("Localizable", "settings.navigation-bar.title.even.deeper")
internal static let settingsUserProfileSectionFooterText = L10n.tr("Localizable", "settings.user_profile_section.footer_text")
internal static let settingsUserProfileSectionHEADERTITLE = L10n.tr("Localizable", "settings.user_profile_section.HEADER_TITLE")
}
// swiftlint:enable function_parameter_count identifier_name line_length type_body_length

// MARK: - Implementation Details

extension L10n {
private static func tr(_ table: String, _ key: String, _ args: CVarArg...) -> String {
let format = NSLocalizedString(key, tableName: table, bundle: Bundle(for: BundleToken.self), comment: "")
return String(format: format, locale: Locale.current, arguments: args)
}
}

private final class BundleToken {}
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
// swiftlint:disable all
// Generated using SwiftGen, by O.Halligon — https://github.com/SwiftGen/SwiftGen

import Foundation

// swiftlint:disable superfluous_disable_command
// swiftlint:disable file_length

// MARK: - Strings

// swiftlint:disable function_parameter_count identifier_name line_length type_body_length
@objcMembers
public final class L10n: NSObject {
/// Some alert body there
public static let alertMessage = L10n.tr("Localizable", "alert_message")
/// Title of the alert
public static let alertTitle = L10n.tr("Localizable", "alert_title")
/// These are %3$@'s %1$d %2$@.
public static func objectOwnership(_ p1: Int, _ p2: String, _ p3: String) -> String {
return L10n.tr("Localizable", "ObjectOwnership", p1, p2, p3)
}
/// Hello, my name is %@ and I'm %d
public static func `private`(_ p1: String, _ p2: Int) -> String {
return L10n.tr("Localizable", "private", p1, p2)
}
/// You have %d apples
public static func applesCount(_ p1: Int) -> String {
return L10n.tr("Localizable", "apples.count", p1)
}
/// Those %d bananas belong to %@.
public static func bananasOwner(_ p1: Int, _ p2: String) -> String {
return L10n.tr("Localizable", "bananas.owner", p1, p2)
}
/// Some Reserved Keyword there
public static let settingsNavigationBarSelf = L10n.tr("Localizable", "settings.navigation-bar.self")
/// DeepSettings
public static let settingsNavigationBarTitleDeeperThanWeCanHandleNoReallyThisIsDeep = L10n.tr("Localizable", "settings.navigation-bar.title.deeper.than.we.can.handle.no.really.this.is.deep")
/// Settings
public static let settingsNavigationBarTitleEvenDeeper = L10n.tr("Localizable", "settings.navigation-bar.title.even.deeper")
/// Here you can change some user profile settings.
public static let settingsUserProfileSectionFooterText = L10n.tr("Localizable", "settings.user_profile_section.footer_text")
/// User Profile Settings
public static let settingsUserProfileSectionHEADERTITLE = L10n.tr("Localizable", "settings.user_profile_section.HEADER_TITLE")
}
// swiftlint:enable function_parameter_count identifier_name line_length type_body_length

// MARK: - Implementation Details

extension L10n {
private static func tr(_ table: String, _ key: String, _ args: CVarArg...) -> String {
let format = NSLocalizedString(key, tableName: table, bundle: Bundle(for: BundleToken.self), comment: "")
return String(format: format, locale: Locale.current, arguments: args)
}
}

private final class BundleToken {}
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
// swiftlint:disable all
// Generated using SwiftGen, by O.Halligon — https://github.com/SwiftGen/SwiftGen

import Foundation

// swiftlint:disable superfluous_disable_command
// swiftlint:disable file_length

// MARK: - Strings

// swiftlint:disable function_parameter_count identifier_name line_length type_body_length
@objcMembers
internal final class L10n: NSObject {
@objcMembers @objc(L10nLocalizable)
internal final class Localizable: NSObject {
/// Some alert body there
internal static let alertMessage = L10n.tr("Localizable", "alert_message")
/// Title of the alert
internal static let alertTitle = L10n.tr("Localizable", "alert_title")
/// These are %3$@'s %1$d %2$@.
internal static func objectOwnership(_ p1: Int, _ p2: String, _ p3: String) -> String {
return L10n.tr("Localizable", "ObjectOwnership", p1, p2, p3)
}
/// Hello, my name is %@ and I'm %d
internal static func `private`(_ p1: String, _ p2: Int) -> String {
return L10n.tr("Localizable", "private", p1, p2)
}
/// You have %d apples
internal static func applesCount(_ p1: Int) -> String {
return L10n.tr("Localizable", "apples.count", p1)
}
/// Those %d bananas belong to %@.
internal static func bananasOwner(_ p1: Int, _ p2: String) -> String {
return L10n.tr("Localizable", "bananas.owner", p1, p2)
}
/// Some Reserved Keyword there
internal static let settingsNavigationBarSelf = L10n.tr("Localizable", "settings.navigation-bar.self")
/// DeepSettings
internal static let settingsNavigationBarTitleDeeperThanWeCanHandleNoReallyThisIsDeep = L10n.tr("Localizable", "settings.navigation-bar.title.deeper.than.we.can.handle.no.really.this.is.deep")
/// Settings
internal static let settingsNavigationBarTitleEvenDeeper = L10n.tr("Localizable", "settings.navigation-bar.title.even.deeper")
/// Here you can change some user profile settings.
internal static let settingsUserProfileSectionFooterText = L10n.tr("Localizable", "settings.user_profile_section.footer_text")
/// User Profile Settings
internal static let settingsUserProfileSectionHEADERTITLE = L10n.tr("Localizable", "settings.user_profile_section.HEADER_TITLE")
}
@objcMembers @objc(L10nLocMultiline)
internal final class LocMultiline: NSObject {
/// multi\nline
internal static let multiline = L10n.tr("LocMultiline", "MULTILINE")
/// test
internal static let multiLineNKey = L10n.tr("LocMultiline", "multiLine\nKey")
/// another\nmulti\n line
internal static let multiline2 = L10n.tr("LocMultiline", "MULTILINE2")
/// single line
internal static let singleline = L10n.tr("LocMultiline", "SINGLELINE")
/// another single line
internal static let singleline2 = L10n.tr("LocMultiline", "SINGLELINE2")
}
}
// swiftlint:enable function_parameter_count identifier_name line_length type_body_length

// MARK: - Implementation Details

extension L10n {
private static func tr(_ table: String, _ key: String, _ args: CVarArg...) -> String {
let format = NSLocalizedString(key, tableName: table, bundle: Bundle(for: BundleToken.self), comment: "")
return String(format: format, locale: Locale.current, arguments: args)
}
}

private final class BundleToken {}
34 changes: 34 additions & 0 deletions Tests/TemplatesTests/StringsTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,33 @@ class StringsTests: XCTestCase {
]
}

let flatSwiftObjCCompatibleVariations: VariationGenerator = { name, context in
switch name {
case "empty":
return [(context: context, suffix: "")]
case "multiple":
return [
(context: try StencilContext.enrich(context: context,
parameters: ["objcCompatible"]),
suffix: "-objc-compatible")
]
default:
break
}

return [
(context: try StencilContext.enrich(context: context,
parameters: ["objcCompatible", "enumName=XCTLoc"]),
suffix: "-objc-compatible-customname"),
(context: try StencilContext.enrich(context: context,
parameters: ["objcCompatible", "noComments"]),
suffix: "-objc-compatible-no-comments"),
(context: try StencilContext.enrich(context: context,
parameters: ["objcCompatible", "publicAccess"]),
suffix: "-objc-compatible-publicAccess")
]
}

func testFlatSwift3() {
test(template: "flat-swift3",
contextNames: Contexts.all,
Expand All @@ -45,6 +72,13 @@ class StringsTests: XCTestCase {
contextVariations: variations)
}

func testFlatSwift4ObjcCompatible() {
test(template: "flat-swift4",
contextNames: Contexts.all,
directory: .strings,
contextVariations: flatSwiftObjCCompatibleVariations)
}

func testStructuredSwift3() {
test(template: "structured-swift3",
contextNames: Contexts.all,
Expand Down
21 changes: 16 additions & 5 deletions templates/strings/flat-swift4.stencil
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@

{% if tables.count > 0 %}
{% set accessModifier %}{% if param.publicAccess %}public{% else %}internal{% endif %}{% endset %}
{% set rootTypeName %}{{param.enumName|default:"L10n"}}{% endset %}
import Foundation

// swiftlint:disable superfluous_disable_command
Expand All @@ -27,22 +28,32 @@ import Foundation
{% endif %}
{% if string.types %}
{{accessModifier}} static func {{string.key|swiftIdentifier:"pretty"|lowerFirstWord|escapeReservedKeywords}}({% call parametersBlock string.types %}) -> String {
return {{enumName}}.tr("{{table}}", "{{string.key}}", {% call argumentsBlock string.types %})
return {{rootTypeName}}.tr("{{table}}", "{{string.key}}", {% call argumentsBlock string.types %})
}
{% else %}
{{accessModifier}} static let {{string.key|swiftIdentifier:"pretty"|lowerFirstWord|escapeReservedKeywords}} = {{enumName}}.tr("{{table}}", "{{string.key}}")
{{accessModifier}} static let {{string.key|swiftIdentifier:"pretty"|lowerFirstWord|escapeReservedKeywords}} = {{rootTypeName}}.tr("{{table}}", "{{string.key}}")
{% endif %}
{% endfor %}
{% for child in item.children %}
{% call recursiveBlock table child %}
{% endfor %}
{% endmacro %}
// swiftlint:disable function_parameter_count identifier_name line_length type_body_length
{% set enumName %}{{param.enumName|default:"L10n"}}{% endset %}
{{accessModifier}} enum {{enumName}} {
{% if param.objcCompatible %}
@objcMembers
{{accessModifier}} final class {{rootTypeName}}: NSObject {
{% else %}
{{accessModifier}} enum {{rootTypeName}} {
{% endif %}
{% if tables.count > 1 %}
{% for table in tables %}
{% set typeName %}{{table.name|swiftIdentifier:"pretty"|escapeReservedKeywords}}{% endset %}
{% if param.objcCompatible %}
@objcMembers @objc({{rootTypeName}}{{typeName}})
{{accessModifier}} final class {{typeName}}: NSObject {
{% else %}
{{accessModifier}} enum {{table.name|swiftIdentifier:"pretty"|escapeReservedKeywords}} {
{% endif %}
{% filter indent:2 %}{% call recursiveBlock table.name table.levels %}{% endfilter %}
}
{% endfor %}
Expand All @@ -54,7 +65,7 @@ import Foundation

// MARK: - Implementation Details

extension {{enumName}} {
extension {{rootTypeName}} {
private static func tr(_ table: String, _ key: String) -> String {
return NSLocalizedString(key, tableName: table, bundle: Bundle(for: BundleToken.self), comment: "")
}
Expand Down

0 comments on commit 68cb890

Please sign in to comment.