1.1 --- a/dew4nb/src/org/netbeans/modules/dew4nb/services/project/IORedirectProvider.java Tue Feb 04 09:48:26 2014 +0100
1.2 +++ b/dew4nb/src/org/netbeans/modules/dew4nb/services/project/IORedirectProvider.java Tue Feb 04 13:57:07 2014 +0100
1.3 @@ -46,6 +46,14 @@
1.4 import java.io.PrintWriter;
1.5 import java.io.Reader;
1.6 import java.io.Writer;
1.7 +import java.lang.ref.Reference;
1.8 +import java.lang.ref.WeakReference;
1.9 +import java.net.URL;
1.10 +import java.util.ArrayList;
1.11 +import java.util.Collection;
1.12 +import java.util.Collections;
1.13 +import java.util.Map;
1.14 +import java.util.WeakHashMap;
1.15 import java.util.concurrent.atomic.AtomicBoolean;
1.16 import java.util.regex.Pattern;
1.17 import org.netbeans.api.annotations.common.NonNull;
1.18 @@ -71,6 +79,10 @@
1.19
1.20 private static final Pattern EMPTY_STR = Pattern.compile("^\\s*$"); //NOI18N
1.21 private static final ThreadLocal<EndPoint.Env> currentEnv = new ThreadLocal<>();
1.22 + private static final Object threadsLock = new Object();
1.23 + //@GuardedBy("threadsLock")
1.24 + private static final Map<RedirectIO,Collection<Reference<Thread>>> activeThreads =
1.25 + new WeakHashMap<>();
1.26
1.27 public IORedirectProvider() {}
1.28
1.29 @@ -84,6 +96,19 @@
1.30 currentEnv.remove();
1.31 }
1.32
1.33 + static void showUrl(@NonNull final URL url) {
1.34 + synchronized(threadsLock) {
1.35 +out: for (Map.Entry<RedirectIO,Collection<Reference<Thread>>> e : activeThreads.entrySet()) {
1.36 + for (Reference<Thread> tr : e.getValue()) {
1.37 + if (Thread.currentThread() == tr.get()) {
1.38 + e.getKey().openUrlImpl(url);
1.39 + break out;
1.40 + }
1.41 + }
1.42 + }
1.43 + }
1.44 + }
1.45 +
1.46 @Override
1.47 public InputOutput getIO(String name, boolean newIO) {
1.48 if (currentEnv.get() == null) {
1.49 @@ -161,20 +186,24 @@
1.50 RedirectIO() {
1.51 this.closed = new AtomicBoolean();
1.52 resetImpl();
1.53 + registerThread();
1.54 }
1.55
1.56 @Override
1.57 public Reader getIn() {
1.58 + registerThread();
1.59 return new NullReader();
1.60 }
1.61
1.62 @Override
1.63 public OutputWriter getOut() {
1.64 + registerThread();
1.65 return new RedirectOutputWriter(this, false);
1.66 }
1.67
1.68 @Override
1.69 public OutputWriter getErr() {
1.70 + registerThread();
1.71 return new RedirectOutputWriter(this, true);
1.72 }
1.73
1.74 @@ -237,7 +266,8 @@
1.75 data,
1.76 err?
1.77 data :
1.78 - null));
1.79 + null,
1.80 + null));
1.81 }
1.82
1.83 void closeImpl() {
1.84 @@ -246,17 +276,42 @@
1.85 env,
1.86 BuildResult.success,
1.87 null,
1.88 + null,
1.89 null));
1.90 }
1.91 }
1.92
1.93 + void openUrlImpl(@NonNull final URL url) {
1.94 + Parameters.notNull("url", url); //NOI18N
1.95 + env.sendObject(createResponse(
1.96 + env,
1.97 + null,
1.98 + null,
1.99 + null,
1.100 + Collections.singleton(url)));
1.101 + }
1.102 +
1.103 void resetImpl() {
1.104 + synchronized (threadsLock) {
1.105 + activeThreads.remove(this);
1.106 + }
1.107 env = currentEnv.get();
1.108 if (env == null) {
1.109 throw new IllegalStateException();
1.110 }
1.111 closed.set(false);
1.112 }
1.113 +
1.114 + private void registerThread() {
1.115 + synchronized (threadsLock) {
1.116 + Collection<Reference<Thread>> myThreads = activeThreads.get(this);
1.117 + if (myThreads == null) {
1.118 + myThreads = new ArrayList<>();
1.119 + activeThreads.put(this, myThreads);
1.120 + }
1.121 + myThreads.add(new WeakReference<>(Thread.currentThread()));
1.122 + }
1.123 + }
1.124 }
1.125
1.126 private static final class NullReader extends Reader {
1.127 @@ -374,7 +429,8 @@
1.128 @NonNull final EndPoint.Env env,
1.129 @NullAllowed final BuildResult result,
1.130 @NullAllowed final String stdOut,
1.131 - @NullAllowed final String stdErr) {
1.132 + @NullAllowed final String stdErr,
1.133 + @NullAllowed final Collection<? extends URL> urls) {
1.134 Parameters.notNull("env", env); //NOI18N
1.135 final ProjectMessageType type = env.getProperty(PROP_TYPE, ProjectMessageType.class);
1.136 Parameters.notNull("type", type); //NOI18N
1.137 @@ -391,6 +447,11 @@
1.138 if (stdErr != null) {
1.139 res.getStderr().add(stdErr);
1.140 }
1.141 + if (urls != null) {
1.142 + for (URL url : urls) {
1.143 + res.getOpenUrl().add(url.toExternalForm());
1.144 + }
1.145 + }
1.146 return res;
1.147 }
1.148 }
2.1 --- a/dew4nb/src/org/netbeans/modules/dew4nb/services/project/InvokeProjectActionHandler.java Tue Feb 04 09:48:26 2014 +0100
2.2 +++ b/dew4nb/src/org/netbeans/modules/dew4nb/services/project/InvokeProjectActionHandler.java Tue Feb 04 13:57:07 2014 +0100
2.3 @@ -86,7 +86,7 @@
2.4 ctx.getUser(),
2.5 ctx.getWorkspace(),
2.6 ctx.getPath()
2.7 - ));
2.8 + ));
2.9 Status res = Status.done;
2.10 if (file != null) {
2.11 final Project prj = FileOwnerQuery.getOwner(file);
3.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
3.2 +++ b/dew4nb/src/org/netbeans/modules/dew4nb/services/project/RedirectURLDisplayer.java Tue Feb 04 13:57:07 2014 +0100
3.3 @@ -0,0 +1,64 @@
3.4 +/*
3.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
3.6 + *
3.7 + * Copyright 2014 Oracle and/or its affiliates. All rights reserved.
3.8 + *
3.9 + * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
3.10 + * Other names may be trademarks of their respective owners.
3.11 + *
3.12 + * The contents of this file are subject to the terms of either the GNU
3.13 + * General Public License Version 2 only ("GPL") or the Common
3.14 + * Development and Distribution License("CDDL") (collectively, the
3.15 + * "License"). You may not use this file except in compliance with the
3.16 + * License. You can obtain a copy of the License at
3.17 + * http://www.netbeans.org/cddl-gplv2.html
3.18 + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
3.19 + * specific language governing permissions and limitations under the
3.20 + * License. When distributing the software, include this License Header
3.21 + * Notice in each file and include the License file at
3.22 + * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this
3.23 + * particular file as subject to the "Classpath" exception as provided
3.24 + * by Oracle in the GPL Version 2 section of the License file that
3.25 + * accompanied this code. If applicable, add the following below the
3.26 + * License Header, with the fields enclosed by brackets [] replaced by
3.27 + * your own identifying information:
3.28 + * "Portions Copyrighted [year] [name of copyright owner]"
3.29 + *
3.30 + * If you wish your version of this file to be governed by only the CDDL
3.31 + * or only the GPL Version 2, indicate your decision by adding
3.32 + * "[Contributor] elects to include this software in this distribution
3.33 + * under the [CDDL or GPL Version 2] license." If you do not indicate a
3.34 + * single choice of license, a recipient has the option to distribute
3.35 + * your version of this file under either the CDDL, the GPL Version 2 or
3.36 + * to extend the choice of license to its licensees as provided above.
3.37 + * However, if you add GPL Version 2 code and therefore, elected the GPL
3.38 + * Version 2 license, then the option applies only if the new code is
3.39 + * made subject to such option by the copyright holder.
3.40 + *
3.41 + * Contributor(s):
3.42 + *
3.43 + * Portions Copyrighted 2014 Sun Microsystems, Inc.
3.44 + */
3.45 +
3.46 +package org.netbeans.modules.dew4nb.services.project;
3.47 +
3.48 +import java.net.URL;
3.49 +import org.netbeans.api.annotations.common.NonNull;
3.50 +import org.openide.awt.HtmlBrowser;
3.51 +import org.openide.util.lookup.ServiceProvider;
3.52 +
3.53 +/**
3.54 + *
3.55 + * @author Tomas Zezula
3.56 + */
3.57 +@ServiceProvider(service = HtmlBrowser.URLDisplayer.class, position = 1)
3.58 +public class RedirectURLDisplayer extends HtmlBrowser.URLDisplayer {
3.59 +
3.60 + @Override
3.61 + public void showURL(@NonNull final URL url) {
3.62 + IORedirectProvider.showUrl(url);
3.63 + }
3.64 +
3.65 +
3.66 +
3.67 +}