Coder Social home page Coder Social logo

fleshgrinder / kotlin-case-format Goto Github PK

View Code? Open in Web Editor NEW
13.0 1.0 2.0 243 KB

String extension functions to convert between various case formats (camelCase, dash-case, …)

License: The Unlicense

Kotlin 100.00%
kotlin kotlin-jvm kotlin-library string-formatter camelcase-to-snakecase

kotlin-case-format's Introduction

Kotlin Case Format

Maven Central GitHub CI Workflow Code Coverage

Kotlin Case Format provides string extension functions to convert between various case formats (camelCase, dash-case, snake_case, …).

Installation

Go to Maven Central where you find the latest release and the code required for your dependency management tool.

Project Info

kotlin-case-format's People

Contributors

fleshgrinder avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar

Forkers

qwwdfsad isgasho

kotlin-case-format's Issues

Improve Performance

The current implementation is nicely DRY, but it is not the fastest possible implementation. We always create an auxiliary array for Chars that should be ignored, at the same time this feature is seldomly used, and we are thus only producing garbage. The big when switching over the ranges is also terribly inefficient, compared to a possible jump table. These functions might be used in hot paths of applications, and should thus be fast.

This is a small isolated project to allow exactly such optimizations, because the possible code duplication that may be introduced by possible optimizations can easily be kept maintainable.

Add Validation Functions

It would be great to have functions with which it is possible to verify if a given string is in an expected case format, or not. These functions can then be used with Kotlin's require and check functions as needed.

public fun String.isUpperCaseFormat(separator: Char, vararg ignore: Char): Boolean
public fun String.isUpperCamelCase(vararg ignore: Char): Boolean
public fun String.isUpperDashCase(vararg ignore: Char): Boolean
public fun String.isUpperSnakeCase(vararg ignore: Char): Boolean

public fun String.isLowerCaseFormat(separator: Char, vararg ignore: Char): Boolean
public fun String.isLowerCamelCase(vararg ignore: Char): Boolean
public fun String.isLowerDashCase(vararg ignore: Char): Boolean
public fun String.isLowerSnakeCase(vararg ignore: Char): Boolean

Strict Camel Case Validation

#1 follow up and in light of #7 regarding the isLowerCamelCase and isUpperCamelCase functions, and potential strict variations isLowerCamelCaseStrict and isUpperCamelCaseStrict where said functions require proper capitalization. Proper would be defined in terms of round trip safeness, and no other limitations need to be imposed (e.g. the c2 has a much stricter definition of camel case, but the camel case we talk about is called BumpyCase there).

Extend CharSequence instead of String

CharSequence is defined in all supported platform, and the functions only require the ability to access the individual Chars, and nothing from String, hence, it makes perfect sense to extend CharSequence instead of String. This will also allow users to define their own types that can be converted, since CharSequence can be implemented by user classes, whereas String cannot.

Change Package to com.fleshgrinder.kotlin

The current package is com.fleshgrinder.extensions.kotlin which makes little sense, because what is com.fleshgrinder.extensions supposed to contain? The idea back then was to collect all kinds of extensions under this group, but no language other than Kotlin (in the JVM world) even has support for that.

A possible alternative package that actually makes sense would be com.fleshgrinder.kotlin.text since String is in kotlin.text. However, there really is no need to match the package of Kotlin, since nobody ever sees that package anyways. Instead we should keep it simple and just go for the obvious choice: com.fleshgrinder.kotlin

We have to maintain backwards compatibility for at least one release and give people a chance to notice the move. Hence, all existing declarations must continue to exist, but with a deprecation that has a replaceWith that automatically fixes the import.

Handling of Abbreviations and Acronyms

Abbreviations and acronyms are dirty business with both lower and upper camel case. Currently the library is doing a perfect job at dealing with them and is too strict in the transformation logic. Here are a few examples:

transform actual expected
"HTTPException".toLowerCamelCase() httpexception httpException
"HTTPException".toUpperCamelCase() Httpexception HttpException
"HTTPException".toLowerDashCase() httpexception http-exception
"HTTPException".toUpperDashCase() HTTPEXCEPTION HTTP-EXCEPTION
"HTTPException".toLowerSnakeCase() httpexception http_exception
"HTTPException".toUpperSnakeCase() HTTPEXCEPTION HTTP_EXCEPTION

There are obviously cases where it becomes impossible to translate these things, this is exactly the reason why people should always treat any abbreviation or acronym like any normal word. This parseDBMXMLFromIPAddress is from Wikipedia and is always going to be transformed incorrectly. However, the following should work as expected.

transform actual expected
"NonlinearXWave".toLowerCamelCase() nonlinearXwave nonlinearXWave
"NonlinearXWave".toUpperCamelCase() NonlinearXwave NonlinearXWave
"NonlinearXWave".toLowerDashCase() nonlinear-xwave nonlinear-x-wave
"NonlinearXWave".toUpperDashCase() NONLINEAR-XWAVE NONLINEAR-X-WAVE
"NonlinearXWave".toLowerSnakeCase() nonlinear_xwave nonlinear_x_wave
"NonlinearXWave".toUpperSnakeCase() NONLINEAR_XWAVE NONLINEAR_X_WAVE

I think that this is doable by treating the last uppercase letter as the beginning of a new word. This is most definitely going to break some other inputs, but it should produce the desired output at least for those inputs I can think of. I am not sure yet how this can be done in any non-camel case format, simply because they usually ignore case altogether. Converting to camel first to then convert to the target seems very wasteful …

It definitely makes sense to look at some other case format libraries, not only JVM, but also other languages. Maybe someone already had a good idea on how to deal with this. Or maybe it's just a fool's errand?

Reuse Existing StringBuilder

All functions construct their own StringBuilder instance, it would be great if users can pass an existing one, in case they use these functions as part of building another, bigger string.

Obviously it would be best if it would be possible to integrate seamlessly with functions like buildString in a way that users do not even have to pass in anything. However, this is impossible until we have multiple receiver support in Kotlin. But, we can add extension functions to StringBuilder instead that are almost as awesome. 😎

public fun StringBuilder.appendUpperCaseFormat(value: String, separator: Char, vararg ignore: Char): StringBuilder
public fun StringBuilder.appendUpperCamelCase(value: String, vararg ignore: Char): StringBuilder
public fun StringBuilder.appendUpperDashCase(value: String, vararg ignore: Char): StringBuilder
public fun StringBuilder.appendUpperSnakeCase(value: String, vararg ignore: Char): StringBuilder

public fun StringBuilder.appendLowerCaseFormat(value: String, separator: Char, vararg ignore: Char): StringBuilder
public fun StringBuilder.appendLowerCamelCase(value: String, vararg ignore: Char): StringBuilder
public fun StringBuilder.appendLowerDashCase(value: String, vararg ignore: Char): StringBuilder
public fun StringBuilder.appendLowerSnakeCase(value: String, vararg ignore: Char): StringBuilder

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.