How do you create custom Polymer and PolymerDart annotations? - annotations

I was doing some research into PolymerDart and the various annotations which can be applied to the dart files. Be it: #Property, #property, #observe, #reflectable, #PolymerRegister, OR #HtmlImport.
So, I started to look into the concept of Dart and how to make annotations for them. I saw on stackoverflow that you can do something like this.
class Datatable {
final String name;
const DataTable(this.name);
}
which can easily do some additional information inside the constructor optionally.
class Datatable {
final String name;
const DataTable(this.name) {
console.log("$name was referenced.");
}
}
So, I can create and implement a variety of Annotations we could leverage, but this is where it starts to get fishy.
I was curious if there was a way to create annotations for polymerdart? is that mostly locked down, or can is there a way to create ones which do simple functions, maybe even for example: creating an Annotation which executes the #Property(computed:"") functionality.
I was wanted to create some sort of customization for our team to use.
For the record, I know that i can do something like
const myCustomAnnotation = const Property();
which would allow me to do:
#myCustomAnnotation
I was thinking I could then do something like like:
class myCustomComputed extends Property {
final String functionName;
const myCustomComputed() : Property(computed: this.functionName);
}
to allow me to do something like:
#myCustomComputed("testFunction(varA)")

This is a big topic, but the brief answer is, yes, what you describe is technically possible but not trivial.
Dart annotations are available at runtime via reflection, but are most often used by pub transformers during the build process. The purpose of a transformer is to modify assets (e.g. dart code) to some new form before runtime.
The Polymer annotations you mentioned above are handled by the Polymer transformer. This transformer handles identifying the annotations you mentioned above and automatically rewriting annotated code to include all the necessary implementations and wiring such that everything behaves as we expect as Polymer elements.
So there's nothing stopping you from defining your own annotations and transformers, including those that build upon the existing Polymer transformers, and packaging it up for your own or others' use.
I will note though that it is somewhat complex topic (ref the Polymer transformer) and there seem to be few simple code-rewriting transformer examples from which to build on.

Related

Enterprise Architect Code Generation: Get tags of interface

