Kurz gesagt, nein. Sie können statische Felder in Spring nicht automatisch verdrahten oder manuell verdrahten. Sie müssen Ihre eigene Logik schreiben, um dies zu tun.
Wenn Sie dabei alten Code finden, handelt es sich um ein Anti-Pattern. Schielen Sie, neigen Sie Ihren Kopf und finden Sie einen besseren Weg, um das Problem zu lösen. Du wirst es nicht bereuen.
Joseph Lust
2
Diese Antwort ist auch hilfreich bei Spring's@AutoWired
Haben Sie eine Idee, wie ich diesen Ansatz beim Initialisieren eines Repositorys verwenden kann?
Kiedysktos
3
Der Nachteil: Es gibt keine Garantie, someThingdie initialisiert wurde, wenn statisch zugegriffen wurde: NewClass.staticMethodWhichUsesSomething();Kann eine NPE auslösen, wenn sie vor der App-Initialisierung verwendet wird
Neeraj
Können Sie die Warnung vermeiden Instance methods should not write to "static" fields (squid:S2696)?
user7294900
@ user7294900: Deaktiviere diese Warnung nur für diesen sehr speziellen Fall.
izogfif
@izogfif immer noch ein Problem, wenn ich diese Lösung in weiten Fällen und Klassen
wähle
67
@Autowired kann mit Setzern verwendet werden, sodass ein Setter ein statisches Feld ändern kann.
Hmmm .. mein Gefühl, warum es nicht empfohlen wird, ist, weil dann die statische Instanz in der Klasse außerhalb der Kontrolle der Feder liegt. Nach der Injektion ist das statische Feld die Referenz für alle Instanzen von Objekten der entsprechenden (umgebenden) Klasse. Aber dieses Verhalten könnte genau das sein, was erwartet wird, und könnte daher als Fehler oder Feature angesehen werden ...
Matthaeus
1
Ja @matthaeus, es ist genau die Funktion, die ich erwartet hatte, als ich auf org.springframework.core.env.Environment zugreifen musste:@Component public class SpringAppEnv{ public static Environment _env; @Autowired public void setEnv(Environment env) {_env = env;} }
user1767316
@ JonLorusso und alle Denn wenn der Klassenlader die statischen Werte lädt, muss der Spring-Kontext noch nicht geladen werden. Der Klassenlader fügt die statische Klasse daher nicht ordnungsgemäß in die Bean ein und schlägt fehl. Antwort von Andrea T
Jeril Kuruvila
14
Initialisieren Sie Ihre automatisch verdrahtete Komponente in der @ PostConstruct-Methode
Sie sollten nach Möglichkeit die Federeinspritzung verwenden, da dies der empfohlene Ansatz ist , dies ist jedoch nicht immer möglich, da Sie sich sicher vorstellen können, dass nicht alles aus dem Federbehälter gezogen werden kann oder Sie sich möglicherweise mit Legacy-Systemen befassen.
Das Testen von Noten kann mit diesem Ansatz auch schwieriger sein.
Wollte zu den Antworten hinzufügen, dass das statische Feld (oder die Konstante) der automatischen Verkabelung ignoriert wird, aber auch keinen Fehler erzeugt:
Haftungsausschluss Dies ist keineswegs Standard und es könnte durchaus einen besseren Frühlingsweg geben, dies zu tun. Keine der obigen Antworten befasst sich mit der Verdrahtung eines öffentlichen statischen Feldes.
Ich wollte drei Dinge erreichen.
Verwenden Sie die Feder für "Autowire" (ich verwende @Value)
Stellen Sie einen öffentlichen statischen Wert bereit
Wir haben bereits 1 & 2 abgehakt, wie wir Anrufe an den Setter verhindern können, da wir sie nicht ausblenden können.
@Component@AspectpublicclassFinalAutowiredHelper{@Before("finalMethods()")publicvoid beforeFinal(JoinPoint joinPoint){thrownewFinalAutowiredHelper().newModifySudoFinalError("");}@Pointcut("execution(* com.free.content.client..*.finalSetBranch(..))")publicvoid finalMethods(){}publicclassModifySudoFinalErrorextendsError{privateString msg;publicModifySudoFinalError(String msg){this.msg = msg;}@OverridepublicString getMessage(){return"Attempted modification of a final property: "+ msg;}}
Dieser Aspekt umschließt alle Methoden, die mit final beginnen, und gibt einen Fehler aus, wenn sie aufgerufen werden.
Ich denke nicht, dass dies besonders nützlich ist, aber wenn Sie ok sind und Ihre Erbsen und Karotten getrennt halten möchten, ist dies eine Möglichkeit, dies sicher zu tun.
Wichtig Spring ruft Ihre Aspekte nicht auf, wenn es eine Funktion aufruft. Das wurde einfacher, schade, dass ich die Logik ausgearbeitet habe, bevor ich das herausgefunden habe.
Während dieser Code die Frage lösen kann, einschließlich einer Erklärung, wie und warum dies das Problem löst, würde dies wirklich dazu beitragen, die Qualität Ihres Beitrags zu verbessern, und wahrscheinlich zu mehr Up-Votes führen. Denken Sie daran, dass Sie in Zukunft die Frage für die Leser beantworten, nicht nur für die Person, die jetzt fragt. Bitte bearbeiten Sie Ihre Antwort, um Erklärungen hinzuzufügen und anzugeben, welche Einschränkungen und Annahmen gelten.
Doppel-Piepton
Ich denke, diese Antwort bedarf möglicherweise keiner Erklärung.
Antworten:
Kurz gesagt, nein. Sie können statische Felder in Spring nicht automatisch verdrahten oder manuell verdrahten. Sie müssen Ihre eigene Logik schreiben, um dies zu tun.
quelle
@AutoWired
quelle
someThing
die initialisiert wurde, wenn statisch zugegriffen wurde:NewClass.staticMethodWhichUsesSomething();
Kann eine NPE auslösen, wenn sie vor der App-Initialisierung verwendet wirdInstance methods should not write to "static" fields (squid:S2696)
?@Autowired
kann mit Setzern verwendet werden, sodass ein Setter ein statisches Feld ändern kann.Nur ein letzter Vorschlag ... NICHT
quelle
@Component public class SpringAppEnv{ public static Environment _env; @Autowired public void setEnv(Environment env) {_env = env;} }
Initialisieren Sie Ihre automatisch verdrahtete Komponente in der @ PostConstruct-Methode
quelle
Instance methods should not write to "static" fields (squid:S2696)
?Erstellen Sie eine Bean, die Sie automatisch verdrahten können, um die statische Variable als Nebeneffekt zu initialisieren.
quelle
Sie können dies mit der XML-Notation und der erreichen
MethodInvokingFactoryBean
. Ein Beispiel finden Sie hier .Sie sollten nach Möglichkeit die Federeinspritzung verwenden, da dies der empfohlene Ansatz ist , dies ist jedoch nicht immer möglich, da Sie sich sicher vorstellen können, dass nicht alles aus dem Federbehälter gezogen werden kann oder Sie sich möglicherweise mit Legacy-Systemen befassen.
Das Testen von Noten kann mit diesem Ansatz auch schwieriger sein.
quelle
Sie können ApplicationContextAware verwenden
dann
quelle
Wollte zu den Antworten hinzufügen, dass das statische Feld (oder die Konstante) der automatischen Verkabelung ignoriert wird, aber auch keinen Fehler erzeugt:
quelle
Haftungsausschluss Dies ist keineswegs Standard und es könnte durchaus einen besseren Frühlingsweg geben, dies zu tun. Keine der obigen Antworten befasst sich mit der Verdrahtung eines öffentlichen statischen Feldes.
Ich wollte drei Dinge erreichen.
Mein Objekt sieht so aus
Wir haben bereits 1 & 2 abgehakt, wie wir Anrufe an den Setter verhindern können, da wir sie nicht ausblenden können.
Dieser Aspekt umschließt alle Methoden, die mit final beginnen, und gibt einen Fehler aus, wenn sie aufgerufen werden.
Ich denke nicht, dass dies besonders nützlich ist, aber wenn Sie ok sind und Ihre Erbsen und Karotten getrennt halten möchten, ist dies eine Möglichkeit, dies sicher zu tun.
Wichtig Spring ruft Ihre Aspekte nicht auf, wenn es eine Funktion aufruft. Das wurde einfacher, schade, dass ich die Logik ausgearbeitet habe, bevor ich das herausgefunden habe.
quelle
quelle