diff --git a/convert.go b/convert.go index 496f28c..3686780 100644 --- a/convert.go +++ b/convert.go @@ -10,15 +10,14 @@ import ( "unicode/utf8" ) -// ToCamelCase can convert all lower case characters behind underscores -// to upper case character. -// Underscore character will be removed in result except following cases. -// * More than 1 underscore. -// "a__b" => "A_B" -// * At the beginning of string. -// "_a" => "_A" -// * At the end of string. -// "ab_" => "Ab_" +// ToCamelCase is to convert words separated by space, underscore and hyphen to camel case. +// +// Some samples. +// "some_words" => "SomeWords" +// "http_server" => "HttpServer" +// "no_https" => "NoHttps" +// "_complex__case_" => "_Complex_Case_" +// "some words" => "SomeWords" func ToCamelCase(str string) string { if len(str) == 0 { return "" @@ -28,12 +27,12 @@ func ToCamelCase(str string) string { var r0, r1 rune var size int - // leading '_' will appear in output. + // leading connector will appear in output. for len(str) > 0 { r0, size = utf8.DecodeRuneInString(str) str = str[size:] - if r0 != '_' { + if !isConnector(r0) { r0 = unicode.ToUpper(r0) break } @@ -55,18 +54,15 @@ func ToCamelCase(str string) string { r0, size = utf8.DecodeRuneInString(str) str = str[size:] - if r1 == '_' && r0 == '_' { + if isConnector(r0) && isConnector(r1) { buf.WriteRune(r1) continue } - if r1 == '_' { + if isConnector(r1) { r0 = unicode.ToUpper(r0) } else { r0 = unicode.ToLower(r0) - } - - if r1 != '_' { buf.WriteRune(r1) } } @@ -164,7 +160,7 @@ func camelCaseToLowerCase(str string, connector rune) string { } if !unicode.IsUpper(r0) { - if r0 == '_' || r0 == ' ' || r0 == '-' { + if isConnector(r0) { r0 = connector buf.WriteRune(unicode.ToLower(r1)) @@ -198,7 +194,7 @@ func camelCaseToLowerCase(str string, connector rune) string { buf.WriteRune(r0) default: - if r0 == ' ' || r0 == '-' || r0 == '_' { + if isConnector(r0) { r0 = connector } @@ -209,6 +205,10 @@ func camelCaseToLowerCase(str string, connector rune) string { return buf.String() } +func isConnector(r rune) bool { + return r == '-' || r == '_' || unicode.IsSpace(r) +} + // SwapCase will swap characters case from upper to lower or lower to upper. func SwapCase(str string) string { var r rune diff --git a/convert_test.go b/convert_test.go index fbf0847..33222a1 100644 --- a/convert_test.go +++ b/convert_test.go @@ -31,6 +31,7 @@ func TestToSnakeCaseAndToKebabCase(t *testing.T) { " sentence case ": "__sentence_case__", " Mixed-hyphen case _and SENTENCE_case and UPPER-case": "_mixed_hyphen_case__and_sentence_case_and_upper_case", + "FROM CamelCase to snake/kebab-case": "from_camel_case_to_snake/kebab_case", "": "", "Abc\uFFFDE\uFFFDf\uFFFDd\uFFFD2\uFFFD00Z\uFFFDZZ\uFFFDZZ": "abc\uFFFD_e\uFFFDf\uFFFDd\uFFFD_2\uFFFD_00z\uFFFD_zz\uFFFD_zz", @@ -51,12 +52,15 @@ func TestToCamelCase(t *testing.T) { "_camel_case": "_CamelCase", "no_https": "NoHttps", "_complex__case_": "_Complex_Case_", + " complex -case ": " Complex Case ", "all": "All", "GOLANG_IS_GREAT": "GolangIsGreat", "GOLANG": "Golang", "a": "A", "好": "好", + "FROM CamelCase to snake/kebab-case": "FromCamelcaseToSnake/kebabCase", + "": "", }) }