mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
-fix handling of string concatenations starting with a binary expression of a different type
-only enable for jdk5 and higher -added test
This commit is contained in:
+35
@@ -0,0 +1,35 @@
|
||||
/*
|
||||
* Copyright 2003-2011 Dave Griffith, Bas Leijdekkers
|
||||
*
|
||||
* 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 com.siyeh.ipp.concatenation;
|
||||
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.util.PsiUtil;
|
||||
import com.siyeh.ipp.base.PsiElementPredicate;
|
||||
import com.siyeh.ipp.psiutils.ConcatenationUtils;
|
||||
import com.siyeh.ipp.psiutils.ErrorUtil;
|
||||
|
||||
class Jdk5StringConcatenationPredicate implements PsiElementPredicate {
|
||||
|
||||
public boolean satisfiedBy(PsiElement element) {
|
||||
if (!PsiUtil.isLanguageLevel5OrHigher(element)) {
|
||||
return false;
|
||||
}
|
||||
if(!ConcatenationUtils.isConcatenation(element)) {
|
||||
return false;
|
||||
}
|
||||
return !ErrorUtil.containsError(element);
|
||||
}
|
||||
}
|
||||
+42
-43
@@ -31,7 +31,7 @@ public class ReplaceConcatenationWithFormatStringIntention
|
||||
@Override
|
||||
@NotNull
|
||||
protected PsiElementPredicate getElementPredicate() {
|
||||
return new SimpleStringConcatenationPredicate(true);
|
||||
return new Jdk5StringConcatenationPredicate();
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -128,50 +128,49 @@ public class ReplaceConcatenationWithFormatStringIntention
|
||||
return true;
|
||||
}
|
||||
|
||||
void buildFormatString(PsiBinaryExpression expression,
|
||||
StringBuilder formatString,
|
||||
List<PsiExpression> formatParameters) {
|
||||
final PsiExpression lhs = expression.getLOperand();
|
||||
appendFormatString(lhs, formatString, formatParameters);
|
||||
final PsiExpression rhs = expression.getROperand();
|
||||
if (rhs != null) {
|
||||
appendFormatString(rhs, formatString, formatParameters);
|
||||
private static void buildFormatString(
|
||||
PsiExpression expression, StringBuilder formatString,
|
||||
List<PsiExpression> formatParameters) {
|
||||
if (expression instanceof PsiLiteralExpression) {
|
||||
final PsiLiteralExpression literalExpression =
|
||||
(PsiLiteralExpression) expression;
|
||||
final Object value = literalExpression.getValue();
|
||||
final String text =
|
||||
String.valueOf(value).replace("%", "%%").replace(
|
||||
"\\'", "'");
|
||||
formatString.append(text);
|
||||
} else if (expression instanceof PsiBinaryExpression) {
|
||||
final PsiType type = expression.getType();
|
||||
if (type != null && type.equalsToText("java.lang.String")) {
|
||||
final PsiBinaryExpression binaryExpression =
|
||||
(PsiBinaryExpression) expression;
|
||||
final PsiExpression lhs = binaryExpression.getLOperand();
|
||||
buildFormatString(lhs, formatString, formatParameters);
|
||||
final PsiExpression rhs = binaryExpression.getROperand();
|
||||
if (rhs != null) {
|
||||
buildFormatString(rhs, formatString, formatParameters);
|
||||
}
|
||||
} else {
|
||||
addFormatParameter(expression, formatString, formatParameters);
|
||||
}
|
||||
} else {
|
||||
addFormatParameter(expression, formatString, formatParameters);
|
||||
}
|
||||
}
|
||||
|
||||
private void appendFormatString(PsiExpression lhs,
|
||||
StringBuilder formatString,
|
||||
List<PsiExpression> formatParameters) {
|
||||
if (lhs instanceof PsiLiteralExpression) {
|
||||
final String text = lhs.getText();
|
||||
final int length = text.length();
|
||||
final PsiType type = lhs.getType();
|
||||
if (type != null && (type.equalsToText("java.lang.String") ||
|
||||
type.equalsToText("char"))) {
|
||||
if (length > 2) {
|
||||
formatString.append(
|
||||
text.substring(1, length - 1).replace("%", "%%")
|
||||
.replace("\\'", "'"));
|
||||
}
|
||||
} else {
|
||||
formatString.append(text);
|
||||
}
|
||||
} else if (lhs instanceof PsiBinaryExpression) {
|
||||
final PsiBinaryExpression binaryExpression =
|
||||
(PsiBinaryExpression) lhs;
|
||||
buildFormatString(binaryExpression, formatString, formatParameters);
|
||||
} else {
|
||||
final PsiType type = lhs.getType();
|
||||
if (type != null &&
|
||||
(type.equalsToText("long") ||
|
||||
type.equalsToText("int") ||
|
||||
type.equalsToText("java.lang.Long") ||
|
||||
type.equalsToText("java.lang.Integer"))) {
|
||||
formatString.append("%d");
|
||||
} else {
|
||||
formatString.append("%s");
|
||||
}
|
||||
formatParameters.add(lhs);
|
||||
}
|
||||
private static void addFormatParameter(PsiExpression expression,
|
||||
StringBuilder formatString,
|
||||
List<PsiExpression> formatParameters) {
|
||||
final PsiType type = expression.getType();
|
||||
if (type != null &&
|
||||
(type.equalsToText("long") ||
|
||||
type.equalsToText("int") ||
|
||||
type.equalsToText("java.lang.Long") ||
|
||||
type.equalsToText("java.lang.Integer"))) {
|
||||
formatString.append("%d");
|
||||
} else {
|
||||
formatString.append("%s");
|
||||
}
|
||||
formatParameters.add(expression);
|
||||
}
|
||||
}
|
||||
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class C {
|
||||
String s = "or not" <caret>+ 0x10;
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class C {
|
||||
String s = String.format("or not16");
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
class C {
|
||||
void printName(String firstName, String lastName) {
|
||||
System.out.println( "My first name is " <caret>+ firstName + " and my last name is " + lastName );
|
||||
}
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
class C {
|
||||
void printName(String firstName, String lastName) {
|
||||
System.out.printf("My first name is %s and my last name is %s%n", firstName, lastName);
|
||||
}
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class C {
|
||||
String s = 1 + 2 +<caret> " to be";
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class C {
|
||||
String s = String.format("%d to be", 1 + 2);
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
class C {
|
||||
String foo(double d, String s) {
|
||||
return "asdf" + d <caret>+ ", " + s;
|
||||
}
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
class C {
|
||||
String foo(double d, String s) {
|
||||
return String.format("asdf%s, %s", d, s);
|
||||
}
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class C {
|
||||
String s = "10%" <caret>+ '\'';
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class C {
|
||||
String s = String.format("10%%'");
|
||||
}
|
||||
+38
@@ -0,0 +1,38 @@
|
||||
/*
|
||||
* Copyright 2011 Bas Leijdekkers
|
||||
*
|
||||
* 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 com.siyeh.ipp.concatenation;
|
||||
|
||||
import com.siyeh.IntentionPowerPackBundle;
|
||||
import com.siyeh.ipp.IPPTestCase;
|
||||
|
||||
public class ReplaceConcatenationWithFormatStringTest extends IPPTestCase {
|
||||
public void testNumericBinaryExpression() { doTest(); }
|
||||
public void testHexadecimalLiteral() { doTest(); }
|
||||
public void testPercentInLiteral() { doTest(); }
|
||||
public void testParameters() { doTest(); }
|
||||
public void testLineSeparator() { doTest(); }
|
||||
|
||||
@Override
|
||||
protected String getIntentionName() {
|
||||
return IntentionPowerPackBundle.message(
|
||||
"replace.concatenation.with.format.string.intention.name");
|
||||
}
|
||||
|
||||
@Override
|
||||
protected String getRelativePath() {
|
||||
return "concatenation/string_format";
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user