001package ball.util.ant.taskdefs;
002/*-
003 * ##########################################################################
004 * Utilities
005 * $Id: InstanceOfTask.java 5853 2020-04-27 19:55:26Z ball $
006 * $HeadURL: svn+ssh://svn.hcf.dev/var/spool/scm/repository.svn/ball-util/trunk/src/main/java/ball/util/ant/taskdefs/InstanceOfTask.java $
007 * %%
008 * Copyright (C) 2008 - 2020 Allen D. Ball
009 * %%
010 * Licensed under the Apache License, Version 2.0 (the "License");
011 * you may not use this file except in compliance with the License.
012 * You may obtain a copy of the License at
013 *
014 *      http://www.apache.org/licenses/LICENSE-2.0
015 *
016 * Unless required by applicable law or agreed to in writing, software
017 * distributed under the License is distributed on an "AS IS" BASIS,
018 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
019 * See the License for the specific language governing permissions and
020 * limitations under the License.
021 * ##########################################################################
022 */
023import ball.activation.ReaderWriterDataSource;
024import ball.util.Factory;
025import ball.util.ant.types.TypedAttributeType;
026import java.beans.ExceptionListener;
027import java.beans.XMLEncoder;
028import java.lang.reflect.Member;
029import java.util.ArrayList;
030import java.util.List;
031import lombok.NoArgsConstructor;
032import lombok.ToString;
033import org.apache.tools.ant.BuildException;
034
035/**
036 * {@link.uri http://ant.apache.org/ Ant} {@link org.apache.tools.ant.Task}
037 * to get an instance of a specified {@link Class}.
038 *
039 * {@ant.task}
040 *
041 * @see Factory
042 *
043 * @author {@link.uri mailto:ball@hcf.dev Allen D. Ball}
044 * @version $Revision: 5853 $
045 */
046@AntTask("instance-of")
047@NoArgsConstructor @ToString
048public class InstanceOfTask extends TypeTask {
049    private final List<TypedAttributeType> list = new ArrayList<>();
050    protected Object instance = null;
051
052    public void addConfiguredArgument(TypedAttributeType argument) {
053        list.add(argument);
054    }
055
056    public List<TypedAttributeType> getArgumentList() { return list; }
057
058    public void setArgument(String string) {
059        list.add(new TypedAttributeType(string));
060    }
061
062    @Override
063    public void execute() throws BuildException {
064        super.execute();
065
066        try {
067            Class<?> type = getClassForName(getType());
068
069            log(type.getName());
070
071            List<Class<?>> parameters = new ArrayList<>(list.size());
072            List<Object> arguments = new ArrayList<>(list.size());
073
074            for (TypedAttributeType argument : list) {
075                Factory<?> factory =
076                    new Factory<>(getClassForName(argument.getType()));
077
078                parameters.add(factory.getType());
079
080                String string =
081                    getProject().replaceProperties(argument.getValue());
082
083                arguments.add(factory.getInstance(string));
084            }
085
086            log(String.valueOf(parameters));
087            log(String.valueOf(arguments));
088
089            Factory<?> factory = new Factory<>(type);
090            Member member =
091                factory.getFactoryMethod(parameters.stream().toArray(Class<?>[]::new));
092
093            log(String.valueOf(member));
094
095            instance =
096                factory.apply(member, arguments.stream().toArray(Object[]::new));
097
098            log(String.valueOf(instance));
099
100            if (getClass().isAssignableFrom(InstanceOfTask.class)) {
101                ReaderWriterDataSourceImpl ds =
102                    new ReaderWriterDataSourceImpl();
103
104                try (XMLEncoder encoder =
105                         new XMLEncoder(ds.getOutputStream())) {
106                    encoder.setExceptionListener(ds);
107                    encoder.writeObject(instance);
108                    encoder.flush();
109                }
110
111                if (ds.length() > 0) {
112                    log();
113                    log(ds.getBufferedReader().lines());
114                }
115            }
116        } catch (BuildException exception) {
117            throw exception;
118        } catch (Throwable throwable) {
119            throwable.printStackTrace();
120            throw new BuildException(throwable);
121        }
122    }
123
124    private class ReaderWriterDataSourceImpl extends ReaderWriterDataSource
125                                             implements ExceptionListener {
126        public ReaderWriterDataSourceImpl() { super(null, null); }
127
128        @Override
129        public void exceptionThrown(Exception exception) { clear(); }
130    }
131}