I use Enterprise Architect for code generation and I would like to automatically retrieve all tags (in my case Java annotations) of the interfaces that a class realizes. Consider the following example:
From this model, I want to generate a class that looks like this:
#AnnotationOfMyInterface
public class MyClass {
...
}
So I want to add annotations as tags to MyInterface that should be applied to MyClass during code generation. In the UI, tags of implemented interfaces are shown so I was hoping there is a way to get these tags during code generation.
I tried to edit the code generation templates and found macros to get
All interfaces that a class implements: %list="ClassInterface" #separator=", "%
All tags with a given name (of the class that code is being generated for): %classTag:"annotations"%
But unfortunately, I cannot combine these macros, i.e., I cannot pass one interface to the classTag macro so that I can retrieve the tags of that particular interface (and not the one I'm generating code for). Is there a way to get classTags of a specific class / interface?
I also tried to create a separate code generation template and "call" it from the main class code generation template. But inside my template, the classTag macro still only gets the tags of the class.
Thanks to the comments above and especially because of an answer to my question in EA's forum, I was able to setup a little proof of concept achieving what I wanted. I'm answering my question to document my solution in case someone has a similar problem in the future.
After Eve's hint in EA's forum I looked into creating an AddIn for Enterprise Architect to use this AddIn from a code generation template. I started by writing a basic AddIn as explained by #Geert Bellekens in this tutorial. Afterwards I changed the AddIn to fit my needs. This is how I finally got the tagged values (annotations) of the interfaces a class realizes:
First step:
Inside a code generation template, I get all the interfaces a class realizes and pass them to my AddIn:
$interfaces=%list="ClassInterface" #separator=", "%
%EXEC_ADD_IN("MyAddin","getInterfaceTags", $interfaces)%
Second step:
As documented here the repository objects gets passed along with the EXEC_ADD_IN call. I use the repository object and query for all interfaces using the names contained in $interfaces. I can then get the tagged values of each interface element. Simple prototype that achieves this for a single interface:
public Object getInterfaceTags(EA.Repository repo, Object args)
{
String[] interfaceNames = args as String[];
String firstInterfaceName = interfaceNames[0];
EA.Element interfaceElement = repo.GetElementsByQuery("Simple", firstInterfaceName).GetAt(0);
String tag = interfaceElement.TaggedValues.GetAt(0);
return interfaceElement.Name + " has tag value" + tag.Value;
}
I know, there are a couple of shortcomings but this is just a simple proof of concept for an idea that will most likely never be production code.

Dependency injection in Flutter - repercussions of different approaches

In Flutter, I feel a bit lost with how I create my params for classes, and knowing what is the best way to create those params. Usually, the params are just classes to inject into another class, to perform tasks. It doesn't really seem to matter how those params are created functionality-wise, since the code works with all manner of creation methods. I see online people talking about service locators, singletons, dependency injection. Riverpod states on the website "Providers are a complete replacement for patterns like Singletons, Service Locators, Dependency Injection or InheritedWidgets." So I guess I don't need a service locator, since I use Riverpod. However I can't find anything online on how I can inject a service with Riverpod providers. I can see you can read a provider with no context with ProviderContainer().read but is this for use as service injection? Is this a singleton so pretty much a service locator? In the Riverpod example, it states that you don't need ProviderContainer().read for Flutter, which kind of sounds like it isn't a replacement for anything like a service locator then:
// Where the state of our providers will be stored.
// Avoid making this a global variable, for testability purposes.
// If you are using Flutter, you do not need this.
final container = ProviderContainer();
Here is a code example, a field in a class which is a ViewModel which takes some use cases as params. Use cases here are domain layer actions classes which call repositories to do external stuff like API requests or local storage manipulations.
final CreateUserViewModel createUserViewModel =
CreateUserViewModel(SavePasswordLocallyUseCase(), CreateUserUseCase());
...
So I just literally created them in-line like SavePasswordLocallyUseCase(), in order to inject them. This is defnitely the easiest approach, with the least code. I guess it might be less efficient since it is creating a new one every time, though i don't see that usually making a visible difference. Will these params that are created in this manner be cleaned up by the garbage collector? What is the repercussion of doing this?
If I had to inject a type AuthenticationService, should I be using a service locator or creating them inline like AuthenticationService(), or using Riverpod's ProviderContainer.read()?
After looking around I can see that dependency injection in Flutter is mostly done by creating a new instance of the param to inject into the constructor like in my question:
final CreateUserViewModel createUserViewModel =
CreateUserViewModel(SavePasswordLocallyUseCase(), CreateUserUseCase());
And that this becomes very messy very fast if the injected classes also need their own params injected. Dependency injection packages mostly aim to solve this by setting up the classes with their required params once, and then you can just request the instance from the dependency injection package without ever needing to create its constructor params again. I believe the Riverpod version of this is indeed to use ProviderContainer.read() if not in the UI layer. Lets say I want to instantiate a class which takes a repository in its constructor:
class SavePasswordLocallyUseCase implements ISavePasswordLocallyUseCase {
const SavePasswordLocallyUseCase(this._userRepository);
final IRegistrationRepository _userRepository;
String invoke(String password, String confirmPassword) {
return _userRepository.putPasswords(password, confirmPassword);
}
And the injected repository itself needs 2 constructor params:
class RegistrationRepository implements IRegistrationRepository {
const RegistrationRepository(
this._authenticationRemoteDataSource, this._registrationLocalDataSource);
}
final AuthenticationRemoteDataSource _authenticationRemoteDataSource;
final IRegistrationLocalDataSource _registrationLocalDataSource;
Instead of instantiating the class like this:
new RegistrationRepository(AuthenticationRemoteDataSource(X()), RegistrationLocalDataSource(Y()))
By creating a stock standard Provider in Riverpod which instantiates the params once:
final registrationRepositoryProvider =
Provider.autoDispose<RegistrationRepository>((ref) {
ref.onDispose(() {
print('disposing');
});
return RegistrationRepository(
AuthenticationRemoteDataSource(X()), RegistrationLocalDataSource(Y()));
});
I can then allow classes to access the RegistrationRepository like so:
ref.container.read(registrationRepositoryProvider);
Or without a ProviderReference:
ProviderContainer().read(registrationRepositoryProvider);
I'm still not sure about lazy loading and singletons in riverpod and if those options are possible. It might be more configurable to use Injectable for DI that is not in the View, which I am considering.

AS3 targeting controller class variable using string

I'm looking for a way of condensing some of my AS3 code to avoid almost duplicate commands.
The issue is that I have multiple variables with almost the same name e.g. frenchLanguage, englishLanguage, germanLanguage, spanishLanguage
My Controller class contains public static variables (these are accessed across multiple classes) and I need a way to be able to call a few of these variables dynamically. If the variables are in the class you are calling them from you can do this to access them dynamically:
this["spanish"+"Language"]
In AS3 it's not possible to write something like:
Controller.this["spanish"+"Language"]
Is there any way to achieve this? Although everything is working I want to be able to keep my code as minimal as possible.
It is possible to access public static properties of a class this way (assuming the class name is Controller as in your example:
Controller['propertyName']
I'm not sure how this helps to have "minimal code", but this would be a different topic/question, which might need some more details on what you want to achive.
Having said that, I like the approach DodgerThud suggests in the comments of grouping similar values in a (dynamic) Object or Dictonary and give it a proper name.
Keep in mind, that if the string you pass in as the key to the class or dynamic object is created from (textual) user input you should have some checks for the validity of that data, otherwise your programm might crash or expose other fields to the user.
It would make sense to utilize a Dictionary object for a set of variables inherited: it provides a solid logic and it happens to work...
I do not think this is what you are trying to accomplish. I may be wrong.
Classes in AS3 are always wrapped within a package - this is true whether you have compiled from Flash, Flex, Air, or any other...
Don't let Adobe confuse you. This was only done in AS3 to use Java-Based conventions. Regardless, a loosely typed language is often misunderstood, unfortunately. So:
this["SuperObject"]["SubObject"]["ObjectsMethod"][ObjectsMethodsVariable"](args..);
... is technically reliable because the compiler avoids dot notation but at runtime it will collect a lot of unnecessary data to maintain those types of calls.
If efficiency becomes an issue..
Use:
package packages {
import flash.*.*:
class This implements ISpecialInterface {
// Data Objects and Function Model
// for This Class
}
package packages {
import...
class ISpecialInterface extends IEventDispatcher

GWT Reflection loading Form

I have a circumstance where I have to create a lot of forms for an application, the forms are all located in the same package. They are named like: A11111.java, A11112.java, etc.
When the user clicks in the NavigationPane, I wish to load the form into a TabItem and display the form. The issue is I need to dynamically generate the name of the form by appending the form name to the location, such as String formName = "com.foo.appName.client.forms" + e.getData("formCode"); something like that, where e is the event of the user click.
I have looked at several Reflection methods, but you cannot pass a derived string to them. How best to do this? Several posts mention using generators, but I get lost trying to sort their logic, and none have to do with displaying forms.
Note, I am not passing any variables to the forms, or calling any methods in the form java files, also the forms are created using uibinding.
Thanks in advance
if you're aiming at lazy-loading classes via the class-loader, like you would when using the command design pattern, note that it can't be done within a GWT application, as the frameworks JRE emulation only provides a subset of types and/or methods available in the JRE, so most of the reflection API - like forName() - will not be available.
rather than lazy-loading classes, think in terms of lazy-rendering widgets to the DOM. this can be achieved by instantiating all your form classes on module load, but only render upon tab-switching. place all your render-related functionality inside onRender() callbacks and you're good to go:
public class FormItem extends TabItem {
#Override
protected void onRender(Element parent, int index) {
super.onRender(parent, index);
// render related functionality
}
}

StructureMap Specifying Explicit Constructor Arguments

I'm working on legacy code.
I have different methods of the same class that pass different arguments to the constructor of a dependency. I'm trying to get some basic IoC usage introduced. Right now I have StructureMap passing my arguments like this:
var thing = ObjectFactory.GetInstance<IThingInterface>(new ExplicitArguments(
new Dictionary<string, object> {
{ "constructorArgA", notShown },
{ "constructorArgB", redacted.Property } }));
Where the actual properties passed for constructorArgA and B change depending on where I am.
Instead of "constructorArgA" is there a way to configure this via actual types, like you can do when configuring the objectFactory, like:
x.For<IHidden>().Use<RealType>()
.Ctor<IConfig>().Is(new Func<IContext, IConfig>(
(context) => someMethodToGetIConfig()));
If I were writing this from scratch I'd probably structure the dependencies a bit different to avoid this, but that's not an option for me right now.
This is something of a classic/common question with DI Containers.
My first choice would be to create a "manual" abstract factory to create IThingInterface, and then use Structuremap to inject IThingInterfaceFactory where it is needed. By manual factory, I mean a class the calls new ThingInterface() and returns it. If you do it this way, your implementation will no longer be container-managed, and if it has dependencies, they would no longer be provided by the container (may or may not be a problem for you).
Second choice would be to create an abstract factory that actually uses/wraps the container. So basically your first code snippet but wrapped in a factory class where the Create() method takes your parameters. This has the advantage of everything (including your implementation and its dependencies) being container-managed, but the disadvantage of referencing your container directly (which is not a best practice--see Article on Composition Roots).
You could also do setter injection, but I would personally consider it a last resort.
Castle Windsor has a good solution to this problem built in (Typed Factory Facility). Not sure if switching containers in an option, but you might consider it.